OSDN Git Service

Add a new class to handle the TLS stuff
authorKazuhiro Fujieda <fujieda@users.sourceforge.jp>
Wed, 12 Mar 2014 09:39:40 +0000 (18:39 +0900)
committerKazuhiro Fujieda <fujieda@users.sourceforge.jp>
Thu, 11 Sep 2014 13:22:29 +0000 (22:22 +0900)
xkeymacsdll/TLS.cpp [new file with mode: 0644]
xkeymacsdll/TLS.h [new file with mode: 0644]
xkeymacsdll/xkeymacsdll-vc10.vcxproj
xkeymacsdll/xkeymacsdll-vc10.vcxproj.filters
xkeymacsdll/xkeymacsdll.cpp

diff --git a/xkeymacsdll/TLS.cpp b/xkeymacsdll/TLS.cpp
new file mode 100644 (file)
index 0000000..78ea55e
--- /dev/null
@@ -0,0 +1,54 @@
+#include "StdAfx.h"\r
+#include "TLS.h"\r
+\r
+DWORD TLS::m_TlsIndex = TLS_OUT_OF_INDEXES;\r
+\r
+bool TLS::Alloc()\r
+{\r
+       return (m_TlsIndex = TlsAlloc()) != TLS_OUT_OF_INDEXES;\r
+}\r
+\r
+void TLS::Free()\r
+{\r
+       FreeLocal();\r
+       if (m_TlsIndex != TLS_OUT_OF_INDEXES)\r
+               TlsFree(m_TlsIndex);\r
+       m_TlsIndex = TLS_OUT_OF_INDEXES;\r
+}\r
+\r
+TLS *TLS::AllocLocal()\r
+{\r
+       if (m_TlsIndex == TLS_OUT_OF_INDEXES)\r
+               return nullptr;\r
+       LPVOID data = TlsGetValue(m_TlsIndex);\r
+       if (!data) {\r
+               data = LocalAlloc(LPTR, sizeof(TLS));\r
+               if (data)\r
+                       TlsSetValue(m_TlsIndex, data);\r
+       }\r
+       return reinterpret_cast<TLS *>(data);\r
+}\r
+\r
+void TLS::FreeLocal()\r
+{\r
+       if (m_TlsIndex == TLS_OUT_OF_INDEXES)\r
+               return;\r
+       LPVOID data = TlsGetValue(m_TlsIndex);\r
+       if (!data)\r
+               return;\r
+       LocalFree(data);\r
+       TlsSetValue(m_TlsIndex, nullptr);\r
+}\r
+\r
+HHOOK TLS::GetKeyboardHook()\r
+{\r
+       TLS *tls = AllocLocal();\r
+       return tls ? tls->m_KeyboardHook : nullptr;\r
+}\r
+\r
+void TLS::PutKeyboardHook(HHOOK hook)\r
+{\r
+       TLS *tls = AllocLocal();\r
+       if (tls)\r
+               tls->m_KeyboardHook = hook;\r
+}
\ No newline at end of file
diff --git a/xkeymacsdll/TLS.h b/xkeymacsdll/TLS.h
new file mode 100644 (file)
index 0000000..e396e0f
--- /dev/null
@@ -0,0 +1,17 @@
+#pragma once\r
+class TLS\r
+{\r
+public:\r
+       static bool Alloc();\r
+       static void Free();\r
+       static void FreeLocal();\r
+       static HHOOK GetKeyboardHook();\r
+       static void PutKeyboardHook(HHOOK hook);\r
+\r
+private:\r
+       static DWORD m_TlsIndex;\r
+       static TLS *m_LocalData;\r
+       HHOOK m_KeyboardHook;\r
+       static TLS *AllocLocal();\r
+};\r
+\r
index 86ec84c..fbdad92 100644 (file)
       <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Create</PrecompiledHeader>\r
       <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">Create</PrecompiledHeader>\r
     </ClCompile>\r
+    <ClCompile Include="TLS.cpp" />\r
     <ClCompile Include="Utils.cpp" />\r
     <ClCompile Include="xkeymacsdll.cpp" />\r
   </ItemGroup>\r
     <ClInclude Include="KbdMacro.h" />\r
     <ClInclude Include="resource.h" />\r
     <ClInclude Include="StdAfx.h" />\r
+    <ClInclude Include="TLS.h" />\r
     <ClInclude Include="tstring.h" />\r
     <ClInclude Include="Utils.h" />\r
     <ClInclude Include="xkeymacsdll.h" />\r
index 9d6f127..fe1251d 100644 (file)
@@ -48,6 +48,9 @@
     <ClCompile Include="PipeName.cpp">\r
       <Filter>Source Files</Filter>\r
     </ClCompile>\r
