miyagawa / cpanminus

cpanminus - get, unpack, build and install modules from CPAN
http://cpanmin.us
755 stars 213 forks source link

Securing Perl: cpanm HTTPS + verify_SSL + verify signatures? #611

Open dweekly opened 4 years ago

dweekly commented 4 years ago

Hi! I'm starting to work across the community to try and help "Securing Perl" by encouraging the checking of module signatures, moving mirrors to HTTPS, nudging defaults toward connecting to HTTPS mirrors when possible, and checking server SSL certificates.

Specific to cpanm, I'm wondering if it makes sense to:

Is there interest in updating cpanm in this way or thoughts on the approach here?

miyagawa commented 4 years ago

verify_SSL is already the default in the Menlo version of cpanm on our git repo. This version can be fetched via Menlo::Legacy distribution. https://github.com/miyagawa/cpanminus/blob/devel/Menlo-Legacy/lib/Menlo/CLI/Compat.pm#L2742

Using https URL by default is challenging because that will make cpanm not work out of the box when the system doesn't support HTTPS (you don't have openssl, you don't have IO::Socket::SSL, your curl/wget doesn't support HTTPS, etc). We have to make it an opt-in so that existing users of this script will continue to work. Same thing applies for SIGNATURES/CHECKSUMS because Module::Signature and gpg/pgp validation is not in perl core.

miyagawa commented 4 years ago

by the way what you just describe is already possible with:

export PERL_CPANM_OPT="-M https://cpan.metacpan.org/ --verify"

assuming you either have LWP + https support (or curl). It will disable querying the http backend for cpanmetadb, and pull everything from the https URL to fetch packages, and run the verifications with signatures/checksums.

I know you're suggesting to change the default, but i can't make a change to the defaults that could break the existing users of the script, because it's widely used in a CI environment and that will be a breaking change.

dweekly commented 4 years ago

Thank you so much for your timely and thoughtful reply! I understand not wanting to introduce breaking changes.

Would it be possible to check for the presence of the required packages and if they are present to set secure defaults that use those packages, such that users with Module::Signature installed will automatically verify module signatures and users with HTTPS support automatically fetch data over HTTPS?

What is your thought about displaying a warning for users who don't have these installed so they know that modules are unchecked / requests are happening via HTTP and there is something they can do about it (install the required modules).

miyagawa commented 4 years ago

--verify is implemented that way, so that if you turn it on while not having Module::Signature it will display a warning and won't actually verify the tarball.

dweekly commented 4 years ago

Excellent. Then it would seem pretty harmless to have --verify enabled by default, yes? I noticed that on the "cpanm --help" screen the "--verify" option isn't visibly shown. Was this intentional, or should we add a line to the help screen for "--verify"?

Would you be open to setting HTTPS as the default when the required packages to implement it are installed?

miyagawa commented 4 years ago

Well, verify slows the installation a bit, and Module::Signature can't be installed on a Mac without installing external CLI tools like gpg, so i'm not keen to changing the default in a way that would result in display a warning for the majority of the users.

I'm open to accept a PR to show --verify in the help screen though.

tobyink commented 4 years ago

Maybe something like cpanm -s could enable HTTPS and verification of signatures?

nanto commented 2 years ago

To respond to Addressing CPAN vulnerabilities related to checksums | NeilB [blogs.perl.org], I think it is time to make HTTPS mirror as default.

If support for old CI environments matters, how about connecting HTTPS at first and then fall back to HTTP? (According to the blog article, CPAN.pm 2.29 behaves in this manner.)

nanto commented 2 years ago

Another solution: delivering old version of cpanm (whose default mirror is http://) via http://cpanmin.us and new version of cpanm (whose default mirror is https://) via https://cpanmin.us.

If a CI environment installs capnm from https://cpanmin.us, that environment might support HTTPS.

sjn commented 11 months ago

Now that we're nearing 2024, how about we make that year into "The CPAN year of «Secure by Default»"? :grin:

stigtsp commented 11 months ago

Imho, cpanm should require https and verify certificates by default. With an optional cpanm --insecure for corner cases that do not have tls libraries, are missing cacerts, use self-signed certificates, or want to use http without tls.

guest20 commented 11 months ago

HTTP::Tiny's verify_SSL — A boolean that indicates whether to validate the TLS/SSL certificate of an https — connection (default is true). Changed from false to true in version 0.083. (2023-06-11)

stigtsp commented 6 months ago

https by default is PRed here:

zakame commented 3 months ago

Hi @miyagawa 👋 Chiming in on behalf of https://github.com/Perl/docker-perl via the efforts of @stigtsp, @dgl and others 🙏

docker-perl now ships with SSL modules out of the box, and GnuPG for Module::Signature support is also already baked in since almost the beginning (by way of its buildpack-deps base image) so docker-perl is in a good position to ship with all the requested features in this issue, without interfering with systems in place that lack these requirements - what else can we do to move this along?

This also seems to be a good opportunity to resume Menlo development - we could ship Menlo::CLI::Compat in docker-perl to replace cpanm...

stigtsp commented 3 months ago

[..] and GnuPG for Module::Signature support

Just to chime in: the PGP signature verification using Module::Signature in cpanminus and other CPAN clients was demonstrated to be insecure in Addressing CPAN vulnerabilities related to checksums.

The recommended mitigation for cpanminus in the blog post was: "set the PERL_CPANM_OPT environment variable to --from https://www.cpan.org"

stigtsp commented 2 months ago

cpanminus in the latest perl docker images now use HTTPS. Thx @zakame!

$ podman run --rm docker.io/library/perl:latest cpanm Mojolicious
--> Working on Mojolicious
Fetching https://www.cpan.org/authors/id/S/SR/SRI/Mojolicious-9.38.tar.gz ... OK
...
robrwo commented 2 months ago

Does CVE-2024-45321 affect the latest version of cpanminus?

stigtsp commented 2 months ago

Does CVE-2024-45321 affect the latest version of cpanminus?

Yes, a patched version for this is not yet available upstream