home / secrets / src / util / hexstring.c

hexstring.c



//
//  hexstring.c
//  secrets
//
//  Created by Anders on 09/07/2020.
//

#include <string.h>
#include <stdint.h>
#include "hexstring.h"
#include "require.h"

static char bin_to_hex_char(uint8_t bin) {
    switch (bin) {
        case 0x0: return '0';
        case 0x1: return '1';
        case 0x2: return '2';
        case 0x3: return '3';
        case 0x4: return '4';
        case 0x5: return '5';
        case 0x6: return '6';
        case 0x7: return '7';
        case 0x8: return '8';
        case 0x9: return '9';
        case 0xa: return 'a';
        case 0xb: return 'b';
        case 0xc: return 'c';
        case 0xd: return 'd';
        case 0xe: return 'e';
        case 0xf: return 'f';
    }
    require(false, "invalid data\n");
    return 0;
}

char* hexstring_from_bin(char *result, const uint8_t *binary, uint32_t size) {
    for (uint32_t i = 0; i < size; ++i) {
        uint8_t p1 = (binary[i] & 0xf0) >> 4;
        *result++ = bin_to_hex_char(p1);
        uint8_t p2 = binary[i] & 0xf;
        *result++ = bin_to_hex_char(p2);
    }
    return result;
}

static uint8_t hex_char_to_bin(char hex) {
    switch (hex) {
        case '0': return 0x0;
        case '1': return 0x1;
        case '2': return 0x2;
        case '3': return 0x3;
        case '4': return 0x4;
        case '5': return 0x5;
        case '6': return 0x6;
        case '7': return 0x7;
        case '8': return 0x8;
        case '9': return 0x9;
        case 'a': return 0xa;
        case 'b': return 0xb;
        case 'c': return 0xc;
        case 'd': return 0xd;
        case 'e': return 0xe;
        case 'f': return 0xf;
    }
    require(false, "invalid data\n");
    return 0;
}

void hexstring_to_bin(uint8_t *result, const char* hexstring, uint32_t expected_size) {
    size_t len = strlen(hexstring);
    require(len / 2 == expected_size, "unexpected sequence size\n");
    
    for (size_t i = 0; i < len; i += 2) {
        uint8_t p1 = hex_char_to_bin(hexstring[i]);
        uint8_t p2 = hex_char_to_bin(hexstring[i + 1]);
        uint8_t tot = (uint8_t)(p1 << 4) + p2;
        *result++ = tot;
    }
}