Ask Ubuntu is a question and answer site for Ubuntu users and developers. Join them; it only takes a minute:

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

I have a (private) apt repository setup on a server. I'm only allowing access to this repository over SSL, and only with a client certificate. I have tested the connection using curl:

$ curl --cacert /opt/CA.crt --cert /opt/user.crt --key /opt/user.key --pass 1234 https://example.com/dists/lucid/main/binary-amd64/Packages.gz

The content is downloaded as expected.

I've created a file in /etc/apt/apt.conf.d/45example-com with

Debug::Acquire::https "true";

Acquire::https::example.com {
    Verify-Peer "true";
    Verify-Host "true";

    CaInfo "/opt/CA.crt";

    SslCert "/opt/user.crt";
    SslKey  "/opt/user.key";
};

I've added a file at /etc/apt/sources.list.d/example.com.list with:

deb https://example.com/ lucid main

There seems to be a problem with the CA cert, when I try an update I get the following:

# apt-get update
* Connected to example.com (8.0.0.8) port 443 (#0)
* found 1 certificates in /opt/CA.crt
* error reading X.509 key or certificate file
* Closing connection #0

The server logs on example.com show that no request got there, so I guess that apt-get is failing before trying to send the request (which matches what the log says).

I've had a hard time finding any documentation on apt-get with ssl on the interwebs, and haven't even been able to find the source code.

Does anyone have any ideas?

share|improve this question
up vote 1 down vote accepted

After some searching I have a better idea of what is happening (but no solution yet).

I found the source code for apt at https://code.launchpad.net/~ubuntu-branches/ubuntu/lucid/apt/lucid. It uses libcurl for ssl, which in turn uses gntls.

The error message comes from libcurl, and it is complaining about the key/password, not the CA certificate. The line:

* found 1 certificates in /opt/CA.crt

is saying that CA.crt was correctly loaded. The error message comes from the following:

if(gnutls_certificate_set_x509_key_file(
     conn->ssl[sockindex].cred,
     data->set.str[STRING_CERT],
     data->set.str[STRING_KEY] ?
     data->set.str[STRING_KEY] : data->set.str[STRING_CERT],
     do_file_type(data->set.str[STRING_CERT_TYPE]) ) !=
   GNUTLS_E_SUCCESS) {
  failf(data, "error reading X.509 key or certificate file");
  return CURLE_SSL_CONNECT_ERROR;
}

(From gtls.c in http://alpha.gnu.org/gnu/gnutls/libtasn1-0.2.10.tar.gz)

The problem is with the password that is associated with that key. I've stripped the password from the key using:

$ openssl rsa -in user.key -out user-nopasswd.key

This isn't ideal, but it seems to work.

share|improve this answer

One issue I ran into while attempting to get apt-get to run over https was that for the SslCert option you cannot use a .pem file as apt-get will fail to recognize this as a valid format for use with connecting to your repository. I have a self signed .pem that I use to connect to my webserver and it is in a .pem format which is why I attempted to use it.

The solution was to just split the .pem into the correct files a .crt and a .key and apt-get successfully connected.

TLDR: split your .pem file into a .crt and a .key and it will work.

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.