Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Windows support: dependency on unix via simple-cmd #8

Open
ruifengx opened this issue Jun 3, 2022 · 6 comments
Open

Windows support: dependency on unix via simple-cmd #8

ruifengx opened this issue Jun 3, 2022 · 6 comments

Comments

@ruifengx
Copy link

ruifengx commented Jun 3, 2022

Hi. First, big thanks for your tool. It helped me free more than 10GiB of disk space on my WSL2 install.

I am currently not able to install this tool on Windows, and this is what I get from stack:

Error: While constructing the build plan, the following exceptions were encountered:

In the dependencies for simple-cmd-0.2.3:
    unix needed, but the stack configuration has no specified version  (latest matching version is 2.7.2.2)
needed due to stack-clean-old-0.4.6 -> simple-cmd-0.2.3

Some different approaches to resolving this:

  * Recommended action: try adding the following to your extra-deps in C:\sr\global-project\stack.yaml:

- unix-2.7.2.2@sha256:15f5365c5995634e45de1772b9504761504a310184e676bc2ef60a14536dbef9,3496

Plan construction failed.

I believe this is due to the (required) dependency on unix in simple-cmd.

P.S. I see in #5 this topic was discussed, but not resolved at that time.

@juhp
Copy link
Owner

juhp commented Jun 4, 2022

Thanks a lot for reporting this.
Can you try building with the above change to simple-cmd?
((I am wondering if the pipe commands make sense either, maybe others also perhaps))

@ruifengx
Copy link
Author

ruifengx commented Jun 4, 2022

Thanks for your quick reply. Yes, I can build stack-clean-old now. However, it does require some additional configuration in stack.yaml (or via the command line using --flag):

flags:
  mintty:
    Win32-2-13-1: False

This is because the following lines in mintty:
https://github.com/RyanGlScott/mintty/blob/28fe58c9927ceff2d636a14b780642092d734bf3/mintty.cabal#L66-L74

It seems package mintty rely on cabal-install to infer the flag Win32-2-13-1. AFAIK, it should usually work in the following way: (1) try the default by setting Win32-2-13-1 to True, (2) see a bound Win32 >= 2.13.1, which is not satisfiable (because Win32 is shipped with GHC), (3) backtrack and set Win32-2-13-1 to False. This logic, however, is not implemented in Stack. Instead, stack produces a warning about the bound Win32 >= 2.13.1 is ignored preferring the bound in the snapshot.

Besides this flag thing, the package did build successfully.

@ruifengx
Copy link
Author

ruifengx commented Jun 4, 2022

I did find another issue, though. I tried stack-clean-old list, and it seeking snapshots in $env:HOME/.stack/snapshots, but on Windows, people usually move stack root to a short path (e.g., C:\sr) and set the environment variable STACK_ROOT accordingly (this is due to the unfortunate limit on lengths of file paths on Windows). I can work around this by setting up a symbolic link $env:HOME/.stack for now.

I guess there are also other kinds of path differences: stack clean-old list asks me to "specify platform with --os-system (-o)". This is probably because GHC is installed in $env:LOCALAPPDATA/Programs/stack/x86_64-windows. I will dive into the source code to spot some required changes on Windows and report back here later.

@juhp
Copy link
Owner

juhp commented Jun 4, 2022

Thanks!

Probably STACK_ROOT could be supported for Windows.

I guess there are also other kinds of path differences: stack clean-old list asks me to "specify platform with --os-system (-o)". This is probably because GHC is installed in $env:LOCALAPPDATA/Programs/stack/x86_64-windows.

Ya, I think on Linux it is "~/.stack/programs/x86_64-linux".

@ruifengx
Copy link
Author

ruifengx commented Aug 9, 2022

Sorry for the delay in my reply. It turned out I have underestimated the differences between UNIX platforms and Windows.

Changing the code to support different installation directories is relatively easy, provided that we are willing to allow invocations of the stack executable at runtime. There is a stack subcommand named "path" for querying all those paths in the same way as stack would normally find them. Here is a list of the paths we might be interested in:

  • stack path --stack-root: stack root, usually specified using the STACK_ROOT environment variable;
  • stack path --programs: path to installed GHCs (and MSYS, if on Windows), this one is configurable in Stack's global configuration file;
  • for snapshots, it seems to always be the subdirectory in STACK_ROOT named snapshot;

The hard part is how to recognise all the directories in snapshots and associate them with GHC versions. I read through your code, but still I might have some misunderstandings, so correct me if anything I say below is not the case. Currently, compiler version is detected by parsing the folder name ~/.stack/snapshots/COMPILER_TRIPLET/SOME_HASH/COMPILER_VERSION, and that is what I see when I inspect my Stack installation on Linux. However, on Windows, (1) there is no COMPILER_TRIPLET in snapshots. The directories with hashes as their names are placed directly under snapshots; (2) there is no COMPILER_VERSION, the folders pkgdb, lib, etc. are placed directly under SOME_HASH.

Anther thing to note is on Linux the hashes are in full 64 hex digits, and on Windows they only have 8 hex digits. Together with the omission of nested x86_64-windows folders, I guess the decisions on Windows are made in such a way that all these paths are as short as possible, to avoid exceeding the MAX_PATH limit. But I digress.

The only way I see to determine the compiler version for each SOME_HASH folder is to go further into the subdirectories lib and share, because under these paths I see a x86_64-windows-ghc-GHC_VERSION folder, which could be parsed to determine the compiler version.

Now the problem is that, due to the difference in structures of snapshot directories on UNIX and Windows, we will have to maintain two different approaches in parallel (currently in my local copy I do runtime detection using System.Info.os). If you find this acceptable, I will clean up my local copy and submit a PR in a day or two. By then, it would be great if someone could confirm that my changes also work on their Windows installation.


Edit: I just noticed there are quite a few SOME_HASH directories that only contain a pkgdb (so neither lib nor share exists). AFAIK there is no practical way to determine the compiler version, because it is impossible to recover the information we need from a hash string of length 8. They don't take up too much disk space (because there are no real packages inside), but I think it is safe to just remove them anyway, because Stack should be able to create them again easily.

@juhp
Copy link
Owner

juhp commented May 31, 2023

Okay using stack path on Windows might helpful indeed here.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants