source: rtos_arduino/trunk/arduino_lib/libraries/Temboo/src/utility/tmbhmac.cpp@ 136

Last change on this file since 136 was 136, checked in by ertl-honda, 8 years ago

ライブラリとOS及びベーシックなサンプルの追加.

File size: 3.1 KB
Line 
1/*
2###############################################################################
3#
4# Temboo Arduino library
5#
6# Copyright 2014, Temboo Inc.
7#
8# Licensed under the Apache License, Version 2.0 (the "License");
9# you may not use this file except in compliance with the License.
10# You may obtain a copy of the License at
11#
12# http://www.apache.org/licenses/LICENSE-2.0
13#
14# Unless required by applicable law or agreed to in writing,
15# software distributed under the License is distributed on an
16# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
17# either express or implied. See the License for the specific
18# language governing permissions and limitations under the License.
19#
20###############################################################################
21*/
22
23#include <string.h>
24#include <avr/pgmspace.h>
25#include "tmbhmac.h"
26
27HMAC::HMAC() {
28}
29
30HMAC::HMAC(const uint8_t* key, uint32_t keyLength) {
31 init(key, keyLength);
32}
33
34void HMAC::init(const uint8_t* key, uint32_t keyLength) {
35
36 m_key = key;
37 m_keyLength = keyLength;
38
39 uint8_t iKeyPad[HMAC_BLOCK_SIZE_BYTES];
40
41 constructKeyPad(iKeyPad, key, keyLength, (uint8_t)0x36);
42
43 m_md5.init();
44 m_md5.process(iKeyPad, HMAC_BLOCK_SIZE_BYTES);
45}
46
47void HMAC::process(const uint8_t* msg, uint32_t msgLength) {
48 // hmac = hash(o_key_pad + hash(i_key_pad + message))
49 // continue hashing the message
50 m_md5.process(msg, msgLength);
51}
52
53void HMAC::finish(uint8_t* dest) {
54 //hmac = hash(o_key_pad + hash(i_key_pad + message))
55 //
56 // Construct the o_key_pad
57 uint8_t finalBlock[HMAC_BLOCK_SIZE_BYTES + HMAC_HASH_SIZE_BYTES];
58 constructKeyPad(finalBlock, m_key, m_keyLength, (uint8_t)0x5C);
59 m_md5.finish(finalBlock + HMAC_BLOCK_SIZE_BYTES);
60
61 m_md5.init();
62 m_md5.process(finalBlock, HMAC_BLOCK_SIZE_BYTES + HMAC_HASH_SIZE_BYTES);
63 m_md5.finish(dest);
64}
65
66void HMAC::finishHex(char* dest) {
67 uint8_t binDest[HMAC_HASH_SIZE_BYTES];
68 finish(binDest);
69 toHex(binDest, dest);
70}
71
72void HMAC::toHex(uint8_t* hmac, char* dest) {
73 static const char hex[17] PROGMEM = "0123456789abcdef";
74 uint16_t i;
75 for (i = 0; i < HMAC_HASH_SIZE_BYTES; i++) {
76 dest[i*2] = pgm_read_byte(&hex[hmac[i] >> 4]);
77 dest[(i*2) + 1] = pgm_read_byte(&hex[hmac[i] & 0x0F]);
78 }
79 dest[HMAC_HASH_SIZE_BYTES * 2] = '\0';
80}
81
82/*
83 * dest MUST be big enough to hold HMAC_BLOCK_SIZE_BYTES
84 */
85void HMAC::constructKeyPad(uint8_t* dest, const uint8_t* key, uint32_t keyLength, uint8_t padByte) {
86
87 if (keyLength > HMAC_BLOCK_SIZE_BYTES) {
88 // If the key is bigger than 1 block,
89 // replace the key with the hash of the key.
90 MD5 md5;
91 md5.process(key, keyLength);
92 md5.finish(dest);
93 keyLength = HMAC_HASH_SIZE_BYTES;
94 } else {
95 // If the key length is <= to the HMAC block length,
96 // just use the key as-is.
97 memcpy(dest, key, keyLength);
98 }
99 // pad the remaining space with 0s
100 if (keyLength < HMAC_BLOCK_SIZE_BYTES) {
101 memset(dest + keyLength, 0, HMAC_BLOCK_SIZE_BYTES-keyLength);
102 }
103
104 for (int i = 0; i < HMAC_BLOCK_SIZE_BYTES; i++) {
105 dest[i] ^= padByte;
106 }
107}
Note: See TracBrowser for help on using the repository browser.