123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092 |
- //*****************************************************************************
- //
- // shamd5.c - Driver for the SHA/MD5 module.
- //
- // Copyright (c) 2012-2020 Texas Instruments Incorporated. All rights reserved.
- // Software License Agreement
- //
- // Redistribution and use in source and binary forms, with or without
- // modification, are permitted provided that the following conditions
- // are met:
- //
- // Redistributions of source code must retain the above copyright
- // notice, this list of conditions and the following disclaimer.
- //
- // Redistributions in binary form must reproduce the above copyright
- // notice, this list of conditions and the following disclaimer in the
- // documentation and/or other materials provided with the
- // distribution.
- //
- // Neither the name of Texas Instruments Incorporated nor the names of
- // its contributors may be used to endorse or promote products derived
- // from this software without specific prior written permission.
- //
- // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- //
- // This is part of revision 2.2.0.295 of the Tiva Peripheral Driver Library.
- //
- //*****************************************************************************
- #include <stdbool.h>
- #include <stdint.h>
- #include "inc/hw_ints.h"
- #include "inc/hw_memmap.h"
- #include "inc/hw_nvic.h"
- #include "inc/hw_shamd5.h"
- #include "inc/hw_types.h"
- #include "driverlib/debug.h"
- #include "driverlib/interrupt.h"
- #include "driverlib/shamd5.h"
- //*****************************************************************************
- //
- //! \addtogroup shamd5_api
- //! @{
- //
- //*****************************************************************************
- //*****************************************************************************
- //
- //! Resets the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //!
- //! This function performs a soft-reset of the SHA/MD5 module using the
- //! SYSCONFIG register.
- //!
- //! \return None.
- //
- //*****************************************************************************
- void
- SHAMD5Reset(uint32_t ui32Base)
- {
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Set the soft-reset bit.
- //
- HWREG(ui32Base + SHAMD5_O_SYSCONFIG) |= SHAMD5_SYSCONFIG_SOFTRESET;
- //
- // Wait for the reset to complete.
- //
- while((HWREG(ui32Base + SHAMD5_O_SYSSTATUS) &
- SHAMD5_SYSSTATUS_RESETDONE) == 0)
- {
- }
- //
- // Force idle mode.
- //
- HWREG(ui32Base + SHAMD5_O_SYSCONFIG) =
- ((HWREG(ui32Base + SHAMD5_O_SYSCONFIG) & ~SHAMD5_SYSCONFIG_SIDLE_M) |
- SHAMD5_SYSCONFIG_SIDLE_FORCE);
- }
- //*****************************************************************************
- //
- //! Enables the uDMA requests in the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //!
- //! This function configures the DMA options of the SHA/MD5 module.
- //!
- //! \return None
- //
- //*****************************************************************************
- void
- SHAMD5DMAEnable(uint32_t ui32Base)
- {
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Write the new configuration into the register.
- //
- HWREG(ui32Base + SHAMD5_O_SYSCONFIG) |=
- SHAMD5_SYSCONFIG_SADVANCED | SHAMD5_SYSCONFIG_DMA_EN;
- }
- //*****************************************************************************
- //
- //! Disables the uDMA requests in the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //!
- //! This function configures the DMA options of the SHA/MD5 module.
- //!
- //! \return None
- //
- //*****************************************************************************
- void
- SHAMD5DMADisable(uint32_t ui32Base)
- {
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Write the new configuration into the register.
- //
- HWREG(ui32Base + SHAMD5_O_SYSCONFIG) &=
- ~(SHAMD5_SYSCONFIG_SADVANCED | SHAMD5_SYSCONFIG_DMA_EN);
- }
- //*****************************************************************************
- //
- //! Get the interrupt status of the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param bMasked is \b false if the raw interrupt status is required and
- //! \b true if the masked interrupt status is required.
- //!
- //! This function returns the current value of the IRQSTATUS register. The
- //! value will be a logical OR of the following:
- //!
- //! - \b SHAMD5_INT_CONTEXT_READY - Context input registers are ready.
- //! - \b SHAMD5_INT_PARTHASH_READY - Context output registers are ready after
- //! a context switch.
- //! - \b SHAMD5_INT_INPUT_READY - Data FIFO is ready to receive data.
- //! - \b SHAMD5_INT_OUTPUT_READY - Context output registers are ready.
- //!
- //! \return Interrupt status
- //
- //*****************************************************************************
- uint32_t
- SHAMD5IntStatus(uint32_t ui32Base, bool bMasked)
- {
- uint32_t ui32Status, ui32Enable, ui32Temp;
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Return the value of the IRQSTATUS register.
- //
- ui32Status = HWREG(ui32Base + SHAMD5_O_IRQSTATUS);
- if(bMasked)
- {
- ui32Enable = HWREG(ui32Base + SHAMD5_O_IRQENABLE);
- ui32Temp = HWREG(ui32Base + SHAMD5_O_DMAMIS);
- return((ui32Status & ui32Enable) |
- ((ui32Temp & 0x00000001) << 19) |
- ((ui32Temp & 0x00000002) << 16) |
- ((ui32Temp & 0x00000004) << 14));
- }
- else
- {
- ui32Temp = HWREG(ui32Base + SHAMD5_O_DMARIS);
- return(ui32Status |
- ((ui32Temp & 0x00000001) << 19) |
- ((ui32Temp & 0x00000002) << 16) |
- ((ui32Temp & 0x00000004) << 14));
- }
- }
- //*****************************************************************************
- //
- //! Enable interrupt sources in the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param ui32IntFlags contains desired interrupts to enable.
- //!
- //! This function enables interrupt sources in the SHA/MD5 module.
- //! ui32IntFlags must be a logical OR of one or more of the following
- //! values:
- //!
- //! - \b SHAMD5_INT_CONTEXT_READY - Context input registers are ready.
- //! - \b SHAMD5_INT_PARTHASH_READY - Context output registers are ready after
- //! a context switch.
- //! - \b SHAMD5_INT_INPUT_READY - Data FIFO is ready to receive data.
- //! - \b SHAMD5_INT_OUTPUT_READY - Context output registers are ready.
- //!
- //! \return None.
- //
- //*****************************************************************************
- void
- SHAMD5IntEnable(uint32_t ui32Base, uint32_t ui32IntFlags)
- {
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- ASSERT((ui32IntFlags == SHAMD5_INT_CONTEXT_READY) ||
- (ui32IntFlags == SHAMD5_INT_PARTHASH_READY) ||
- (ui32IntFlags == SHAMD5_INT_INPUT_READY) ||
- (ui32IntFlags == SHAMD5_INT_OUTPUT_READY));
- //
- // Enable the interrupt sources.
- //
- HWREG(ui32Base + SHAMD5_O_DMAIM) |= (((ui32IntFlags & 0x00010000) >> 14) |
- ((ui32IntFlags & 0x00020000) >> 16) |
- ((ui32IntFlags & 0x00040000) >> 19));
- HWREG(ui32Base + SHAMD5_O_IRQENABLE) |= ui32IntFlags & 0x0000ffff;
- //
- // Enable all interrupts.
- //
- HWREG(ui32Base + SHAMD5_O_SYSCONFIG) |= SHAMD5_SYSCONFIG_IT_EN;
- }
- //*****************************************************************************
- //
- //! Disable interrupt sources in the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param ui32IntFlags contains desired interrupts to disable.
- //!
- //! \e ui32IntFlags must be a logical OR of one or more of the following
- //! values:
- //!
- //! - \b SHAMD5_INT_CONTEXT_READY - Context input registers are ready.
- //! - \b SHAMD5_INT_PARTHASH_READY - Context output registers are ready after
- //! a context switch.
- //! - \b SHAMD5_INT_INPUT_READY - Data FIFO is ready to receive data.
- //! - \b SHAMD5_INT_OUTPUT_READY - Context output registers are ready.
- //!
- //! \return None.
- //
- //*****************************************************************************
- void
- SHAMD5IntDisable(uint32_t ui32Base, uint32_t ui32IntFlags)
- {
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- ASSERT((ui32IntFlags == SHAMD5_INT_CONTEXT_READY) ||
- (ui32IntFlags == SHAMD5_INT_PARTHASH_READY) ||
- (ui32IntFlags == SHAMD5_INT_INPUT_READY) ||
- (ui32IntFlags == SHAMD5_INT_OUTPUT_READY));
- //
- // Clear the corresponding flags disabling the interrupt sources.
- //
- HWREG(ui32Base + SHAMD5_O_DMAIM) &= ~(((ui32IntFlags & 0x00010000) >> 14) |
- ((ui32IntFlags & 0x00020000) >> 16) |
- ((ui32IntFlags & 0x00040000) >> 19));
- HWREG(ui32Base + SHAMD5_O_IRQENABLE) &= ~(ui32IntFlags & 0x0000ffff);
- //
- // If there are no interrupts enabled, then disable all interrupts.
- //
- if(HWREG(ui32Base + SHAMD5_O_IRQENABLE) == 0x0)
- {
- HWREG(ui32Base + SHAMD5_O_SYSCONFIG) &= ~SHAMD5_SYSCONFIG_IT_EN;
- }
- }
- //*****************************************************************************
- //
- //! Clears interrupt sources in the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param ui32IntFlags contains desired interrupts to disable.
- //!
- //! \e ui32IntFlags must be a logical OR of one or more of the following
- //! values:
- //!
- //! - \b SHAMD5_INT_CONTEXT_READY - Context input registers are ready.
- //! - \b SHAMD5_INT_PARTHASH_READY - Context output registers are ready after
- //! a context switch.
- //! - \b SHAMD5_INT_INPUT_READY - Data FIFO is ready to receive data.
- //! - \b SHAMD5_INT_OUTPUT_READY - Context output registers are ready.
- //!
- //! \return None.
- //
- //*****************************************************************************
- void
- SHAMD5IntClear(uint32_t ui32Base, uint32_t ui32IntFlags)
- {
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- ASSERT((ui32IntFlags == SHAMD5_INT_CONTEXT_READY) ||
- (ui32IntFlags == SHAMD5_INT_PARTHASH_READY) ||
- (ui32IntFlags == SHAMD5_INT_INPUT_READY) ||
- (ui32IntFlags == SHAMD5_INT_OUTPUT_READY));
- //
- // Clear the corresponding flags disabling the interrupt sources.
- //
- HWREG(ui32Base + SHAMD5_O_DMAIC) = (((ui32IntFlags & 0x00010000) >> 14) |
- ((ui32IntFlags & 0x00020000) >> 16) |
- ((ui32IntFlags & 0x00040000) >> 19));
- }
- //*****************************************************************************
- //
- //! Registers an interrupt handler for the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param pfnHandler is a pointer to the function to be called when the
- //! enabled SHA/MD5 interrupts occur.
- //!
- //! This function registers the interrupt handler in the interrupt vector
- //! table, and enables SHA/MD5 interrupts on the interrupt controller;
- //! specific SHA/MD5 interrupt sources must be enabled using
- //! SHAMD5IntEnable(). The interrupt handler being registered must clear
- //! the source of the interrupt using SHAMD5IntClear().
- //!
- //! If the application is using a static interrupt vector table stored in
- //! flash, then it is not necessary to register the interrupt handler this way.
- //! Instead, IntEnable() should be used to enable SHA/MD5 interrupts on the
- //! interrupt controller.
- //!
- //! \sa IntRegister() for important information about registering interrupt
- //! handlers.
- //!
- //! \return None.
- //
- //*****************************************************************************
- void
- SHAMD5IntRegister(uint32_t ui32Base, void (*pfnHandler)(void))
- {
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Register the interrupt handler.
- //
- IntRegister(INT_SHA0_TM4C129, pfnHandler);
- //
- // Enable the interrupt
- //
- IntEnable(INT_SHA0_TM4C129);
- }
- //*****************************************************************************
- //
- //! Unregisters an interrupt handler for the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //!
- //! This function unregisters the previously registered interrupt handler and
- //! disables the interrupt in the interrupt controller.
- //!
- //! \sa IntRegister() for important information about registering interrupt
- //! handlers.
- //!
- //! \return None.
- //
- //*****************************************************************************
- void
- SHAMD5IntUnregister(uint32_t ui32Base)
- {
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Disable the interrupt.
- //
- IntDisable(INT_SHA0_TM4C129);
- //
- // Unregister the interrupt handler.
- //
- IntUnregister(INT_SHA0_TM4C129);
- }
- //*****************************************************************************
- //
- //! Write the hash length to the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param ui32Length is the hash length in bytes.
- //!
- //! This function writes the length of the hash data of the current operation
- //! to the SHA/MD5 module. The value must be a multiple of 64 if the close
- //! hash is not set in the mode register.
- //!
- //! \note When this register is written, hash processing is triggered.
- //!
- //! \return None.
- //
- //*****************************************************************************
- void
- SHAMD5HashLengthSet(uint32_t ui32Base, uint32_t ui32Length)
- {
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Set the LENGTH register and start processing.
- //
- HWREG(ui32Base + SHAMD5_O_LENGTH) = ui32Length;
- }
- //*****************************************************************************
- //
- //! Writes the mode in the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param ui32Mode is the mode of the SHA/MD5 module.
- //!
- //! This function writes the mode register configuring the SHA/MD5 module.
- //!
- //! The ui32Mode parameter is a bit-wise OR of values:
- //!
- //! - \b SHAMD5_ALGO_MD5 - Regular hash with MD5
- //! - \b SHAMD5_ALGO_SHA1 - Regular hash with SHA-1
- //! - \b SHAMD5_ALGO_SHA224 - Regular hash with SHA-224
- //! - \b SHAMD5_ALGO_SHA256 - Regular hash with SHA-256
- //! - \b SHAMD5_ALGO_HMAC_MD5 - HMAC with MD5
- //! - \b SHAMD5_ALGO_HMAC_SHA1 - HMAC with SHA-1
- //! - \b SHAMD5_ALGO_HMAC_SHA224 - HMAC with SHA-224
- //! - \b SHAMD5_ALGO_HMAC_SHA256 - HMAC with SHA-256
- //!
- //! \return None
- //
- //*****************************************************************************
- void
- SHAMD5ConfigSet(uint32_t ui32Base, uint32_t ui32Mode)
- {
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- ASSERT((ui32Mode == SHAMD5_ALGO_MD5) ||
- (ui32Mode == SHAMD5_ALGO_SHA1) ||
- (ui32Mode == SHAMD5_ALGO_SHA224) ||
- (ui32Mode == SHAMD5_ALGO_SHA256) ||
- (ui32Mode == SHAMD5_ALGO_HMAC_MD5) ||
- (ui32Mode == SHAMD5_ALGO_HMAC_SHA1) ||
- (ui32Mode == SHAMD5_ALGO_HMAC_SHA224) ||
- (ui32Mode == SHAMD5_ALGO_HMAC_SHA256));
- //
- // Write the value in the MODE register.
- //
- HWREG(ui32Base + SHAMD5_O_MODE) = ui32Mode;
- }
- //*****************************************************************************
- //
- //! Perform a non-blocking write of 16 words of data to the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param pui32Src is the pointer to the 16-word array of data that will be
- //! written.
- //!
- //! This function writes 16 words of data into the data register regardless
- //! of whether or not the module is ready to accept the data.
- //!
- //! \return This function returns true if the write completed successfully.
- //! It returns false if the module was not ready.
- //
- //*****************************************************************************
- bool
- SHAMD5DataWriteNonBlocking(uint32_t ui32Base, uint32_t *pui32Src)
- {
- uint32_t ui32Counter;
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Check that the SHA/MD5 module is ready for data. If not, return false.
- //
- if((HWREG(ui32Base + SHAMD5_O_IRQSTATUS) & SHAMD5_INT_INPUT_READY) == 0)
- {
- return(false);
- }
- //
- // Write the 16 words of data.
- //
- for(ui32Counter = 0; ui32Counter < 64; ui32Counter += 4)
- {
- HWREG(ui32Base + SHAMD5_O_DATA_0_IN + ui32Counter) = *pui32Src++;
- }
- //
- // Return true as a sign of successfully completing the function.
- //
- return(true);
- }
- //*****************************************************************************
- //
- //! Perform a blocking write of 16 words of data to the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param pui32Src is the pointer to the 16-word array of data that will be
- //! written.
- //!
- //! This function does not return until the module is ready to accept data and
- //! the data has been written.
- //!
- //! \return None.
- //
- //*****************************************************************************
- void
- SHAMD5DataWrite(uint32_t ui32Base, uint32_t *pui32Src)
- {
- uint32_t ui32Counter;
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Wait for the module to be ready to accept data.
- //
- while((HWREG(ui32Base + SHAMD5_O_IRQSTATUS) & SHAMD5_INT_INPUT_READY) == 0)
- {
- }
- //
- // Write the 16 words of data.
- //
- for(ui32Counter = 0; ui32Counter < 64; ui32Counter += 4)
- {
- HWREG(ui32Base + SHAMD5_O_DATA_0_IN + ui32Counter) = *pui32Src++;
- }
- }
- //*****************************************************************************
- //
- //! Reads the result of a hashing operation.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param pui32Dest is the pointer to the 16-word array of data that will be
- //! written.
- //!
- //! This function does not return until the module is ready to accept data and
- //! the data has been written.
- //!
- //! \return None.
- //
- //*****************************************************************************
- void
- SHAMD5ResultRead(uint32_t ui32Base, uint32_t *pui32Dest)
- {
- uint32_t ui32Idx, ui32Count;
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Determine the number of bytes in the result, based on the hash type.
- //
- switch(HWREG(ui32Base + SHAMD5_O_MODE) & SHAMD5_MODE_ALGO_M)
- {
- //
- // The MD5 hash is being used.
- //
- case SHAMD5_MODE_ALGO_MD5:
- {
- //
- // There are 16 bytes in the MD5 hash.
- //
- ui32Count = 16;
- //
- // Done.
- //
- break;
- }
- //
- // The SHA-1 hash is being used.
- //
- case SHAMD5_MODE_ALGO_SHA1:
- {
- //
- // There are 20 bytes in the SHA-1 hash.
- //
- ui32Count = 20;
- //
- // Done.
- //
- break;
- }
- //
- // The SHA-224 hash is being used.
- //
- case SHAMD5_MODE_ALGO_SHA224:
- {
- //
- // There are 28 bytes in the SHA-224 hash.
- //
- ui32Count = 28;
- //
- // Done.
- //
- break;
- }
- //
- // The SHA-256 hash is being used.
- //
- case SHAMD5_MODE_ALGO_SHA256:
- {
- //
- // There are 32 bytes in the SHA-256 hash.
- //
- ui32Count = 32;
- //
- // Done.
- //
- break;
- }
- //
- // The hash type is not recognized.
- //
- default:
- {
- //
- // Return without reading a result since the hardware appears to be
- // misconfigured.
- //
- return;
- }
- }
- //
- // Read the hash result.
- //
- for(ui32Idx = 0; ui32Idx < ui32Count; ui32Idx += 4)
- {
- *pui32Dest++ = HWREG(ui32Base + SHAMD5_O_IDIGEST_A + ui32Idx);
- }
- }
- //*****************************************************************************
- //
- //! Writes multiple words of data into the SHA/MD5 data registers.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param pui32DataSrc is a pointer to an array of data to be written.
- //! \param ui32DataLength is the length of the data to be written in bytes.
- //!
- //! This function writes a variable number of words into the SHA/MD5 data
- //! registers. The function waits for each block of data to be processed
- //! before another is written. The \e ui32DataLength parameter must be a
- //! multiple of 4 to fall on a word boundry.
- //!
- //! \note This function is used by SHAMD5DataProcess() and SHAMD5HMACProcess()
- //! to process data.
- //!
- //! \return None.
- //
- //*****************************************************************************
- static void
- _SHAMD5DataWriteMultiple(uint32_t ui32Base, uint32_t *pui32DataSrc,
- uint32_t ui32DataLength)
- {
- uint32_t ui32Idx, ui32Count;
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Calculate the number of blocks of data.
- //
- ui32Count = ui32DataLength / 64;
- //
- // Loop through all the blocks and write them into the data registers
- // making sure to block additional operations until we can write the
- // next 16 words.
- //
- for(ui32Idx = 0; ui32Idx < ui32Count; ui32Idx++)
- {
- //
- // Write the block of data.
- //
- SHAMD5DataWrite(ui32Base, pui32DataSrc);
- //
- // Increment the pointer to next block of data.
- //
- pui32DataSrc += 16;
- }
- //
- // Calculate the remaining bytes of data that don't make up a full block.
- //
- ui32Count = ui32DataLength % 64;
- //
- // If there are bytes that do not make up a whole block, then
- // write them separately.
- //
- if(ui32Count)
- {
- //
- // Wait until the engine has finished processing the previous block.
- //
- while((HWREG(ui32Base + SHAMD5_O_IRQSTATUS) &
- SHAMD5_INT_INPUT_READY) == 0)
- {
- }
- //
- // Loop through the remaining words.
- //
- for(ui32Idx = 0; ui32Idx < ui32Count; ui32Idx += 4)
- {
- //
- // Write the word into the data register.
- //
- HWREG(ui32Base + SHAMD5_O_DATA_0_IN + ui32Idx) = *pui32DataSrc++;
- }
- }
- }
- //*****************************************************************************
- //
- //! Compute a hash using the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param pui32DataSrc is a pointer to an array of data that contains the
- //! data that will be hashed.
- //! \param ui32DataLength specifies the length of the data to be hashed in
- //! bytes.
- //! \param pui32HashResult is a pointer to an array that holds the result
- //! of the hashing operation.
- //!
- //! This function computes the hash of an array of data using the SHA/MD5
- //! module.
- //!
- //! The length of the hash result is dependent on the algorithm that is in use.
- //! The following table shows the correct array size for each algorithm:
- //!
- //! -----------------------------------------
- //! | Algorithm | Number of Words in Result |
- //! -----------------------------------------
- //! | MD5 | 4 Words (128 bits) |
- //! | SHA-1 | 5 Words (160 bits) |
- //! | SHA-224 | 7 Words (224 bits) |
- //! | SHA-256 | 8 Words (256 bits) |
- //! -----------------------------------------
- //!
- //! \return None
- //
- //*****************************************************************************
- void
- SHAMD5DataProcess(uint32_t ui32Base, uint32_t *pui32DataSrc,
- uint32_t ui32DataLength, uint32_t *pui32HashResult)
- {
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- ASSERT((ui32DataLength % 64) == 0);
- //
- // Wait for the context to be ready before writing the mode.
- //
- while((HWREG(ui32Base + SHAMD5_O_IRQSTATUS) & SHAMD5_INT_CONTEXT_READY) ==
- 0)
- {
- }
- //
- // Write the length.
- //
- SHAMD5HashLengthSet(ui32Base, ui32DataLength);
- //
- // Write the data.
- //
- _SHAMD5DataWriteMultiple(ui32Base, pui32DataSrc, ui32DataLength);
- //
- // Wait for the output to be ready.
- //
- while((HWREG(ui32Base + SHAMD5_O_IRQSTATUS) & SHAMD5_INT_OUTPUT_READY) ==
- 0)
- {
- }
- //
- // Read the result.
- //
- SHAMD5ResultRead(ui32Base, pui32HashResult);
- }
- //*****************************************************************************
- //
- //! Compute a HMAC with key pre-processing using the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param pui32DataSrc is a pointer to an array of data that contains the
- //! data that is to be hashed.
- //! \param ui32DataLength specifies the length of the data to be hashed in
- //! bytes.
- //! \param pui32HashResult is a pointer to an array that holds the result
- //! of the hashing operation.
- //!
- //! This function computes a HMAC with the given data using the SHA/MD5
- //! module with a preprocessed key.
- //!
- //! The length of the hash result is dependent on the algorithm that is
- //! selected with the \e ui32Algo argument. The following table shows the
- //! correct array size for each algorithm:
- //!
- //! -----------------------------------------
- //! | Algorithm | Number of Words in Result |
- //! -----------------------------------------
- //! | MD5 | 4 Words (128 bits) |
- //! | SHA-1 | 5 Words (160 bits) |
- //! | SHA-224 | 7 Words (224 bits) |
- //! | SHA-256 | 8 Words (256 bits) |
- //! -----------------------------------------
- //!
- //! \return None
- //
- //*****************************************************************************
- void
- SHAMD5HMACProcess(uint32_t ui32Base, uint32_t *pui32DataSrc,
- uint32_t ui32DataLength, uint32_t *pui32HashResult)
- {
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Wait for the context to be ready before writing the mode.
- //
- while((HWREG(ui32Base + SHAMD5_O_IRQSTATUS) & SHAMD5_INT_CONTEXT_READY) ==
- 0)
- {
- }
- //
- // Write the length.
- //
- SHAMD5HashLengthSet(ui32Base, ui32DataLength);
- //
- // Write the data in the registers.
- //
- _SHAMD5DataWriteMultiple(ui32Base, pui32DataSrc, ui32DataLength);
- //
- // Wait for the output to be ready.
- //
- while((HWREG(ui32Base + SHAMD5_O_IRQSTATUS) & SHAMD5_INT_OUTPUT_READY) ==
- 0)
- {
- }
- //
- // Read the result.
- //
- SHAMD5ResultRead(ui32Base, pui32HashResult);
- }
- //*****************************************************************************
- //
- //! Process an HMAC key using the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param pui32Key is a pointer to an array that contains the key to be
- //! processed.
- //! \param pui32PPKey is the pointer to the array that contains the
- //! pre-processed key.
- //!
- //! This function processes an HMAC key using the SHA/MD5. The resultant
- //! pre-processed key can then be used with later HMAC operations to speed
- //! processing time.
- //!
- //! The \e pui32Key array must be 16 words (512 bits) long. If the key is less
- //! than 512 bits, it must be padded with zeros. The \e pui32PPKey array must
- //! each be 16 words (512 bits) long.
- //!
- //! \return None
- //
- //*****************************************************************************
- void
- SHAMD5HMACPPKeyGenerate(uint32_t ui32Base, uint32_t *pui32Key,
- uint32_t *pui32PPKey)
- {
- uint32_t ui32Index;
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Wait for the context to be ready before writing the mode.
- //
- while((HWREG(ui32Base + SHAMD5_O_IRQSTATUS) & SHAMD5_INT_CONTEXT_READY) ==
- 0)
- {
- }
- //
- // Write the HMAC key.
- //
- for(ui32Index = 0; ui32Index < 64; ui32Index += 4)
- {
- HWREG(ui32Base + SHAMD5_O_ODIGEST_A + ui32Index) = *pui32Key++;
- }
- //
- // Set the flag to cause the HMAC key to be pre-processed.
- //
- HWREG(ui32Base + SHAMD5_O_MODE) |= SHAMD5_MODE_HMAC_KEY_PROC;
- //
- // Set the length to zero to start the HMAC key pre-processing.
- //
- HWREG(ui32Base + SHAMD5_O_LENGTH) = 0;
- //
- // Wait for key to be processed.
- //
- while((HWREG(ui32Base + SHAMD5_O_IRQSTATUS) & SHAMD5_INT_OUTPUT_READY) ==
- 0)
- {
- }
- //
- // Read the pre-processed key from the SHA/MD5 module.
- //
- for(ui32Index = 0; ui32Index < 64; ui32Index += 4)
- {
- *pui32PPKey++ = HWREG(ui32Base + SHAMD5_O_ODIGEST_A + ui32Index);
- }
- }
- //*****************************************************************************
- //
- //! Writes an HMAC key to the digest registers in the SHA/MD5 module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param pui32Src is the pointer to the 16-word array of the HMAC key.
- //!
- //! This function is used to write HMAC key to the digest registers for
- //! key preprocessing. The size of pui32Src must be 512 bytes. If the key is
- //! less than 512 bytes, then it must be padded with zeros.
- //!
- //! \note It is recommended to use the SHAMD5IntStatus() function to check
- //! whether the context is ready before writing the key.
- //!
- //! \return None
- //
- //*****************************************************************************
- void
- SHAMD5HMACKeySet(uint32_t ui32Base, uint32_t *pui32Src)
- {
- uint32_t ui32Idx;
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Write the key to the digest registers.
- //
- for(ui32Idx = 0; ui32Idx < 64; ui32Idx += 4)
- {
- HWREG(ui32Base + SHAMD5_O_ODIGEST_A + ui32Idx) = *pui32Src++;
- }
- //
- // Configure the SHA engine for HMAC operation.
- //
- HWREG(ui32Base + SHAMD5_O_MODE) |= (SHAMD5_MODE_HMAC_OUTER_HASH |
- SHAMD5_MODE_HMAC_KEY_PROC |
- SHAMD5_MODE_CLOSE_HASH);
- }
- //*****************************************************************************
- //
- //! Writes a pre-processed HMAC key to the digest registers in the SHA/MD5
- //! module.
- //!
- //! \param ui32Base is the base address of the SHA/MD5 module.
- //! \param pui32Src is the pointer to the 16-word array of the HMAC key.
- //!
- //! This function is used to write HMAC key to the digest registers for
- //! key preprocessing. The size of pui32Src must be 512 bytes. If the key is
- //! less than 512 bytes, then it must be padded with zeros.
- //!
- //! \note It is recommended to use the SHAMD5IntStatus() function to check
- //! whether the context is ready before writing the key.
- //!
- //! \return None
- //
- //*****************************************************************************
- void
- SHAMD5HMACPPKeySet(uint32_t ui32Base, uint32_t *pui32Src)
- {
- uint32_t ui32Idx;
- //
- // Check the arguments.
- //
- ASSERT(ui32Base == SHAMD5_BASE);
- //
- // Write the key to the digest registers.
- //
- for(ui32Idx = 0; ui32Idx < 64; ui32Idx += 4)
- {
- HWREG(ui32Base + SHAMD5_O_ODIGEST_A + ui32Idx) = *pui32Src++;
- }
- //
- // Configure the SHA engine to continue the HMAC.
- //
- HWREG(ui32Base + SHAMD5_O_MODE) |= (SHAMD5_MODE_HMAC_OUTER_HASH |
- SHAMD5_MODE_CLOSE_HASH);
- //
- // Write the digest count to 64 to account for the preprocessed key.
- //
- HWREG(ui32Base + SHAMD5_O_DIGEST_COUNT) = 64;
- }
- //*****************************************************************************
- //
- // Close the Doxygen group.
- //! @}
- //
- //*****************************************************************************
|