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

globalprotect-openconnect: add core logic and packages for 2.x releases #316526

Merged
merged 4 commits into from
Sep 22, 2024

Conversation

Binary-Eater
Copy link
Member

@Binary-Eater Binary-Eater commented Jun 1, 2024

Description of changes

The 1.x iteration of globalprotect-openconnect is no longer being
developed. Remove related components from nixpkgs.

The GUI of GlobalProtect-openconnect is unfree software, while the CLI is
licensed as GPLv3-only. This packaging work focuses on the CLI, and
components required for the CLI.

Things done

  • Built on platform(s)
    • x86_64-linux
    • aarch64-linux
    • x86_64-darwin
    • aarch64-darwin
  • For non-Linux: Is sandboxing enabled in nix.conf? (See Nix manual)
    • sandbox = relaxed
    • sandbox = true
  • Tested, as applicable:
  • Tested compilation of all packages that depend on this change using nix-shell -p nixpkgs-review --run "nixpkgs-review rev HEAD". Note: all changes have to be committed, also see nixpkgs-review usage
  • Tested basic functionality of all binary files (usually in ./result/bin/)
  • 24.11 Release Notes (or backporting 23.11 and 24.05 Release notes)
    • (Package updates) Added a release notes entry if the change is major or breaking
    • (Module updates) Added a release notes entry if the change is significant
    • (Module addition) Added a release notes entry if adding a new NixOS module
  • Fits CONTRIBUTING.md.

Add a 👍 reaction to pull requests you find important.

@github-actions github-actions bot added 6.topic: nixos Issues or PRs affecting NixOS modules, or package usability issues specific to NixOS 8.has: documentation This PR adds or changes documentation 8.has: changelog 8.has: module (update) This PR changes an existing module in `nixos/` 8.has: maintainer-list (update) This PR changes `maintainers/maintainer-list.nix` labels Jun 1, 2024
@Binary-Eater Binary-Eater force-pushed the package/gpclient branch 2 times, most recently from 1ad80b9 to 96ec2b5 Compare June 1, 2024 22:57
@ofborg ofborg bot added 8.has: clean-up 8.has: package (new) This PR adds a new package 11.by: package-maintainer This PR was created by the maintainer of the package it changes 10.rebuild-darwin: 1-10 10.rebuild-linux: 1-10 labels Jun 1, 2024
@Binary-Eater Binary-Eater force-pushed the package/gpclient branch 3 times, most recently from 7a78a6e to 52907bd Compare June 19, 2024 08:11
@davisRoman
Copy link

davisRoman commented Jun 26, 2024

I'm keeping an eye on this PR as I'm also in need to a 2.x version of globalprotect.

While in most cases I would pitch in to help move a PR along, I'm unfortunately still very new to nix however if you need someone to help test then please let me know.

@jerith666
Copy link
Contributor

Thanks for getting a great start on v2!

I built this locally and tried ./result/bin/gpclient connect <SERVER>. It quickly fell into a loop repeating this warning:

[2024-06-27T03:11:42Z WARN  gpauth::auth_window] Failed to load uri: https://a**********m/o/saml2/idp?idpid=C**********f&SAMLRequest=l**********C&RelayState=d**********%3D with error: TLS/SSL support not available; install glib-networking

Next I tried sudo -E ./result/bin/gpclient connect --default-browser <SERVER>. It said:

[2024-06-27T03:16:44Z INFO  gpauth::cli] Please continue the authentication process in the default browser
[2024-06-27T03:16:44Z INFO  gpclient::connect] Waiting for the browser authentication to complete...
[2024-06-27T03:16:44Z INFO  gpclient::connect] Listening authentication data on port 42529

The browser opened and appeared to authenticate, landing me on a page with this message:

When you see the dialog on the browser, click Open GlobalProtect. If the dialog does not appear, click here to launch GlobalProtect.

that "click here" is a globalprotectcallback:... link; clicking it does nothing.

I base64-decoded the bit after the globalprotectcallback:... and got a small html document with a <prelogin-cookie/> element in it.

On a hunch, I did telnet localhost 42529 and pasted in that base64-encoded blob. That produced this from gpclient:

