| OLD | NEW | 
|    1 #include "PluginStdAfx.h" |    1 #include "PluginStdAfx.h" | 
|    2  |    2  | 
|    3 #include "PluginSettings.h" |    3 #include "PluginSettings.h" | 
|    4 #include "PluginSystem.h" |    4 #include "PluginSystem.h" | 
|    5 #include "PluginFilter.h" |    5 #include "PluginFilter.h" | 
|    6 #include "PluginClientFactory.h" |    6 #include "PluginClientFactory.h" | 
|    7 #include "PluginDictionary.h" |    7 #include "PluginDictionary.h" | 
|    8 #include "PluginHttpRequest.h" |    8 #include "PluginHttpRequest.h" | 
|    9 #include "PluginMutex.h" |    9 #include "PluginMutex.h" | 
|   10 #include "PluginClass.h" |   10 #include "PluginClass.h" | 
 |   11 #include "PluginUtil.h" | 
|   11  |   12  | 
|   12 #include "AdblockPlusClient.h" |   13 #include "AdblockPlusClient.h" | 
|   13  |   14  | 
 |   15 namespace | 
 |   16 { | 
 |   17   // TODO: GetUserName, pipeName, bufferSize, AutoHandle, ReadMessage, WriteMess
     age, MarshalStrings and UnmarshalStrings are | 
 |   18   //       duplicated in AdblockPlusEngine. We should find a way to reuse them. | 
 |   19  | 
 |   20   std::wstring GetUserName() | 
 |   21   { | 
 |   22     const DWORD maxLength = UNLEN + 1; | 
 |   23     std::auto_ptr<wchar_t> buffer(new wchar_t[maxLength]); | 
 |   24     DWORD length = maxLength; | 
 |   25     if (!::GetUserName(buffer.get(), &length)) | 
 |   26     { | 
 |   27       std::stringstream stream; | 
 |   28       stream << "Failed to get the current user's name (Error code: " << GetLast
     Error() << ")"; | 
 |   29       throw std::runtime_error("Failed to get the current user's name"); | 
 |   30     } | 
 |   31     return std::wstring(buffer.get(), length); | 
 |   32   } | 
 |   33  | 
 |   34   const std::wstring pipeName = L"\\\\.\\pipe\\adblockplusengine_" + GetUserName
     (); | 
 |   35   const int bufferSize = 1024; | 
 |   36  | 
 |   37   class AutoHandle | 
 |   38   { | 
 |   39   public: | 
 |   40     AutoHandle() | 
 |   41     { | 
 |   42     } | 
 |   43  | 
 |   44     AutoHandle(HANDLE handle) : handle(handle) | 
 |   45     { | 
 |   46     } | 
 |   47  | 
 |   48     ~AutoHandle() | 
 |   49     { | 
 |   50       CloseHandle(handle); | 
 |   51     } | 
 |   52  | 
 |   53     HANDLE get() | 
 |   54     { | 
 |   55       return handle; | 
 |   56     } | 
 |   57  | 
 |   58   private: | 
 |   59     HANDLE handle; | 
 |   60  | 
 |   61     AutoHandle(const AutoHandle& autoHandle); | 
 |   62     AutoHandle& operator=(const AutoHandle& autoHandle); | 
 |   63   }; | 
 |   64  | 
 |   65   std::string MarshalStrings(const std::vector<std::string>& strings) | 
 |   66   { | 
 |   67     // TODO: This is some pretty hacky marshalling, replace it with something mo
     re robust | 
 |   68     std::string marshalledStrings; | 
 |   69     for (std::vector<std::string>::const_iterator it = strings.begin(); it != st
     rings.end(); it++) | 
 |   70       marshalledStrings += *it + ';'; | 
 |   71     return marshalledStrings; | 
 |   72   } | 
 |   73  | 
 |   74   std::vector<std::string> UnmarshalStrings(const std::string& message) | 
 |   75   { | 
 |   76     std::stringstream stream(message); | 
 |   77     std::vector<std::string> strings; | 
 |   78     std::string string; | 
 |   79     while (std::getline(stream, string, ';')) | 
 |   80         strings.push_back(string); | 
 |   81     return strings; | 
 |   82   } | 
 |   83  | 
 |   84   std::string ReadMessage(HANDLE pipe) | 
 |   85   { | 
 |   86     std::stringstream stream; | 
 |   87     std::auto_ptr<char> buffer(new char[bufferSize]); | 
 |   88     bool doneReading = false; | 
 |   89     while (!doneReading) | 
 |   90     { | 
 |   91       DWORD bytesRead; | 
 |   92       if (ReadFile(pipe, buffer.get(), bufferSize * sizeof(char), &bytesRead, 0)
     ) | 
 |   93         doneReading = true; | 
 |   94       else if (GetLastError() != ERROR_MORE_DATA) | 
 |   95       { | 
 |   96         std::stringstream stream; | 
 |   97         stream << "Error reading from pipe: " << GetLastError(); | 
 |   98         throw std::runtime_error(stream.str()); | 
 |   99       } | 
 |  100       stream << std::string(buffer.get(), bytesRead); | 
 |  101     } | 
 |  102     return stream.str(); | 
 |  103   } | 
 |  104  | 
 |  105   void WriteMessage(HANDLE pipe, const std::string& message) | 
 |  106   { | 
 |  107     DWORD bytesWritten; | 
 |  108     if (!WriteFile(pipe, message.c_str(), message.length(), &bytesWritten, 0))  | 
 |  109       throw std::runtime_error("Failed to write to pipe"); | 
 |  110   } | 
 |  111  | 
 |  112   HANDLE OpenPipe(const std::wstring& name) | 
 |  113   { | 
 |  114     if (WaitNamedPipe(name.c_str(), 5000)) | 
 |  115       return CreateFile(name.c_str(), GENERIC_READ | GENERIC_WRITE, 0, 0, OPEN_E
     XISTING, 0, 0); | 
 |  116     return INVALID_HANDLE_VALUE; | 
 |  117   } | 
 |  118  | 
 |  119   void SpawnAdblockPlusEngine() | 
 |  120   { | 
 |  121     std::wstring engineExecutablePath = DllDir() + L"AdblockPlusEngine.exe"; | 
 |  122     STARTUPINFO startupInfo = {}; | 
 |  123     PROCESS_INFORMATION processInformation = {}; | 
 |  124  | 
 |  125     HANDLE token; | 
 |  126     OpenProcessToken(GetCurrentProcess(), TOKEN_DUPLICATE | TOKEN_ADJUST_DEFAULT
      | TOKEN_QUERY | TOKEN_ASSIGN_PRIMARY, &token); | 
 |  127     HANDLE newToken; | 
 |  128     DuplicateTokenEx(token, 0, 0, SecurityImpersonation, TokenPrimary, &newToken
     ); | 
 |  129  | 
 |  130     if (!CreateProcessAsUser(newToken, 0, const_cast<wchar_t*>(engineExecutableP
     ath.c_str()), 0, 0, 0, 0, 0, 0, | 
 |  131                              &startupInfo, &processInformation)) | 
 |  132     { | 
 |  133       DWORD error = GetLastError(); | 
 |  134       throw std::runtime_error("Failed to start Adblock Plus Engine"); | 
 |  135     } | 
 |  136  | 
 |  137     CloseHandle(processInformation.hProcess); | 
 |  138     CloseHandle(processInformation.hThread); | 
 |  139   } | 
 |  140  | 
 |  141   HANDLE OpenAdblockPlusEnginePipe() | 
 |  142   { | 
 |  143     try | 
 |  144     { | 
 |  145       HANDLE pipe = OpenPipe(pipeName); | 
 |  146       if (pipe == INVALID_HANDLE_VALUE) | 
 |  147       { | 
 |  148         SpawnAdblockPlusEngine(); | 
 |  149  | 
 |  150         int timeout = 10000; | 
 |  151         while ((pipe = OpenPipe(pipeName)) == INVALID_HANDLE_VALUE) | 
 |  152         { | 
 |  153           const int step = 10; | 
 |  154           Sleep(step); | 
 |  155           timeout -= step; | 
 |  156           if (timeout <= 0) | 
 |  157             throw std::runtime_error("Unable to open Adblock Plus Engine pipe"); | 
 |  158         } | 
 |  159       } | 
 |  160  | 
 |  161       DWORD mode = PIPE_READMODE_MESSAGE;  | 
 |  162       if (!SetNamedPipeHandleState(pipe, &mode, 0, 0))  | 
 |  163          throw std::runtime_error("SetNamedPipeHandleState failed"); | 
 |  164  | 
 |  165       return pipe; | 
 |  166     } | 
 |  167     catch(std::exception e) | 
 |  168     { | 
 |  169       DEBUG_GENERAL(e.what()); | 
 |  170       return INVALID_HANDLE_VALUE; | 
 |  171     } | 
 |  172   } | 
 |  173 } | 
