anchore / grype

A vulnerability scanner for container images and filesystems
Apache License 2.0
8.84k stars 574 forks source link

How do you configure grype to use a private certificate authority? #653

Closed woodsonmiles closed 2 years ago

woodsonmiles commented 2 years ago

I can see that support was added for this here: https://github.com/anchore/grype/pull/494

However, I cannot find any documentation that explains what command line option allows you to provide a private x509 cert.

I'm interested in this feature because I'm trying run this program from behind a corporate proxy, which prevents grype from loading its vulnerability database.

ERROR failed to fetch latest version: Get "https://toolbox-data.anchore.io/grype/releases/latest/VERSION": x509: certificate signed by unknown authority
2 errors occurred:
        * failed to load vulnerability db: vulnerability database is corrupt (run db update to correct): database metadata not found: /.cache/grype/db/3
        * failed to catalog: could not fetch image 'dockerhub.com/postgres': unable determine image source
luhring commented 2 years ago

Hi @woodsonmiles — I just took a look, and you're absolutely right. We need to document how to do this. 😱

It should be possible to use the environment variable GRYPE_DB_CA_CERT, where the value is set to the path to a PEM file that includes the private CA cert.

Can you try that and let me know if you have any issues?

And we'll keep this issue open at least until documentation is added.

woodsonmiles commented 2 years ago

Hey @luhring , thank you for helping me find that variable. Alas, I haven't found luck with it. Hard to know if the issue is on my end. Perhaps you can spot my mistake?

My one idea is, I don't know for sure which cert authority is bothering grype. My company has 4 root authorities and I've tried them all, but maybe there is a different cert it doesn't like or maybe its in a slightly different format than what I'm feeding it. Would be great if the error message gave a little info on the untrusted cert. Not sure how difficult that would be to add.

I'm running it with docker.

Dockerfile:

FROM anchore/grype
COPY ./lm.pem /lm.pem
ENV GRYPE_DB_CA_CERT=/lm.pem

CLI:

docker build -t my_grype .
docker run my_grype -vv postgres

Output:

[0000] DEBUG application config:
output: ""
file: ""
output-template-file: ""
quiet: false
check-for-app-update: true
only-fixed: false
search:
  scope: Squashed
  unindexed-archives: false
  indexed-archives: true
ignore: []
exclude: []
db:
  cache-dir: /.cache/grype/db
  update-url: https://toolbox-data.anchore.io/grype/databases/listing.json
  ca-cert: /lm.pem
  auto-update: true
  validate-by-hash-on-start: false
dev:
  profile-cpu: false
  profile-mem: false
fail-on-severity: ""
registry:
  insecure-skip-tls-verify: false
  insecure-use-http: false
  auth: []
log:
  structured: false
  level: ""
  file: ""

[0000]  INFO grype version: 0.33.1
[0000] DEBUG   ├── buildDate: 2022-02-27T00:01:17Z
[0000] DEBUG   ├── compiler: gc
[0000] DEBUG   ├── gitCommit: b0c8dc0e578d4b7c38a6bb4bdfbbda21a4640e53
[0000] DEBUG   ├── gitDescription: v0.33.1
[0000] DEBUG   ├── goVersion: go1.17.7
[0000] DEBUG   ├── platform: linux/amd64
[0000] DEBUG   ├── syftVersion: v0.39.3
[0000] DEBUG   └── version: 0.33.1
[0000] ERROR failed to fetch latest version: Get "https://toolbox-data.anchore.io/grype/releases/latest/VERSION": x509: certificate signed by unknown authority
[0000] DEBUG No new grype update available
[0000] DEBUG gathering packages
[0000] DEBUG loading DB
[0000] DEBUG looking for updates on vulnerability database
[0000] DEBUG checking for available database updates
[0000] DEBUG no socket address was found. Trying default address: /run/user/0/podman/podman.sock from-lib=stereoscope
[0000] DEBUG looking for socket file: stat /run/user/0/podman/podman.sock: no such file or directory from-lib=stereoscope
[0000] DEBUG image: source=OciRegistry location=postgres from-lib=stereoscope
[0000] DEBUG pulling image info directly from registry image="postgres" from-lib=stereoscope
[0000] DEBUG no registry credentials configured, using the default keychain from-lib=stereoscope
[0001] DEBUG found database update candidate: Listing(url=https://toolbox-data.anchore.io/grype/databases/vulnerability-db_v3_2022-03-04T08:16:20Z.tar.gz)
[0001] DEBUG cannot find existing metadata, using update...
[0001] DEBUG database update available: Listing(url=https://toolbox-data.anchore.io/grype/databases/vulnerability-db_v3_2022-03-04T08:16:20Z.tar.gz)
[0001]  INFO downloading new vulnerability DB
[0015]  INFO updated vulnerability DB to version=3 built="2022-03-04 08:16:20 +0000 UTC"
1 error occurred:
        * failed to catalog: could not fetch image 'postgres': unable to use OciRegistry source: failed to get image descriptor from registry: Get "https://index.docker.io/v2/": x509: certificate signed by unknown authority
luhring commented 2 years ago

Hi @woodsonmiles, thanks for the log data. I think I'm understanding what's happening more specifically now.

INFO updated vulnerability DB to version=3 built="2022-03-04 08:16:20 +0000 UTC"

It looks like the GRYPE_DB_CA_CERT adjustment actually worked, and the DB was downloaded successfully.

This config value controls the CA trusted for "DB curation" specifically, not all HTTPS requests that happen within Grype's execution. The PR you mentioned (#494) is specifically for DB curation. (We still need to document this, though! 😄 )

... Get "https://index.docker.io/v2/": x509: certificate signed by unknown authority

This looks like the HTTPS request to Docker Hub failed because Grype couldn't verify the certificate it received when it sent a request to https://index.docker.io/v2/.

It looks like you're running Grype in a container image. When you build the image, can you adjust the CA certs stored in the image (i.e. in /etc/ssl/certs/ca-certificates.crt)? This way you could set the trust for your private network environment in exactly the way you need, so if Grype receives a cert from a corporate proxy, it should in theory successfully verify the cert because that cert is chained back to a corporate CA trusted within the container.

woodsonmiles commented 2 years ago

Thanks @luhring , your suggestion is correct! I replaced /etc/ssl/certs/ca-certificates.crt with my corporate cert. It was important to keep the exact same name, ca-certificates.crt. Once I did that everything worked, regardless of whether I used the GRYPE_BD_CA_CERT option.

spiffcs commented 2 years ago

Thanks @woodsonmiles for verifying this is working for you now! I'll close this issue unless you need anything else.