织梦网站上传图片不行,咸阳网站建设报价,免费1级做爰片打网站,跨境电商个人开店的平台转自#xff1a;https://blog.csdn.net/u013761036/article/details/54960277
这个东西并不陌生了#xff0c;之前写过了一个关于这个的应用#xff0c;利用静态TLS姿势实现代码段静态加密免杀或者所谓的加壳思路。地址在这:http://blog.csdn.net/u013761036/article/detai…
转自https://blog.csdn.net/u013761036/article/details/54960277
这个东西并不陌生了之前写过了一个关于这个的应用利用静态TLS姿势实现代码段静态加密免杀或者所谓的加壳思路。地址在这:http://blog.csdn.net/u013761036/article/details/53967943今天就简单的整理下TLS的相关概念和常规应用。一开始说了一大堆的Windows的进程与线程啥啥啥的概念和原理这里直接省略。
什么是线程局部存储 线程局部存储Thread Local Storage,TLS很好的解决了多线程设计中变量同步问题比如你写一个exe里面有N个线程你可以放弃使用TLS因为你对自己设计的程序有比较全面的把握。你清楚自己设计的进程里总共有多少个线程每个线程使用了哪些数据结构内存空间申请、释放都在你的掌控之下全局变量的访问全部都采用了同步技术那是没问题的。如果你是一个DLL开发者你无法确定调用这个DLL的素质程序里到底有多少个线程每个线程的数据是如何定义的这时可以考虑使用线程据存储技术。 TLS分为静态和动态两种
动态TLS,主要是使用这几个API TlsAlloc ,TlsGetValue,TlsSetValue,TlsFree
下面是微软MSDN上的一个例子看下理解下 [cpp] view plain copy
code classlanguage-cpp#include windows.h #include stdio.h #define THREADCOUNT 4 DWORD dwTlsIndex; VOID ErrorExit(LPSTR); VOID CommonFunc(VOID) { LPVOID lpvData; // Retrieve a data pointer for the current thread. lpvData TlsGetValue(dwTlsIndex); if ((lpvData 0) (GetLastError() ! ERROR_SUCCESS)) ErrorExit(TlsGetValue error); // Use the data stored for the current thread. printf(common: thread %d: lpvData%lx\n, GetCurrentThreadId(), lpvData); Sleep(5000); } DWORD WINAPI ThreadFunc(VOID) { LPVOID lpvData; // Initialize the TLS index for this thread. lpvData (LPVOID) LocalAlloc(LPTR, 256); if (! TlsSetValue(dwTlsIndex, lpvData)) ErrorExit(TlsSetValue error); printf(thread %d: lpvData%lx\n, GetCurrentThreadId(), lpvData); CommonFunc(); // Release the dynamic memory before the thread returns. lpvData TlsGetValue(dwTlsIndex); if (lpvData ! 0) LocalFree((HLOCAL) lpvData); return 0; } int main(VOID) { DWORD IDThread; HANDLE hThread[THREADCOUNT]; int i; // Allocate a TLS index. if ((dwTlsIndex TlsAlloc()) TLS_OUT_OF_INDEXES) ErrorExit(TlsAlloc failed); // Create multiple threads. for (i 0; i THREADCOUNT; i) { hThread[i] CreateThread(NULL, // default security attributes 0, // use default stack size (LPTHREAD_START_ROUTINE) ThreadFunc, // thread function NULL, // no thread function argument 0, // use default creation flags IDThread); // returns thread identifier // Check the return value for success. if (hThread[i] NULL) ErrorExit(CreateThread error\n); } for (i 0; i THREADCOUNT; i) WaitForSingleObject(hThread[i], INFINITE); TlsFree(dwTlsIndex); return 0; } VOID ErrorExit (LPSTR lpszMessage) { fprintf(stderr, %s\n, lpszMessage); ExitProcess(0); }/code 静态TLS 静态线程局部存储是操作系统提供的另外一种线程与数据绑定的技术。它与动态TLS的区别在于通过静态线程局部存储指定的数据无需使用专门的API函数随意在易用性上会更好一些。 静态线程局部存储预先将变量定义在PE文件内部一般使用.tls节存储对于相关API的调用由操作系统来完成。这种方式的有点就是从高级语言程序员角度来看更简单了。这种实现方式使得TLS数据的定义与初始化就像程序中使用普通的静态变量那样。 对静态TLS变量的定义不需要想动态线程局部存储一样调用相关API只需要做如下声明即可:
_declspec(thread) int tlsFlag1; 为了支持这种编程模式。PE中的.tls节会包含一下信息:
初始化数据
用于每个线程初始化和终止的回调函数
TLS索引