Ninja: Ninja 应该有办法通过 IPC 而不是 CreateProcess 触发编译

创建于 2019-08-23  ·  6评论  ·  资料来源: ninja-build/ninja

Windows 上的 CreateProcess 在最好的时候很慢,而 Chrome 开发人员经常发现自己不在最好的时候。 过去几年在 Chrome 构建中处理的一些进程创建/销毁问题包括:

  1. 由于 Windows 回归,Chrome 构建在进程破坏期间遇到 UserCrit 锁定争用,导致构建速度减慢和在 goma 构建期间出现严重的鼠标卡顿。 在 Windows 中修复,修复最终传播到所有相关的 Windows 10 版本 (https://randomascii.wordpress.com/2017/07/09/24-core-cpu-and-i-cant-move-my-mouse/)
  2. 由于 gomacc.exe 间接拉入 gdi32.dll,Chrome 构建在进程破坏期间遇到了 UserCrit 锁争用,导致构建速度减慢和在 goma 构建期间出现严重的鼠标卡顿。 通过避免 gdi32.dll 在 gomacc 中修复。
  3. 反恶意软件在 CreateProcess 中导致了大约 11 毫秒的回归,使得完整的 Chrome 构建不可能快于大约 10 分钟,并减慢所有构建。 通过禁用此反恶意软件来修复。
  4. 问题 3 中至少有两个变体,包括未正确禁用或即使禁用仍具有开销 (MsMpEng.exe) 的其他反恶意软件。
  5. Chrome 构建中的高进程创建率触发了 SCCM 中的错误,导致僵尸进程最终导致高达 32 GB 的内存丢失(https://randomascii.wordpress.com/2018/02/11/zombie-processes-are-吃你的记忆/)
  6. 为 gomacc.exe 启用 App Verifier 以调查偶尔的堆损坏在日志文件创建中遇到了 O(n^2) 性能问题 (https://randomascii.wordpress.com/2018/10/15/making-windows-slower-第 2 部分流程创建/)

其他不影响 Chrome 构建的进程创建/销毁问题包括:

  1. Chromium 的大型测试二进制文件在 Windows 中遇到了 O(n^2) CFG 性能错误,这导致 unit_tests.exe 在 Windows 10 上花费了大约 5 倍的时间。通过在测试二进制文件 (https://randomascii.txt) 中禁用 CFG 来修复。 wordpress.com/2019/04/21/on2-in-createprocess/)
  2. clang-cl 单元测试在进程破坏期间遇到 UserCrit 锁争用,导致测试时间是 Windows 10 上应有的时间的 5 倍,并导致严重的鼠标卡顿。 通过避免拉入 gdi32.dll 来修复。

目前所有这些问题都得到了缓解,但 MsMpEng.exe 会导致非零开销,即使所有内容都在排除的文件夹中。 然而,需要持续努力保持所有 Chrome 开发人员的机器正确配置,并且由于需要许多排除来保持良好的构建性能而导致一些安全性损失。 还在不断努力检测和调查这些问题。

在某些时候,不再值得对 CreateProcess 风车倾斜,而是避免如此频繁地调用 CreateProcess。 可以教 ninja.exe 如何使用 IPC 与本地服务器进程通信,该进程将管理一个编译进程池(goma 和/或 clang-cl),以避免在构建过程中 99% 的 CreateProcess 调用。

这样做将降低 CreateProcess 的 CPU 成本,将从 ninja 中的序列化关键路径中删除 CreateProcess,将允许使用更少的排除项启用更多安全监控,并将为我们节省未来回归的成本(调查时间和构建时间) .

或者 ninja 可以多线程 CreateProcess 但这不是一个完整的解决方案。

在 ninja 中从 CreateProcess 切换到 IPC 显然不是正确的做法,但值得讨论。 原型已创建,因此应在此处共享测试结果。

所有6条评论

在我看来,库化 Ninja 将允许像这样的努力更容易地注入他们想要的行为,例如通过从接口类派生来自定义流程创建行为。

毫不奇怪,我强烈反对这一点。 Ninja 是一个简单的构建系统,它假设构建环境是健全的。 还有其他具有不同设计的构建系统可能会假设敌对的构建环境,但 ninja 不是那个系统。

听起来 ninja 的当前设计有助于识别许多值得修复的错误。 我认为这是一个功能。

@nico ,我非常不同意你对此事的看法。

首先,Ninja 最初是作为一种工具来改进 Chrome 项目的编译时间。 http://neugierig.org/software/chromium/notes/2011/02/ninja.html

现在,您告诉正在谈论如何改善 chrome 项目编译时间的人,他们的贡献不受欢迎。

如果 Ninja 首先是图形执行库,然后是构建工具,那么它很容易适应使用 IPC 来执行构建作业。 这将允许将 IPC 逻辑注入到库中,而不是存在于核心代码中。

此外,作为一个项目的“维护者”,很少看到如此复杂的错误报告(隐含承诺跟进实际代码),你会在完全不讨论该主题的情况下关闭这个报告是相当荒谬的,但没有其他 189 个问题仍然悬而未决,有些甚至已有 8 年的历史。

而且,当然,称 Windows 为敌对构建环境很可能是正确的,但这并不是忽略贡献的有效理由。 Windows 仍然是使用最广泛的开发操作系统之一,忽略这一点充其量是虚伪的。

@nico我鼓励你离开 Ninja 项目。 您几个月内唯一的行动就是驳回复杂的贡献,并附上解释问题和所寻求解决方案的大量文档。

@randomascii我很高兴看到像您在这里谈论的那样的贡献集成到 Ninja 中。 在我的最后一个工作场所,我强烈怀疑像这样的 IPC 机制可以将每次构建的构建时间至少缩短几分钟,这会很棒。

您能否详细描述如何管理编译进程池? Windows 是否具有允许重新使用进程来执行其他操作的机制? 或者这是否需要编译器进程可重用?

我的理解是一位同事有一个 ninja-with-IPC 的原型。

我对在没有更多讨论的情况下关闭它的主要担忧是它错过了讨论安全权衡的机会。 我们减轻 CreateProcess 成本/序列化的大多数方法是禁用各种安全检查。 我不是这些检查价值的专家,但让那些专家权衡能够启用它们的好处可能会有所启发。

我会鼓励你的同事在 github 上提交一个带有他们的原型的 Pull Request,以便可以讨论实现。

此页面是否有帮助?
0 / 5 - 0 等级

相关问题

8l picture 8l  ·  7评论

ghost picture ghost  ·  14评论

evmar picture evmar  ·  10评论

nico picture nico  ·  20评论

Alexander-- picture Alexander--  ·  20评论