📄 pycrypt.tex
字号:
entropy of 8 bits. Now consider a one-byte field in a database containing aperson's sex, represented as a single character \samp{M} or \samp{F}.What's the entropy of this field? Since there are only two possiblevalues, it's not 8 bits, but one; if you were trying to guess the value,you wouldn't have to bother trying \samp{Q} or \samp{@}. Now imagine running that single byte field through a hash function thatproduces 128 bits of output. Is the entropy of the resulting hash value128 bits? No, it's still just 1 bit. The entropy is a measure of how manypossible states of the data exist. For Englishtext, the entropy of a five-character string is not 40 bits; it'ssomewhat less, because not all combinations would be seen. \samp{Guido}is a possible string, as is \samp{In th}; \samp{zJwvb} is not.The relevance to random number generation? We want enough bits ofentropy to avoid making an attack on our generator possible. Anexample: One computer system had a mechanism which generated nonsensepasswords for its users. This is a good idea, since it would preventpeople from choosing their own name or some other easily guessed string.Unfortunately, the random number generator used only had 65536 states,which meant only 65536 different passwords would ever be generated, andit was easy to compute all the possible passwords and try them. Theentropy of the random passwords was far too low. By the same token, ifyou generate an RSA key with only 32 bits of entropy available, thereare only about 4.2 billion keys you could have generated, and anadversary could compute them all to find your private key. See \rfc{1750},"Randomness Recommendations for Security", for an interesting discussionof the issues related to random number generation.The \module{randpool} module implements a strong random number generatorin the \class{RandomPool} class. The internal state consists of a stringof random data, which is returned as callers request it. The classkeeps track of the number of bits of entropy left, and provides a function toadd new random data; this data can be obtained in various ways, such asby using the variance in a user's keystroke timings. \begin{classdesc}{RandomPool}{\optional{numbytes, cipher, hash} }An object of the \code{RandomPool} class can be created withoutparameters if desired. \var{numbytes} sets the number of bytes ofrandom data in the pool, and defaults to 160 (1280 bits). \var{hash}can be a string containing the module name of the hash function to usein stirring the random data, or a module object supporting the hashinginterface. The default action is to use SHA.The \var{cipher} argument is vestigial; it was removed from version1.1 so RandomPool would work even in the limited exportable subset ofthe code. I recommend passing \var{hash} using a keyword argument sothat someday I can safely delete the \var{cipher} argument\end{classdesc}\class{RandomPool} objects define the following variables and methods:\begin{methoddesc}{add_event}{time\optional{, string}}Adds an event to the random pool. \var{time} should be set to thecurrent system time, measured at the highest resolution available.\var{string} can be a string of data that will be XORed into the pool,and can be used to increase the entropy of the pool. For example, ifyou're encrypting a document, you might use the hash value of thedocument; an adversary presumably won't have the plaintext of thedocument, and thus won't be able to use this information to break thegenerator.\end{methoddesc}The return value is the value of \member{self.entropy} after the data hasbeen added. The function works in the following manner: the timebetween successive calls to the \method{add_event()} method is determined,and the entropy of the data is guessed; the larger the time betweencalls, the better. The system time is then read and added to the pool,along with the \var{string} parameter, if present. The hope is that thelow-order bits of the time are effectively random. In an application,it is recommended that \method{add_event()} be called as frequently aspossible, with whatever random data can be found.\begin{memberdesc}{bits}A constant integer value containing the number of bits of data inthe pool, equal to the \member{bytes} attribute multiplied by 8.\end{memberdesc}\begin{memberdesc}{bytes}A constant integer value containing the number of bytes of data inthe pool.\end{memberdesc}\begin{memberdesc}{entropy}An integer value containing the number of bits of entropy currently inthe pool. The value is incremented by the \method{add_event()} method,and decreased by the \method{get_bytes()} method.\end{memberdesc}\begin{methoddesc}{get_bytes}{num}Returns a string containing \var{num} bytes of random data, anddecrements the amount of entropy available. It is not an error toreduce the entropy to zero, or to call this function when the entropyis zero. This simply means that, in theory, enough random information has beenextracted to derive the state of the generator. It is the caller'sresponsibility to monitor the amount of entropy remaining and decidewhether it is sufficent for secure operation.\end{methoddesc}\begin{methoddesc}{stir}{}Scrambles the random pool using the previously chosen encryption andhash function. An adversary may attempt to learn or alter the stateof the pool in order to affect its future output; this functiondestroys the existing state of the pool in a non-reversible way. Itis recommended that \method{stir()} be called before and after usingthe \class{RandomPool} object. Even better, several calls to\method{stir()} can be interleaved with calls to \method{add_event()}.\end{methoddesc}The \class{PersistentRandomPool} class is a subclass of \class{RandomPool} that adds the capability to save and load the pool from a disk file.\begin{classdesc}{PersistentRandomPool}{filename, \optional{numbytes, cipher, hash}}The path given in \var{filename} will be automatically opened, and anexisting random pool read; if no such file exists, the pool will beinitialized as usual. If omitted, the filename defaults to the emptystring, which will prevent it from being saved to a file. Thesearguments are identical to those for the \class{RandomPool}constructor.\end{classdesc}\begin{methoddesc}{save}{}Opens the file named by the \member{filename} attribute, and saves therandom data into the file using the \module{pickle} module.\end{methoddesc}The \class{KeyboardRandomPool} class is a subclass of\class{PersistentRandomPool} that provides a method to obtain randomdata from the keyboard:\begin{methoddesc}{randomize}{}(Unix systems only) Obtain random data from the keyboard. This worksby prompting theuser to hit keys at random, and then using the keystroke timings (andalso the actual keys pressed) to add entropy to the pool. This workssimilarly to PGP's random pool mechanism.\end{methoddesc}\subsection{Crypto.Util.RFC1751}The keys for private-key algorithms should be arbitrary binary data.Many systems err by asking the user to enter a password, and thenusing the password as the key. This limits the space of possiblekeys, as each key byte is constrained within the range of possibleASCII characters, 32-127, instead of the whole 0-255 range possiblewith ASCII. Unfortunately, it's difficult for humans to remember 16or 32 hex digits.One solution is to request a lengthy passphrase from the user, andthen run it through a hash function such as SHA or MD5. Anothersolution is discussed in RFC 1751, "A Convention for Human-Readable128-bit Keys", by Daniel L. McDonald. Binary keys are transformedinto a list of short English words that should be easier to remember.For example, the hex key EB33F77EE73D4053 is transformed to "TIDE ITCHSLOW REIN RULE MOT".\begin{funcdesc}{key_to_english}{key}Accepts a string of arbitrary data \var{key}, and returns a stringcontaining uppercase English words separated by spaces. \var{key}'slength must be a multiple of 8.\end{funcdesc}\begin{funcdesc}{english_to_key}{string}Accepts \var{string} containing English words, and returns a string ofbinary data representing the key. Words must be separated bywhitespace, and can be any mixture of uppercase and lowercasecharacters. 6 words are required for 8 bytes of key data, sothe number of words in \var{string} must be a multiple of 6.\end{funcdesc}%======================================================================\section{Extending the Toolkit}Preserving the a common interface for cryptographic routines is a goodidea. This chapter explains how to write new modules for the Toolkit.The basic process is as follows:\begin{enumerate}\item Add a new \file{.c} file containing an implementation of the newalgorithm. This file must define 3 or 4 standard functions,a few constants, and a C \code{struct} encapsulating the state variables required by the algorithm.\item Add the new algorithm to \file{setup.py}.\item Send a copy of the code to me, if you like; code for newalgorithms will be gratefully accepted.\end{enumerate}\subsection{Adding Hash Algorithms}The required constant definitions are as follows:\begin{verbatim}#define MODULE_NAME MD2 /* Name of algorithm */#define DIGEST_SIZE 16 /* Size of resulting digest in bytes */\end{verbatim}The C structure must be named \ctype{hash_state}:\begin{verbatim}typedef struct { ... whatever state variables you need ...} hash_state;\end{verbatim}There are four functions that need to be written: to initialize thealgorithm's state, to hash a string into the algorithm's state, to geta digest from the current state, and to copy a state.\begin{itemize} \item \code{void hash_init(hash_state *self);} \item \code{void hash_update(hash_state *self, unsigned char *buffer, int length);} \item \code{PyObject *hash_digest(hash_state *self);} \item \code{void hash_copy(hash_state *source, hash_state *dest);}\end{itemize}Put \code{\#include "hash_template.c"} at the end of the file toinclude the actual implementation of the module.\subsection{Adding Block Encryption Algorithms}The required constant definitions are as follows:\begin{verbatim}#define MODULE_NAME AES /* Name of algorithm */#define BLOCK_SIZE 16 /* Size of encryption block */#define KEY_SIZE 0 /* Size of key in bytes (0 if not fixed size) */\end{verbatim}The C structure must be named \ctype{block_state}:\begin{verbatim}typedef struct { ... whatever state variables you need ...} block_state;\end{verbatim}There are three functions that need to be written: to initialize thealgorithm's state, and to encrypt and decrypt a single block.\begin{itemize} \item \code{void block_init(block_state *self, unsigned char *key, int keylen);} \item \code{void block_encrypt(block_state *self, unsigned char *in, unsigned char *out);} \item \code{void block_decrypt(block_state *self, unsigned char *in, unsigned char *out);}\end{itemize}Put \code{\#include "block_template.c"} at the end of the file toinclude the actual implementation of the module.\subsection{Adding Stream Encryption Algorithms}The required constant definitions are as follows:\begin{verbatim}#define MODULE_NAME ARC4 /* Name of algorithm */#define BLOCK_SIZE 1 /* Will always be 1 for a stream cipher */#define KEY_SIZE 0 /* Size of key in bytes (0 if not fixed size) */\end{verbatim}The C structure must be named \ctype{stream_state}:\begin{verbatim}typedef struct { ... whatever state variables you need ...} stream_state;\end{verbatim}There are three functions that need to be written: to initialize thealgorithm's state, and to encrypt and decrypt a single block.\begin{itemize} \item \code{void stream_init(stream_state *self, unsigned char *key, int keylen);} \item \code{void stream_encrypt(stream_state *self, unsigned char *block, int length);} \item \code{void stream_decrypt(stream_state *self, unsigned char *block, int length);}\end{itemize}Put \code{\#include "stream_template.c"} at the end of the file toinclude the actual implementation of the module.\end{document}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -