Back to home page

OSCL-LXR

 
 

    


0001 Code Examples
0002 =============
0003 
0004 Code Example For Symmetric Key Cipher Operation
0005 -----------------------------------------------
0006 
0007 This code encrypts some data with AES-256-XTS.  For sake of example,
0008 all inputs are random bytes, the encryption is done in-place, and it's
0009 assumed the code is running in a context where it can sleep.
0010 
0011 ::
0012 
0013     static int test_skcipher(void)
0014     {
0015             struct crypto_skcipher *tfm = NULL;
0016             struct skcipher_request *req = NULL;
0017             u8 *data = NULL;
0018             const size_t datasize = 512; /* data size in bytes */
0019             struct scatterlist sg;
0020             DECLARE_CRYPTO_WAIT(wait);
0021             u8 iv[16];  /* AES-256-XTS takes a 16-byte IV */
0022             u8 key[64]; /* AES-256-XTS takes a 64-byte key */
0023             int err;
0024 
0025             /*
0026              * Allocate a tfm (a transformation object) and set the key.
0027              *
0028              * In real-world use, a tfm and key are typically used for many
0029              * encryption/decryption operations.  But in this example, we'll just do a
0030              * single encryption operation with it (which is not very efficient).
0031              */
0032 
0033             tfm = crypto_alloc_skcipher("xts(aes)", 0, 0);
0034             if (IS_ERR(tfm)) {
0035                     pr_err("Error allocating xts(aes) handle: %ld\n", PTR_ERR(tfm));
0036                     return PTR_ERR(tfm);
0037             }
0038 
0039             get_random_bytes(key, sizeof(key));
0040             err = crypto_skcipher_setkey(tfm, key, sizeof(key));
0041             if (err) {
0042                     pr_err("Error setting key: %d\n", err);
0043                     goto out;
0044             }
0045 
0046             /* Allocate a request object */
0047             req = skcipher_request_alloc(tfm, GFP_KERNEL);
0048             if (!req) {
0049                     err = -ENOMEM;
0050                     goto out;
0051             }
0052 
0053             /* Prepare the input data */
0054             data = kmalloc(datasize, GFP_KERNEL);
0055             if (!data) {
0056                     err = -ENOMEM;
0057                     goto out;
0058             }
0059             get_random_bytes(data, datasize);
0060 
0061             /* Initialize the IV */
0062             get_random_bytes(iv, sizeof(iv));
0063 
0064             /*
0065              * Encrypt the data in-place.
0066              *
0067              * For simplicity, in this example we wait for the request to complete
0068              * before proceeding, even if the underlying implementation is asynchronous.
0069              *
0070              * To decrypt instead of encrypt, just change crypto_skcipher_encrypt() to
0071              * crypto_skcipher_decrypt().
0072              */
0073             sg_init_one(&sg, data, datasize);
0074             skcipher_request_set_callback(req, CRYPTO_TFM_REQ_MAY_BACKLOG |
0075                                                CRYPTO_TFM_REQ_MAY_SLEEP,
0076                                           crypto_req_done, &wait);
0077             skcipher_request_set_crypt(req, &sg, &sg, datasize, iv);
0078             err = crypto_wait_req(crypto_skcipher_encrypt(req), &wait);
0079             if (err) {
0080                     pr_err("Error encrypting data: %d\n", err);
0081                     goto out;
0082             }
0083 
0084             pr_debug("Encryption was successful\n");
0085     out:
0086             crypto_free_skcipher(tfm);
0087             skcipher_request_free(req);
0088             kfree(data);
0089             return err;
0090     }
0091 
0092 
0093 Code Example For Use of Operational State Memory With SHASH
0094 -----------------------------------------------------------
0095 
0096 ::
0097 
0098 
0099     struct sdesc {
0100         struct shash_desc shash;
0101         char ctx[];
0102     };
0103 
0104     static struct sdesc *init_sdesc(struct crypto_shash *alg)
0105     {
0106         struct sdesc *sdesc;
0107         int size;
0108 
0109         size = sizeof(struct shash_desc) + crypto_shash_descsize(alg);
0110         sdesc = kmalloc(size, GFP_KERNEL);
0111         if (!sdesc)
0112             return ERR_PTR(-ENOMEM);
0113         sdesc->shash.tfm = alg;
0114         return sdesc;
0115     }
0116 
0117     static int calc_hash(struct crypto_shash *alg,
0118                  const unsigned char *data, unsigned int datalen,
0119                  unsigned char *digest)
0120     {
0121         struct sdesc *sdesc;
0122         int ret;
0123 
0124         sdesc = init_sdesc(alg);
0125         if (IS_ERR(sdesc)) {
0126             pr_info("can't alloc sdesc\n");
0127             return PTR_ERR(sdesc);
0128         }
0129 
0130         ret = crypto_shash_digest(&sdesc->shash, data, datalen, digest);
0131         kfree(sdesc);
0132         return ret;
0133     }
0134 
0135     static int test_hash(const unsigned char *data, unsigned int datalen,
0136                  unsigned char *digest)
0137     {
0138         struct crypto_shash *alg;
0139         char *hash_alg_name = "sha1-padlock-nano";
0140         int ret;
0141 
0142         alg = crypto_alloc_shash(hash_alg_name, 0, 0);
0143         if (IS_ERR(alg)) {
0144                 pr_info("can't alloc alg %s\n", hash_alg_name);
0145                 return PTR_ERR(alg);
0146         }
0147         ret = calc_hash(alg, data, datalen, digest);
0148         crypto_free_shash(alg);
0149         return ret;
0150     }
0151 
0152 
0153 Code Example For Random Number Generator Usage
0154 ----------------------------------------------
0155 
0156 ::
0157 
0158 
0159     static int get_random_numbers(u8 *buf, unsigned int len)
0160     {
0161         struct crypto_rng *rng = NULL;
0162         char *drbg = "drbg_nopr_sha256"; /* Hash DRBG with SHA-256, no PR */
0163         int ret;
0164 
0165         if (!buf || !len) {
0166             pr_debug("No output buffer provided\n");
0167             return -EINVAL;
0168         }
0169 
0170         rng = crypto_alloc_rng(drbg, 0, 0);
0171         if (IS_ERR(rng)) {
0172             pr_debug("could not allocate RNG handle for %s\n", drbg);
0173             return PTR_ERR(rng);
0174         }
0175 
0176         ret = crypto_rng_get_bytes(rng, buf, len);
0177         if (ret < 0)
0178             pr_debug("generation of random numbers failed\n");
0179         else if (ret == 0)
0180             pr_debug("RNG returned no data");
0181         else
0182             pr_debug("RNG returned %d bytes of data\n", ret);
0183 
0184     out:
0185         crypto_free_rng(rng);
0186         return ret;
0187     }