6

I don't trust certificate authorities, so I'm using a self-signed certificate on my server. The server provides both a website as well as other services.

Most modern SSL-capable software, upon encountering SSL, checks if the certificate is given by a CA and if not throws up a very scary warning. Contrary to Mozilla's logic, I believe that in my case a self-signed certificate is actually more secure, because it avoids the risk of malicious or incompetent CAs.

But let's say I want to give a friend access to my website or my server. Maybe I have a few photos on it from my trip that I want to show them: If I just give them the secure URI, their computer will also throw up the usual warnings. But since unlike me, they weren't the ones who configured everything, how will they know that Everything Is Fine™ (unless the fingerprint doesn't match)?

I could have a little notice in the HTTP version of my page explaining the error, and how to manually verify the fingerprint and make sure that Everything Is Fine. But:

  • If the connection was compromised, the attacker could just alter this notice to say "nah bro self-signed certs are totally fine, trust me".
  • If the user goes straight to the HTTPS URI, how will they know to check the HTTP version?
  • If the user uses a non-web service accessed through its own program, how will they even know about the notice?
  • If the user doesn't know how SSL works, they'll just believe their browser and close the site, instead of investigating why there is a self-signed cert (since unfortunately the documentation/UI authors' attitude seems to have been "there's no good reason ever").

So how can I ensure that when I send a user to my server, and they are confronted with the "self-signed certificate" warning, they are able to decide for themselves whether to trust it or not, instead of having to believe the skewed picture that their software paints for them?

I don't want to tell users to "just ignore the warning, it's fine", because not only does this reinforce a bad habit in general (what if their CA-verified bank gets compromised one day and presents a self-signed cert?) but also there would be no way for them to tell if my server is compromised.

Also worth mentioning is that the certificates are not forever, and eventually expire, so the user must be able to tell the difference between suspicious change of cert (say well before the planned expiration of the current one), suspicious change of cert that is made to look non-suspicious (a MITM executed just when I was scheduled to renew my cert), legitimate change of cert (when my cert expires and I issue a fresh one), and legitimate change that happens to look suspicious (I decided to issue a new cert way ahead of schedule for whatever reason).

We can assume that:

  • I have few users, so scalability is not so important. For instance, the users emailing me or calling my phone number to verify the certificate are perfectly valid solutions.
  • The users trust me and can communicate with me through a secure channel. For example, they can talk to me in person or send me encrypted email.
  • The users are reasonably intelligent, and can be expected to understand basic security concepts like "if the certificate changes unexpectedly, the site may have been compromised".

My main concern is dealing with less technical users, who would be confused when they see the self-signed certificate warning.

Superbest
  • 1,094
  • 8
  • 20
  • Although Steffen and Philipp have already answered you, I'd like to emphasize that you're asking for users to get out of their way to solve a problem that your own negligence / mistake / limited budget has caused. You should *not* issue invalid certificates, and if you do, *you* should be the one who bears the cost of configuring client browsers for them to recognise your cert (rather than take users' time to "educate" them about something they don't care about). If (for any reason) you can't implement security properly, you should take it upon yourself to make things right. – Steve Dodier-Lazaro Apr 22 '15 at 10:47

4 Answers4

6

So how can I ensure that when I send a user to my server, and they are confronted with the "self-signed certificate" warning, they are able to decide for themselves whether to trust it or not, instead of having to believe the skewed picture that their software paints for them?

If you are not using pre-defined trust anchors (e.g. the root CA of the browser) you have to find a way to give your users the necessary trust information in a secure way. The preferred way would be of course personal, because any indirect ways like phone call or PGP signed mails need a pre-established trust, e.g. associating phone numbers or keys with you.

Also worth mentioning is that the certificates are not forever, and eventually expire, so the user must be able to tell the difference between suspicious change of cert...

In this case you have again inform the user about the change in a secure way.

The whole idea of the trusted CA in the browser is to start with some pre-defined trust and then defer trust information about other sites. This is similar to real life: you initially trust some people (parents..) and from them to learn trust other people. But once you abandon any initial trust settings you have to start from zero and thus find your own way to make your users trust you.

If you want to establish your own certificate as trusted you can only start with the existing trust relationships, i.e. friends which know you directly, know your phone number, your PGP key etc. These trust relations then must be used to transport the new trust into your certificate (i.e. fingerprint or similar). The best approach then depends on the kind of trust relations you already have to your friends and which one can be used as the best transport for the new trust.

Steffen Ullrich
  • 184,332
  • 29
  • 363
  • 424
  • Personally distributing trust info was actually what I had in mind: I could just give them the correct fingerprint along with the URI when I tell them to go there (but they may get confused) or I can tell them to just call me and check (but how do I get the warning dialog to say "call Superbest"?). I was wondering if there's anything more practical. – Superbest Apr 21 '15 at 09:07
  • As for your second remark, I don't have a problem with the web-of-trust model. I have a problem with who is at the base of the current version. If I personally knew and trusted the operator of a CA, I would have no problem just having them sign me. But unfortunately, I neither know nor trust any of the CAs out there. – Superbest Apr 21 '15 at 09:09
  • 1
    @Superbest: You could have two different websites; one whose URI you give them and one they are directed to from the other. –  Apr 21 '15 at 09:10
  • You have to use an established trust path to send the information needed for the new trust. If they already know your phone number they can call you. If they trust your PGP key already you could use signed mails etc. There is no general answer what's best, it depends on the amount and kind of existing trust relations. – Steffen Ullrich Apr 21 '15 at 10:24
  • 1
    If your users are meant to be returning users of your website, then a point to highlight would be to ask them to check the box asking the browser to "Permanently store this exception". By this way, the browser will internally link this URL to the self-signed certificate and be able to tell on future visits whether your website is still showing the expected self-signed certificate or if it has been changed (similar behavior as the 'ssh' command, for instance). – WhiteWinterWolf Apr 21 '15 at 13:21
  • @GZBK To my mind, that is in fact the only scenario where this makes sense. If they are first time visitors, the self-signed certificate is of course useless for security. – Superbest Apr 21 '15 at 16:51
  • 1
    @Superbest: there might be other scenario, however the point here is that the average user reaction, seeing a warning about a suspicious certificate, would be to uncheck the "Permanently store" box because he has been told everywhere to never save any suspicious document from Internet to his computer. However, in this precise case, the most secure posture is the opposite one and store the certificate. This may not seem obvious to a lot of people... – WhiteWinterWolf Apr 22 '15 at 09:53
3

Edit: The question author made significant edits to their question after this answer was posted. This answer is based on an earlier version of the question which gave the impression that they were asking about a usual public website.

You can not explain that a self-signed certificate is fine, because on a public website it is not! The other question you mentioned was about a different context: Using your own CA to sign your certificates and have a limited and known number of clients which trust that custom CA. From the perspective of the browser this is technically not different from using an "official" CA and it requires that the clients obtain the CA root certificate via a trusted channel. But with anonymous internet users, this is not possible.

No matter how much you distrust the CA system (and you have good reason to do so, but that's a different topic), using a self-signed certificate on a public website is even worse. Any MITM attacker could decode the communication, replace your certificate with their own and re-encrypt it for the user. Without a trusted 3rd party to verify the signature of the certificate, there is no defense against this. So there is no way to verify that indeed "everything is fine".

Providing the fingerprint of your certificate is pointless, because you have no way to send it to the user in a way which can not be manipulated by the MITM attacker. A https website can be manipulated as previously described, and a http website is even easier to manipulate. The attacker could just replace the fingerprint on the website with that of their own.

There is hope that one day a better system like DANE (which moves the trust role to the DNS system) will finally replace the flawed CA system, but until then certificate authorities are still the best solution we have.

Philipp
  • 48,867
  • 8
  • 127
  • 157
  • Sorry for the drastic edit! Your note about having no way of sending the fingerprint securely must refer to the earlier version where I failed to point out that I do have an alternative secure channel of communications with the user. In that case, you are quite correct. I expressly specified that I have a secure channel (eg. phone call or encrypted email) to avoid that caveat. The question isn't "how to get the fingerprint to user". The question is, how to make sure the user knows to call me and ask about the fingerprint, instead of just giving up and closing the browse window. – Superbest Apr 21 '15 at 16:47
  • @Superbest: You could use my comment to Steffen's answer. –  Apr 22 '15 at 01:32
2

When you have secure(!) contact with all of your users over a different medium, you can send them the root certificate of your own certificate authority which you used to sign the certificate of your website and give them instructions how to add it to the list of trusted certificates of their web browser (or maybe even a handy install script which does it automatically).

When they did this correctly, the website will no longer appear as self-signed in their browser. The browser will instead treat it like if it were signed by any other "real" certificate authority.

This, of course, does not protect your users from a rogue CA which creates a false certificate for your website, because common web browsers do usually not support CA pinning (telling them to only trust one specific CA for a specific website).

You should also make your users aware that this means that you now can also impersonate other websites they visit, so it requires a large amount of trust. This problem is also not fixable, because currently there is no such concept as a CA which is only trusted for specific domains.

Thankfully, this problem might one day be solved with DANE which puts the DNS servers into the role of the certificate authorities. You will then be able to distribute your domains TLS certificate by the DNS server which is responsible for your domain (and only that one). But currently there are no browsers which support it out-of-the-box, and considering that there are several companies which have financial interests in keeping the CA system (which is practically a money printing license sold by browser developers) it might take a while until it takes off.

Philipp
  • 48,867
  • 8
  • 127
  • 157
  • 1
    Not an expert in certificates, but I seem to believe you can now tell browsers to cache the last working certificate for your site and issue a warning when a different certificate is encountered instead? I really can't remember the name of the protocol that performs this, though. – Steve Dodier-Lazaro Apr 22 '15 at 10:43
-3

The Best approach (for the use case of a limited user group and a personal website) I use is to have a non secured page somewhere where my users can download the root certificate (my own CA) and find instructions how to install that into there trust store. this way the computer can trust my 'self-signed' certificate.

one of the headaches with this approach is that for windows or mac it usually suffices to put it in the systems key-store application. on Linux / UNIX most applications have there own certificates store. And sometimes browsers have there own store. I usually solve this by offering my users (remote) help installing the certificates and putting it on all the right places.

but with a user group of less than 100 people this is feasible.

as to your "more secure" remark. It is impossible to say its more secure. Those other CA's have regular audits. I doubt you have the time / money to be audited like a CA. so we simply do not know if your more secure.

LvB
  • 8,217
  • 1
  • 26
  • 43
  • How do the users ensure the root cert is secure? Couldn't an attacker simply issue their own root cert? The caveat of small groups is very apt - I'm assuming that I will never have to deal with so many users that I can't personally provide support if necessary. – Superbest Apr 21 '15 at 08:54
  • Also, about security: It's not that I believe I'm safer than the CA. However, I prefer trusting only my own security as opposed to trusting my own security AND the CA. – Superbest Apr 21 '15 at 08:56
  • 4
    heh,heh,heh,hahahaha. That certainly is "The Best approach" _for Lawri_; it would let him MitM connections without needing to subvert a CA. –  Apr 21 '15 at 09:02
  • The page where you can get my root certificate is on a read only part of my webserver (as my nginx sees it anyway) and it also has MD5 / SHA1 / SHA256 / SHA512 signatures for it, as well as the "certificate signature" and instructions how to check any of them. The same page is also protected by my own Ca (on a https part) , as a means for the user to verify the root certificate is installed correctly. – LvB Apr 21 '15 at 09:02
  • For a server I control, I can MiTM without the need for anything else. And on a broader scope. it would allow anyone that has an CA to do MitM. To protect Users form MitM Certificates are just not the solution on them self. You use Certificate Pinning and Strict Transport headers for that. – LvB Apr 21 '15 at 09:12
  • The problem as sketched is one of intricate trust, and there is no approach that does not require 'the user' to trust 'someone else', this is not different than with a bought certificate. – LvB Apr 21 '15 at 09:17
  • I think the downvotes are a bit unfair. It's true that this requires undue trust: The user must not only trust your cert, but also trust that you won't leverage the scenario to perform MITM when they later login to their bank account (with just a self-signed cert, you don't get any help doing MITM on other sites). Still, I think it's an interesting option if that flaw is made clear. – Superbest Apr 21 '15 at 15:33
  • 1
    @LawrivanBuël As a MITM I can easily manipulate your non-secure part of your website to serve my certificate instead of yours. I now also control the TLS-encrypted version and can replace all references to your certificate (like signatures, fingerprints etc.) with those to mine. – Philipp Apr 21 '15 at 16:02
  • @Philipp Good luck with that, Since both the config and the http page are Read-only mounted. Also that would hold true for any official CA, Your right in that the 'public' part of a site needs additional protection but that is needed anyways. – LvB Apr 22 '15 at 21:20
  • @LawrivanBuël You don't seem to understand me. For a man-in-the-middle attacker it is completely irrelevant if your config or http pages are mounted read-only. The MITM attacker is between your system and the client. They can not do anything on either system, but they can manipulate the data exchanged between them. A certificate from an official CA makes a man-in-the-middle attack impossible, unless the MITM manages to actively compromise a CA and gets them to sign a certificate for them. – Philipp Apr 23 '15 at 07:32
  • @Philipp than I fail to see how my Own CA (as in I made my own CA and sign my Certificates with that) is any diffrent from a 'official' CA. or how it enables a MitM by itself. If you mean 'an attacker could intercept and alter the certificate before the first installation' than, yes your right. but its a small window that you mitigate through other means. (you could sign a zip file or use a startssl cert on that site to prevent modification mid-transit) all of which are outside of the scope of this question. and unless its a targeted attack not really applicable when using a 'trusted' line. – LvB Apr 23 '15 at 09:11
  • @LawrivanBuël By distributing the certificate of your own CA over an insecure channel, you can not ensure that the correct certificate gets installed by the user. The time-window isn't as small as you think because it applies to every new user. When you exclude targeted attacks from your security considerations, then your threat vector become so narrow that all this theatre with your own manually installed CA becomes unnecessary. – Philipp Apr 23 '15 at 09:23
  • @LawrivanBuël Signing a zip means you again need to securely transfer a public key to confirm the signature somewhere - again the same issue. When you trust StartSSL to secure distribution of your root CA certificate, then you are again require trust in the root CA system. So why not use the StartSSL cert to secure your whole site? – Philipp Apr 23 '15 at 09:27
  • Use case was a small set of users with assisted installation, not a 'general use' use case. for general use (so new users are being attached 'all the time') your absolutely right in that you simply can not do that. It is however just as insecure as any CA since all CA's I have checked host there root certificate, CRL and OCSP responders using plain HTTP. – LvB Apr 23 '15 at 09:30
  • @Philipp why use your own CA. for example when you want to use Client side certification and not spend a lot of money on it, You want your own CA. OR when your on site where there is no Internet but you do want to employ SSL you need your own CA. etc. – LvB Apr 23 '15 at 09:49
  • A real Root CA can avoid this problem (MITM attack on Root Cert download) any number of ways: publish cert (or fingerprint) in a national newspaper full page ad, copy to a thumb drive and hand carry to a browser developer, fax it, read fingerprint over the phone, hand write a note and place it in a dead drop box, ... – Andrew Philips Nov 22 '15 at 00:10