← Back to context

Comment by barrkel

11 hours ago

Just use ssh from Cygwin. DLL hell was rarely a problem, just always install everything via setup.exe.

The single biggest problem it has is slow forking. I learned to write my scripts in pure bash as much as possible, or as a composition of streaming executables, and avoid executing an executable per line of input or similar.

On your own system, sure.

As a dependency of a shipping Windows application that needs to cleanly coexist side-by-side with existing Cygwin installations and optionally support silent install/upgrade/uninstall through mechanisms like SCCM, Intune, and Group Policy?

Not so much.

I do use the setup program to build the self-contained Cygwin root that's ultimately bundled into my program's MSI package and installed as a subdirectory of its Program Files directory, however.

I've never had a problem installing from setup, but some tools were (maybe still are, it is a long time since I've needed anything not in the main repo) ported to windows using the cygwin dlls were distributed with their own versions and could clobber the versions you have otherwise (and have their versions clobbered when you fix that).

> slow forking

There isn't much that can be done about that: starting up and tearing down a process on Windows is much more resource intensive operation than most other OSs because there is a lot going on by default that on other OSs a process ops into, only if it needs to, by interacting with GUI libraries and such. This is why threads were much more popular on Windows: while they are faster than forking on other OSs too, especially of course if data needs to be shared between the tasks because IPC is a lot more expensive than just sharing in-process memory, the difference is not as stark as seen under Windows so the potential difficulties of threaded development wasn't always worth the effort.

Cygwin can't do anything about the cost of forking processes, unfortunately.

Try using the Windows busybox port of "Bash":

https://frippery.org/busybox/index.html

It has a subset of bash implemented on Ash/Dash. Arrays are not supported, but it is quite fast.

The forking problem is still present, though.

  • Cygwin bash isn't slow either. The problem is a typical bash script isn't a series of bash operations, it's a series of command line program executions.

    For example, someone might do something like this (completely ignoring the need to quote in the interests of illustrating the actual issue, forking):

        for x in *; do
          new_name=$(echo $x | sed 's/old/new/')
          mv $x $new_name
        done
    

    Instead of something like this:

        for x in *; do
          echo $x
        done | sed -r 's|(.*)old(.*)|mv \1old\2 \1new\2|' | grep '^mv ' | bash
    

    This avoids a sed invocation per loop and eliminates self-renames, but it's harder to work with.

    Of course the code as written is completely unusuable in the presence of spaces or other weird characters in filenames, do not use this.

Slow forking is only the second biggest problem IMO. The biggest is the lack of proper signals. There's a bunch of software out there that just isn't architected to work well without non-cooperative preemption.