关于bash:如何加速Cygwin?

How to speed up Cygwin?

我已经在我相对快速的Windows机器上使用cygwin运行drush脚本(对于drupal),但是我仍然需要等待大约一分钟才能执行任何drush命令(特别是drush cache clear)。

我很确定这与cygwin的速度有关,因为我的开发人员(运行Linux)可以在5秒内运行这些脚本。

有没有办法让Cygwin在每个终端上使用更多的内存和/或CPU?


您遇到的问题不是Cygwin中的某些任意限制,您可以通过更改设置来消除这些限制。这是Cygwin工作方式的一个固有方面,以获得在其预期下构建的POSIX语义程序。

posix fork()系统调用在Windows上没有本机等效项,因此cygwin被迫以非常低效的方式模拟它。shell脚本每次执行外部进程时都会调用fork(),这种情况经常发生,因为shell脚本语言相对于我们通常称之为编程语言的语言非常贫乏。外部程序是shell脚本如何完成任何结果的。

Cygwin还有其他一些效率低下的地方,但是如果你分析一下它,你可能会发现这是第一速度命中率。在大多数地方,使用cygwin构建的程序和底层操作系统之间的cygwin层非常薄。Cygwin的开发人员在提供正确的POSIX语义的同时,尽可能地保持层的薄。当前在fork()调用模拟中的异常厚度是不可避免的,除非微软在其操作系统中添加一个本地fork()类型的工具。他们这样做的动机不是很好。

上面作为评论发布的解决方案也不错。

另一种可能性是浏览drush脚本,看看是否有对外部程序的调用,可以用shell内部函数或更有效的构造替换。我不希望通过这样做来获得巨大的速度改进,但它有一个很好的特性,您也可以在Linux方面加快速度。(fork()在Linux上效率很高,但是启动外部程序仍然是一个巨大的速度冲击,您可能不必像现在这样经常支付。)例如:

1
2
numlines=`grep somepattern $somefile | wc -l`
if [ $numlines -gt 0 ] ; then ...

运行速度更快:

1
if grep -q somepattern $somefile ; then ...

第一个版本可以说是更清晰的,但它至少需要三个外部程序调用,使用原始shell时需要四个。(你看到所有这些了吗?)替换只需要一个外部程序调用。


还可以看看那些减慢Cygwin启动的因素:

  • 修剪Windows路径(到%SystemRoot%System32;%SystemRoot%这样的裸骨)
  • 从bashrc和bash_配置文件中删除不需要的内容
  • 将终端窗口中只需要的东西从bashrc移动到bash_配置文件
  • 在Cygwin中,一个惊人的大时间是bash完成。如果您正在使用它(而且您应该这样做,因为它很好),那么只需要完成您所需要的命令的源代码(而不是所有以前是默认值的命令)。如前所述,来源于bash_profile,而非bashrc


你可以给Cygwin更高的优先级。

编写新的批处理文件,例如"cygstart.bat",内容如下:

1
start"Cygwin" /high C:\cygwin\Cygwin.bat

/high开关为shell提供了更高的进程优先级。