[2024-06-27T03:26:46Z INFO  gpclient::connect] Received the browser authentication data from the socket
[2024-06-27T03:26:56Z INFO  gpapi::auth] Parsing SAML auth data...
[2024-06-27T03:26:56Z INFO  gpclient::connect] Failed to connect portal with prelogin: No auth data found

Note that I have not actually added this to environment.systemPackages and rebuilt; maybe that would help the "click here" link in the browser work, not sure. Anyway, time for bed here, but I'm happy to test other scenarios if it helps!

@Binary-Eater
Copy link
Member Author

@jerith666 The behavior you described is exactly what is expected when you run the program out of ./result. This is because the xdg-mime-info for the globalprotect callback is not registered when testing that way. Like you guessed, installing under environment.systemPackages ends up installing the callback handler xdg-mime-info type. That's how I am using this on a day-to-day basis. Hope that helps.

@Binary-Eater
Copy link
Member Author

@davisRoman @jerith666 if you find this PR helpful, it would help if you both could add a 👍 to this PR. Thanks.

@davisRoman
Copy link

Out of curiosity, since it'll take some time to polish and upstream this PR, would it be possible for me to cherry-pick these commits locally somehow?

Unfortunately, the lack of a 2.x globalprotect is preventing me from using my NixOS laptop as my work laptop. I am aware of others at my job that are in the same boat.

@Binary-Eater
Copy link
Member Author

I have a couple techniques for this depending on my use case (quick testing, long term use, etc.).

For your use case, I would recommend the following.

  1. Download the related Nix files.
  2. Use callPackage in your environment.systemPackages or however you choose to install packages

As an example, this is something I hacked up under my ~/.config/nixpkgs/overlays/config.nix (I do not like installing everything as a system package).

      (callPackage ~/Documents/nixos/nixpkgs/pkgs/tools/networking/globalprotect-openconnect/gpclient { gpauth = (callPackage ~/Documents/nixos/nixpkgs/pkgs/tools/networking/globalprotect-openconnect/gpauth {}); })

@wegank wegank added the 2.status: merge conflict This PR has merge conflicts with the target branch label Jul 4, 2024
@Binary-Eater
Copy link
Member Author

@wegank Aside from the merge conflict due to the changelog, would you say this PR is in a good shape to be merged or would we need to wait on other reviewers?

@jerith666
Copy link
Contributor

Just a note that I haven't had a chance to come back and try via environment.systemPackages, but still hope to!

@wegank
Copy link
Member

wegank commented Jul 7, 2024

The PR also fails a CI check, so there's still some work to be done.

@Binary-Eater
Copy link
Member Author

@wegank The only PR check it's failing is the one about putting the packages in the by-name directory path. If you look at the change, you will see that it's not feasible since there is a common.nix file that is depended on for both gpclient and gpagent, so that check if a false positive. Let me know if you think otherwise.

@Binary-Eater
Copy link
Member Author

It looks like I will have to follow this recommendation just for the sake of suppressing the warning.

https://github.com/NixOS/nixpkgs/blob/fd4919bca028f1d133a9f1171920f6b12a22d4b5/pkgs/by-name/README.md#recommendation-for-new-packages-with-multiple-versions

@wegank
Copy link
Member

wegank commented Jul 7, 2024

That check is mandatory: merging this PR while ignoring the error will cause CI check to fail on all other pull requests.

I'd suggest dropping common.nix since there's no much that's reused, and you can always do inherit (gpauth) version src meta; in the other package if really necessary.

@Binary-Eater
Copy link
Member Author

You do not want gpauth and gpclient having out of sync source code but want them to be separate packages (API compatibility but gpauth could be used standalone without gpclient). I will opt for the alternative suggested in the docs and use the ./maintainers/scripts/check-by-name.sh script to verify the solution.

@Binary-Eater
Copy link
Member Author

The inherit trick is pretty smart though, so will fall back to that if my change does not work. Thanks.

@jerith666
Copy link
Contributor

Okay, I've used this for a few days at work this week, and it works.

I'd like to keep v1 around too, because I prefer it for the ergonomic reasons I gave above. But if others feel that's a bad idea since it's unmaintained upstream, I can work around it locally.

@psiri
Copy link

psiri commented Sep 10, 2024

I have tested this locally (installed to system packages using a similar callPackage method mentioned above) with the latest version as of this moment (2.3.7) and it's working great.

