是否可以强制在特定的CPU上运行go例程?

时间:2013-11-03 22:26:53

标签: go runtime

我正在阅读go包“runtime”,看看我可以在其他(func GOMAXPROCS(n int))中设置可用于运行程序的CPU单元数。我可以强制goroutine在我选择的特定CPU上运行吗?

2 个答案:

答案 0 :(得分:13)

在现代Go中,我不会将goroutine锁定到线程以提高效率。去1.5 added goroutine scheduling affinity, to minimize how often goroutines switch between OS threads。并且必须权衡CPU之间剩余迁移的任何成本与用户模式调度程序的好处,避免上下文切换到内核模式。最后,当转换成本是一个真正的问题时,有时候更好的关注点是改变你的程序逻辑,因此它需要减少切换,比如通过批量工作而不是单个工作项。

但即使考虑到所有这些,有时你只需要锁定一个goroutine,就像C API需要它一样,我会假设下面是这种情况。


如果整个程序以GOMAXPROCS=1运行,则it's relatively simple to set a CPU affinity by calling out to the taskset utility from the schedutils package

我认为你GOMAXPROCS > 1因为pid而失败了,因为那时goroutines are migrated between OS threads at runtime。实际上,James Henstridge指出你可以使用runtime.LockOSThread()来保持你的goroutine不会迁移。但是,一旦你锁定了goroutine,我就不知道任何Go stdlib函数来设置当前线程的CPU亲和力。您可以使用cgo并致电pthread_setaffinity_np,因为显然Go uses pthreads in cgo mode。由于我们正在讨论系统调用,因此操作系统会有所不同。

(如果您的整个程序都是纯Go(没有C链接),可以通过syscall模块调用sched_setaffinity参数为零{{1}}。但是那个&#39 ; s会变得棘手。)

答案 1 :(得分:1)

取决于您的工作负载,但有时为每个CPU启动一个go进程是有益的,将gomaxprocs设置为1并使用taskset将进程固定到CPU。以下是来自awesome fasthttp库的该主题的摘录:

  
      
  • 使用reuseport   监听器。
  •   
  • 使用GOMAXPROCS = 1为每个CPU核心运行单独的服务器实例。
  •   
  • 使用taskset将每个服务器实例固定到单独的CPU核心。
  •   
  • 确保多核网卡的中断在CPU核心之间均匀分布。请参阅this article   的信息。
  •   
  • 使用Go 1.6,因为它提供了一些可观的性能改进。
  •   

来源:https://github.com/valyala/fasthttp#performance-optimization-tips-for-multi-core-systems