Is there an implementation of ID-based encryption? - encryption

I've been reading up about ID-based encryption, but can't find any implementations (the maths in the paper is a bit much for me). Does anyone know where I might go looking to find an implementation? I don't really mind what language it's in.

You can try Stanford PBC or IBE toolkit

IBE permits any string of bits to be used as a public key, and the private key is derived on the fly from it by the PKG after authentication. Private key generation in this manner is not possible with methods like RSA or using classic CA's where pre generated key pairs are needed before any encryption can take place.
IBE is a different approach and avoids the need for the certificate to bind the public key to an identity: authentication and identity verification is independent and separater in an IBE scheme versus tightly coupled in legacy PKI. This means that the need to generate, bind, manage, publish, revoke, have responders for etc for public key certificates is removed. Also, given all keys are generated other than the root key(s), there's no database of public keys, no need for an escrow database etc. This makes operational matters far simpler.
Generally IBE keys are short lived too e.g. a week, an hour etc which removes the need for a revocation process as they naturally retire.
Given the public key can be any arbitrary string, this means that time can be bound into the string, as well as policy information. This provides a lot of flexibility to handle ad-hoc public key encryption and naturally permits federation - very important in cloud environments for example.
Commercial implementations exist - www.voltage.com being the most well known. Its standardized - IEEE 1363.3 and IETF 5091 et al.
http://www.ietf.org/rfc/rfc5091.txt

SSL with certificates is a form of IBE. Verisign is the PKG from the article; it generates certificates for verified and trusted network channels, which expose the RSA public key used to send messages to this endpoint. The private key is also obtained via the PKG. Now, when communicating with this endpoint, callers can encrypt with the public key from the word go, meaning no information has to be sent "cleartext".

Related

Encrypting/signing with libsodium to myself?

I've got a list of public keys, and my private key, and want to provide a signed/encrypted data value for all of them, including myself.
Is it safe to sign/encrypt to myself as to all others? In crypt_box_easy (with a random nonce which gets published), can I use the private/public keys from a single keypair?
Yes, for sure you can. In PGP it is even semi-standard for you to encrypt for yourself as well. Using your own public key doesn't leak any information about the message or private key. This reasoning is not so libsodium specific, it's likely to be valid for any PKI based protocol.
The signature generation is of course exactly identical, nothing needs to change there. It has the added benefit that you can (hopefully) trust any public key for which you manage the private key. There's no difference there.
Beware that it is generally better to use separate key pairs for encryption and signing. Please make sure that libsodium matches your needs in that regard. Key management is always the tricky part of applications that use cryptography.

Protect public RSA key during transit

