Using Bash in Windows
I have pretty much always been using windows. Most of my software development history is ASP.Net, with occasional forays into Java, Node.JS, and others. Even when I was developing in Java or Node, and even though the software I wrote would live in a completely Linux based ecosystem, my laptop always had Windows on it.
That being said, I have had continual exposure to the multitude of flavors of Linux. From desktop Ubuntu, to Centos, to DSL, LFS, RHEL, you name it. What I have never done, however, is install Linux on my laptop. For some reason Linux always seemed to me something that is disposable. If you need Linux to compile something, run your app, or host the church website, just kick up a VM on AWS and SSH into it.
This brings me to this topic — bash. Bash has many quirks and intricacies, but once you get used to it, going back to cmd just seems sad (and I’m not going to get into a PowerShell discussion, thank you). Wouldn’t it be great if we could use a bash shell in windows?
And mind you when I say “bash”, I am really referring to bash and coreutils.
There are a number of ways to get a bash kind of environment working in windows, so today I’m going to look at a few options that have appeared over the years.
At this point one might ask what is so hard about just using a bash shell in windows? After all we’re not talking about running Linux programs in windows (see Cygwin for that), we just want a shell. Can’t one just recompile awk and sed and everything to work on windows?
The simple answer is probably no, you can’t just recompile for Windows. The shell (specifically bash) is a core component for any Linux operating system. Furthermore, Windows and Linux paths are quite different. If there wasn’t some translation done between the formats, bash would be pretty useless on Windows. There are other differences too like the way bash expands wildcards, the way bash invokes executables, and the fact that some Windows and Linux tools have the same executable name, but work quite differently (e.g. sort or find).
Though there are many difficulties in getting a Linux based shell working, let alone CoreUtils, there have been a number of more or less successful attempts.
As far as I know Cygwin was the first attempt at getting a Linux-like environment working on Windows. It works by cross compiling Linux programs for windows, and includes a number of Libraries to reconcile the differences between the Windows operating system and Linux (like forking and threads).
Cygwin is quite comprehensive and sometimes feels like a Linux distro complete with package manager, X11 support and POSIX compliance. In many cases you can compile programs written for Linux without modification. But as the documentation is sure to point out, it’s still windows and the core workings of the operating system remain the same.
One can use Cygwin with it’s bash shell for general use in Windows, but I get the impression that this is not really the idea behind Cygwin. Furthermore Cygwin is pretty technical to install, and will take a good while unless you have low latency to the server you download from.
Though Cygwin is perhaps a bit much if you just want to use Bash inside Windows, MSYS comes to the rescue!
(For more information on Cygwin head over to the Cygwin home page.)
MSYS stands for “Minimal System.” and comes as part of MinGW — the minimalist GNU development environment for Windows. What they did was rip Bash and CoreUtils out of Cygwin and make it available as MSYS: a general purpose shell for Windows.
MSYS has kind of been abandoned as far as I can tell and has been superseded by MSYS2.
(MSYS and MinGw can be found on the MinGw website.)
MSYS2 is a rewrite of MSYS and aims to be Bash and a set of tools supporting the MinGW-w64 development toolchain (which is different from MinGw, if you were wondering).
MSYS2 aims to have better Windows interoperability, and also has a package manager of sorts.
(More info can be found on the MSYS2 website.)
Git for Windows
If you have Git installed on windows, you have probably already noticed that you have “Git Bash.” This Bash is the shell taken from MSYS2 and provided for use with Git related stuff. Git for windows also installs parts of MinGw. If you install the Git for Windows SDK, it will install a MinGw tool chain as well.
(Note: Bash and MinGw-w64 are needed to build Git on Windows, but I’m not sure whether Bash is needed to use git. I’m guessing Git internally uses Bash for something. Hooks or something I guess.)
Personally I find Git for Windows is a Bash shell on Windows that works really well. I’ve developed software projects that have tons of bash scripts and I rarely have problems running the same scripts on Windows and Linux. I’ve made it my default shell in VS Code and much prefer it to using CMD, even though the paths work differently.
I also set the option in the installer to make all the tools available in PATH. It warns that it might break windows scripts but I haven’t had any problems thus far.
In my opinion this is the best option for using Bash in Windows right now and is very useful if you are building a cross-platform software project using something like Node.JS or Docker.
Bash on Ubuntu on Windows Subsystem for Linux
Now here is something different. to be discussed later.