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.

CC1310: CC1310: AES Encryption and Decryption and key protocol communication and its implementation.

Part Number: CC1310
Other Parts Discussed in Thread: SHA-256

Hello,
I am a student and I am doing a graduation project, the subject of which is the security of a wireless sensor network. I did the encryption and decryption of packets transmits and received by AES-CCM on CC1310; I have some questions to ask you:
1 / I would like to add a hash function like sha-256, but I have not found any examples of code or information about this part?
2 / I will use a key communication protocol that I proposed, and that is based on three keys:
         1) The first key will be private and static.
         2) A session key generated by the random generator and will be encrypted with a challenge hello to make the transfers between the nodes and the sink.
         3) An authentication key that will be generated by the random generator and will remain constant for 24 hours.
The other questions are:
1) Is there a secure part in the memory, or I can store my private key. a part in the separate memory of the code?
2) How can I make this change, by code? (I am in second master electronic, system and I did not have much notion on the aspect security and its implementation.)
3) If you have examples of key exchange codes with algo AES can you share with me or point me to the right path.

NB: wireless sensor network: star topology, I work on two nodes CC1310 lanchpads but after, it is necessary that the code works on a system of more than 100 nodes. Thank you in advance for your answer

  • ECC and SHA2 could be found in driverlib. Code snippets showing how to use them could be found in the header file.

    Here is some code that was written last summer that should get you started. This is an example on what to do it and you have to look into if it exist better methods to do this from a security standpoint:

    /* Signs public key with private key before it is loaded on EasyLink Tx Packet */
     static uint8_t eccTxSignPublicKey(EasyLink_TxPacket *txPacket, uint8_t *privateKey, uint8_t *publicKey, uint8_t keyCoordinateType)
     {
        uint8_t status;
        /* Buffers for the signature outputs */
        uint8_t ecdsaSignature1[ROM_MODULE_KEY_LENGTH] = {8};
        uint8_t ecdsaSignature2[ROM_MODULE_KEY_LENGTH] = {8};
    
        /* Buffer for the txPacket data to be signed, which includes metadata + public key */
        uint8_t signaturePacketData[PAYLOAD_SIGNATURE_LENGTH] = {0};
    
        /* Buffer for the SHA-2 output of the hashed data to be signed */
        uint8_t signedDataShaOutput[ROM_MODULE_KEY_LENGTH] = {8};
    
        /* Load public key and packet metadata to the txPacket */
        txPacket->dstAddr[0] = 0xaa;
        txPacket->len        = PACKET_PAYLOAD_OFFSET + ROM_MODULE_KEY_LENGTH * 3;
        txPacket->payload[0] = keyCoordinateType;
        memcpy(txPacket->payload + PACKET_PAYLOAD_OFFSET, publicKey, ROM_MODULE_KEY_LENGTH);
    
        /* Fill signaturePacketData */
    
        /* copy dstAddr first */
        memcpy(signaturePacketData, txPacket, EASYLINK_MAX_ADDR_SIZE);
    
        /* copy payload and len byte */
        memcpy(signaturePacketData + EASYLINK_MAX_ADDR_SIZE, &txPacket->len, ROM_MODULE_KEY_LENGTH + PACKET_PAYLOAD_OFFSET + 1);
    
        /* Nonce required for the ECDSA algorithm */
        uint8_t randStr[ROM_MODULE_KEY_LENGTH] = {8};
    
        /* Use Trng to generate a random nonce */
        gen32ByteRandomValue(randStr + ECC_KEY_LENGTH_OFFSET, ECC_KEY_LENGTH);
    
        /* Perform SHA-2 computation on the data to be signed */
        SHA256_memory_t sha256Memory;
        status = SHA256_runFullAlgorithm(&sha256Memory, (uint8_t *)signaturePacketData, sizeof(signaturePacketData), &signedDataShaOutput[4]);
    
        if(status != SHA256_OUTPUT_OK) {
            /* SHA256 failed to compute */
            return status;
        }
    
        /* Sign some key data to verify to the receiver that this unit has the corresponding private key to the transmit public key pair */
        status = ECC_ECDSA_sign((uint32_t *)privateKey,
                                (uint32_t *)signedDataShaOutput,
                                (uint32_t *)randStr,
                                (uint32_t *)ecdsaSignature1,
                                (uint32_t *)ecdsaSignature2);
    
        if(status != ECC_ECDSA_SIGN_OK) {
            return status;
        }
    
        /* Load the signatures on the txPacket */
        memcpy(txPacket->payload + PAYLOAD_SIGNATURE_OFFSET, ecdsaSignature1, ROM_MODULE_KEY_LENGTH);
        memcpy(txPacket->payload + PAYLOAD_SIGNATURE_OFFSET + ROM_MODULE_KEY_LENGTH, ecdsaSignature2, ROM_MODULE_KEY_LENGTH);
    
        return ECC_ECDSA_SIGN_OK;
     }
    
    /* generates private-public key pair which is then stored on parameter buffers */
    static uint8_t eccTxGenKeys(uint8_t *privateKey, uint8_t *publicKeyX, uint8_t *publicKeyY)
    {
        /* Buffer for the private key generated */
        uint8_t eccPrivateKey[ROM_MODULE_KEY_LENGTH] = {8};
    
        /* Use TRNG to generate a new random private key */
        gen32ByteRandomValue(eccPrivateKey + ECC_KEY_LENGTH_OFFSET, ECC_KEY_LENGTH);
    
        /* Generate public key pair for this unit by using elliptic curve cryptography
         * The local private key is used as the random input, generating the same private key
         * as the local private key
         */
        return ECC_generateKey((uint32_t *)eccPrivateKey,
                               (uint32_t *)privateKey,
                               (uint32_t *)publicKeyX,
                               (uint32_t *)publicKeyY);
    }
    
    /* Computes a shared secret which is then used to derive an AES Key*/
    static uint8_t eccTxGenAesKey(uint8_t *privateKey, uint8_t *aesKey)
    {
        uint8_t status;
    
        /* Buffers for the computed shared secret */
        uint8_t sharedSecretBufX[ROM_MODULE_KEY_LENGTH] = {8};
        uint8_t sharedSecretBufY[ROM_MODULE_KEY_LENGTH] = {8};
    
        /* Buffer for the computed shared secret */
        uint8_t sharedSecret[ECC_KEY_LENGTH] = {0};
    
        /* Buffer for the generated ecc key */
        uint8_t symmetricKey[ECC_KEY_LENGTH];
    
        /* Compute the shared secret using this units own private key + public keys from the other unit */
        status = ECC_ECDH_computeSharedSecret((uint32_t *)privateKey,
                                              (uint32_t *)rxPublicKeyX,
                                              (uint32_t *)rxPublicKeyY,
                                              (uint32_t *)sharedSecretBufX,
                                              (uint32_t *)sharedSecretBufY);
    
        if(status != ECC_ECDH_COMMON_KEY_OK) {
            /* Computation of the shared secret failed */
            return status;
        }
    
        /* Remove the prepended length specifier so it is not a part of the shared secret */
        memcpy(sharedSecret, &sharedSecretBufX[ECC_KEY_LENGTH_OFFSET], ECC_KEY_LENGTH);
    
        /* Use SHA-2 as a key derivation function */
        SHA256_memory_t shaMemory;
        status = SHA256_runFullAlgorithm(&shaMemory, sharedSecret, ECC_KEY_LENGTH, symmetricKey);
        if(status != SHA256_OUTPUT_OK) {
            /* SHA256 computation failed */
            return status;
        }
        /* AES keys used by the crypto module are 128-bit long, so truncate the generated entropy */
        memcpy(aesKey, symmetricKey, AES_KEY_LENGTH);
    
        return SHA256_OUTPUT_OK;
    }
    
    /* Encrypts and authenticates data that are then loaded on EasyLink TxPacket */
    static int encryptTxPacket(CryptoCC26XX_Handle cryptoHandle, EasyLink_TxPacket *txPacket, uint8_t *aesKey)
    {
        uint32_t keyIndex;
        int32_t status;
    
        char msgBuffer[CIPHERTEXT_LENGTH] = {'t', 'h', 'i', 's', ' ', 'i', 's', ' ', 'p', 'l', 'a', 'i', 'n', 't', 'e', 'x', 't'};
    
        /* Header contains lengths of different data elements and address */
        uint8_t header[HEADER_LENGTH]     = {0xaa, HEADER_LENGTH, NONCE_LENGTH, CIPHERTEXT_LENGTH, ENCRYPTED_PACKET_LENGTH};
    
        /* Generate an unique nonce everytime a message is sent */
        uint8_t nonce[NONCE_LENGTH];
        generateUniqueNonce(nonce, NONCE_LENGTH);
    
        /* Allocate the key */
        keyIndex = CryptoCC26XX_allocateKey(cryptoHandle, CRYPTOCC26XX_KEY_ANY, (const uint32_t*)aesKey);
    
        CryptoCC26XX_AESCCM_Transaction trans;
    
        /* Load key to the key register */
        CryptoCC26XX_loadKey(cryptoHandle, keyIndex, (const uint32_t *)aesKey);
    
        /* Initialize encryption transaction */
        CryptoCC26XX_Transac_init((CryptoCC26XX_Transaction *)&trans, CRYPTOCC26XX_OP_AES_CCM_ENCRYPT);
    
        trans.keyIndex      = keyIndex;
        trans.authLength    = MAC_LENGTH;
        trans.nonce         = (char *) nonce;
        trans.header        = (char *) header;
        trans.fieldLength   = 15 - NONCE_LENGTH; /* Following condition must be true 15 = fieldLength + nonceLength */
        trans.msgInLength   = PLAINTEXT_LENGTH;
        trans.headerLength  = HEADER_LENGTH;
        trans.msgIn         = msgBuffer; /* Points to the plaintext */
        trans.msgOut        = (char *)msgBuffer + PLAINTEXT_LENGTH ; /* position of MAC field */
    
        /* Start the encryption transaction and return status */
        status = CryptoCC26XX_transact(cryptoHandle, (CryptoCC26XX_Transaction *)&trans);
    
        if(status == CRYPTOCC26XX_STATUS_SUCCESS) {
            /* Load the encrypted packet, first byte indicates type of packet */
            txPacket->payload[0] = ENCRYPTED_PACKET;
            memcpy(txPacket->payload + PACKET_PAYLOAD_OFFSET, header, HEADER_LENGTH);
            memcpy(txPacket->payload + PACKET_PAYLOAD_OFFSET + HEADER_LENGTH, nonce , NONCE_LENGTH);
            memcpy(txPacket->payload + PACKET_PAYLOAD_OFFSET + HEADER_LENGTH + NONCE_LENGTH , msgBuffer, CIPHERTEXT_LENGTH);
            txPacket->len = ENCRYPTED_PACKET_LENGTH;
            txPacket->dstAddr[0] = 0xaa;
       }
    
       return CRYPTOCC26XX_STATUS_SUCCESS;
    }

  •  Hello,

    Thank you so much for your answer, it will help me a lot during my work.