*Clarification: My question relates to setting up a "secure" communication channel between two parties where a key (read passphrase) has been agreed upon in the real world. Only using RSA allows for MITM-attacks (if I'm not misstaken), so I was thinking encrypting the public keys with AES (the key that both have agreed upon) before sending them to respective parties *
I'm currently trying to build two applications that talks with eachother. To secure the exchanged messages I was thinking on using RSA where each application has it's own set of keys.
Before communication is started between the two applications they do need to exchange keys. That shouldn't be a problem but I was thinking on using AES to encrypt the public keys before sending them over the internet.
I know what the word public (as in public key) means but I was thinking that this would see to that the right application/computer gets the key and no one else.
So I want to exchange keys and to protect them from MITM attacks.
If anybody could give a better suggestion (I'm using the LibCrypto library btw), I'm all ears.
Thank you.
Best regards
/Tomas Gustavsson
This question shows many misconceptions from your part.
I know what the word public (as in public key) means but I was
thinking that this would see to that the right application/computer
gets the key and no one else.
I think this is the real problem you have and ask.
Which I think is: How can you know that you are using the public key of the entity you actually want to communicate with and not the public key of a malicious entity claiming to be the who you want to communicate with?
This problem is solved in a typical installation by certificates signed by a trusted authority and issued to the specific entity i.e. IP or DNS name.
In your case you haven't given any details of your certificates.
You could just as well manually pre-install them and use them for your secure connections.
If you follow some other plan e.g. symmetric encryption then your would start asking other questions e.g. how do you securely share the secret key etc

Static or random IV for a license file

I have made a small program that will allow me to send licenses in encrypted form to users.
At the moment I have
An RSA private key that encrypts my AES key
A single AES/CBC key that encrypts the data
An RSA public key
Both the AES and public key are hard coded onto the device.
How should I deal with the IV when a license is requested, should I create a static one on the device or send a new one with every new license I create?
If I understand what you are trying to do then, like most licensing schemes, it is basically a DRM scheme. I'll only address the cryptography problem, but there is also of course the problem of playing hide-and-seek from the hackers. You should know that no DRM scheme offers any measurable security (unless perhaps security hardware is involved) in the cryptographic sense, but they are still common and some developers are comfortable with the logic behind them.
What you want to do is generate your license data and include some information that prevents a user from simply copying a valid license file from a legitimate user. Examples might be mac address, phone number, etc. Then you sign this data. The license then consists of the unencrypted license and the signature bytes. On the user side, your installation software will verify the signature using the hard-coded public key, and perform any other checks (mac address matches, phone number matches, etc).
This would be the core of your scheme, and is enough for most developers. You can take this core and further obfuscate it using ad-hoc including encryption, splitting, etc., depending on how far you want to go with the hide-and-seek game.
EDIT:
If I may make a suggestion, I think the book Beginning Cryptography With Java would be a wise investment. It includes examples that using the Bouncycastle library. You can donwload the examples for free from the same website.
Isn't this proposal totally silly?
You should encrypt with RSA public keys not with a private key. If you encrypt with a private key as you propose then everyone with access to the public key will learn the AES key and will be able to decrypt or forge anything. Of course for the same reason you should also not use the same AES key for distinct receivers.
And to answer the question, you should use a new random IV for each AES/CBC encryption.

Which of the encryption approaches should I use?

I need a system to exchange very secret data (source code that is a trade secret). I will use Crypto++ so practically I can use all encryption algorithms, although I really prefer to use an industry standard.
Currently I'm thinking on these methods:
Have the server generate 2048/4096-bit RSA keys, send the public key over to the client, have the client encrypt the data then send it over to the server.
Use a key exchange method like Diffie-Hellman (Diffie-Hellman-Merkle to be correct) to exchange an AES-256 key.
Initiate a TLS connection and tell the server the AES key directly.
Which approach do you believe I should use? I'm not concerned about performance as long as it's reasonable; security is what matters. If none of them, please suggest another method.
P.S.: I might use chaining on the symmetric algorithm, like AES-Twofish-Serpent.
EDIT: Any recommended software must be in a license that won't restrict proprietary usage. LGPL is as restrictive as it must get. That rules out GPL.
Don't develop your own key exchange and/or key provisioning protocol(s). This is what historically breaks most products and, unless you are a cryoptographer (not a programmer with crypto experience), you'll likely get it wrong.
Use off-the-shelf protocols like SSL/TLS. Eg. TLS initialized with RSA keypairs for mutual authentication and AES session keys sounds appropiate for what you describe
Updated
Bruce Schneier:
"A colleague once told me that the world was full of bad security
systems designed by people who read
Applied Cryptography"
erickson in his post has already give you plenty of evidence why designing your own key provisioning and management protocol is flawed. I just want to drive the point home why Mallory is alive and doing quite well, thanks to overconfident developers:
You design the scheme you propose where the client encrypts with a public key and sends the document back to you. Things work great, but 1 year down the road the certificate is approaching expiration. You send an email out to your clients with the new certificate containing the public key you want your users to sign encrypts the documents with for you. Unknown to you is that over the past 4 months your ISP admin has received a bribe to route all your IP traffic through a remote machine. Your email is intercepted before distribution and your attached certificate is replaced with another one. All your clients are now sending their ultra secret documents encryted for someone else's private key. An application decrypts each one, stores it, then encrypts it with your public key and forwards the traffic to you. You won't even know is happening, untill by accident during a visit to a client's site you notice that the certificate he uses is not the one you distributed.
You mention in your post as an option to chain algorithms. Nobody is going to brute force you. Your weakness will be key management, and the attack will take some form of social engineering to fool someone is using the wrong key, or reveling the private key (again, bribes go a long way). Industry agreed protocols have steps to prevent man-in-the-middle attacks, they may rely on PKI infrastructure that recognizes designated key use and trusted authorities, they add certificate revocation list check steps to the validation etc etc. Just 'I encrypt with public key, you decrypt with private' does not make a secret safe.
I'd recommend using an existing S/MIME (or CMS) implementation with a solid cryptographic module to encrypt your content.
S/MIME enveloped data makes a nice format for storage of encrypted data "at rest": the envelope records information about the algorithms and keys used so that the information will be available to authorized recipients later, when it is needed.
Also, even if it doesn't support the "best" algorithms (like ECDH key agreement), a good library is much less likely to have vulnerabilities than something written by a general programmer. Since it is far, far more likely that security will be breached by an implementation error than cryptanalysis, it makes sense to minimize those errors.
In legitimate protocols, public keys are signed by one of a small number of trusted issuers, whose public keys are distributed by some secure means "out-of-band". If you already have a secure means to get a public key to the message sender, why bother sending another? And if you don't, you're screwed.
TLS and S/MIME depend on having a set of well known CA certificates at every client. These are used to sign the server's public key so that a client can detect attempts to substitute keys. The protocol can't bootstrap itself; there must be a secure way to distribute "trust anchors" out-of-band.
Also note that RSA is incredibly slow compared to symmetric ciphers. Real protocols generate a "content encryption key" for a symmetric algorithm like AES, then use an RSA public key as a "key encryption key" to encrypt the content encryption key for the message recipient(s).
So, the main problem is getting your public key to the client securely. If you can do that, either option #1 or #2 is good—assuming that you just use that public key, rather than trying to send another one "in-band". In fact, in CMS, Option #1 is called "key transport", and Option #2 is called "key agreement".
In practice, the "server" could use a certificate issued by a CA that is already well known, or the client can compare a hash of the certificate with one that you tell him over the phone, or carve into the face of a cliff, or whatever. The critical thing is, all of your security depends on the integrity of the certificate. You have to protect it from tampering.
While Crypto++ is an "industry standard", its security depends on how you use it. Just like Jerry told Kramer, "the door must be… closed!" Using the cryptographic primitives in Crypto++ with in a poorly designed protocol will get you nowhere. That's why I'm stressing the use of CMS (a higher-level protocol) together with a good cryptographic module (cryptographic primitives).
What about ssh ? (rsync on ssh for example) ?

What is the difference between encrypting and signing in asymmetric encryption? [closed]

Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
This question does not appear to be about programming within the scope defined in the help center.
Closed 1 year ago.
Improve this question
What is the difference between encrypting some data vs signing some data (using RSA)?
Does it simply reverse the role of the public-private keys?
For example, I want to use my private key to generate messages so only I can possibly be the sender. I want my public key to be used to read the messages and I do not care who reads them. I want to be able to encrypt certain information and use it as a product-key for my software. I only care that I am the only one who can generate these. I would like to include my public key in my software to decrypt/read the signature of the key. I do not care who can read the data in the key, I only care that I am the only verifiable one who can generate them.
Is signing useful in this scenario?
When encrypting, you use their public key to write a message and they use their private key to read it.
When signing, you use your private key to write message's signature, and they use your public key to check if it's really yours.
I want to use my private key to generate messages so only I can possibly be the sender.
I want my public key to be used to read the messages and I do not care who reads them
This is signing, it is done with your private key.
I want to be able to encrypt certain information and use it as a product key for my software.
I only care that I am the only one who can generate these.
If you only need to know it to yourself, you don't need to mess with keys to do this. You may just generate random data and keep it in a database.
But if you want people to know that the keys are really yours, you need to generate random data, keep in it a database AND sign it with your key.
I would like to include my public key in my software to decrypt/read the signature of the key.
You'll probably need to purchase a certificate for your public key from a commercial provider like Verisign or Thawte, so that people may check that no one had forged your software and replaced your public key with theirs.
In RSA crypto, when you generate a key pair, it's completely arbitrary which one you choose to be the public key, and which is the private key. If you encrypt with one, you can decrypt with the other - it works in both directions.
So, it's fairly simple to see how you can encrypt a message with the receiver's public key, so that the receiver can decrypt it with their private key.
A signature is proof that the signer has the private key that matches some public key. To do this, it would be enough to encrypt the message with that sender's private key, and include the encrypted version alongside the plaintext version. To verify the sender, decrypt the encrypted version, and check that it is the same as the plaintext.
Of course, this means that your message is not secret. Anyone can decrypt it, because the public key is well known. But when they do so, they have proved that the creator of the ciphertext has the corresponding private key.
However, this means doubling the size of your transmission - plaintext and ciphertext together (assuming you want people who aren't interested in verifying the signature, to read the message). So instead, typically a signature is created by creating a hash of the plaintext. It's important that fake hashes can't be created, so cryptographic hash algorithms such as SHA-2 are used.
So:
To generate a signature, make a hash from the plaintext, encrypt it with your private key, include it alongside the plaintext.
To verify a signature, make a hash from the plaintext, decrypt the signature with the sender's public key, check that both hashes are the same.
There are two distinct but closely related problems in establishing a secure communication
Encrypt data so that only authorized persons can decrypt and read it.
Verify the identity/authentication of sender.
Both of these problems can be elegantly solved using public key cryptography.
I. Encryption and decryption of data
Alice wants to send a message to Bob which no one should be able to read.
Alice encrypts the message with Bob's public key and sends it over.
Bob receives the message and decrypts it using his private Key.
Note that if A wants to send a message to B, A needs to use the Public
key of B (which is publicly available to anyone) and neither public
nor private key of A comes into picture here.
So if you want to send a message to me you should know and use my public key which I provide to you and only I will be able to decrypt the message since I am the only one who has access to the corresponding private key.
II. Verify the identity of sender (Authentication)
Alice wants to send a message to Bob again. The problem of encrypting the data is solved using the above method.
But what if I am sitting between Alice and Bob, introducing myself as 'Alice' to Bob and sending my own message to Bob instead of forwarding the one sent by Alice. Even though I can not decrypt and read the original message sent by Alice(that requires access to Bob's private key) I am hijacking the entire conversation between them.
Is there a way Bob can confirm that the messages he is receiving are actually sent by Alice?
Alice signs the message with her private key and sends it over. (In practice, what is signed is a hash of the message, e.g. SHA-256 or SHA-512.)
Bob receives it and verifies it using Alice's public key. Since Alice's public key successfully verified the message, Bob can conclude that the message has been signed by Alice.
Yeah think of signing data as giving it your own wax stamp that nobody else has. It is done to achieve integrity and non-repudiation. Encryption is so no-one else can see the data. This is done to achieve confidentiality. See wikipedia http://en.wikipedia.org/wiki/Information_security#Key_concepts
A signature is a hash of your message signed using your private key.
Signing is producing a "hash" with your private key that can be verified with your public key. The text is sent in the clear.
Encrypting uses the receiver's public key to encrypt the data; decoding is done with their private key.
So, the use of keys is not reversed (otherwise your private key wouldn't be private anymore!).
You are describing exactly how and why signing is used in public key cryptography. Note that it's very dangerous to sign (or encrypt) aritrary messages supplied by others - this allows attacks on the algorithms that could compromise your keys.
Signing indicates you really are the source or vouch for of the object signed. Everyone can read the object, though.
Encrypting means only those with the corresponding private key can read it, but without signing there is no guarantee you are behind the encrypted object.
Functionally, you use public/private key encryption to make certain only the receiver can read your message. The message is encrypted using the public key of the receiver and decrypted using the private key of the receiver.
Signing you can use to let the receiver know you created the message and it has not changed during transfer. Message signing is done using your own private key. The receiver can use your public key to check the message has not been tampered.
As for the algorithm used: that involves a one-way function see for example wikipedia. One of the first of such algorithms use large prime-numbers but more one-way functions have been invented since.
Search for 'Bob', 'Alice' and 'Mallory' to find introduction articles on the internet.
What is the difference between encrypting some data vs signing some data (using RSA)?
Encryption preserves confidentiality of the message ("some data"), while signing provides non-repudiation: i.e. only the entity that signed it could have signed it. There are functional differences as well; read on.
Does it simply reverse the role of the public-private keys?
Absolutely not. The use of the same private keys for signing and decryption (or, likewise, the same public keys for verification and encryption) is frowned upon, as you should not mix purposes. This is not so much a mathematical issue (RSA should still be secure), but a problem with key management, where e.g. the signing key should have a shorter live and contain more protection before it is used.
For the same message, you should use the senders private key for signing and the receivers trusted public key for encryption. Commonly sign-then-encrypt is used otherwise an adversary could replace the signature with his own. Likewise you should use the private key of the receiver for decryption and the trusted public key of the sender for verification.
Furthermore, you should understand that signature generation doesn't use "encryption with the private key". Although all RSA operations are based upon modular exponentiation, the padding scheme is entirely different for signature generation. Furthermore, the public key has entirely different properties than the RSA private key in all practical uses of RSA.
For example, I want to use my private key to generate messages so only I can possibly be the sender.
That's non-repudiation property, which can be achieved by signing.
I want my public key to be used to read the messages and I do not care who reads them.
The public key should be considered known by all. If you want everybody to read the messages, then you simply do not encrypt them.
Signing will generally not influence the content of the message. The message is is considered separate from signatures. Officially such signatures are known as "signatures with appendix" where the appendix is the message. It's a bit weird name as the message is considered more important than the signature over it, but yeah. Only few signatures offer (partial) message recovery; they are not used much anymore and are generally considered deprecated.
Note that signature protocols such as CMS may deploy a container format that includes both the message and the signature. In that case you'd need first get the - still unencrypted - message out of the container, much like unzipping a file from a plain .zip archive. So the message may be hidden from view and cannot be directly used in that case.
I want to be able to encrypt certain information and use it as a product-key for my software. I only care that I am the only one who can generate these.
Encryption is used to achieve confidentiality. In the past RSA signature generation was often thought of as "encryption with the private key". However, the operations are quite different as explained above, and the later standards desperately try and separate encryption and signature generation.
I would like to include my public key in my software to decrypt/read the signature of the key. I do not care who can read the data in the key, I only care that I am the only verifiable one who can generate them.
Yes, this is called establishing trust in the public key. However, protecting your program code is very different from protecting messages. You can perform code signing but then you'd need something to check the signature outside of your code. There are operating systems that offer this.
There is Microsoft Authenticode for instance. Application stores like the iStore and Android app store may or may not use code signing, but they offer some reassurance that your application isn't cloned or at least not cloned within the store. Cryptography is not always the solution after all.
Keeping your code from being cloned / altered at all is much harder, and you'd be solidly in DRM territory if you go that way.
Is signing useful in this scenario?
Yes, absolutely. It can certainly help making sure that the messages were only signed by you, if there is trust in the public key. If it can be helpful for authenticating your application code / integrated public key depends entirely on the environment that you expect to run the code in.
In your scenario, you do not encrypt in the meaning of asymmetric encryption; I'd rather call it "encode".
So you encode your data into some binary representation, then you sign with your private key. If you cannot verify the signature via your public key, you know that the signed data is not generated with your private key. ("verification" meaning that the unsigned data is not meaningful)
Answering this question in the content that the questioners intent was to use the solution for software licensing, the requirements are:
No 3rd party can produce a license key from decompiling the app
The content of the software key does not need to be secure
Software key is not human readable
A Digital Signature will solve this issue as the raw data that makes the key can be signed with a private key which makes it not human readable but could be decoded if reverse engineered. But the private key is safe which means no one will be able to make licenses for your software (which is the point).
Remember you can not prevent a skilled person from removing the software locks on your product. So if they have to hack each version that is released. But you really don't want them to be able to generate new keys for your product that can be shared for all versions.
Python
The PyNaCl documentation has an example of 'Digital Signature' which will suite the purpose. http://pynacl.readthedocs.org/en/latest/signing/
and of cause NaCl project to C examples
What is the difference between encrypting some data vs signing some data (using RSA)?
RSA merely the only public-key cryptosystem that naively supports both public-key encryption and digital signatures.
This usually confuses beginners since various sources/lecturers that say
RSA decryption is the RSA signature.
No, it is not!
The confusing comes from the textbook RSA
the textbook RSA encryption;
message m and calculates c = m^e mod n for encryption and m = c^d mod n for the decryption.
the textbook RSA signatures;
message m and calculates sg = m^d mod n for verification and m == sg^e mod n for the signature verification.
Both are not secure and they are not used in the real-life!
Does it simply reverse the role of the public-private keys?
No, it is not!
Encryption
For RSA encryption one must be using either RSASSA-PKCS1-v1_5 padding or Optimal Asymmetric Encryption Padding (OAEP). These paddings have overhead to the message. For example, PKCS1-v1_5 defined as
It has an EM structure as this
EM = 0x00 || 0x02 || PS || 0x00 || M.
so what are they;
PS is at least eight FFs block
M is the message
the first 0x00 guarantees that EM is less than the modulus.
The rest details like the size of FF block etc. can be found in rfc 8017 section 7.2.1
So it has a special message structure to be secure which is proven to be secure very lately (2018). The padding has at least 11-byte overhead.
Signature
The correct term for signature is signing and verification. For secure signing, RSA needs RSA-PSS (Probabilistic signature scheme). The structure is a bit complex, a picture will tell most of it
Once you hash the message and properly padded, then you can use your private key to sign your padded message!
For the verification, use the public key on the signed message and verify using the padding rules.
Prefer OAEP since RSASSA-PKCS1-v1_5 hard to implement correctly and those incorrect implementations caused many attacks over the year despite that is is proven to be secure.
Let finish all with the Cornell University page;
RSA Signing is Not RSA Decryption

Resources