I've tested against a dozen or so portals supporting various combinations of auth (everything from local to SAML to CIE / Cloud Auth) and had success.

While I switched almost everything over to Nix last year, lack of GP support for newer Palo Alto auth methods had forced me to use a VM up until now. Awesome work @Binary-Eater , much appreciated!

@wegank wegank added the 2.status: merge conflict This PR has merge conflicts with the target branch label Sep 10, 2024
The 1.x iteration of globalprotect-openconnect is no longer being
developed. Remove related components from nixpkgs.

Signed-off-by: Rahul Rameshbabu <sergeantsagara@protonmail.com>
Add maintainer information for Rahul Rameshbabu.

Signed-off-by: Rahul Rameshbabu <sergeantsagara@protonmail.com>
The GUI of GlobalProtect-openconnect is unfree software, while the CLI is
licensed as GPLv3-only. This packaging work focuses on the CLI, and
components required for the CLI.

Link: https://github.com/yuezk/GlobalProtect-openconnect
Signed-off-by: Rahul Rameshbabu <sergeantsagara@protonmail.com>
@Binary-Eater
Copy link
Member Author

@psiri Thanks for the testing feedback. I just updated the packaging for 2.3.7 along with resolving the merge conflict.

@wegank now that the merge conflict is resolved, can we go ahead and merge this once all the CI checks are complete? I can also ask for review on the NixOS Matrix room.

@ofborg ofborg bot removed the 2.status: merge conflict This PR has merge conflicts with the target branch label Sep 21, 2024
@wegank
Copy link
Member

wegank commented Sep 21, 2024

@ofborg build gpauth gpclient

Copy link
Contributor

@jerith666 jerith666 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As I said, I'll probably keep using v1 until $job updates their server & it's no longer compatible, for ergonomic reasons. But I just rebuilt & tested again, and it's still working, so let's get this in.

@wegank wegank merged commit 84cd38f into NixOS:master Sep 22, 2024
24 checks passed
gvolpe added a commit to gvolpe/nix-config that referenced this pull request Oct 6, 2024
@gvolpe
Copy link
Member

gvolpe commented Oct 6, 2024

Anyone in here relying on this other package? https://github.com/yuezk/GlobalProtect-openconnect

I had to bring back the deleted module and package to keep it working. I wish I didn't need all this software, but it's $work... 🤷🏽

@jerith666
Copy link
Contributor

You mean v1 of that package? This PR updated us from v1 to v2 of that package.

I am still using v1, which I did by basically reverting the parts of this PR that removed the v1 package in my fork of nixpkgs.

@Binary-Eater
Copy link
Member Author

@gvolpe did you try the V2 version of the software that was merged?

@Binary-Eater Binary-Eater deleted the package/gpclient branch October 7, 2024 00:17
@Binary-Eater
Copy link
Member Author

Binary-Eater commented Oct 7, 2024

As a note, the v2 package is named gpclient and not globalprotect-openconnect (even though they stem from the same repository). v1 is deprecated/unmaintained but v2 should be able to connect to the same gateways as v1 and more.

@gvolpe
Copy link
Member

gvolpe commented Oct 7, 2024

@Binary-Eater sorry, I should have provided more info, was caught by surprise by this change and spent most of my Sunday trying to get it back to a working state as I need it for work.

The new gpclient-v2.3.7 fails to launch in gui-mode, it seems wrongly patched?

$ gpclient launch-gui                                                                                       
[2024-10-07T05:59:37Z INFO  gpclient::cli] gpclient started: 2.3.7 (2024-10-05)
[2024-10-07T05:59:37Z INFO  gpclient::launch_gui] Log file: /home/gvolpe/.local/share/gpclient/gpclient.log
[2024-10-07T05:59:37Z INFO  gpclient::launch_gui] Service exited with status: exit status: 127

The log shows the following error:

Error accessing /usr/bin/gpservice: No such file or directory

EDIT: Nevermind, I missed this bit on the PR description

The GUI of GlobalProtect-openconnect is unfree software, while the CLI is
licensed as GPLv3-only. This packaging work focuses on the CLI, and
components required for the CLI.


And trying to connect with the CLI directly seems to get stuck in a loop:

