我们能否在多线程环境中以轮询模式使用 SHA2和 AES 驱动程序来实现同步处理? 在这种同时访问的情况下,我们会看到异常行为,SHA 函数 addData()不会返回。
This thread has been locked.
If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.
我们能否在多线程环境中以轮询模式使用 SHA2和 AES 驱动程序来实现同步处理? 在这种同时访问的情况下,我们会看到异常行为,SHA 函数 addData()不会返回。
通过修改 ti\simplelink_cc13x2_26x2_sdk_5_10_00_48\examples\rtos\CC26X2R1_LAUNCHXL\drivers\sha2hash 下的现有示例工程、我能够非常轻松地重现此情况。 一旦 PuTTY 停止打印任何新数据, 即不会返回 SHA2_addData()。 我已附加两个更新的项目源文件。 在 sha2hash-c 中搜索"问题"、其中函数在问题后从未返回。
因为论坛不允许我创建 syscfg 文件。
/**
*生成此文件时使用了这些参数。 它们将自动应用于后续加载
*通过 GUI 或 CLI。 使用'--help'运行 CLI 以获取有关如何覆盖这些参数的其他信息。
*@clipArgs -板"/ti/boards/CC26X2R1_LAUNCHXL -产品"simplelink_cc13x2_26x2_sdk@5.10.00.48
*@版本{"data":"2021031521"、"时间戳":"2021031521"、"工具":"1.8.0+1863"、"模板":空}
*
/**
*导入此配置中使用的模块。
*
const AESCM=scripting.AddModule ("/ti/drivers/AESCCM、{}、false);
const AESCM1 = AESCM.addInstance();
const RTOS = scripting.AddModule ("/ti/drivers/RTOS);
const SHA2 = scripting.AddModule ("/ti/drivers/SHA2);
CONST SHA21 = SHA2.addInstance();
const UART = scripting.AddModule ("/ti/drivers/UART);
const UART1 = UART.addInstance();
/**
*将自定义配置值写入导入的模块。
*
AESCM1.$name ="CONFIG_AESCM_0";
const CCFG = scripting.AddModule ("/ti/devices/CCFG、{}、false);
CCFG.ccfgTemplate。$name ="ti_devices_CCFGTemplate0";
SHA21.$name ="CONFIG_SHA2_0";
UART1。$name ="CONFIG_UART_0";
UART1.$hardware = system.deviceData.board.components.XDS110UART;
UART1.txPinInstance.$name ="CONFIG_PIN_0";
UART1.rxPinInstance.$name ="CONFIG_PIN_1";
/**
*用于解锁引脚/外设的 Pinmux 解决方案。 这可确保将来对自动解算器进行细微更改
*该工具的版本不会影响您最初看到的引脚多路复用器。 可以完全删除这些行、以便
*从头开始重新解决。
*
UART1.UART.$建议解决方案="UART1";
UART1.UART.txPin。$sendestSolution ="BoosterPack.4";
UART1.UART.rxPin。$建议解决方案="BoosterPack.3";
e2e.ti.com/.../2388.main_5F00_tirtos.ce2e.ti.com/.../sha2hash.c
。
我找到了一个文档、其中指定 SHA 和 AES 不能同时使用:
AES (高级加密标准) API 提供对加密内核 AES 和密钥存储功能的访问。 SHA2加速器也包含在加密内核中。 因此、只能同时使用 SHA2和 AES 中的一个。 此模块使用 AES 块化环为多种协议提供硬件加速。 以下协议受硬件支持。 driverlib 文档仅明确引用最常用的文档。
现在知道这一点、是否可以将 SHA 操作置于关键部分? 如果没有、是否在互斥之下?
您好、Mehul、
此问题很可能与您使用 SHA2_addData 的方式有关。 我从 TI 驱动程序运行时 API 中获取了一个示例 、并且没有遇到与使用 AES CCM 的第二个线程共存的问题。
/* * Copyright (c) 2017-2019, Texas Instruments Incorporated * All rights reserved. * * 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. */ /* * ======== sha2hash.c ======== */ #include <stdint.h> #include <stdio.h> #include <string.h> #include <ti/sysbios/knl/Task.h> // For Task_construct and task related configuration #include <ti/drivers/utils/Random.h> // for Random_getNumber() /* Driver Header files */ #include <ti/drivers/UART.h> #include <ti/drivers/SHA2.h> #include <ti/drivers/AESCCM.h> // for AES-CCM #include <ti/drivers/cryptoutils/cryptokey/CryptoKeyPlaintext.h> // for CryptoKeyPlaintext_initKey() #include <ti/drivers/dpl/HwiP.h> const char message[] = "Premature optimization is the root of all evil (or at least most of it) in programming."; uint8_t actualDigest[SHA2_DIGEST_LENGTH_BYTES_256]; uint8_t expectedDigest[] = { 0xF2, 0x6A, 0xFF, 0x01, 0x11, 0x6B, 0xF6, 0x77, 0x63, 0x91, 0xFE, 0xD9, 0x47, 0x56, 0x99, 0xB2, 0xAD, 0x7D, 0x64, 0x16, 0xF7, 0x40, 0x1A, 0x5B, 0xCC, 0xC7, 0x08, 0x3D, 0xE8, 0x6B, 0x35, 0x6D, }; SHA2_Handle handle; int_fast16_t result; SHA2_Params params; /* Driver configuration */ #include "ti_drivers_config.h" int intState; /* Defines */ #define MAX_MSG_LENGTH 256 /* UART pre-formated strings */ static const char promptStartup[] = "\n\n\rSHA2 Driver hash demo."; static const char promptHash[] = "\n\n\rRandom Number: "; /* Message buffers */ static char formatedMsg[MAX_MSG_LENGTH]; /* * ======== printHash ======== */ void printHash(UART_Handle handle, uint8_t* msg) { uint32_t i; /* Format the message as printable hex */ for (i = 0; i < 1; i++) { sprintf(formatedMsg + (i * 2), "%02X", *(msg + i)); } /* Print prompt */ UART_write(handle, promptHash, strlen(promptHash)); /* Print result */ UART_write(handle, formatedMsg, strlen(formatedMsg)); } /* * ======== mainThread ======== */ void *mainThread(void *arg0) { int_fast16_t result; /* Driver handles */ UART_Handle uartHandle; SHA2_Handle sha2Handle; /* UART variables */ UART_Params uartParams; /* Call driver initialization functions */ UART_init(); SHA2_init(); /* Open UART for console output */ UART_Params_init(&uartParams); uartParams.writeDataMode = UART_DATA_BINARY; uartParams.readDataMode = UART_DATA_BINARY; uartParams.readReturnMode = UART_RETURN_FULL; uartParams.readEcho = UART_ECHO_OFF; uartParams.baudRate = 115200; uartHandle = UART_open(CONFIG_UART_0, &uartParams); if (!uartHandle) { /* UART_open() failed */ while (1); } SHA2_Params_init(¶ms); params.returnBehavior = SHA2_RETURN_BEHAVIOR_BLOCKING; /* Prompt startup message */ UART_write(uartHandle, promptStartup, strlen(promptStartup)); for(;;) { handle = SHA2_open(0, ¶ms); if(handle == NULL) {while(1);} // We can configure the driver even after SHA2_open() result = SHA2_setHashType(handle, SHA2_HASH_TYPE_256); if(result != SHA2_STATUS_SUCCESS){while(1);} // Process data in chunks. The driver buffers incomplete blocks internally. result = SHA2_addData(handle, &message[0], 17); if(result != SHA2_STATUS_SUCCESS){while(1);} result = SHA2_addData(handle, &message[17], strlen(message) - 17); if(result != SHA2_STATUS_SUCCESS){while(1);} // Compute the resulting digest result = SHA2_finalize(handle, actualDigest); if(result != SHA2_STATUS_SUCCESS){while(1);} // Verify result = memcmp(actualDigest, expectedDigest, SHA2_DIGEST_LENGTH_BYTES_256); SHA2_close(handle); uint32_t randomNumber = Random_getNumber(); randomNumber %= 17; Task_sleep((xdc_UInt32)randomNumber); printHash(uartHandle, &randomNumber); } } /* * ======== mainThread ======== */ void *mainThread2(void *arg0) { // // SETUP // AESCCM_Handle aeshandle; AESCCM_Params params; CryptoKey cryptoKey; AESCCM_Operation operation; int_fast16_t status = 0; // Initialize the AES-CCM peripheral AESCCM_init(); AESCCM_Params_init(¶ms); params.returnBehavior = AESCCM_RETURN_BEHAVIOR_POLLING; for(;;) { aeshandle = AESCCM_open(0, ¶ms); if (!aeshandle) { while (1); } uint8_t nonce[] = {0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16}; uint8_t aad[] = {0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07}; uint8_t plaintext[] = {0x20, 0x21, 0x22, 0x23}; uint8_t keyingMaterial[] = {0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59, 0x5A, 0x5B, 0x5C, 0x5D, 0x5E, 0x5F}; uint8_t mac[4]; uint8_t ciphertext_generated[4]; memset(ciphertext_generated, 0, 4); uint8_t plaintext_generated[4]; memset(plaintext_generated, 0, 4); // Create the key CryptoKeyPlaintext_initKey(&cryptoKey, keyingMaterial, 32); // Verify Encryption AESCCM_Operation_init(&operation); operation.key = &cryptoKey; operation.aad = &aad[0]; operation.aadLength = 8; operation.input = &plaintext[0]; operation.output = &ciphertext_generated[0]; operation.inputLength = 4; operation.nonce = &nonce[0]; operation.nonceLength = 7; operation.mac = &mac[0]; operation.macLength = 4; status = AESCCM_oneStepEncrypt(aeshandle, &operation); AESCCM_close(aeshandle); // again wait so TDC_REF clock request can be acknowledge //Task_sleep((xdc_UInt32)100); uint32_t randomNumber = Random_getNumber(); Task_sleep((xdc_UInt32)randomNumber % 23); } }
此致、
Ryan
Ryan、
请查看上面的链接。 它表示 SHA 和 AES 不能同时使用。
dev.ti.com/.../group__aes__api.html
你能评论吗?
Mehul
您好、Ryan、
我不确定我是否理解了你对长度的看法。 我提供的代码只是内部闪存数据中地址的起点、在该地址上计算 SHA。 此外、当数据长度相当大而不是1字节左右(< 50字节)时、也会发生此问题。
我同意这样的观点、即在使用 SHA 的同时使用 AES 不是问题。 我也在 Simple Peripheral 示例项目中再现了"SHA 模块卡在 SHA2_addData()中、从不返回"的问题。 我会在另一份答覆中提出所需的详情。
我已将您的简单外设和 SHA 调查拆分为一篇新文章: https://e2e.ti.com/f/1/t/1135928
BLE 专家将通过该主题进一步为您提供帮助。
此致、
Ryan
该问题 与您使用指针有关。 当我将 input_correct_2更改为全局变量并将其地址分配给 SHA2_addData 时、代码永远不会中断。 我对您在 INPUT_correct_2之后的意图一无所知、但最好优化其使用方式。
/* * Copyright (c) 2017-2019, Texas Instruments Incorporated * All rights reserved. * * 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. */ /* * ======== sha2hash.c ======== */ #include <stdint.h> #include <stdio.h> #include <string.h> #include <ti/sysbios/knl/Task.h> // For Task_construct and task related configuration #include <ti/drivers/utils/Random.h> // for Random_getNumber() /* Driver Header files */ #include <ti/drivers/UART.h> #include <ti/drivers/SHA2.h> #include <ti/drivers/AESCCM.h> // for AES-CCM #include <ti/drivers/cryptoutils/cryptokey/CryptoKeyPlaintext.h> // for CryptoKeyPlaintext_initKey() /* Driver configuration */ #include "ti_drivers_config.h" /* Defines */ #define MAX_MSG_LENGTH 256 /* UART pre-formated strings */ static const char promptStartup[] = "\n\n\rSHA2 Driver hash demo."; static const char promptHash[] = "\n\n\rRandom Number: "; /* Message buffers */ static char formatedMsg[MAX_MSG_LENGTH]; unsigned char input_correct_2; /* * ======== printHash ======== */ void printHash(UART_Handle handle, uint8_t* msg) { uint32_t i; /* Format the message as printable hex */ for (i = 0; i < 1; i++) { sprintf(formatedMsg + (i * 2), "%02X", *(msg + i)); } /* Print prompt */ UART_write(handle, promptHash, strlen(promptHash)); /* Print result */ UART_write(handle, formatedMsg, strlen(formatedMsg)); } /* * ======== mainThread ======== */ void *mainThread(void *arg0) { int_fast16_t result; /* Driver handles */ UART_Handle uartHandle; SHA2_Handle sha2Handle; /* UART variables */ UART_Params uartParams; /* Call driver initialization functions */ UART_init(); SHA2_init(); /* Open UART for console output */ UART_Params_init(&uartParams); uartParams.writeDataMode = UART_DATA_BINARY; uartParams.readDataMode = UART_DATA_BINARY; uartParams.readReturnMode = UART_RETURN_FULL; uartParams.readEcho = UART_ECHO_OFF; uartParams.baudRate = 115200; uartHandle = UART_open(CONFIG_UART_0, &uartParams); if (!uartHandle) { /* UART_open() failed */ while (1); } SHA2_Params params; SHA2_Params_init(¶ms); params.hashType = SHA2_HASH_TYPE_512; params.returnBehavior = SHA2_RETURN_BEHAVIOR_POLLING; sha2Handle = SHA2_open(0, ¶ms); if (!sha2Handle) { /* SHA2_open() failed */ while(1); } /* Prompt startup message */ UART_write(uartHandle, promptStartup, strlen(promptStartup)); for(;;) { uint32_t randomNumber = Random_getNumber(); input_correct_2 = (randomNumber % 1000); // Verify correct input generates expected output result = SHA2_addData(sha2Handle, &input_correct_2, 8192); // --> ISSUE: Never returns randomNumber %= 17; Task_sleep((xdc_UInt32)randomNumber); printHash(uartHandle, &randomNumber); } } /* * ======== mainThread ======== */ void *mainThread2(void *arg0) { // // SETUP // AESCCM_Handle aeshandle; AESCCM_Params params; CryptoKey cryptoKey; AESCCM_Operation operation; int_fast16_t status = 0; // Initialize the AES-CCM peripheral AESCCM_init(); AESCCM_Params_init(¶ms); params.returnBehavior = AESCCM_RETURN_BEHAVIOR_POLLING; for(;;) { aeshandle = AESCCM_open(0, ¶ms); if (!aeshandle) { while (1); } uint8_t nonce[] = {0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16}; uint8_t aad[] = {0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07}; uint8_t plaintext[] = {0x20, 0x21, 0x22, 0x23}; uint8_t keyingMaterial[] = {0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x4B, 0x4C, 0x4D, 0x4E, 0x4F, 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59, 0x5A, 0x5B, 0x5C, 0x5D, 0x5E, 0x5F}; uint8_t mac[4]; uint8_t ciphertext_generated[4]; memset(ciphertext_generated, 0, 4); uint8_t plaintext_generated[4]; memset(plaintext_generated, 0, 4); // Create the key CryptoKeyPlaintext_initKey(&cryptoKey, keyingMaterial, 32); // Verify Encryption AESCCM_Operation_init(&operation); operation.key = &cryptoKey; operation.aad = &aad[0]; operation.aadLength = 8; operation.input = &plaintext[0]; operation.output = &ciphertext_generated[0]; operation.inputLength = 4; operation.nonce = &nonce[0]; operation.nonceLength = 7; operation.mac = &mac[0]; operation.macLength = 4; status = AESCCM_oneStepEncrypt(aeshandle, &operation); AESCCM_close(aeshandle); // again wait so TDC_REF clock request can be acknowledge //Task_sleep((xdc_UInt32)100); uint32_t randomNumber = Random_getNumber(); Task_sleep((xdc_UInt32)randomNumber % 23); } }
此致、
Ryan
您好、Ryan、
感谢您的参与。
但是、您拥有的更新代码与我尝试执行的代码不同。 本质上、我所需要的只是提供一个从内部闪存散列的数据的起始地址(内部闪存基址为0x00000000)。 您更新为 RAM 数据段中分配的 INPUT_correct_2变量的代码、当您将其地址传递给散列函数(即&INPUT_correct_2)时、它是 RAM 数据段的起始地址、而不是我在代码中使用的起始地址。 您是否尝试将起始地址传递到内部闪存地址的散列? 我们在内部闪存中有一些数据、我们要根据这些数据计算哈希值以确保其完整性。
这是我的更新代码。 尽管我已将 start_address_for_hash-data 分配为全局数据、但代码仍会卡住。 这里的重点是执行 SHA 操作所针对的数据来自内部闪存地址、而不是来自 RAM。 希望它能帮助:
是的、我已将内部闪存地址传递给 SHA2_addData。 这就是我在2016年9月共享的 const "message"所做的事情。 它位于地址0x00006546、我执行的长度为1024、超过了数组的长度。 但是、最好避免存储在闪存开头的.resetVecs。 我可以向您的随机分配(0x3C)添加偏移量、而不会遇到任何其他问题。 相反、传递0x0000地址也会导致代码失败。
此致、
Ryan
Ryan、
有趣。 您是否知道起始地址0x00000000为什么是个问题? 我知道矢量表位于那里。 但是、SHA 操作应该读取该数据、而不是对该数据执行任何写操作? 以下是映射文件显示的内容:
运行 origin load origin length init length atts members
------ ------ ------ ------ ---- ----
00000000 00000000 000068f0 000068f0 r-x
00000000 00000000 0000003c 0000003c r-.Vecresets
此外、我还更新了代码、将0x00000000作为起始地址传递、数据长度为0x3C。 这意味着 SHA 仅在矢量表上执行。 然而、代码从未卡住。 请参阅随附的源文件。 那么、从复位矢量表到 SHA 的起始地址不应该成为问题?
结果= SHA2_addData (shA2Handle、(void *) 0x00000000、0x3C);
我还想澄清一下、我们的应用固件问题与我们修改过的简单外设示例非常接近。 我希望阿马尔更接近根本原因。 但是,我们认为,在两个项目中了解问题的根本原因将会更好。