Introduction To Cryptography
Traditional use of cryptography:
plaintext
>>>>>>>>>> ciphertext >>>>>>>>> plaintext
(encryption) (decryption)
cryptographer: invent clever secret codes.
cryptanalyst: attempt
to break these codes.
Fundamental Tenet of
Cryptography:
If lots of smart people failed to solve a problem,
then it probably won't be
solved (soon).
Ø The time required to break a code
should be longer than
the time the encrypted data
must remain secret.
Ø The value of most data decreases overtime.
Cryptographic System: Algorithm
+ Key
It is perfectly OK to let everyone know the algorithm because knowledge of the algorithm without the key does not help unmangle the information.
Publishing the algorithm provides an enormous
amount of free consulting to uncover weaknesses.
Computational Difficulty:
Example: combination lock
Ø Typically require 3 numbers between 1 and 40.
If it takes 10
seconds for a good guy,
it would take 10*(40**3) seconds or about 1 week for the bad guy.
Ø By requiring 4 numbers,
If it takes 13 seconds for
the good guy,
it would take 13*(40**4) seconds or about 1 year for the bad guy!
In general, increasing the key length by 1 bit makes the good guy's job just a little bit harder, but makes the bad guy's job twice as hard!
Example of Secret Codes:
Caesar cipher: substitute each letter with another
letter which is 3 letters away in the alphabet (with wrap
around).
E.g., dozen >>> grchq.
Extension: Instead
of 3 use any number n between 1 and 25.
E.g., for n=1, HAL >>> IBM.
Monoalphabetic cipher: arbitrary map one letter to another.
There are 26!=4*(10**26)
possibilities.
Ø If each possibility takes 1 microsecond it would take 10 trillion years to try all possibilities.
Ø However statistical analysis of language makes it much easier
to break.
Breaking An Encryption Scheme
Ciphertext Only: Because it is important for Trudy to be
able to differentiate plaintext from gibberish, this attack sometime known as recognizable plaintext attack.
It is also essential for Trudy
to have enough
ciphertext, e.g.,
there is no way to know the plaintext corresponding to XYZ is THE or CAT or HAT.
Known Plaintext: Knowing <plaintext, ciphertext> pairs is helpful for Trudy,
e.g., in monoalphabetic cipher
Trudy learn the mapping.
How to obtain plaintext? secret data might not remain secret
forever,
e.g., which city to attack might
not be secret after that attack!
Chosen Plaintext: Trudy can choose any plaintext he wants and get the system to provide corresponding ciphertext, e.g., telegraph company can encrypt and send any message you provide.
Example: If Trudy knows that
Types of Cryptographic Functions:
(encryption)
plaintext >>>>>>>>> ciphertext
|
key
|
ciphertext
>>>>>>>>
plaintext
(decryption)
Can be used for:
An eavesdropper will only see unintelligible data.
Forgetting the key makes the data irrevocably lost.
challenge: r >>>>>>> r
response:
K{r} <<<<<<< K{r}
r is a random number,
K{r} is the secret
key encryption of r using shared key K.
Each individual has two keys:
private key (not revealed to anyone)
public key (make it known to everyone)
(encryption)
plaintext
>>>>>>>>>>
ciphertext
|
public key
private
key
|
ciphertext
>>>>>>>>>
plaintext
(decryption)
The reverse process is called digital signature:
(signing)
plaintext
>>>>>>>>>
ciphertext
|
private key
public key
|
ciphertext
>>>>>>>>
plaintext
(verification)
Ø Public key cryptographic algorithms are orders of magnitude slower than the best known secret key cryptographic algorithms.
Ø Thus they normally used to establish temporary shared secret key for use during a session.
Uses of Public Key Cryptography:
{K}eB >>>>>>>>>
[K]dB
K{mB}
>>>>>>>>>
K{mB}
K{mA} <<<<<<<<< K{mA}
K is a random session key.
<eB, dB> is the <public-key , private-key> pair for Bob.
{m}eB is the public key encryption of message m with eB.
[m]dB is the public key decryption of message m with dB.
K{m} is the symmetric key encryption of message m with K.
mB message for Bob.
mA message for
F= K{File}
KF= {K}eA
To restore the file:
K= [KF]dA
File = K{F}
challenge: c = { r }eB >>>>> c
response:
r
<<<<<
r = [c]dB
r is a random number
(also known as message digest /fingerprint,
one-way functions
)
The
hash of a message m, h=H(m) has the following properties:
Uses of Hash Algorithms:
Using Secret Key:
m,h where h =
H(m|K) >>>>>
m,h , OK if h =
H (m|K)
K is the shared secret between Alice and Bob
Ø Bob is sure that Alice sent the message, since she knows K.
Ø Bob can NOT prove to any one that Alice sent him
message m, since he also knows K.
Using Public Key:
m,sh where sh = [H(m)]dA
>> m,sh , OK if H (m) = {sh}eA
<eA, dA> is the
public/private key pair of
Ø Bob is sure that Alice sent the message, since she knows dA.
Ø He can also prove to any one that
This property
of public key cryptography is known as non-repudiation,
where
the sender should not be able to falsely deny that he sent a message.
OS like UNIX stores the hash of passwords instead of storing the actual passwords.
Ø For each user U, there is a tuple <U, h>
where h
= H(P) is
the hash of password P of
Ø When a user U types a password, P, the OS
compute H(P) and
if it is equal to the saved
value h in the tuple <U,h>, the user is OK.
The magic of XOR:
A Simple XOR symmetric
algorithm:
(from
Bruce
Shneier textbook)
0 ® 0 = 0
0 ® 1 = 1
1 ® 0 = 1
1 ® 1 = 0
Note that:
x ®
x = 0
x ® 0
= x
The following program is a very simple symmetric algorithm.
(see /home/cs772/public_html/demos/xor
)
Ø To encrypt: the plaintext P is XORed with a key K to produce a ciphertext C.
Ø To decrypt: the ciphertext C is XORed with a key K to produce a plaintext P.
Why?
P ® K = C
C ® K = P
Since C ® K = (P ® K) ® K = P ® (K ® K) = P ® 0 = P
This is a
very insecure algorithm that can be easily broken.
It is good enough to keep "your
kid sister" from reading your files!
crypto
Usage:
%
crypto
<key>
<input_file>
<output_file>
Example:
Ø
To encrypt
infile:
% crypto
"odu computer science"
infile outfile
Ø
To decrypt
outfile:
% crypto
"odu computer science"
outfile tmpfile
tmpfile is identical to infile
Code
void main (int argc, char *argv[])
{
FILE *fi,
*fo;
char *cp;
int c;
if ((cp = argv[1]) && *cp!='\0') {
if ((fi = fopen(argv[2], “rb”)) != NULL) {
if ((fo = fopen(argv[3], “wb”)) != NULL) {
while ((c = getc(fi)) !=
EOF) {
if (!*cp) cp = argv[1];
c ^= *(cp++);
putc(c,fo);
}
fclose(fo);
}
fclose(fi);
}
}
}