$ gpclient connect $work-server.com
[2024-10-07T06:03:59Z INFO  gpauth::auth_window] Loaded uri: https://i**********m/app/panw_globalprotect/...OOD697/sso/saml?SAMLRequest=l**********%3D&RelayState=6**********x
[2024-10-07T06:03:59Z INFO  gpauth::auth_window] No response found in main resource
[2024-10-07T06:03:59Z INFO  gpauth::auth_window] Got invalid auth data, retrying...
[2024-10-07T06:03:59Z INFO  gpapi::portal::prelogin] Portal prelogin with user_agent: PAN GlobalProtect
[2024-10-07T06:03:59Z INFO  gpauth::auth_window] Injected loading element successfully
[2024-10-07T06:03:59Z INFO  gpapi::portal::prelogin] Perform prelogin, user_agent: PAN GlobalProtect
[2024-10-07T06:03:59Z INFO  gpauth::auth_window] Load the SAML request as URI...
[2024-10-07T06:03:59Z WARN  gpauth::auth_window] Failed to load uri: https://i**********m/app/panw_globalprotect/...OOD697/sso/saml?SAMLRequest=l**********%3D&RelayState=8**********x with error: TLS/SSL support not available; install glib-networking
[2024-10-07T06:03:59Z INFO  gpauth::auth_window] Loaded uri: https://i**********m/app/panw_globalprotect/...OOD697/sso/saml?SAMLRequest=l**********%3D&RelayState=8**********x
[2024-10-07T06:03:59Z INFO  gpauth::auth_window] No response found in main resource
[2024-10-07T06:03:59Z INFO  gpauth::auth_window] Got invalid auth data, retrying...

Same issue running it with sudo. This is all working fine with v1.4.9.


For completeness, here's how I install these new packages on my NixOS (Hyprland / Wayland) machine:

environment.systemPackages = with pkgs; [ gpauth gpclient ];

@gvolpe
Copy link
Member

gvolpe commented Oct 7, 2024

Okay I followed this approach shared by @jerith666 and I've made some progress.

The following command launches a new tab on my open work browser and I get successfully redirected back to the terminal where I'm prompted to select the gateway. After I do so, I get permission denied errors:

