indygreg / indygreg/PyOxidizer

Cannot establish SSL connection on Fedora, default cert chain not found

Open
#283 2 comments 1 reaction 0 assignees View on GitHub

Nobody has claimed this yet.

bug
Dominant language
Rust
Stars
6.2k
Forks
256
PR merge metrics
No merged PRs in 30d

Description

(I assume this is more relevant to `python-build-standalone` but I'm reporting it here since I've experienced it with PyOxidizer.)

Using the low-level SSL and socket APIs, attempting to make an SSL connection on a fresh install of Fedora 32 fails with:

```
Traceback (most recent call last):
File "test", line 11, in
File "ssl", line 423, in wrap_socket
File "ssl", line 870, in _create
File "ssl", line 1139, in do_handshake
ssl.SSLCertVerificationError: [SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: unable to get local issuer certificate (_ssl.c:1076)
```

After some modest digging, I discovered that the CA paths differ between the Fedora-vendored Python and PyOx's own Python. This is the return value of `__import__('ssl').get_default_verify_paths()` with Fedora's Python:

```
DefaultVerifyPaths(cafile='/etc/pki/tls/cert.pem', capath='/etc/pki/tls/certs', openssl_cafile_env='SSL_CERT_FILE', openssl_cafile='/etc/pki/tls/cert.pem', openssl_capath_env='SSL_CERT_DIR', openssl_capath='/etc/pki/tls/certs')
```

And this is PyOxidizer:

```
DefaultVerifyPaths(cafile=None, capath='/etc/ssl/certs', openssl_cafile_env='SSL_CERT_FILE', openssl_cafile='/etc/ssl/cert.pem', openssl_capath_env='SSL_CERT_DIR', openssl_capath='/etc/ssl/certs')
```

When creating a new SSL context, the SSL module calls `set_default_verify_paths` with the output of `get_default_verify_paths`. The PyOx `openssl_cafile`, `/etc/ssl/cert.pem`, does not exist, whatever that might be indicative of; `/etc/ssl/certs` is a symlink to `/etc/pki/tls/certs`. You can repro this by bundling:

```py
import socket
import ssl

context = ssl.create_default_context()

print(ssl.get_default_verify_paths())

with socket.create_connection(('github.com', 443)) as sock:
with context.wrap_socket(sock, server_hostname='github.com') as ssock:
ssock.send(b'HEAD / HTTP/1.0\r\nHost: github.com\r\n\r\n')
print(ssock.recv(64).decode() + '...')
```

In effect this means that you cannot make any HTTPS requests at all on Fedora out of the box using PyOx.

Contributor guide

No contributing guide indexed for this repository

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start by running the provided SSL and socket reproduction script in a fresh Fedora 32 environment and compare PyOxidizer's default verification paths with Fedora Python's. Done means the bundled Python can establish the github.com HTTPS connection and resolves Fedora's CA file or certificate directory correctly.

Written by the indexing model from the issue text.

Assessment

Tech stack
python, rust
Domain
security, tooling
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
45/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.