|   14  |  174  | 
|   15 CAdblockPlusClient* CAdblockPlusClient::s_instance = NULL; |  175 CAdblockPlusClient* CAdblockPlusClient::s_instance = NULL; | 
|   16  |  176  | 
|   17  |  | 
|   18 CAdblockPlusClient::CAdblockPlusClient() : CPluginClientBase() |  177 CAdblockPlusClient::CAdblockPlusClient() : CPluginClientBase() | 
|   19 { |  178 { | 
|   20   try |  179   m_filter = std::auto_ptr<CPluginFilter>(new CPluginFilter()); | 
|   21   { |  180 } | 
|   22     DEBUG_GENERAL("Building client"); |  | 
|   23     m_filter = std::auto_ptr<CPluginFilter>(new CPluginFilter()); |  | 
|   24     AdblockPlus::AppInfo appInfo; |  | 
|   25     appInfo.name = "adblockplusie"; |  | 
|   26     appInfo.version = CT2CA(_T(IEPLUGIN_VERSION), CP_UTF8); |  | 
|   27     appInfo.platform = "msie"; |  | 
|   28    |  | 
|   29     DEBUG_GENERAL(L"Building engine"); |  | 
|   30  |  181  | 
|   31     JsEnginePtr jsEngine(AdblockPlus::JsEngine::New(appInfo)); |  | 
|   32     filterEngine = std::auto_ptr<AdblockPlus::FilterEngine>(new AdblockPlus::Fil
     terEngine(jsEngine)); |  | 
|   33  |  | 
|   34   } |  | 
|   35   catch(std::exception ex) |  | 
|   36   { |  | 
|   37     DEBUG_GENERAL(ex.what()); |  | 
|   38   } |  | 
|   39 } |  | 
|   40 CAdblockPlusClient::~CAdblockPlusClient() |  182 CAdblockPlusClient::~CAdblockPlusClient() | 
|   41 { |  183 { | 
|   42   s_instance = NULL; |  184   s_instance = NULL; | 
|   43 } |  185 } | 
|   44  |  186  | 
|   45  |  187  | 
|   46 CAdblockPlusClient* CAdblockPlusClient::GetInstance() |  188 CAdblockPlusClient* CAdblockPlusClient::GetInstance() | 
|   47 { |  189 { | 
|   48   CAdblockPlusClient* instance = NULL; |  190   CAdblockPlusClient* instance = NULL; | 
|   49  |  191  | 
|   50   s_criticalSectionLocal.Lock(); |  192   s_criticalSectionLocal.Lock(); | 
|   51   { |  193   { | 
|   52     if (!s_instance) |  194     if (!s_instance) | 
|   53     { |  195     { | 
|   54       CAdblockPlusClient* client = new CAdblockPlusClient(); |  196       CAdblockPlusClient* client = new CAdblockPlusClient(); | 
|   55  |  197  | 
|   56       s_instance = client; |  198       s_instance = client; | 
|   57     } |  199     } | 
|   58  |  200  | 
|   59     instance = s_instance; |  201     instance = s_instance; | 
|   60   } |  202   } | 
|   61   s_criticalSectionLocal.Unlock(); |  203   s_criticalSectionLocal.Unlock(); | 
|   62  |  204  | 
|   63   return instance; |  205   return instance; | 
|   64 } |  206 } | 
|   65  |  207  | 
|   66 AdblockPlus::FilterEngine* CAdblockPlusClient::GetFilterEngine() |  | 
|   67 { |  | 
|   68   return filterEngine.get(); |  | 
|   69 } |  | 
|   70  |  208  | 
|   71 bool CAdblockPlusClient::ShouldBlock(CString src, int contentType, const CString
     & domain, bool addDebug) |  209 bool CAdblockPlusClient::ShouldBlock(CString src, int contentType, const CString
     & domain, bool addDebug) | 
