xref: /isa-l_crypto/include/sha256_mb.h (revision 672a042c19c7c87254f91480c1dd123e38f226e0)
1 /**********************************************************************
2   Copyright(c) 2011-2016 Intel Corporation All rights reserved.
3 
4   Redistribution and use in source and binary forms, with or without
5   modification, are permitted provided that the following conditions
6   are met:
7     * Redistributions of source code must retain the above copyright
8       notice, this list of conditions and the following disclaimer.
9     * Redistributions in binary form must reproduce the above copyright
10       notice, this list of conditions and the following disclaimer in
11       the documentation and/or other materials provided with the
12       distribution.
13     * Neither the name of Intel Corporation nor the names of its
14       contributors may be used to endorse or promote products derived
15       from this software without specific prior written permission.
16 
17   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18   "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
19   LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
20   A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
21   OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
22   SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
23   LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24   DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25   THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26   (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
27   OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 **********************************************************************/
29 
30 #ifndef _SHA256_MB_H_
31 #define _SHA256_MB_H_
32 
33 /**
34  *  @file sha256_mb.h
35  *  @brief Multi-buffer CTX API SHA256 function prototypes and structures
36  *
37  * Interface for multi-buffer SHA256 functions
38  *
39  * <b> Multi-buffer SHA256  Entire or First-Update..Update-Last </b>
40  *
41  * The interface to this multi-buffer hashing code is carried out through the
42  * context-level (CTX) init, submit and flush functions and the ISAL_SHA256_HASH_CTX_MGR and
43  * ISAL_SHA256_HASH_CTX objects. Numerous ISAL_SHA256_HASH_CTX objects may be instantiated by the
44  * application for use with a single ISAL_SHA256_HASH_CTX_MGR.
45  *
46  * The CTX interface functions carry out the initialization and padding of the jobs
47  * entered by the user and add them to the multi-buffer manager. The lower level "scheduler"
48  * layer then processes the jobs in an out-of-order manner. The scheduler layer functions
49  * are internal and are not intended to be invoked directly. Jobs can be submitted
50  * to a CTX as a complete buffer to be hashed, using the ISAL_HASH_ENTIRE flag, or as partial
51  * jobs which can be started using the ISAL_HASH_FIRST flag, and later resumed or finished
52  * using the ISAL_HASH_UPDATE and ISAL_HASH_LAST flags respectively.
53  *
54  * <b>Note:</b> The submit function does not require data buffers to be block sized.
55  *
56  * The SHA256 CTX interface functions are available for 4 architectures: SSE, AVX, AVX2 and
57  * AVX512. In addition, a multibinary interface is provided, which selects the appropriate
58  * architecture-specific function at runtime.
59  *
60  * <b>Usage:</b> The application creates a ISAL_SHA256_HASH_CTX_MGR object and initializes it
61  * with a call to sha256_ctx_mgr_init*() function, where henceforth "*" stands for the
62  * relevant suffix for each architecture; _sse, _avx, _avx2, _avx512(or no suffix for the
63  * multibinary version). The ISAL_SHA256_HASH_CTX_MGR object will be used to schedule processor
64  * resources, with up to 4 ISAL_SHA256_HASH_CTX objects (or 8 in the AVX2 case, 16 in the AVX512)
65  * being processed at a time.
66  *
67  * Each ISAL_SHA256_HASH_CTX must be initialized before first use by the isal_hash_ctx_init macro
68  * defined in multi_buffer.h. After initialization, the application may begin computing
69  * a hash by giving the ISAL_SHA256_HASH_CTX to a ISAL_SHA256_HASH_CTX_MGR using the submit
70  * functions sha256_ctx_mgr_submit*() with the ISAL_HASH_FIRST flag set. When the
71  * ISAL_SHA256_HASH_CTX is returned to the application (via this or a later call to
72  * sha256_ctx_mgr_submit*() or sha256_ctx_mgr_flush*()), the application can then re-submit it with
73  * another call to sha256_ctx_mgr_submit*(), but without the ISAL_HASH_FIRST flag set.
74  *
75  * Ideally, on the last buffer for that hash, sha256_ctx_mgr_submit is called with
76  * ISAL_HASH_LAST, although it is also possible to submit the hash with ISAL_HASH_LAST and a zero
77  * length if necessary. When a ISAL_SHA256_HASH_CTX is returned after having been submitted with
78  * ISAL_HASH_LAST, it will contain a valid hash. The ISAL_SHA256_HASH_CTX can be reused immediately
79  * by submitting with ISAL_HASH_FIRST.
80  *
81  * For example, you would submit hashes with the following flags for the following numbers
82  * of buffers:
83  * <ul>
84  *  <li> one buffer: ISAL_HASH_FIRST | ISAL_HASH_LAST  (or, equivalently, ISAL_HASH_ENTIRE)
85  *  <li> two buffers: ISAL_HASH_FIRST, ISAL_HASH_LAST
86  *  <li> three buffers: ISAL_HASH_FIRST, ISAL_HASH_UPDATE, ISAL_HASH_LAST
87  * etc.
88  * </ul>
89  *
90  * The order in which SHA256_CTX objects are returned is in general different from the order
91  * in which they are submitted.
92  *
93  * A few possible error conditions exist:
94  * <ul>
95  *  <li> Submitting flags other than the allowed entire/first/update/last values
96  *  <li> Submitting a context that is currently being managed by a ISAL_SHA256_HASH_CTX_MGR.
97  *  <li> Submitting a context after ISAL_HASH_LAST is used but before ISAL_HASH_FIRST is set.
98  * </ul>
99  *
100  *  These error conditions are reported by returning the ISAL_SHA256_HASH_CTX immediately after
101  *  a submit with its error member set to a non-zero error code (defined in
102  *  multi_buffer.h). No changes are made to the ISAL_SHA256_HASH_CTX_MGR in the case of an
103  *  error; no processing is done for other hashes.
104  *
105  */
106 
107 #include <stdint.h>
108 #include <string.h>
109 #include "multi_buffer.h"
110 #include "types.h"
111 
112 #ifndef _MSC_VER
113 #include <stdbool.h>
114 #endif
115 
116 #ifdef __cplusplus
117 extern "C" {
118 #endif
119 
120 /*
121  * Define enums from API v2.24, so applications that were using this version
122  * will still be compiled successfully.
123  * This list does not need to be extended for new definitions.
124  */
125 #ifndef NO_COMPAT_ISAL_CRYPTO_API_2_24
126 /***** Previous hash constants and typedefs *****/
127 #define SHA256_DIGEST_NWORDS       ISAL_SHA256_DIGEST_NWORDS
128 #define SHA256_PADLENGTHFIELD_SIZE ISAL_SHA256_PADLENGTHFIELD_SIZE
129 #define SHA256_MAX_LANES           ISAL_SHA256_MAX_LANES
130 #define SHA256_MIN_LANES           ISAL_SHA256_MIN_LANES
131 #define SHA256_BLOCK_SIZE          ISAL_SHA256_BLOCK_SIZE
132 #define SHA256_WORD_T              ISAL_SHA256_WORD_T
133 
134 /***** Previous structure definitions *****/
135 #define SHA256_JOB          ISAL_SHA256_JOB
136 #define SHA256_MB_ARGS_X16  ISAL_SHA256_MB_ARGS_X16
137 #define SHA256_LANE_DATA    ISAL_SHA256_LANE_DATA
138 #define SHA256_MB_JOB_MGR   ISAL_SHA256_MB_JOB_MGR
139 #define SHA256_HASH_CTX_MGR ISAL_SHA256_HASH_CTX_MGR
140 #define SHA256_HASH_CTX     ISAL_SHA256_HASH_CTX
141 #endif /* !NO_COMPAT_ISAL_CRYPTO_API_2_24 */
142 
143 // Hash Constants and Typedefs
144 #define ISAL_SHA256_DIGEST_NWORDS       8
145 #define ISAL_SHA256_MAX_LANES           16
146 #define ISAL_SHA256_MIN_LANES           4
147 #define ISAL_SHA256_BLOCK_SIZE          64
148 #define ISAL_SHA256_PADLENGTHFIELD_SIZE 8
149 
150 typedef uint32_t sha256_digest_array[ISAL_SHA256_DIGEST_NWORDS][ISAL_SHA256_MAX_LANES];
151 typedef uint32_t ISAL_SHA256_WORD_T;
152 
153 /** @brief Scheduler layer - Holds info describing a single SHA256 job for the multi-buffer manager
154  */
155 
156 typedef struct {
157         uint8_t *buffer; //!< pointer to data buffer for this job
158         uint64_t len;    //!< length of buffer for this job in blocks.
159         DECLARE_ALIGNED(uint32_t result_digest[ISAL_SHA256_DIGEST_NWORDS], 64);
160         ISAL_JOB_STS status; //!< output job status
161         void *user_data;     //!< pointer for user's job-related data
162 } ISAL_SHA256_JOB;
163 
164 /** @brief Scheduler layer -  Holds arguments for submitted SHA256 job */
165 
166 typedef struct {
167         sha256_digest_array digest;
168         uint8_t *data_ptr[ISAL_SHA256_MAX_LANES];
169 } ISAL_SHA256_MB_ARGS_X16;
170 
171 /** @brief Scheduler layer - Lane data */
172 
173 typedef struct {
174         ISAL_SHA256_JOB *job_in_lane;
175 } ISAL_SHA256_LANE_DATA;
176 
177 /** @brief Scheduler layer - Holds state for multi-buffer SHA256 jobs */
178 
179 typedef struct {
180         ISAL_SHA256_MB_ARGS_X16 args;
181         DECLARE_ALIGNED(uint32_t lens[ISAL_SHA256_MAX_LANES], 16);
182         uint64_t unused_lanes; //!< each nibble is index (0...3 or 0...7) of unused lanes, nibble 4
183                                //!< or 8 is set to F as a flag
184         ISAL_SHA256_LANE_DATA ldata[ISAL_SHA256_MAX_LANES];
185         uint32_t num_lanes_inuse;
186 } ISAL_SHA256_MB_JOB_MGR;
187 
188 /** @brief Context layer - Holds state for multi-buffer SHA256 jobs */
189 
190 typedef struct {
191         ISAL_SHA256_MB_JOB_MGR mgr;
192 } ISAL_SHA256_HASH_CTX_MGR;
193 
194 /** @brief Context layer - Holds info describing a single SHA256 job for the multi-buffer CTX
195  * manager This structure must be allocated to 16-byte aligned memory */
196 
197 typedef struct {
198         ISAL_SHA256_JOB job;             // Must be at struct offset 0.
199         ISAL_HASH_CTX_STS status;        //!< Context status flag
200         ISAL_HASH_CTX_ERROR error;       //!< Context error flag
201         uint64_t total_length;           //!< Running counter of length processed for this CTX's job
202         const void *incoming_buffer;     //!< pointer to data input buffer for this CTX's job
203         uint32_t incoming_buffer_length; //!< length of buffer for this job in bytes.
204         uint8_t partial_block_buffer[ISAL_SHA256_BLOCK_SIZE * 2]; //!< CTX partial blocks
205         uint32_t partial_block_buffer_length;
206         void *user_data; //!< pointer for user to keep any job-related data
207 } ISAL_SHA256_HASH_CTX;
208 
209 /******************** multibinary function prototypes **********************/
210 
211 /**
212  * @brief Initialize the SHA256 multi-buffer manager structure.
213  * @requires SSE4.1 or AVX or AVX2
214  * @deprecated Please use isal_sha256_ctx_mgr_init() instead.
215  *
216  * @param mgr	Structure holding context level state info
217  * @returns void
218  */
219 ISAL_DEPRECATED("Please use isal_sha256_ctx_mgr_init() instead")
220 void
221 sha256_ctx_mgr_init(ISAL_SHA256_HASH_CTX_MGR *mgr);
222 
223 /**
224  * @brief  Submit a new SHA256 job to the multi-buffer manager.
225  * @requires SSE4.1 or AVX or AVX2
226  * @deprecated Please use isal_sha256_ctx_mgr_submit() instead.
227  *
228  * @param  mgr Structure holding context level state info
229  * @param  ctx Structure holding ctx job info
230  * @param  buffer Pointer to buffer to be processed
231  * @param  len Length of buffer (in bytes) to be processed
232  * @param  flags Input flag specifying job type (first, update, last or entire)
233  * @returns NULL if no jobs complete or pointer to jobs structure.
234  */
235 ISAL_DEPRECATED("Please use isal_sha256_ctx_mgr_submit() instead")
236 ISAL_SHA256_HASH_CTX *
237 sha256_ctx_mgr_submit(ISAL_SHA256_HASH_CTX_MGR *mgr, ISAL_SHA256_HASH_CTX *ctx, const void *buffer,
238                       uint32_t len, ISAL_HASH_CTX_FLAG flags);
239 
240 /**
241  * @brief Finish all submitted SHA256 jobs and return when complete.
242  * @requires SSE4.1 or AVX or AVX2
243  * @deprecated Please use isal_sha256_ctx_mgr_flush() instead.
244  *
245  * @param mgr	Structure holding context level state info
246  * @returns NULL if no jobs to complete or pointer to jobs structure.
247  */
248 ISAL_DEPRECATED("Please use isal_sha256_ctx_mgr_flush() instead")
249 ISAL_SHA256_HASH_CTX *
250 sha256_ctx_mgr_flush(ISAL_SHA256_HASH_CTX_MGR *mgr);
251 
252 /**
253  * @brief Initialize the SHA256 multi-buffer manager structure.
254  * @requires SSE4.1 for x86 or ASIMD for ARM
255  *
256  * @param[in] mgr Structure holding context level state info
257  * @return Operation status
258  * @retval 0 on success
259  * @retval Non-zero \a ISAL_CRYPTO_ERR on failure
260  */
261 int
262 isal_sha256_ctx_mgr_init(ISAL_SHA256_HASH_CTX_MGR *mgr);
263 
264 /**
265  * @brief  Submit a new SHA256 job to the multi-buffer manager.
266  * @requires SSE4.1 for x86 or ASIMD for ARM
267  *
268  * @param[in] mgr Structure holding context level state info
269  * @param[in] ctx_in Structure holding ctx job info
270  * @param[out] ctx_out	Pointer address to output job ctx info.
271  *			Modified to point to completed job structure or
272  *			NULL if no jobs completed.
273  * @param[in] buffer Pointer to buffer to be processed
274  * @param[in] len Length of buffer (in bytes) to be processed
275  * @param[in] flags Input flag specifying job type (first, update, last or entire)
276  * @return Operation status
277  * @retval 0 on success
278  * @retval Non-zero \a ISAL_CRYPTO_ERR on failure
279  */
280 int
281 isal_sha256_ctx_mgr_submit(ISAL_SHA256_HASH_CTX_MGR *mgr, ISAL_SHA256_HASH_CTX *ctx_in,
282                            ISAL_SHA256_HASH_CTX **ctx_out, const void *buffer, const uint32_t len,
283                            const ISAL_HASH_CTX_FLAG flags);
284 
285 /**
286  * @brief Finish all submitted SHA256 jobs and return when complete.
287  * @requires SSE4.1 for x86 or ASIMD for ARM
288  *
289  * @param[in] mgr Structure holding context level state info
290  * @param[out] ctx_out	Pointer address to output job ctx info.
291  *			Modified to point to completed job structure or
292  *			NULL if no jobs completed.
293  * @return Operation status
294  * @retval 0 on success
295  * @retval Non-zero \a ISAL_CRYPTO_ERR on failure
296  */
297 int
298 isal_sha256_ctx_mgr_flush(ISAL_SHA256_HASH_CTX_MGR *mgr, ISAL_SHA256_HASH_CTX **ctx_out);
299 #ifdef __cplusplus
300 }
301 #endif
302 
303 #endif // _SHA256_MB_H_
304