Click to see logs
$ gpclient connect $work-server.com --browser work-browser                                        
[2024-10-07T07:21:46Z INFO  gpclient::cli] gpclient started: 2.3.7 (2024-10-05)
[2024-10-07T07:21:46Z INFO  gpapi::portal::prelogin] Portal prelogin with user_agent: PAN GlobalProtect
[2024-10-07T07:21:46Z INFO  gpapi::portal::prelogin] Perform prelogin, user_agent: PAN GlobalProtect
[2024-10-07T07:21:47Z INFO  gpauth::cli] gpauth started: 2.3.7 (2024-10-05)
[2024-10-07T07:21:47Z INFO  gpapi::process::browser_authenticator] Launching browser: work-browser
[2024-10-07T07:21:47Z INFO  gpauth::cli] Please continue the authentication process in the default browser
[2024-10-07T07:21:47Z INFO  gpauth::cli] Listening authentication data on port 45807
[2024-10-07T07:21:47Z INFO  gpauth::cli] If it hangs, please check the logs at `/tmp/gpcallback.log` for more information
[2024-10-07T07:21:55Z INFO  gpauth::cli] Received the browser authentication data from the socket
[2024-10-07T07:21:55Z INFO  gpauth::cli] Authentication completed
[2024-10-07T07:21:55Z INFO  gpapi::portal::config] Retrieve the portal config, user_agent: PAN GlobalProtect
[2024-10-07T07:21:56Z INFO  gpapi::gateway::parse_gateways] Try to parse the external gateways...
> Which gateway do you want to connect to? REDACTED
[2024-10-07T07:22:02Z INFO  gpclient::connect] Connecting to the selected gateway: REDACTED
[2024-10-07T07:22:02Z INFO  gpapi::gateway::login] Perform gateway login, user_agent: PAN GlobalProtect
[2024-10-07T07:22:03Z INFO  openconnect::ffi] openconnect version: v9.12
[2024-10-07T07:22:03Z INFO  openconnect::ffi] User agent: PAN GlobalProtect
[2024-10-07T07:22:03Z INFO  openconnect::ffi] VPNC script: /nix/store/j769xj3qq2q6s6wh4csapr6mw0sig84v-vpnc-scripts-unstable-2023-01-03/bin/vpnc-script
[2024-10-07T07:22:03Z INFO  openconnect::ffi] OS: linux
[2024-10-07T07:22:03Z INFO  openconnect::ffi] CSD_USER: 1000
[2024-10-07T07:22:03Z INFO  openconnect::ffi] CSD_WRAPPER: (null)
[2024-10-07T07:22:03Z INFO  openconnect::ffi] RECONNECT_TIMEOUT: 300
[2024-10-07T07:22:03Z INFO  openconnect::ffi] MTU: 0
[2024-10-07T07:22:03Z INFO  openconnect::ffi] DISABLE_IPV6: 0
[2024-10-07T07:22:03Z INFO  openconnect::ffi] NO_DTLS: 0
[2024-10-07T07:22:03Z INFO  openconnect::ffi] POST https://work-server.com/ssl-vpn/getconfig.esp
[2024-10-07T07:22:03Z INFO  openconnect::ffi] Connected to REDACTED IP ADDRESS
[2024-10-07T07:22:03Z INFO  openconnect::ffi] SSL negotiation with GATEWAY
[2024-10-07T07:22:04Z INFO  openconnect::ffi] Connected to HTTPS on GATEWAY with ciphersuite (TLS1.2)-(ECDHE-SECP256R1)-(RSA-SHA256)-(AES-256-GCM)
[2024-10-07T07:22:04Z INFO  openconnect::ffi] Tunnel timeout (rekey interval) is 2880 minutes.
[2024-10-07T07:22:04Z INFO  openconnect::ffi] Idle timeout is 2880 minutes.
[2024-10-07T07:22:04Z WARN  openconnect::ffi] No MTU received. Calculated 1422 for ESP tunnel
[2024-10-07T07:22:04Z INFO  openconnect::ffi] POST https://work-server.com/ssl-vpn/hipreportcheck.esp
[2024-10-07T07:22:04Z WARN  openconnect::ffi] WARNING: Server asked us to submit HIP report with md5sum 109cd121dfdf5faf1f420ca7fab50501.
        VPN connectivity may be disabled or limited without HIP report submission.
        You need to provide a --csd-wrapper argument with the HIP report submission script.
[2024-10-07T07:22:04Z INFO  openconnect::ffi] ESP session established with server
[2024-10-07T07:22:04Z INFO  openconnect::ffi] ESP tunnel connected; exiting HTTPS mainloop.
mkdir: cannot create directory ‘/var/run/vpnc’: Permission denied
[2024-10-07T07:22:04Z WARN  openconnect::ffi] Failed to bind local tun device (TUNSETIFF): Operation not permitted
[2024-10-07T07:22:04Z WARN  openconnect::ffi] To configure local networking, openconnect must be running as root
    See https://www.infradead.org/openconnect/nonroot.html for more information
mkdir: cannot create directory ‘/var/run/vpnc’: Permission denied
[2024-10-07T07:22:04Z WARN  openconnect::ffi] Failed to bind local tun device (TUNSETIFF): Operation not permitted
[2024-10-07T07:22:04Z WARN  openconnect::ffi] To configure local networking, openconnect must be running as root
    See https://www.infradead.org/openconnect/nonroot.html for more information
[2024-10-07T07:22:04Z WARN  openconnect::ffi] Set up tun device failed
[2024-10-07T07:22:04Z INFO  openconnect::ffi] POST https://work-server.com/ssl-vpn/logout.esp
[2024-10-07T07:22:04Z INFO  openconnect::ffi] SSL negotiation with GATEWAY
[2024-10-07T07:22:05Z INFO  openconnect::ffi] Connected to HTTPS on GATEWAY with ciphersuite (TLS1.2)-(ECDHE-SECP256R1)-(RSA-SHA256)-(AES-256-GCM)
[2024-10-07T07:22:05Z INFO  openconnect::ffi] Logout successful.
[2024-10-07T07:22:05Z INFO  openconnect::ffi] openconnect_mainloop returned -5, exiting

So I tried the same command but with sudo. My default "work-browser" (firefox) I run as a user no longer works, so the process hangs. I had to install chromium at the system level and I got further.

