零基础逆向工程36_Win32_10_互斥体_互斥体与临界区的区别
1 引言
讲了第二个内核对象,互斥体。前面已经学过一个内核对象,线程。这节讲两个函数,WaitForSingleObject()和WaitForMultipleObjects()。因此这两个函数是根据内核对象的状态来进行操作的。
临界区:一个进程里面对线程进行互斥的控制。
互斥体:实现跨进程的互斥的控制。多个进程抢同一个全局变量,怎样保证最终只有一个进程来用。
2 ForSingleObject()
DWORD WaitForSingleObject(
HANDLE hHandle, // handle to object
DWORD dwMilliseconds // time-out interval
);
功能说明:
等待函数可使线程自愿进入等待状态,直到一个特定的内核对象变为已通知状态为止.
hHandle:
内核对象句柄,可以是进程也可以是线程.
dwMilliseconds:
等待时间,单位是毫秒 INFINITE(-1)一直等待
返回值:
WAIT_OBJECT_0(0) 等待对象变为已通知
WAIT_TIMEOUT(0x102) 超时
特别说明:
1、内核对象中的每种对象都可以说是处于已通知或未通知的状态之中
2、这种状态的切换是由Microsoft为每个对象建立的一套规则来决定的
3、当线程正在运行的时候,线程内核对象处于未通知状态
4、当线程终止运行的时候,它就变为已通知状态
5、在内核中就是个BOOL值,运行时FALSE 结束TRUE
代码演示
DWORD WINAPI ThreadProc1(LPVOID lpParameter)
{
for(int i=0;i<5;i++)
{
printf("+++++++++\n");
Sleep(1000);
}
return 0;
}
int main(int argc, char* argv[])
{
//创建一个新的线程
HANDLE hThread1 = ::CreateThread(NULL, 0, ThreadProc1,
NULL, 0, NULL);
DWORD dwCode = ::WaitForSingleObject(hThread1, INFINITE);
MessageBox(0,0,0,0);
return 0;
}
3 和WaitForMultipleObjects()
DWORD WaitForMultipleObjects(
DWORD nCount, // number of handles in array
CONST HANDLE *lpHandles, // object-handle array
BOOL bWaitAll, // wait option
DWORD dwMilliseconds // time-out interval
);
功能说明:同时查看若干个内核对象的已通知状态
nCount:要查看内核对象的数量
lpHandles:内核对象数组
bWaitAll:等到类型 TRUE 等到所有变为已通知 FALSE 只要有一个变为已通知
dwMilliseconds:超时时间
INFINITE一直等待
返回值:
bWaitAll为TRUE时,返回WAIT_OBJECT_0(0) 代码所以内核对象都变成已通知
bWaitAll为FALSE时,返回最先变成已通知的内核对象在数组中的索引
WAIT_TIMEOUT(0x102)
代码演示:
DWORD WINAPI ThreadProc1(LPVOID lpParameter)
{
for(int i=0;i<5;i++)
{
printf("+++++++++\n");
Sleep(1000);
}
return 0;
}
DWORD WINAPI ThreadProc2(LPVOID lpParameter)
{
for(int i=0;i<3;i++)
{
printf("---------\n");
Sleep(1000);
}
return 0;
}
int main(int argc, char* argv[])
{
HANDLE hArray[2];
//创建一个新的线程
HANDLE hThread1 = ::CreateThread(NULL, 0, ThreadProc1,
NULL, 0, NULL);
//创建一个新的线程
HANDLE hThread2 = ::CreateThread(NULL, 0, ThreadProc2,
NULL, 0, NULL);
hArray[0] = hThread1;
hArray[1] = hThread2;
DWORD dwCode = ::WaitForMultipleObjects(2, hArray,FALSE,INFINITE);
MessageBox(0,0,0,0);
return 0;
}
4 跨进程的线程控制与互斥体
进程一:
HANDLE g_hMutex = CreateMutex(NULL,FALSE, "XYZ");
进程二:
HANDLE g_hMutex = OpenMutex(MUTEX_ALL_ACCESS,FALSE, "XYZ");
WaitForSingleObject(g_hMutex,INFINITE);
//逻辑代码
ReleaseMutex(g_hMutex);
进程三:
HANDLE g_hMutex = OpenMutex(MUTEX_ALL_ACCESS,FALSE, "XYZ");
WaitForSingleObject(g_hMutex,INFINITE);
//逻辑代码
ReleaseMutex(g_hMutex);
互斥体与临界区的区别:
1、临界区只能用于单个进程间的线程控制.
2、互斥体可以设定等待超时,但临界区不能.
3、线程意外终结时,Mutex可以避免无限等待.
4、Mutex效率没有临界区高.
5 练习项目
做一个抢红包项目,要求如下
第一步:在第一个文本框中输入一个值,比如1000
第二步:点击抢红包,同时创建3个线程,每个线程循环进行抢红包的操作,每次抢50
第三步:使用Mutex进行线程控制,当第一个文本框中的值<50时,强红包线程结束.
特别说明:
1、四个文本框中的值总和应该为1000
2、强红包线程每次延时50毫秒.
3、使用WaitForMultipleObjects监听所有线程,当线程全部结束后
调用CloseHandle关闭句柄.
零基础逆向工程36_Win32_10_互斥体_互斥体与临界区的区别的更多相关文章
- 零基础逆向工程39_Win32_13_进程创建_句柄表_挂起方式创建进程
1 进程的创建过程 打开系统 --> 双击要运行的程序 --> EXE开始执行 步骤一: 当系统启动后,创建一个进程:Explorer.exe(也就是桌面进程) 步骤二: 当用户双击某一个 ...
- 零基础逆向工程40_Win32_14_枚举窗口_模拟鼠标键盘
1 查找窗口 1.1 代码案例 //查找指定窗口 TCHAR szTitle[MAX_PATH] = {0}; HWND hwnd = ::FindWindow(TEXT("#32770&q ...
- 零基础逆向工程31_Win32_05_提取图标_修改标题
在程序中使用图标 1.加载图标 HICON hIcon; hIcon = LoadIcon (hAppInstance, MAKEINTRESOURCE (IDI_ICON)); hAppInstan ...
- 零基础逆向工程30_Win32_04_资源文件_消息断点
1 资源文件,创建对话框 详细步骤: 1.创建一个空的Win32应用程序 2.在VC6中新增资源 File -> New -> Resource Script 创建成功后会新增2个文件:x ...
- 零基础逆向工程20_PE结构04_任意节空白区_新增节_扩大节添加代码
向代码节添加代码实现 作者经过一周不断的失败,再思考以及无数次调试终于实现. 思路:八个步骤 1. 文件拷到文件缓冲区(FileBuffer) //图示见(零基础逆向工程18之PE加载过程) 2. 文 ...
- 零基础逆向工程38_Win32_12_信号量_线程控制小结
1 信号量 信号量(Semaphore),有时被称为信号灯,是在多线程环境下使用的一种设施,是可以用来保证两个或多个关键代码段不被并发调用.[百度百科] 1.1 创建信号量 HANDLE Create ...
- 零基础逆向工程11_C语言05_结构体
结构体小结 结构体是按照分配的大小,局部变量会自动数据对齐 1字节对齐,省空间,但cpu查找效率低 4字节对齐,不省空间,但cpu查找效率高 VC6默认的结构对齐大小 项目右键-> settin ...
- 零基础逆向工程37_Win32_11_事件_线程同步
1 内核对象 前面已经学过线程和互斥体两个内核对象.此节讲了事件这个内核对象.前面提出了内核对象这个概念,可能不太清晰,简单来说内核对象就是系统层的东西. 1.1 小结内核对象: 进程.线程.事件.互 ...
- 零基础逆向工程29_Win32_03_ESP寻址_定位回调函数_子窗口_消息处理函数
1 Win32应用程序入口识别 思路:根据WinMain的四个参数,由调用顺序,知道最后压栈的是hInstance句柄(也就是WinMain函数的第一个参数,其值等于ImageBase),根据反汇编, ...
随机推荐
- sap abap 流水号设置
1.TCODE:SNRO,进入如图所示界面 2. 短文本和长文本用来说明这个编号范围对象,输入任意描述即可. 子对象数据元素我们这里不填.这里需要说明一下,所谓子对象,多数指一个组织结构,比如公司代码 ...
- JavaScript权威指南--闭包讲解摘记
不积跬步无以至千里,不积小流无以成江河. 关于闭包的解释,在<JavaScript权威指南>中讲的很透彻了.今天看了书中的一个段讲解,更加深了对闭包的理解,特此记下,以备查阅. 在同一个作 ...
- hdu2553 N皇后问题(dfs+回溯)
N皇后问题 Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submi ...
- 缓存算法及Redis、Memcached、Guava、Ehcache中的算法
https://my.oschina.net/ffy/blog/501003 https://yq.aliyun.com/articles/622757 https://blog.csdn.net/s ...
- spark 2.X 疑难问题汇总
当前spark任务都是运行在yarn上,所以不用启动长进程worker,也没有master的HA问题,所以主要的问题在任务执行层面. 作业故障分类故障主要分为版本,内存和权限三方面. - 各种版本不一 ...
- day 006 小数据池和再谈编码
1.小数据池. 目的:缓存我们的字符串,整数,布尔值.在使用的时候不需要创建过多的对象 缓存: int str bool int 范围:-5~256 str: 1.长度小于等于1,直接缓存 2.长度大 ...
- sql的几种常用锁简述
比较全的文章地址保存下:http://www.cnblogs.com/knowledgesea/p/3714417.html SELECT * FROM dbo.AASELECT * FROM dbo ...
- Problem01 不死神兔
题目:有一对兔子,从出生后第3个月起每个月都生一对兔子,小兔子长到第三个月后每个月又生一对兔子,假如兔子都不死,问每个月的兔子对数为多少? 程序分析:兔子的规律为数列1,1,2,3,5,8,13,21 ...
- readline的用法
with open(r'C:\Users\admin\pycdtest\wanyue\llduizhang_20180207\33_1517970821000304388_119061116',enc ...
- Python collections
#count对象 Only 2.7 from collections import Counter #统计字母出现的次数 Counter('hello world') Counter(['red', ...