The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/contrib/openzfs/module/icp/core/kcf_prov_lib.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 /*
    2  * CDDL HEADER START
    3  *
    4  * The contents of this file are subject to the terms of the
    5  * Common Development and Distribution License (the "License").
    6  * You may not use this file except in compliance with the License.
    7  *
    8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
    9  * or https://opensource.org/licenses/CDDL-1.0.
   10  * See the License for the specific language governing permissions
   11  * and limitations under the License.
   12  *
   13  * When distributing Covered Code, include this CDDL HEADER in each
   14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
   15  * If applicable, add the following below this CDDL HEADER, with the
   16  * fields enclosed by brackets "[]" replaced with your own identifying
   17  * information: Portions Copyright [yyyy] [name of copyright owner]
   18  *
   19  * CDDL HEADER END
   20  */
   21 /*
   22  * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
   23  * Use is subject to license terms.
   24  */
   25 
   26 #include <sys/zfs_context.h>
   27 #include <modes/modes.h>
   28 #include <sys/crypto/common.h>
   29 #include <sys/crypto/impl.h>
   30 
   31 /*
   32  * Utility routine to copy a buffer to a crypto_data structure.
   33  */
   34 
   35 /*
   36  * Utility routine to apply the command COPY_TO_DATA to the
   37  * data in the uio structure.
   38  */
   39 static int
   40 crypto_uio_copy_to_data(crypto_data_t *data, uchar_t *buf, int len)
   41 {
   42         zfs_uio_t *uiop = data->cd_uio;
   43         off_t offset = data->cd_offset;
   44         size_t length = len;
   45         uint_t vec_idx;
   46         size_t cur_len;
   47         uchar_t *datap;
   48 
   49         ASSERT(data->cd_format == CRYPTO_DATA_UIO);
   50         if (zfs_uio_segflg(uiop) != UIO_SYSSPACE) {
   51                 return (CRYPTO_ARGUMENTS_BAD);
   52         }
   53 
   54         /*
   55          * Jump to the first iovec containing data to be
   56          * processed.
   57          */
   58         offset = zfs_uio_index_at_offset(uiop, offset, &vec_idx);
   59 
   60         if (vec_idx == zfs_uio_iovcnt(uiop) && length > 0) {
   61                 /*
   62                  * The caller specified an offset that is larger than
   63                  * the total size of the buffers it provided.
   64                  */
   65                 return (CRYPTO_DATA_LEN_RANGE);
   66         }
   67 
   68         while (vec_idx < zfs_uio_iovcnt(uiop) && length > 0) {
   69                 cur_len = MIN(zfs_uio_iovlen(uiop, vec_idx) -
   70                     offset, length);
   71 
   72                 datap = (uchar_t *)(zfs_uio_iovbase(uiop, vec_idx) + offset);
   73                 memcpy(datap, buf, cur_len);
   74                 buf += cur_len;
   75 
   76                 length -= cur_len;
   77                 vec_idx++;
   78                 offset = 0;
   79         }
   80 
   81         if (vec_idx == zfs_uio_iovcnt(uiop) && length > 0) {
   82                 /*
   83                  * The end of the specified iovecs was reached but
   84                  * the length requested could not be processed.
   85                  */
   86                 data->cd_length = len;
   87                 return (CRYPTO_BUFFER_TOO_SMALL);
   88         }
   89 
   90         return (CRYPTO_SUCCESS);
   91 }
   92 
   93 int
   94 crypto_put_output_data(uchar_t *buf, crypto_data_t *output, int len)
   95 {
   96         switch (output->cd_format) {
   97         case CRYPTO_DATA_RAW:
   98                 if (output->cd_raw.iov_len < len) {
   99                         output->cd_length = len;
  100                         return (CRYPTO_BUFFER_TOO_SMALL);
  101                 }
  102                 memcpy((uchar_t *)(output->cd_raw.iov_base +
  103                     output->cd_offset), buf, len);
  104                 break;
  105 
  106         case CRYPTO_DATA_UIO:
  107                 return (crypto_uio_copy_to_data(output, buf, len));
  108         default:
  109                 return (CRYPTO_ARGUMENTS_BAD);
  110         }
  111 
  112         return (CRYPTO_SUCCESS);
  113 }
  114 
  115 int
  116 crypto_update_iov(void *ctx, crypto_data_t *input, crypto_data_t *output,
  117     int (*cipher)(void *, caddr_t, size_t, crypto_data_t *))
  118 {
  119         ASSERT(input != output);
  120 
  121         if (input->cd_raw.iov_len < input->cd_length)
  122                 return (CRYPTO_ARGUMENTS_BAD);
  123 
  124         return ((cipher)(ctx, input->cd_raw.iov_base + input->cd_offset,
  125             input->cd_length, output));
  126 }
  127 
  128 int
  129 crypto_update_uio(void *ctx, crypto_data_t *input, crypto_data_t *output,
  130     int (*cipher)(void *, caddr_t, size_t, crypto_data_t *))
  131 {
  132         zfs_uio_t *uiop = input->cd_uio;
  133         off_t offset = input->cd_offset;
  134         size_t length = input->cd_length;
  135         uint_t vec_idx;
  136         size_t cur_len;
  137 
  138         ASSERT(input != output);
  139 
  140         if (zfs_uio_segflg(input->cd_uio) != UIO_SYSSPACE) {
  141                 return (CRYPTO_ARGUMENTS_BAD);
  142         }
  143 
  144         /*
  145          * Jump to the first iovec containing data to be
  146          * processed.
  147          */
  148         offset = zfs_uio_index_at_offset(uiop, offset, &vec_idx);
  149         if (vec_idx == zfs_uio_iovcnt(uiop) && length > 0) {
  150                 /*
  151                  * The caller specified an offset that is larger than the
  152                  * total size of the buffers it provided.
  153                  */
  154                 return (CRYPTO_DATA_LEN_RANGE);
  155         }
  156 
  157         /*
  158          * Now process the iovecs.
  159          */
  160         while (vec_idx < zfs_uio_iovcnt(uiop) && length > 0) {
  161                 cur_len = MIN(zfs_uio_iovlen(uiop, vec_idx) -
  162                     offset, length);
  163 
  164                 int rv = (cipher)(ctx, zfs_uio_iovbase(uiop, vec_idx) + offset,
  165                     cur_len, output);
  166 
  167                 if (rv != CRYPTO_SUCCESS) {
  168                         return (rv);
  169                 }
  170                 length -= cur_len;
  171                 vec_idx++;
  172                 offset = 0;
  173         }
  174 
  175         if (vec_idx == zfs_uio_iovcnt(uiop) && length > 0) {
  176                 /*
  177                  * The end of the specified iovec's was reached but
  178                  * the length requested could not be processed, i.e.
  179                  * The caller requested to digest more data than it provided.
  180                  */
  181 
  182                 return (CRYPTO_DATA_LEN_RANGE);
  183         }
  184 
  185         return (CRYPTO_SUCCESS);
  186 }

Cache object: 5da43ef09351cf591ea8921166dbca2a


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.