I am not an expert (not even a novice :))) in security certificates and such - thus the question - but I was wondering if one can generate a new certificate by using a known fingerprint? :D (lost my certificate for a google play app and was wondering about this workaround)
Thanks.
This is practically impossible. The fingerprint uses a cryptographic hash like SHA-1 or SHA-256. With current technology it is impossible for a normal user to create the input which results in a specific hash value. It is doable with lots of efforts (i.e. still very very expensive) when MD5 was used for the fingerprint (not common), it might be doable by the NSA for SHA-1 and it is considered impossible to do it today for SHA-256.
Apart from that certificates are commonly not validated by the fingerprint but because a trusted CA has signed this certificate. This signature is part of the certificate so that you would not only need to recreate the certificate but also somehow get a valid signature which is impossible without having the private key of the CA which of course you don't.
Related
Looking at LetsEncrypt FAQ page, they have clearly stated that email encryption and code signing require a different type of certificate and therefore they are not supported by LetsEncrypt.
My understanding is that https and S/MIME both require X.509 certificates. What is the difference between certificates these two technologies require?
Among other things (like the encryption key), an X.509 certificate also specifies what it may be used for. X.509 certificates for HTTPS and S/MIME usage basically have different usages.
The structure of an X.509 certificate is fairly complex. Its possible usage depends on attributes and extensions within the certificate, and require that specific combinations of them with specific values must be present.
For example, an S/MIME certificate, requires a Key Usage attribute with something like Encrypt, Verify, Wrap, Derive, a Key Usage extension that must have the Critical attribute set to Yes and include a Usage attribute with Key Encipherment plus in the Extended Key Usage extension (sic!) it should list the Purpose attribute value Email Protection.
Note that Key Usage extension Data Encipherment is not required, because in S/MIME, the data contents are encrypted by a random symmetric key which then is encrypted with the private key from the certificate. This is called hybrid encryption and it is done for performance and scalability reasons.
The certificate requirements even extend into the certificate chain, meaning that the certificate must be signed by another certificate that has been issued to sign certificates for that usage.
Note that the above example may not be 100% correct, because the subject is so complex, and I don't fully understand every aspect of it myself. I found this quote which I think describes the situation fairly well:
I think a lot of purists would rather have PKI be useless to anyone in
any practical terms than to have it made simple enough to use, but
potentially "flawed". — Chris Zimman
Resources that helped me:
X.509 Style Guide by Peter Gutmann: an attempt to shed light on the relations of attributes and extensions and their interpretations
RFC 4262 - X.509 Certificate Extension for Secure/Multipurpose Internet Mail Extensions (S/MIME) Capabilities
Might be an unqualified question, but are there any encryption systems where two encryption keys are generated (one public, one private), and...
A) The public key is used for encrypting the information, but cannot be used to decrypt it
B) The private key is used for decrypting the information, and cannot be used to encrypt it.
I am asking because I see this as the only practical way to secure a login session to a web service (such as a forum) without the use of SSL/HTTPS. Though, with my limited knowledge of system security and cryptography, it's more than likely that I'm wrong.
The most common private key encryption algorithm is RSA. However, if you don't know what you're doing, stick to higher level constructs such as SSL/TLS.
I was arguing about an S3 like aproach using authorization hash with a secret key as the seed and some data on the request as the message signed with hmac sha1 (Amazon S3 way) vs an other developer supporting symetric encryption of the data with a secret key known by the emiter and the server.
What are the advantage of using signed data with hmac sha1 vs symetric key other than the fact that with the former, we do not need to encrypt the username or password.
What would be the hardest to break ? symetric encryption or sha1 hashing at la S3 ?
If all big players are using oauth and similar without symetric key it is sure that there are obvious advantages, what are those ?
An hmac and a symmetric cipher are not mutually exclusive ideas. In fact AES-CMAC which is both an MAC (not hashed) and a symmetric cipher, AES-CMAC is the cryptographic primitive that makes WPA secure. (Although a WPA can still be broken using a rainbow table).
You should not need an exotic authentication system for this. Logging in with a username and password and maintaining session state with a cookie is commonly used because it is easy to implement and it is secure. By storing state, like a cookie its no longer technically RESTful, but there is nothing stopping you from doing it.
However, in terms of authentication I believe that asymmetric cryptography like RSA is the most secure. (Amazon uses asymmetric cryptography for ssh connections by default.) This allows you to only store the public keys, so that if your server where to be compromised no authentication credentials could be used. It also defends against MITM attacks. In many cases this can be implanted quite easily with REST because HTTPS already supports client certificates. You can sign the clients certificates for free and then verify them your self.
If implemented properly, the strength of an hmac vs symmetric cipher it mostly comes down to the strength of the secret. If you are using a secret like a password, then both systems are equally very weak. These secretes must be large, Cryptographically Secure Psudorandom Numbers. Another thing to keep in mind is that symmetric ciphers are very difficult to implement properly. Most programmers do not understand this and end up reusing PRNG when using stream cipher or when using a block cipher they use an incorrect mode and leave the IV null. By contrast HMACS are very easy to implement and less can go wrong. If everything is transmitted over HTTPS, and your are using an hmac then its easy to implement a secure authentication system. If you really want to implement a symmetric cipher you must get a copy of Piratical Cryptography, there are a few chapters devoted to symmetric ciphers alone because so much can go horribly wrong. You also have to take key distribution into consideration, ssl uses a DH-Key Exchange for its symmetric keys.
Make sure to read the OWASP top 10, especially Broken Authentication and Session Management. This requires the use of https for the entire session, most web application programmers don't realize this.
The big differences would be that HMAC would provide integrity but no privacy, while encryption would provide privacy without integrity. Many use cases would require both, but I can't think of any where integrity is unnecessary. HMAC seems like a minimum requirement, with encryption being a likely companion.
I'm not a cryptography expert, I actually only have a little bit of experience using it at all. Anyways, the time has come where one of my applications demands that I have some encryption set up. Please note, the program won't be managing anything super critical that will be able to cause a lot of damage.
Anyways, I was just trying to see if this scheme that I'm using is common and if there are flaws (of which there may be completely stupid & horribly flawed design, that's why I'm asking).
Ok, I have a client -> server communication. The Client I can hard code in the public portion of a 2048-bit RSA key. When the client wants to initiate a secure connection, he sends his username, md5 hash of his password, and a hash of a random UUID, all of which has been encrypted against the server's Public Key. The server receives the information and decrypts using its private key. Checks the database to see if his login + pass work & if they do, create a new entry in the "Sessions" table in the DB. This includes a SessionID, UID (user ID), and the UUID hash. Using the corresponding session ID's UUID as the keyphrase, the server will then send back a message that has the Blowfish encrypted word "Success!" + a random UUID (this message is Digitally Signed so we can determine if it came from the server or not). From that point on, when the client sends info to the server, it will be with a plaintext sess_id & include a Blowfish encrypted message, using the corresponding Session ID's blowfish secret (stored encrypted in the DB) as the key to encrypt / decrypt.
Specifically, I am curious as to whether this system "should work" or if anyone notices that it's glaringly obvious that a vulnerability exists, such as MITM.
Issues I can see off the top of my head (although you have left out most of the details, which is where the devil famously resides):
If you're using a UUID generator rather than a real cryptographic RNG, it likely has insufficient entropy. Don't discount this - in the real world, the favourite way of covertly weakening an encryption system has been to weaken the RNG;
Your initial RSA encryption sounds like it is susceptible to a small-exponent attack, and potentially other creative attacks. There's too much structure there to be comfortable;
It sounds like there's numerous opportunities for replay attacks;
What block cipher mode are you using with Blowfish?
I recommend using TLS/SSL - it's had a lot more friendly eyes looking at it for a lot longer than anything you build yourself ever will.
Just use SSL or DTLS, IKEv2, HIP, EAP or some suitable standard protocol. Don't try to invent your own crypto protocols, nobody has enough expertise to do this on their own. Your protocol doesn't have nearly enough entropy in it, so far as I can see, so your resulting keys will be pretty weak.
From that point on, when the client sends info to the server, it will be with a plaintext sess_id & include a Blowfish encrypted message, using the corresponding Session ID as the key to encrypt / decrypt.
If you're sending the session id in plaintext, and using it as the encryption key, how is that secure?
I see no reason why you can't use standard SSL authentication and let the library implementer worry about the handshaking.
Question for all the SSL experts out there:
We have an embedded device with a little web server on it, and we can install our own SSL self-signed certificates on it. The client is written in .NET (but that doesn't matter so much).
How can I authenticate the device in .NET? Is it enough to compare the fingerprint of the certificate against a known entry in the database?
My understanding is that the fingerprint is a hash of the whole certificate, including the public key. A device faking to be my device could of course send the same public certificate, but it couldn't know the private key, right?
Or do I have to build up my own chain of trust, create my own CA root certificate, sign the web server certificate and install that on the client?
What you propose is in principle ok. It is for example used during key signing parties. Here the participants usually just exchange their name and fingerprints of their public keys and make sure that the person at the party really is who he/she claims. Just verifying fingerprints is much easier than to verify a long public key.
Another example is the so called self certifying file system. Here again only hashes of public keys get exchanged over a secure channel. (I.e. these hashes are embedded in URLs.) In this scheme the public keys don't have to be sent securely. The receiver only has to check that the hash of the public keys matche the hashes embedded in the URLs. Of course the receiver also has to make sure that these URLs come from a trusted source.
This scheme and what you propose are simpler than using a CA. But there is a disadvantage. You have to make sure that your database with hashes is authentic. If your database is large then this will likeley be difficult. If you use CAs then you only have to ensure that the root keys are authentic. This usually simplifies the key management significantly and is of course one reason, why CA based schemes are more popular than e.g. the self certifying file system mentioned above.
In the same way you wouldn't and shouldn't consider two objects to be equal just because their hash codes matched, you shouldn't consider a certificate to be authentic just because its fingerprint appears in a list of "known certificate fingerprints".
Collisions are a fact of life with hash algorithms, even good ones, and you should guard against the possibility that a motivated attacker could craft a rogue certificate with a matching fingerprint hash. The only way to guard against that is to check the validity of the certificate itself, i.e. check the chain of trust as you're implying in your last statement.
Short:
Well in theory you then do exactly what a Certificate Authority does for you. So it should be fine.
Longer:
When a Certificate Authority signs your public-key/certificate/certificate request it doesn't sign the whole certificate data. But just the calculated hash value of the whole certificate data.
This keeps the signature small.
When you don't want to establish your own CA or use a commercial/free one -
by comparing the fingerprint with the one you trust you'll gain the second most trustworthy configuration. The most trustworthy solution would be by comparing the whole certificate, because also protects you from hash collision attacks.
As the other guys here stated you should make sure to use a secure/safe hashing algorithm. SHA-1 is no longer secure.
more detailed informations to this topic:
https://security.stackexchange.com/questions/6737
https://security.stackexchange.com/questions/14330