+    <ClCompile Include="TLS.cpp">\r
+      <Filter>Source Files</Filter>\r
+    </ClCompile>\r
   </ItemGroup>\r
   <ItemGroup>\r
     <None Include="xkeymacsdll.def">\r
     <ClInclude Include="PipeName.h">\r
       <Filter>Header Files</Filter>\r
     </ClInclude>\r
+    <ClInclude Include="TLS.h">\r
+      <Filter>Header Files</Filter>\r
+    </ClInclude>\r
   </ItemGroup>\r
   <ItemGroup>\r
     <ResourceCompile Include="xkeymacsdll.rc">\r
index f49c0db..d8da65e 100644 (file)
@@ -5,6 +5,7 @@
 #include "Utils.h"\r
 #include "Commands.h"\r
 #include "CmdTable.h"\r
+#include "TLS.h"\r
 #include "../xkeymacs/resource.h"\r
 #include <math.h>\r
 #include <Imm.h>\r
@@ -19,13 +20,11 @@ static char THIS_FILE[] = __FILE__;
 static AFX_EXTENSION_MODULE XkeymacsdllDLL = { NULL, NULL };\r
 \r
 static HINSTANCE g_hDllInst = NULL;\r
-static DWORD g_TlsIndex = 0;\r
 \r
 extern "C" int APIENTRY\r
 DllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID lpReserved)\r
 {\r
        g_hDllInst = hInstance;\r
-       LPVOID lpData;\r
        \r
        // Remove this if you use lpReserved\r
        UNREFERENCED_PARAMETER(lpReserved);\r
@@ -58,27 +57,20 @@ DllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID lpReserved)
                        e->Delete();\r
 //                     CUtils::Log("DllMain: 'new' threw an exception");\r
                }\r
-\r
-               if ((g_TlsIndex = TlsAlloc()) == TLS_OUT_OF_INDEXES)\r
+               if (!TLS::Alloc())\r
                        return FALSE;\r
-               // fall through\r
        case DLL_THREAD_ATTACH:\r
-               if ((lpData = LocalAlloc(LPTR, sizeof(HHOOK))) != NULL)\r
-                       TlsSetValue(g_TlsIndex, lpData);\r
                break;\r
        case DLL_PROCESS_DETACH:\r
                TRACE0("XKEYMACSDLL.DLL Terminating!\n");\r
                // Terminate the library before destructors are called\r
                AfxTermExtensionModule(XkeymacsdllDLL);\r
                CXkeymacsDll::ReleaseKeyboardHook();\r
-               if ((lpData = TlsGetValue(g_TlsIndex)) != NULL)\r
-                       LocalFree(lpData);\r
-               TlsFree(g_TlsIndex);\r
+               TLS::Free();\r
                break;\r
        case DLL_THREAD_DETACH:\r
                CXkeymacsDll::ReleaseKeyboardHook();\r
-               if ((lpData = TlsGetValue(g_TlsIndex)) != NULL)\r
-                       LocalFree(lpData);\r
+               TLS::FreeLocal();\r
                break;\r
        }\r
        return 1;   // ok\r
@@ -164,17 +156,8 @@ void CXkeymacsDll::SetHooks()
 \r
 void CXkeymacsDll::SetKeyboardHook(DWORD threadId)\r
 {\r
-       LPVOID lpData = TlsGetValue(g_TlsIndex);\r
-       if (!lpData) {\r
-               lpData = LocalAlloc(LPTR, sizeof(HHOOK));\r
-               if (!lpData)\r
-                       return;\r
-               if (!TlsSetValue(g_TlsIndex, lpData))\r
-                       return;\r
-       }\r
-       HHOOK *phHook = reinterpret_cast<HHOOK *>(lpData);\r
-       if (!*phHook)\r
-               *phHook = SetWindowsHookEx(WH_KEYBOARD, KeyboardProc, g_hDllInst, threadId ? threadId : GetCurrentThreadId());\r
+       if (!TLS::GetKeyboardHook())\r
+               TLS::PutKeyboardHook(SetWindowsHookEx(WH_KEYBOARD, KeyboardProc, g_hDllInst, threadId ? threadId : GetCurrentThreadId()));\r
 }\r
 \r
 inline void unhook(HHOOK &hh)\r
@@ -201,9 +184,10 @@ void CXkeymacsDll::ReleaseHooks()
 \r
 void CXkeymacsDll::ReleaseKeyboardHook()\r
 {\r
-       HHOOK *phHook = reinterpret_cast<HHOOK *>(TlsGetValue(g_TlsIndex));\r
-       if (phHook)\r
-               unhook(*phHook);\r
+       HHOOK hook = TLS::GetKeyboardHook();\r
+       if (!hook)\r
+               return;\r
+       UnhookWindowsHookEx(hook);\r
 }\r
 \r
 void CXkeymacsDll::SetHookStateDirect(bool enable)\r