DOS Batch 多核亲和性不起作用
DOS Batch multicore affinity not working
我有一个批处理启动一些可执行文件 .exe 和 .py (python) 来处理一些数据。
具有 开始/亲和力 X mybatch.bat
只有当 X 等于 0、2、4 或 8(单个核心)时,它才会正常工作
但是,如果我将使用像 15 或 F 或 0xF 这样的多核 X(在我看来,这意味着所有 4 个内核)它仍然 运行 仅在第一个内核上。
这是否与批处理调用的 .exe 文件可能无法通过这种方式进行关联控制有关?
OS:Windows 7 64 位
AFAIK /AFFINITY 使用十六进制值作为参数。以下是有关此主题的更多信息:Set affinity with start /AFFINITY command on Windows 7
编辑:0xF
应该是适合您的参数,因为您要加载所有 4 个 CPU,这需要位掩码 00001111
,即 F
in 十六进制.
这更像是对评论中出现的问题的回答,但我希望它可能有所帮助。我必须将它添加为答案只是因为它对于评论限制来说太大了:
这里似乎对两件事存在误解:"processor affinity" 的实际含义,以及 Windows 调度程序的实际工作方式。
这个SetProcessAffinityMask(...)
的意思是"which processors can this process (i.e. "所有个线程在进程内)可以运行 上,"
而
SetThreadAffinityMask(...)
显然是特定于线程的。
Windows 调度程序(在最基本的级别)完全不区分线程和进程 - "process" 只是一个包含一个或多个线程的容器。 IOW(并且过度简化) - 调度程序没有 process 这样的东西,"threads" 是可调度的东西:processes 与此无关("processes" 更多关于打开句柄、资源等的生命周期管理问题)
如果您有一个单线程进程,那么将 "process" affinity mask 设置为什么并不重要:一个 线程将由调度程序(对于任何屏蔽处理器)根据 1)它最后绑定到哪个处理器 - 理想情况,更少的开销,2)下一个可用于给定 运行nable[=53= 的处理器] 相同优先级的线程(比这更复杂,但总体思路),以及 3) 可能是暂时性的 关于优先级反转、可等待对象、内核 APC 事件等的问题
所以回答你的问题(比预期的冗长得多):
"But if I will use a multicore X like 15 or F or 0xF (meaning in my opinion all 4 cores) it will still run only on the first core"
我之前所说的有关调度程序尝试使用最近使用的处理器的内容在这里很重要:如果您有一个(或本质上)单线程进程,则调度算法会采用最乐观的方法:先前绑定 CPU 用于切回(对于 CPU/main 内存缓存、先前的分支预测评估等可能更便宜)。这解释了为什么您会看到一个应用程序(无论进程级亲和力如何)只有一个(同样,注意事项适用于此)线程看似 "stuck" 到一个 CPU/core。
所以:
您使用“/affinity X”开关有效地做的是
1) 将调度程序限制为 仅 在 CPU 个内核的子集上调度您的线程(即 并非全部 ) , 和
2) 将它们限制在调度器内核认为 "available for next runnable thread switch-to" 和
的子集内
3)如果它们不是多线程应用程序(并且能够利用它),"more cores" 并没有真正帮助任何东西 - 你可能只是将执行的单个线程跳到不同的内核(尽管调度程序试图最小化这个,如上所述)。
这就是为什么您的线程是 "sticky" - 您告诉调度程序让它们如此。
我有一个批处理启动一些可执行文件 .exe 和 .py (python) 来处理一些数据。
具有 开始/亲和力 X mybatch.bat
只有当 X 等于 0、2、4 或 8(单个核心)时,它才会正常工作
但是,如果我将使用像 15 或 F 或 0xF 这样的多核 X(在我看来,这意味着所有 4 个内核)它仍然 运行 仅在第一个内核上。
这是否与批处理调用的 .exe 文件可能无法通过这种方式进行关联控制有关?
OS:Windows 7 64 位
AFAIK /AFFINITY 使用十六进制值作为参数。以下是有关此主题的更多信息:Set affinity with start /AFFINITY command on Windows 7
编辑:0xF
应该是适合您的参数,因为您要加载所有 4 个 CPU,这需要位掩码 00001111
,即 F
in 十六进制.
这更像是对评论中出现的问题的回答,但我希望它可能有所帮助。我必须将它添加为答案只是因为它对于评论限制来说太大了:
这里似乎对两件事存在误解:"processor affinity" 的实际含义,以及 Windows 调度程序的实际工作方式。
这个SetProcessAffinityMask(...)
的意思是"which processors can this process (i.e. "所有个线程在进程内)可以运行 上,"
而
SetThreadAffinityMask(...)
显然是特定于线程的。
Windows 调度程序(在最基本的级别)完全不区分线程和进程 - "process" 只是一个包含一个或多个线程的容器。 IOW(并且过度简化) - 调度程序没有 process 这样的东西,"threads" 是可调度的东西:processes 与此无关("processes" 更多关于打开句柄、资源等的生命周期管理问题)
如果您有一个单线程进程,那么将 "process" affinity mask 设置为什么并不重要:一个 线程将由调度程序(对于任何屏蔽处理器)根据 1)它最后绑定到哪个处理器 - 理想情况,更少的开销,2)下一个可用于给定 运行nable[=53= 的处理器] 相同优先级的线程(比这更复杂,但总体思路),以及 3) 可能是暂时性的 关于优先级反转、可等待对象、内核 APC 事件等的问题
所以回答你的问题(比预期的冗长得多):
"But if I will use a multicore X like 15 or F or 0xF (meaning in my opinion all 4 cores) it will still run only on the first core"
我之前所说的有关调度程序尝试使用最近使用的处理器的内容在这里很重要:如果您有一个(或本质上)单线程进程,则调度算法会采用最乐观的方法:先前绑定 CPU 用于切回(对于 CPU/main 内存缓存、先前的分支预测评估等可能更便宜)。这解释了为什么您会看到一个应用程序(无论进程级亲和力如何)只有一个(同样,注意事项适用于此)线程看似 "stuck" 到一个 CPU/core。
所以:
您使用“/affinity X”开关有效地做的是
1) 将调度程序限制为 仅 在 CPU 个内核的子集上调度您的线程(即 并非全部 ) , 和
2) 将它们限制在调度器内核认为 "available for next runnable thread switch-to" 和
的子集内
3)如果它们不是多线程应用程序(并且能够利用它),"more cores" 并没有真正帮助任何东西 - 你可能只是将执行的单个线程跳到不同的内核(尽管调度程序试图最小化这个,如上所述)。
这就是为什么您的线程是 "sticky" - 您告诉调度程序让它们如此。