root/crypto/scatterwalk.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. memcpy_dir
  2. scatterwalk_copychunks
  3. scatterwalk_map_and_copy
  4. scatterwalk_ffwd

   1 // SPDX-License-Identifier: GPL-2.0-or-later
   2 /*
   3  * Cryptographic API.
   4  *
   5  * Cipher operations.
   6  *
   7  * Copyright (c) 2002 James Morris <jmorris@intercode.com.au>
   8  *               2002 Adam J. Richter <adam@yggdrasil.com>
   9  *               2004 Jean-Luc Cooke <jlcooke@certainkey.com>
  10  */
  11 
  12 #include <crypto/scatterwalk.h>
  13 #include <linux/kernel.h>
  14 #include <linux/mm.h>
  15 #include <linux/module.h>
  16 #include <linux/scatterlist.h>
  17 
  18 static inline void memcpy_dir(void *buf, void *sgdata, size_t nbytes, int out)
  19 {
  20         void *src = out ? buf : sgdata;
  21         void *dst = out ? sgdata : buf;
  22 
  23         memcpy(dst, src, nbytes);
  24 }
  25 
  26 void scatterwalk_copychunks(void *buf, struct scatter_walk *walk,
  27                             size_t nbytes, int out)
  28 {
  29         for (;;) {
  30                 unsigned int len_this_page = scatterwalk_pagelen(walk);
  31                 u8 *vaddr;
  32 
  33                 if (len_this_page > nbytes)
  34                         len_this_page = nbytes;
  35 
  36                 if (out != 2) {
  37                         vaddr = scatterwalk_map(walk);
  38                         memcpy_dir(buf, vaddr, len_this_page, out);
  39                         scatterwalk_unmap(vaddr);
  40                 }
  41 
  42                 scatterwalk_advance(walk, len_this_page);
  43 
  44                 if (nbytes == len_this_page)
  45                         break;
  46 
  47                 buf += len_this_page;
  48                 nbytes -= len_this_page;
  49 
  50                 scatterwalk_pagedone(walk, out & 1, 1);
  51         }
  52 }
  53 EXPORT_SYMBOL_GPL(scatterwalk_copychunks);
  54 
  55 void scatterwalk_map_and_copy(void *buf, struct scatterlist *sg,
  56                               unsigned int start, unsigned int nbytes, int out)
  57 {
  58         struct scatter_walk walk;
  59         struct scatterlist tmp[2];
  60 
  61         if (!nbytes)
  62                 return;
  63 
  64         sg = scatterwalk_ffwd(tmp, sg, start);
  65 
  66         scatterwalk_start(&walk, sg);
  67         scatterwalk_copychunks(buf, &walk, nbytes, out);
  68         scatterwalk_done(&walk, out, 0);
  69 }
  70 EXPORT_SYMBOL_GPL(scatterwalk_map_and_copy);
  71 
  72 struct scatterlist *scatterwalk_ffwd(struct scatterlist dst[2],
  73                                      struct scatterlist *src,
  74                                      unsigned int len)
  75 {
  76         for (;;) {
  77                 if (!len)
  78                         return src;
  79 
  80                 if (src->length > len)
  81                         break;
  82 
  83                 len -= src->length;
  84                 src = sg_next(src);
  85         }
  86 
  87         sg_init_table(dst, 2);
  88         sg_set_page(dst, sg_page(src), src->length - len, src->offset + len);
  89         scatterwalk_crypto_chain(dst, sg_next(src), 2);
  90 
  91         return dst;
  92 }
  93 EXPORT_SYMBOL_GPL(scatterwalk_ffwd);

/* [<][>][^][v][top][bottom][index][help] */