|   72 { |  210 { | 
|   73   bool isBlocked = false; |  211   bool isBlocked = false; | 
|   74  |  212  | 
|   75   bool isCached = false; |  213   bool isCached = false; | 
|   76  |  214  | 
|   77   CPluginSettings* settings = CPluginSettings::GetInstance(); |  215   CPluginSettings* settings = CPluginSettings::GetInstance(); | 
|   78  |  216  | 
|   79   m_criticalSectionCache.Lock(); |  217   m_criticalSectionCache.Lock(); | 
| (...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  156   BYTE version[50]; |  294   BYTE version[50]; | 
|  157   cbData = 50; |  295   cbData = 50; | 
|  158   status = RegQueryValueEx(hKey, L"Version", NULL, &type, (BYTE*)version, &cbDat
     a); |  296   status = RegQueryValueEx(hKey, L"Version", NULL, &type, (BYTE*)version, &cbDat
     a); | 
|  159   if (status != 0) |  297   if (status != 0) | 
|  160   { |  298   { | 
|  161     return 0; |  299     return 0; | 
|  162   } |  300   } | 
|  163   RegCloseKey(hKey); |  301   RegCloseKey(hKey); | 
|  164   return (int)(version[0] - 48); |  302   return (int)(version[0] - 48); | 
|  165 } |  303 } | 
 |  304  | 
 |  305 std::string CallAdblockPlusEngineProcedure(const std::vector<std::string>& args) | 
 |  306 { | 
 |  307   AutoHandle pipe(OpenAdblockPlusEnginePipe()); | 
 |  308   WriteMessage(pipe.get(), MarshalStrings(args)); | 
 |  309   return ReadMessage(pipe.get()); | 
 |  310 } | 
 |  311  | 
 |  312 bool CAdblockPlusClient::Matches(const std::string& url, const std::string& cont
     entType, const std::string& domain) | 
 |  313 { | 
 |  314   std::vector<std::string> args; | 
 |  315   args.push_back("Matches"); | 
 |  316   args.push_back(url); | 
 |  317   args.push_back(contentType); | 
 |  318   args.push_back(domain); | 
 |  319  | 
 |  320   try | 
 |  321   { | 
 |  322     std::string response = CallAdblockPlusEngineProcedure(args); | 
 |  323     return response == "1"; | 
 |  324   } | 
 |  325   catch (const std::exception& e) | 
 |  326   { | 
 |  327     DEBUG_GENERAL(e.what()); | 
 |  328     return false; | 
 |  329   } | 
 |  330 } | 
 |  331  | 
 |  332 std::vector<std::string> CAdblockPlusClient::GetElementHidingSelectors(std::stri
     ng domain) | 
 |  333 { | 
 |  334   std::vector<std::string> args; | 
 |  335   args.push_back("GetElementHidingSelectors"); | 
 |  336   args.push_back(domain); | 
 |  337  | 
 |  338   try | 
 |  339   { | 
 |  340     std::string response = CallAdblockPlusEngineProcedure(args); | 
 |  341     return UnmarshalStrings(response); | 
 |  342   } | 
 |  343   catch (const std::exception& e) | 
 |  344   { | 
 |  345     DEBUG_GENERAL(e.what()); | 
 |  346     return std::vector<std::string>(); | 
 |  347   } | 
 |  348 } | 
 |  349  | 
 |  350 std::vector<AdblockPlus::SubscriptionPtr> CAdblockPlusClient::FetchAvailableSubs
     criptions() | 
 |  351 { | 
 |  352   //TODO: implement this | 
 |  353   return std::vector<AdblockPlus::SubscriptionPtr>(); | 
 |  354 } | 
 |  355  | 
 |  356 std::vector<AdblockPlus::FilterPtr> CAdblockPlusClient::GetListedFilters() | 
 |  357 { | 
 |  358   //TODO: implement this | 
 |  359   return std::vector<AdblockPlus::FilterPtr>(); | 
 |  360 } | 
 |  361  | 
 |  362 AdblockPlus::FilterPtr CAdblockPlusClient::GetFilter(std::string text) | 
 |  363 { | 
 |  364   //TODO: implement this | 
 |  365   return AdblockPlus::FilterPtr(); | 
 |  366 } | 
 |  367  | 
 |  368 std::vector<AdblockPlus::SubscriptionPtr> CAdblockPlusClient::GetListedSubscript
     ions() | 
 |  369 { | 
 |  370   //TODO: implement this | 
 |  371   return std::vector<AdblockPlus::SubscriptionPtr>(); | 
 |  372 } | 
 |  373  | 
 |  374 AdblockPlus::SubscriptionPtr CAdblockPlusClient::GetSubscription(std::string url
     ) | 
 |  375 { | 
 |  376   //TODO: imlement this | 
 |  377   return AdblockPlus::SubscriptionPtr(); | 
 |  378 } | 
| OLD | NEW |