other-licenses/7zstub/src/7zip/Archive/7z/7zMethods.cpp

Tue, 06 Jan 2015 21:39:09 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Tue, 06 Jan 2015 21:39:09 +0100
branch
TOR_BUG_9701
changeset 8
97036ab72558
permissions
-rw-r--r--

Conditionally force memory storage according to privacy.thirdparty.isolate;
This solves Tor bug #9701, complying with disk avoidance documented in
https://www.torproject.org/projects/torbrowser/design/#disk-avoidance.

     1 // 7zMethods.cpp
     3 #include "StdAfx.h"
     5 #include "7zMethods.h"
     7 #include "../../../Windows/FileFind.h"
     8 #include "../../../Windows/DLL.h"
     9 #include "../../../Windows/PropVariant.h"
    10 #include "../../../Windows/Synchronization.h"
    12 #include "../../ICoder.h"
    13 #include "../Common/CodecsPath.h"
    15 using namespace NWindows;
    17 namespace NArchive {
    18 namespace N7z {
    20 static CObjectVector<CMethodInfo2> g_Methods;
    21 static bool g_Loaded = false;
    23 typedef UInt32 (WINAPI *GetNumberOfMethodsFunc)(UInt32 *numMethods);
    25 typedef UInt32 (WINAPI *GetMethodPropertyFunc)(
    26     UInt32 index, PROPID propID, PROPVARIANT *value);
    28 static void Load(const CSysString &folderPrefix)
    29 {
    30   NFile::NFind::CEnumerator enumerator(folderPrefix + CSysString(TEXT("*")));
    31   NFile::NFind::CFileInfo fileInfo;
    32   while (enumerator.Next(fileInfo))
    33   {
    34     if (fileInfo.IsDirectory())
    35       continue;
    36     CSysString filePath = folderPrefix + fileInfo.Name;
    37     {
    38       NDLL::CLibrary library;
    39       if (!library.LoadEx(filePath, LOAD_LIBRARY_AS_DATAFILE))
    40         continue;
    41     }
    42     NDLL::CLibrary library;
    43     if (!library.Load(filePath))
    44       continue;
    45     GetMethodPropertyFunc getMethodProperty = (GetMethodPropertyFunc)
    46         library.GetProcAddress("GetMethodProperty");
    47     if (getMethodProperty == NULL)
    48       continue;
    50     UInt32 numMethods = 1;
    51     GetNumberOfMethodsFunc getNumberOfMethodsFunc = (GetNumberOfMethodsFunc)
    52         library.GetProcAddress("GetNumberOfMethods");
    53     if (getNumberOfMethodsFunc != NULL)
    54       if (getNumberOfMethodsFunc(&numMethods) != S_OK)
    55         continue;
    57     for(UInt32 i = 0; i < numMethods; i++)
    58     {
    59       CMethodInfo2 info;
    60       info.FilePath = filePath;
    62       NWindows::NCOM::CPropVariant propVariant;
    63       if (getMethodProperty(i, NMethodPropID::kID, &propVariant) != S_OK)
    64         continue;
    65       if (propVariant.vt != VT_BSTR)
    66         continue;
    67       info.MethodID.IDSize = SysStringByteLen(propVariant.bstrVal);
    68       memmove(info.MethodID.ID, propVariant.bstrVal, info.MethodID.IDSize);
    69       propVariant.Clear();
    71       if (getMethodProperty(i, NMethodPropID::kName, &propVariant) != S_OK)
    72         continue;
    73       if (propVariant.vt == VT_EMPTY)
    74       {
    75       }
    76       else if (propVariant.vt == VT_BSTR)
    77         info.Name = propVariant.bstrVal;
    78       else
    79         continue;
    80       propVariant.Clear();
    82       if (getMethodProperty (i, NMethodPropID::kEncoder, &propVariant) != S_OK)
    83         continue;
    84       if (propVariant.vt == VT_EMPTY)
    85         info.EncoderIsAssigned = false;
    86       else if (propVariant.vt == VT_BSTR)
    87       {
    88         info.EncoderIsAssigned = true;
    89         info.Encoder = *(const GUID *)propVariant.bstrVal;
    90       }
    91       else
    92         continue;
    93       propVariant.Clear();
    95       if (getMethodProperty (i, NMethodPropID::kDecoder, &propVariant) != S_OK)
    96         continue;
    97       if (propVariant.vt == VT_EMPTY)
    98         info.DecoderIsAssigned = false;
    99       else if (propVariant.vt == VT_BSTR)
   100       {
   101         info.DecoderIsAssigned = true;
   102         info.Decoder = *(const GUID *)propVariant.bstrVal;
   103       }
   104       else
   105         continue;
   106       propVariant.Clear();
   108       if (getMethodProperty (i, NMethodPropID::kInStreams, &propVariant) != S_OK)
   109         continue;
   110       if (propVariant.vt == VT_EMPTY)
   111         info.NumInStreams = 1;
   112       else if (propVariant.vt == VT_UI4)
   113         info.NumInStreams = propVariant.ulVal;
   114       else
   115         continue;
   116       propVariant.Clear();
   118       if (getMethodProperty (i, NMethodPropID::kOutStreams, &propVariant) != S_OK)
   119         continue;
   120       if (propVariant.vt == VT_EMPTY)
   121         info.NumOutStreams = 1;
   122       else if (propVariant.vt == VT_UI4)
   123         info.NumOutStreams = propVariant.ulVal;
   124       else
   125         continue;
   126       propVariant.Clear();
   128       g_Methods.Add(info);
   129     }
   130   }
   131 }
   133 static NSynchronization::CCriticalSection g_CriticalSection;
   135 void LoadMethodMap()
   136 {
   137   NSynchronization::CCriticalSectionLock lock(g_CriticalSection);
   138   if (g_Loaded)
   139     return;
   140   g_Loaded = true;
   141   Load(GetCodecsFolderPrefix());
   142 }
   144 bool GetMethodInfo(const CMethodID &methodID, CMethodInfo &methodInfo)
   145 {
   146   for(int i = 0; i < g_Methods.Size(); i++)
   147   {
   148     const CMethodInfo2 &method = g_Methods[i];
   149     if (method.MethodID == methodID)
   150     {
   151       methodInfo = (CMethodInfo)method;
   152       return true;
   153     }
   154   }
   155   return false;
   156 }
   158 bool GetMethodInfo(const UString &name, CMethodInfo2 &methodInfo)
   159 {
   160   for(int i = 0; i < g_Methods.Size(); i++)
   161   {
   162     const CMethodInfo2 &method = g_Methods[i];
   163     if (method.Name.CompareNoCase(name) == 0)
   164     {
   165       methodInfo = method;
   166       return true;
   167     }
   168   }
   169   return false;
   170 }
   172 }}

mercurial