$ sudo gpclient connect $work-server.com --browser chromium
...
[2024-10-07T07:30:20Z INFO  gpapi::process::browser_authenticator] Launching browser: chromium
[2024-10-07T07:30:20Z INFO  gpauth::cli] Please continue the authentication process in the default browser
[2024-10-07T07:30:20Z INFO  gpauth::cli] Listening authentication data on port 39543
[2024-10-07T07:30:20Z INFO  gpauth::cli] If it hangs, please check the logs at `/tmp/gpcallback.log` for more information

Unfortunately, it fails to execute the callback so it just hangs on the terminal.

I tried sending the prelogin-cookie/callback base64 string as follows:

$ echo PRELOGIN_COOKIE | ncat localhost 39543

But I just get "Invalid auth data", so I'm missing this last piece:

$ [2024-10-07T07:32:02Z INFO  gpauth::cli] Received the browser authentication data from the socket
[2024-10-07T07:32:02Z WARN  gpapi::auth] Failed to decode SAML auth data: Invalid byte 10, offset 380.
[2024-10-07T07:32:02Z INFO  gpauth::cli] Authentication completed
[2024-10-07T07:32:02Z INFO  gpclient::connect] Failed to connect portal with prelogin: Invalid auth data

Error: Invalid auth data

@gvolpe
Copy link
Member

gvolpe commented Oct 7, 2024

This works:

$ gpauth <portal> --browser work-browser 2>/dev/null | sudo gpclient connect <portal> --cookie-on-stdin

This too (the -E is key):

$ sudo -E gpclient connect <portal> --browser work-browser

I'm still keeping v1 due to ergonomics, though. It's nice to have a UI that sits on the system tray with a built-in webview where the authentication can be performed, so there's no messing around with different browsers and no need for sudo. For instance, I use two different Firefox profiles and this can be problematic with terminal clients that assume a default browser instance.

@Binary-Eater
Copy link
Member Author

@gvolpe I agree in terms of ergonomics that this new V2 client is a downgrade. Unfortunately, the V1 client is no longer maintained and does not support every new authentication scheme GlobalProtect has come up with recently. Unfortunately, the GUI component for V2 is unfree (you also need a paid license, which is not as big of an issue) and more importantly unauditable (which seems somewhat problematic for a VPN client), so I felt hesitant to package something like that when the cli is easy to audit.

@gvolpe
Copy link
Member

gvolpe commented Oct 7, 2024

@Binary-Eater completely agree with the approach, appreciate your work on this! Fingers crossed a new open-source UI comes around for v2 🤞🏽 (didn't know one needed a paid license to use it 😮 ).

@jerith666
Copy link
Contributor

jerith666 commented Oct 12, 2024

Here's how I ended up wrapping the v2 client to make it work in the most painless way I could:

let

vpnScript = pkgs.stdenv.mkDerivation {
  name="vpn";

  src = pkgs.writeScript "vpn" ''
    #! ${pkgs.bash}/bin/bash

    id

    ${pkgs.gpclient}/bin/gpclient \
        connect \
        --browser ${pkgs.chromium}/bin/chromium \
        https://<redacted> \
        --csd-wrapper ${pkgs.openconnect}/libexec/openconnect/hipreport.sh
  '';

  dontUnpack=true;

  installPhase = ''
    mkdir -p $out/bin
    ln -s $src $out/bin/vpn
  '';
};

in
{
  security.wrappers = {
    vpn = {
      owner = "root";
      group = "root";
      setuid = true;
      setgid = true;
      source = "${vpnScript}/bin/vpn";
    };
  };
}

Though for some reason I still have to use sudo (actually sudo -E) to get it to have elevated permissions -- I'm clearly missing something with how security.wrappers is supposed to work.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
6.topic: nixos Issues or PRs affecting NixOS modules, or package usability issues specific to NixOS 8.has: changelog 8.has: clean-up 8.has: documentation This PR adds or changes documentation 8.has: maintainer-list (update) This PR changes `maintainers/maintainer-list.nix` 8.has: module (update) This PR changes an existing module in `nixos/` 8.has: package (new) This PR adds a new package 10.rebuild-darwin: 1-10 10.rebuild-linux: 1-10 11.by: package-maintainer This PR was created by the maintainer of the package it changes 12.approvals: 1 This PR was reviewed and approved by one reputable person
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants