1baa3858d3f5d128a5c8466b700098109edcad5f2repo sync// LoadCodecs.cpp
2baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
3baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "StdAfx.h"
4baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
5baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "LoadCodecs.h"
6baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
7baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../../../Common/MyCom.h"
8baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifdef NEW_FOLDER_INTERFACE
9baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../../../Common/StringToInt.h"
10baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
11baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../../../Windows/PropVariant.h"
12baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
13baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../../ICoder.h"
14baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../../Common/RegisterArc.h"
15baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
16baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifdef EXTERNAL_CODECS
17baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../../../Windows/FileFind.h"
18baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../../../Windows/DLL.h"
19baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifdef NEW_FOLDER_INTERFACE
20baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "../../../Windows/ResourceString.h"
21baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic const UINT kIconTypesResId = 100;
22baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
23baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
24baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifdef _WIN32
25baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#include "Windows/Registry.h"
26baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
27baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
28baa3858d3f5d128a5c8466b700098109edcad5f2repo syncusing namespace NWindows;
29baa3858d3f5d128a5c8466b700098109edcad5f2repo syncusing namespace NFile;
30baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
31baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifdef _WIN32
32baa3858d3f5d128a5c8466b700098109edcad5f2repo syncextern HINSTANCE g_hInstance;
33baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
34baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
35baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic CSysString GetLibraryFolderPrefix()
36baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
37baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef _WIN32
38baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  TCHAR fullPath[MAX_PATH + 1];
39baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  ::GetModuleFileName(g_hInstance, fullPath, MAX_PATH);
40baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  CSysString path = fullPath;
41baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  int pos = path.ReverseFind(TEXT(CHAR_PATH_SEPARATOR));
42baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return path.Left(pos + 1);
43baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #else
44baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return CSysString(); // FIX IT
45baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
46baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
47baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
48baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#define kCodecsFolderName TEXT("Codecs")
49baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#define kFormatsFolderName TEXT("Formats")
50baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic const TCHAR *kMainDll = TEXT("7z.dll");
51baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
52baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifdef _WIN32
53baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic LPCTSTR kRegistryPath = TEXT("Software") TEXT(STRING_PATH_SEPARATOR) TEXT("7-zip");
54baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic LPCTSTR kProgramPathValue = TEXT("Path");
55baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic bool ReadPathFromRegistry(HKEY baseKey, CSysString &path)
56baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
57baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  NRegistry::CKey key;
58baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if(key.Open(baseKey, kRegistryPath, KEY_READ) == ERROR_SUCCESS)
59baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (key.QueryValue(kProgramPathValue, path) == ERROR_SUCCESS)
60baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    {
61baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      NName::NormalizeDirPathPrefix(path);
62baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      return true;
63baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    }
64baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return false;
65baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
66baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
67baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
68baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
69baa3858d3f5d128a5c8466b700098109edcad5f2repo syncCSysString GetBaseFolderPrefixFromRegistry()
70baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
71baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  CSysString moduleFolderPrefix = GetLibraryFolderPrefix();
72baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef _WIN32
73baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (!NFind::DoesFileExist(moduleFolderPrefix + kMainDll) &&
74baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      !NFind::DoesDirExist(moduleFolderPrefix + kCodecsFolderName) &&
75baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      !NFind::DoesDirExist(moduleFolderPrefix + kFormatsFolderName))
76baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
77baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    CSysString path;
78baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (ReadPathFromRegistry(HKEY_CURRENT_USER, path))
79baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      return path;
80baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (ReadPathFromRegistry(HKEY_LOCAL_MACHINE, path))
81baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      return path;
82baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
83baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
84baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return moduleFolderPrefix;
85baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
86baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
87baa3858d3f5d128a5c8466b700098109edcad5f2repo synctypedef UInt32 (WINAPI *GetNumberOfMethodsFunc)(UInt32 *numMethods);
88baa3858d3f5d128a5c8466b700098109edcad5f2repo synctypedef UInt32 (WINAPI *GetNumberOfFormatsFunc)(UInt32 *numFormats);
89baa3858d3f5d128a5c8466b700098109edcad5f2repo synctypedef UInt32 (WINAPI *GetHandlerPropertyFunc)(PROPID propID, PROPVARIANT *value);
90baa3858d3f5d128a5c8466b700098109edcad5f2repo synctypedef UInt32 (WINAPI *GetHandlerPropertyFunc2)(UInt32 index, PROPID propID, PROPVARIANT *value);
91baa3858d3f5d128a5c8466b700098109edcad5f2repo synctypedef UInt32 (WINAPI *CreateObjectFunc)(const GUID *clsID, const GUID *iid, void **outObject);
92baa3858d3f5d128a5c8466b700098109edcad5f2repo synctypedef UInt32 (WINAPI *SetLargePageModeFunc)();
93baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
94baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
95baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic HRESULT GetCoderClass(GetMethodPropertyFunc getMethodProperty, UInt32 index,
96baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    PROPID propId, CLSID &clsId, bool &isAssigned)
97baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
98baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  NWindows::NCOM::CPropVariant prop;
99baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  isAssigned = false;
100baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  RINOK(getMethodProperty(index, propId, &prop));
101baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (prop.vt == VT_BSTR)
102baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
103baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    isAssigned = true;
104baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    clsId = *(const GUID *)prop.bstrVal;
105baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
106baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  else if (prop.vt != VT_EMPTY)
107baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return E_FAIL;
108baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return S_OK;
109baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
110baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
111baa3858d3f5d128a5c8466b700098109edcad5f2repo syncHRESULT CCodecs::LoadCodecs()
112baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
113baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  CCodecLib &lib = Libs.Back();
114baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  lib.GetMethodProperty = (GetMethodPropertyFunc)lib.Lib.GetProc("GetMethodProperty");
115baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (lib.GetMethodProperty == NULL)
116baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return S_OK;
117baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
118baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  UInt32 numMethods = 1;
119baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  GetNumberOfMethodsFunc getNumberOfMethodsFunc = (GetNumberOfMethodsFunc)lib.Lib.GetProc("GetNumberOfMethods");
120baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (getNumberOfMethodsFunc != NULL)
121baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
122baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    RINOK(getNumberOfMethodsFunc(&numMethods));
123baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
124baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
125baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  for(UInt32 i = 0; i < numMethods; i++)
126baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
127baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    CDllCodecInfo info;
128baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    info.LibIndex = Libs.Size() - 1;
129baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    info.CodecIndex = i;
130baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
131baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    RINOK(GetCoderClass(lib.GetMethodProperty, i, NMethodPropID::kEncoder, info.Encoder, info.EncoderIsAssigned));
132baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    RINOK(GetCoderClass(lib.GetMethodProperty, i, NMethodPropID::kDecoder, info.Decoder, info.DecoderIsAssigned));
133baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
134baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    Codecs.Add(info);
135baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
136baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return S_OK;
137baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
138baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
139baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic HRESULT ReadProp(
140baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    GetHandlerPropertyFunc getProp,
141baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    GetHandlerPropertyFunc2 getProp2,
142baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    UInt32 index, PROPID propID, NCOM::CPropVariant &prop)
143baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
144baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (getProp2)
145baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return getProp2(index, propID, &prop);;
146baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return getProp(propID, &prop);
147baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
148baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
149baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic HRESULT ReadBoolProp(
150baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    GetHandlerPropertyFunc getProp,
151baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    GetHandlerPropertyFunc2 getProp2,
152baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    UInt32 index, PROPID propID, bool &res)
153baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
154baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  NCOM::CPropVariant prop;
155baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  RINOK(ReadProp(getProp, getProp2, index, propID, prop));
156baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (prop.vt == VT_BOOL)
157baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    res = VARIANT_BOOLToBool(prop.boolVal);
158baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  else if (prop.vt != VT_EMPTY)
159baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return E_FAIL;
160baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return S_OK;
161baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
162baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
163baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic HRESULT ReadStringProp(
164baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    GetHandlerPropertyFunc getProp,
165baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    GetHandlerPropertyFunc2 getProp2,
166baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    UInt32 index, PROPID propID, UString &res)
167baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
168baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  NCOM::CPropVariant prop;
169baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  RINOK(ReadProp(getProp, getProp2, index, propID, prop));
170baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (prop.vt == VT_BSTR)
171baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    res = prop.bstrVal;
172baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  else if (prop.vt != VT_EMPTY)
173baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return E_FAIL;
174baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return S_OK;
175baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
176baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
177baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
178baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
179baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic const unsigned int kNumArcsMax = 48;
180baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic unsigned int g_NumArcs = 0;
181baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic const CArcInfo *g_Arcs[kNumArcsMax];
182baa3858d3f5d128a5c8466b700098109edcad5f2repo syncvoid RegisterArc(const CArcInfo *arcInfo)
183baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
184baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (g_NumArcs < kNumArcsMax)
185baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    g_Arcs[g_NumArcs++] = arcInfo;
186baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
187baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
188baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic void SplitString(const UString &srcString, UStringVector &destStrings)
189baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
190baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  destStrings.Clear();
191baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  UString s;
192baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  int len = srcString.Length();
193baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (len == 0)
194baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return;
195baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  for (int i = 0; i < len; i++)
196baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
197baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    wchar_t c = srcString[i];
198baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (c == L' ')
199baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    {
200baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      if (!s.IsEmpty())
201baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      {
202baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        destStrings.Add(s);
203baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        s.Empty();
204baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      }
205baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    }
206baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    else
207baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      s += c;
208baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
209baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (!s.IsEmpty())
210baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    destStrings.Add(s);
211baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
212baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
213baa3858d3f5d128a5c8466b700098109edcad5f2repo syncvoid CArcInfoEx::AddExts(const wchar_t *ext, const wchar_t *addExt)
214baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
215baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  UStringVector exts, addExts;
216baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (ext != 0)
217baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    SplitString(ext, exts);
218baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (addExt != 0)
219baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    SplitString(addExt, addExts);
220baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  for (int i = 0; i < exts.Size(); i++)
221baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
222baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    CArcExtInfo extInfo;
223baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    extInfo.Ext = exts[i];
224baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (i < addExts.Size())
225baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    {
226baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      extInfo.AddExt = addExts[i];
227baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      if (extInfo.AddExt == L"*")
228baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        extInfo.AddExt.Empty();
229baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    }
230baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    Exts.Add(extInfo);
231baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
232baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
233baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
234baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifdef EXTERNAL_CODECS
235baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
236baa3858d3f5d128a5c8466b700098109edcad5f2repo syncHRESULT CCodecs::LoadFormats()
237baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
238baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  const NDLL::CLibrary &lib = Libs.Back().Lib;
239baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  GetHandlerPropertyFunc getProp = 0;
240baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  GetHandlerPropertyFunc2 getProp2 = (GetHandlerPropertyFunc2)lib.GetProc("GetHandlerProperty2");
241baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (getProp2 == NULL)
242baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
243baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    getProp = (GetHandlerPropertyFunc)lib.GetProc("GetHandlerProperty");
244baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (getProp == NULL)
245baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      return S_OK;
246baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
247baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
248baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  UInt32 numFormats = 1;
249baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  GetNumberOfFormatsFunc getNumberOfFormats = (GetNumberOfFormatsFunc)lib.GetProc("GetNumberOfFormats");
250baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (getNumberOfFormats != NULL)
251baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
252baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    RINOK(getNumberOfFormats(&numFormats));
253baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
254baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (getProp2 == NULL)
255baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    numFormats = 1;
256baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
257baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  for(UInt32 i = 0; i < numFormats; i++)
258baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
259baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    CArcInfoEx item;
260baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    item.LibIndex = Libs.Size() - 1;
261baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    item.FormatIndex = i;
262baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
263baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    RINOK(ReadStringProp(getProp, getProp2, i, NArchive::kName, item.Name));
264baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
265baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    NCOM::CPropVariant prop;
266baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (ReadProp(getProp, getProp2, i, NArchive::kClassID, prop) != S_OK)
267baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      continue;
268baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (prop.vt != VT_BSTR)
269baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      continue;
270baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    item.ClassID = *(const GUID *)prop.bstrVal;
271baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    prop.Clear();
272baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
273baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    UString ext, addExt;
274baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    RINOK(ReadStringProp(getProp, getProp2, i, NArchive::kExtension, ext));
275baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    RINOK(ReadStringProp(getProp, getProp2, i, NArchive::kAddExtension, addExt));
276baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    item.AddExts(ext, addExt);
277baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
278baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    ReadBoolProp(getProp, getProp2, i, NArchive::kUpdate, item.UpdateEnabled);
279baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (item.UpdateEnabled)
280baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      ReadBoolProp(getProp, getProp2, i, NArchive::kKeepName, item.KeepName);
281baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
282baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (ReadProp(getProp, getProp2, i, NArchive::kStartSignature, prop) == S_OK)
283baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      if (prop.vt == VT_BSTR)
284baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      {
285baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        UINT len = ::SysStringByteLen(prop.bstrVal);
286baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        item.StartSignature.SetCapacity(len);
287baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        memmove(item.StartSignature, prop.bstrVal, len);
288baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      }
289baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    Formats.Add(item);
290baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
291baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return S_OK;
292baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
293baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
294baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifdef NEW_FOLDER_INTERFACE
295baa3858d3f5d128a5c8466b700098109edcad5f2repo syncvoid CCodecIcons::LoadIcons(HMODULE m)
296baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
297baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  UString iconTypes = MyLoadStringW(m, kIconTypesResId);
298baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  UStringVector pairs;
299baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  SplitString(iconTypes, pairs);
300baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  for (int i = 0; i < pairs.Size(); i++)
301baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
302baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    const UString &s = pairs[i];
303baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    int pos = s.Find(L':');
304baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    CIconPair iconPair;
305baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    iconPair.IconIndex = -1;
306baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (pos < 0)
307baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      pos = s.Length();
308baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    else
309baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    {
310baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      UString num = s.Mid(pos + 1);
311baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      if (!num.IsEmpty())
312baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      {
313baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        const wchar_t *end;
314baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        iconPair.IconIndex = (UInt32)ConvertStringToUInt64(num, &end);
315baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        if (*end != L'\0')
316baa3858d3f5d128a5c8466b700098109edcad5f2repo sync          continue;
317baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      }
318baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    }
319baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    iconPair.Ext = s.Left(pos);
320baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    IconPairs.Add(iconPair);
321baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
322baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
323baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
324baa3858d3f5d128a5c8466b700098109edcad5f2repo syncbool CCodecIcons::FindIconIndex(const UString &ext, int &iconIndex) const
325baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
326baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  iconIndex = -1;
327baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  for (int i = 0; i < IconPairs.Size(); i++)
328baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
329baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    const CIconPair &pair = IconPairs[i];
330baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (ext.CompareNoCase(pair.Ext) == 0)
331baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    {
332baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      iconIndex = pair.IconIndex;
333baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      return true;
334baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    }
335baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
336baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return false;
337baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
338baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
339baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
340baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifdef _7ZIP_LARGE_PAGES
341baa3858d3f5d128a5c8466b700098109edcad5f2repo syncextern "C"
342baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
343baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  extern SIZE_T g_LargePageSize;
344baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
345baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
346baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
347baa3858d3f5d128a5c8466b700098109edcad5f2repo syncHRESULT CCodecs::LoadDll(const CSysString &dllPath, bool needCheckDll)
348baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
349baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (needCheckDll)
350baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
351baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    NDLL::CLibrary library;
352baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (!library.LoadEx(dllPath, LOAD_LIBRARY_AS_DATAFILE))
353baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      return S_OK;
354baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
355baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  Libs.Add(CCodecLib());
356baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  CCodecLib &lib = Libs.Back();
357baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef NEW_FOLDER_INTERFACE
358baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  lib.Path = dllPath;
359baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
360baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  bool used = false;
361baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  HRESULT res = S_OK;
362baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (lib.Lib.Load(dllPath))
363baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
364baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    #ifdef NEW_FOLDER_INTERFACE
365baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    lib.LoadIcons();
366baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    #endif
367baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
368baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    #ifdef _7ZIP_LARGE_PAGES
369baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (g_LargePageSize != 0)
370baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    {
371baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      SetLargePageModeFunc setLargePageMode = (SetLargePageModeFunc)lib.Lib.GetProc("SetLargePageMode");
372baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      if (setLargePageMode != 0)
373baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        setLargePageMode();
374baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    }
375baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    #endif
376baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
377baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    lib.CreateObject = (CreateObjectFunc)lib.Lib.GetProc("CreateObject");
378baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (lib.CreateObject != 0)
379baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    {
380baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      int startSize = Codecs.Size();
381baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      res = LoadCodecs();
382baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      used = (Codecs.Size() != startSize);
383baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      if (res == S_OK)
384baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      {
385baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        startSize = Formats.Size();
386baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        res = LoadFormats();
387baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        used = used || (Formats.Size() != startSize);
388baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      }
389baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    }
390baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
391baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (!used)
392baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    Libs.DeleteBack();
393baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return res;
394baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
395baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
396baa3858d3f5d128a5c8466b700098109edcad5f2repo syncHRESULT CCodecs::LoadDllsFromFolder(const CSysString &folderPrefix)
397baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
398baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  NFile::NFind::CEnumerator enumerator(folderPrefix + CSysString(TEXT("*")));
399baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  NFile::NFind::CFileInfo fi;
400baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  while (enumerator.Next(fi))
401baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
402baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (fi.IsDir())
403baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      continue;
404baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    RINOK(LoadDll(folderPrefix + fi.Name, true));
405baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
406baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return S_OK;
407baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
408baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
409baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
410baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
411baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifndef _SFX
412baa3858d3f5d128a5c8466b700098109edcad5f2repo syncstatic inline void SetBuffer(CByteBuffer &bb, const Byte *data, int size)
413baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
414baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  bb.SetCapacity(size);
415baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  memmove((Byte *)bb, data, size);
416baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
417baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
418baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
419baa3858d3f5d128a5c8466b700098109edcad5f2repo syncHRESULT CCodecs::Load()
420baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
421baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef NEW_FOLDER_INTERFACE
422baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  InternalIcons.LoadIcons(g_hInstance);
423baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
424baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
425baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  Formats.Clear();
426baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef EXTERNAL_CODECS
427baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  Codecs.Clear();
428baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
429baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  for (UInt32 i = 0; i < g_NumArcs; i++)
430baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
431baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    const CArcInfo &arc = *g_Arcs[i];
432baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    CArcInfoEx item;
433baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    item.Name = arc.Name;
434baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    item.CreateInArchive = arc.CreateInArchive;
435baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    item.CreateOutArchive = arc.CreateOutArchive;
436baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    item.AddExts(arc.Ext, arc.AddExt);
437baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    item.UpdateEnabled = (arc.CreateOutArchive != 0);
438baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    item.KeepName = arc.KeepName;
439baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
440baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    #ifndef _SFX
441baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    SetBuffer(item.StartSignature, arc.Signature, arc.SignatureSize);
442baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    #endif
443baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    Formats.Add(item);
444baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
445baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef EXTERNAL_CODECS
446baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  const CSysString baseFolder = GetBaseFolderPrefixFromRegistry();
447baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  RINOK(LoadDll(baseFolder + kMainDll, false));
448baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  RINOK(LoadDllsFromFolder(baseFolder + kCodecsFolderName TEXT(STRING_PATH_SEPARATOR)));
449baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  RINOK(LoadDllsFromFolder(baseFolder + kFormatsFolderName TEXT(STRING_PATH_SEPARATOR)));
450baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
451baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return S_OK;
452baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
453baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
454baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifndef _SFX
455baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
456baa3858d3f5d128a5c8466b700098109edcad5f2repo syncint CCodecs::FindFormatForArchiveName(const UString &arcPath) const
457baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
458baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  int slashPos1 = arcPath.ReverseFind(WCHAR_PATH_SEPARATOR);
459baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  int slashPos2 = arcPath.ReverseFind(L'.');
460baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  int dotPos = arcPath.ReverseFind(L'.');
461baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (dotPos < 0 || dotPos < slashPos1 || dotPos < slashPos2)
462baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return -1;
463baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  UString ext = arcPath.Mid(dotPos + 1);
464baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  for (int i = 0; i < Formats.Size(); i++)
465baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
466baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    const CArcInfoEx &arc = Formats[i];
467baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (!arc.UpdateEnabled)
468baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      continue;
469baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (arc.FindExtension(ext) >= 0)
470baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      return i;
471baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
472baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return -1;
473baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
474baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
475baa3858d3f5d128a5c8466b700098109edcad5f2repo syncint CCodecs::FindFormatForExtension(const UString &ext) const
476baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
477baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (ext.IsEmpty())
478baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return -1;
479baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  for (int i = 0; i < Formats.Size(); i++)
480baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (Formats[i].FindExtension(ext) >= 0)
481baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      return i;
482baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return -1;
483baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
484baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
485baa3858d3f5d128a5c8466b700098109edcad5f2repo syncint CCodecs::FindFormatForArchiveType(const UString &arcType) const
486baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
487baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  for (int i = 0; i < Formats.Size(); i++)
488baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (Formats[i].Name.CompareNoCase(arcType) == 0)
489baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      return i;
490baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return -1;
491baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
492baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
493baa3858d3f5d128a5c8466b700098109edcad5f2repo syncbool CCodecs::FindFormatForArchiveType(const UString &arcType, CIntVector &formatIndices) const
494baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
495baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  formatIndices.Clear();
496baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  for (int pos = 0; pos < arcType.Length();)
497baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
498baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    int pos2 = arcType.Find('.', pos);
499baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (pos2 < 0)
500baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      pos2 = arcType.Length();
501baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    const UString name = arcType.Mid(pos, pos2 - pos);
502baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    int index = FindFormatForArchiveType(name);
503baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (index < 0 && name != L"*")
504baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    {
505baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      formatIndices.Clear();
506baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      return false;
507baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    }
508baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    formatIndices.Add(index);
509baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    pos = pos2 + 1;
510baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
511baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return true;
512baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
513baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
514baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
515baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
516baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifdef EXTERNAL_CODECS
517baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
518baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#ifdef EXPORT_CODECS
519baa3858d3f5d128a5c8466b700098109edcad5f2repo syncextern unsigned int g_NumCodecs;
520baa3858d3f5d128a5c8466b700098109edcad5f2repo syncSTDAPI CreateCoder2(bool encode, UInt32 index, const GUID *iid, void **outObject);
521baa3858d3f5d128a5c8466b700098109edcad5f2repo syncSTDAPI GetMethodProperty(UInt32 codecIndex, PROPID propID, PROPVARIANT *value);
522baa3858d3f5d128a5c8466b700098109edcad5f2repo sync// STDAPI GetNumberOfMethods(UInt32 *numCodecs);
523baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
524baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
525baa3858d3f5d128a5c8466b700098109edcad5f2repo syncSTDMETHODIMP CCodecs::GetNumberOfMethods(UInt32 *numMethods)
526baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
527baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  *numMethods =
528baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      #ifdef EXPORT_CODECS
529baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      g_NumCodecs +
530baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      #endif
531baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      Codecs.Size();
532baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return S_OK;
533baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
534baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
535baa3858d3f5d128a5c8466b700098109edcad5f2repo syncSTDMETHODIMP CCodecs::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *value)
536baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
537baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef EXPORT_CODECS
538baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (index < g_NumCodecs)
539baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return GetMethodProperty(index, propID, value);
540baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
541baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
542baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  const CDllCodecInfo &ci = Codecs[index
543baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      #ifdef EXPORT_CODECS
544baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      - g_NumCodecs
545baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      #endif
546baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      ];
547baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
548baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (propID == NMethodPropID::kDecoderIsAssigned)
549baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
550baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    NWindows::NCOM::CPropVariant propVariant;
551baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    propVariant = ci.DecoderIsAssigned;
552baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    propVariant.Detach(value);
553baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return S_OK;
554baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
555baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (propID == NMethodPropID::kEncoderIsAssigned)
556baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
557baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    NWindows::NCOM::CPropVariant propVariant;
558baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    propVariant = ci.EncoderIsAssigned;
559baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    propVariant.Detach(value);
560baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return S_OK;
561baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
562baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return Libs[ci.LibIndex].GetMethodProperty(ci.CodecIndex, propID, value);
563baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
564baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
565baa3858d3f5d128a5c8466b700098109edcad5f2repo syncSTDMETHODIMP CCodecs::CreateDecoder(UInt32 index, const GUID *iid, void **coder)
566baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
567baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef EXPORT_CODECS
568baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (index < g_NumCodecs)
569baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return CreateCoder2(false, index, iid, coder);
570baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
571baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  const CDllCodecInfo &ci = Codecs[index
572baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      #ifdef EXPORT_CODECS
573baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      - g_NumCodecs
574baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      #endif
575baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      ];
576baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (ci.DecoderIsAssigned)
577baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return Libs[ci.LibIndex].CreateObject(&ci.Decoder, iid, (void **)coder);
578baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return S_OK;
579baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
580baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
581baa3858d3f5d128a5c8466b700098109edcad5f2repo syncSTDMETHODIMP CCodecs::CreateEncoder(UInt32 index, const GUID *iid, void **coder)
582baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
583baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef EXPORT_CODECS
584baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (index < g_NumCodecs)
585baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return CreateCoder2(true, index, iid, coder);
586baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
587baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  const CDllCodecInfo &ci = Codecs[index
588baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      #ifdef EXPORT_CODECS
589baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      - g_NumCodecs
590baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      #endif
591baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      ];
592baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (ci.EncoderIsAssigned)
593baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return Libs[ci.LibIndex].CreateObject(&ci.Encoder, iid, (void **)coder);
594baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return S_OK;
595baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
596baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
597baa3858d3f5d128a5c8466b700098109edcad5f2repo syncHRESULT CCodecs::CreateCoder(const UString &name, bool encode, CMyComPtr<ICompressCoder> &coder) const
598baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
599baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  for (int i = 0; i < Codecs.Size(); i++)
600baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
601baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    const CDllCodecInfo &codec = Codecs[i];
602baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (encode && !codec.EncoderIsAssigned || !encode && !codec.DecoderIsAssigned)
603baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      continue;
604baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    const CCodecLib &lib = Libs[codec.LibIndex];
605baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    UString res;
606baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    NWindows::NCOM::CPropVariant prop;
607baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    RINOK(lib.GetMethodProperty(codec.CodecIndex, NMethodPropID::kName, &prop));
608baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (prop.vt == VT_BSTR)
609baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      res = prop.bstrVal;
610baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    else if (prop.vt != VT_EMPTY)
611baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      continue;
612baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (name.CompareNoCase(res) == 0)
613baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      return lib.CreateObject(encode ? &codec.Encoder : &codec.Decoder, &IID_ICompressCoder, (void **)&coder);
614baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
615baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return CLASS_E_CLASSNOTAVAILABLE;
616baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
617baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
618baa3858d3f5d128a5c8466b700098109edcad5f2repo syncint CCodecs::GetCodecLibIndex(UInt32 index)
619baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
620baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef EXPORT_CODECS
621baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (index < g_NumCodecs)
622baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return -1;
623baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
624baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef EXTERNAL_CODECS
625baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  const CDllCodecInfo &ci = Codecs[index
626baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      #ifdef EXPORT_CODECS
627baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      - g_NumCodecs
628baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      #endif
629baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      ];
630baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return ci.LibIndex;
631baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #else
632baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return -1;
633baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
634baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
635baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
636baa3858d3f5d128a5c8466b700098109edcad5f2repo syncbool CCodecs::GetCodecEncoderIsAssigned(UInt32 index)
637baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
638baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef EXPORT_CODECS
639baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (index < g_NumCodecs)
640baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  {
641baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    NWindows::NCOM::CPropVariant prop;
642baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (GetProperty(index, NMethodPropID::kEncoder, &prop) == S_OK)
643baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      if (prop.vt != VT_EMPTY)
644baa3858d3f5d128a5c8466b700098109edcad5f2repo sync        return true;
645baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return false;
646baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  }
647baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
648baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #ifdef EXTERNAL_CODECS
649baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  const CDllCodecInfo &ci = Codecs[index
650baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      #ifdef EXPORT_CODECS
651baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      - g_NumCodecs
652baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      #endif
653baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      ];
654baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return ci.EncoderIsAssigned;
655baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #else
656baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return false;
657baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  #endif
658baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
659baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
660baa3858d3f5d128a5c8466b700098109edcad5f2repo syncHRESULT CCodecs::GetCodecId(UInt32 index, UInt64 &id)
661baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
662baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  UString s;
663baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  NWindows::NCOM::CPropVariant prop;
664baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  RINOK(GetProperty(index, NMethodPropID::kID, &prop));
665baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (prop.vt != VT_UI8)
666baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    return E_INVALIDARG;
667baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  id = prop.uhVal.QuadPart;
668baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return S_OK;
669baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
670baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
671baa3858d3f5d128a5c8466b700098109edcad5f2repo syncUString CCodecs::GetCodecName(UInt32 index)
672baa3858d3f5d128a5c8466b700098109edcad5f2repo sync{
673baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  UString s;
674baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  NWindows::NCOM::CPropVariant prop;
675baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  if (GetProperty(index, NMethodPropID::kName, &prop) == S_OK)
676baa3858d3f5d128a5c8466b700098109edcad5f2repo sync    if (prop.vt == VT_BSTR)
677baa3858d3f5d128a5c8466b700098109edcad5f2repo sync      s = prop.bstrVal;
678baa3858d3f5d128a5c8466b700098109edcad5f2repo sync  return s;
679baa3858d3f5d128a5c8466b700098109edcad5f2repo sync}
680baa3858d3f5d128a5c8466b700098109edcad5f2repo sync
681baa3858d3f5d128a5c8466b700098109edcad5f2repo sync#endif
682