Micro-ECC is an open source implementation for ECC running in an embedded microcontroller. This is a port for mbed. Please do more test and update assembly optimization for Cortex-M, aka, ARM-thumb.
main.cpp
- Committer:
- allankliu
- Date:
- 2017-09-13
- Revision:
- 2:a2a77f01dd26
- Parent:
- 0:f83fc7ecf97b
File content as of revision 2:a2a77f01dd26:
/*
* Micro-ECC ported to mbed platform
* Original Author: Ken MacKay
* Original Project: https://github.com/kmackay/micro-ecc
* Ported by: Allan K Liu
*
* Micro-ECC is ported to mbed to evalute its performance
* Micro-ECC is optimized for ARM/ARM-thumb/ARM-thumb2/AVR platform
* Micro-ECC mbed version disabled thumb/thumb2 optimization because of its GCC syntax.
* PS: I am not good at assembly for those projects.
* Micro-ECC is highly sensitive to Random Number Generator, using two seperate ADC as input
*/
#include "mbed.h"
#include "uECC.h"
Serial pc(USBTX, USBRX);
AnalogIn rnd1(A1);
AnalogIn rnd2(A2);
AnalogIn rnd3(A3);
AnalogIn rnd4(A4);
AnalogIn rnd5(A5);
Timer t;
//#define RNG_TEST 1
#if defined(RNG_TEST)
void randtest()
{
uint8_t buf[16];
pc.printf("randtest():\r\n");
for(int i=0; i<16; i++){
buf[i] = rand();
pc.printf("%02X",buf[i]);
}
}
#endif
void adctest()
{
float buf[5];
buf[0] = rnd1.read()*3300;
buf[1] = rnd2.read()*3300;
buf[2] = rnd3.read()*3300;
buf[3] = rnd4.read()*3300;
buf[4] = rnd5.read()*3300;
pc.printf("adctest():\r\n");
for(int i=0; i<5; i++){
pc.printf("%.0f\t",buf[i]);
}
pc.printf("\r\n");
}
static int rawadc2int() {
uint8_t lsb;
uint8_t msb;
msb = uint8_t(rnd1.read()*3300);
lsb = uint8_t(rnd3.read()*3300);
return ((msb<<8)|lsb);
}
static int RNG(uint8_t *dest, unsigned size) {
// Use the least-significant bits from the ADC for an unconnected pin (or connected to a source of
// random noise). This can take a long time to generate random data if the result of analogRead(0)
// doesn't change very frequently.
pc.printf("RNG():\r\n");
while (size) {
uint8_t val = 0;
for (unsigned i = 0; i < 8; ++i) {
//int init = rnd.read();
//int init = rand();
//int init = rnd1.read()*3300;
int init = rawadc2int();
pc.printf("%04X",init);
int count = 0;
//while (rnd.read() == init) {
//while (rand() == init) {
//while((rnd1.read()*3300) == init){
while(rawadc2int() == init){
++count;
}
if (count == 0) {
val = (val << 1) | (init & 0x01);
} else {
val = (val << 1) | (count & 0x01);
}
}
*dest = val;
++dest;
--size;
pc.printf("\r\n");
}
// NOTE: it would be a good idea to hash the resulting random data using SHA-256 or similar.
return 1;
}
void dumphex(const char* name, uint8_t* buf, uint8_t size){
pc.printf(name);
for(int i=0; i<size; i++){
pc.printf("%02X",buf[i]);
}
pc.printf("\r\n");
}
void loop(){
const struct uECC_Curve_t * curve = uECC_secp160r1();
int r;
long d;
uint8_t private1[21];
uint8_t private2[21];
uint8_t public1[40];
uint8_t public2[40];
uint8_t secret1[20];
uint8_t secret2[20];
memset(private1, 0, 21);
memset(private2, 0, 21);
memset(public1, 0, 40);
memset(public2, 0, 40);
memset(secret1, 0, 20);
memset(secret2, 0, 20);
pc.printf("Start ECC computation\r\n");
pc.printf("make key 1\r\n");
t.start();
uECC_make_key(public1, private1, curve);
dumphex("public1:\r\n", public1, sizeof(public1));
dumphex("private1:\r\n", private1, sizeof(private1));
t.stop(); d = t.read_ms(); t.reset(); t.start();
pc.printf("time: %dms\r\n",d);
pc.printf("make key 2\r\n");
t.start();
uECC_make_key(public2, private2, curve);
dumphex("public2:\r\n", public2, sizeof(public2));
dumphex("private2:\r\n", private2, sizeof(private2));
t.stop(); d = t.read_ms(); t.reset(); t.start();
pc.printf("time: %dms\r\n",d);
pc.printf("make share secret 1\r\n");
t.start();
r = uECC_shared_secret(public2, private1, secret1, curve);
pc.printf("r: %04X\r\n",r);
dumphex("secret1:\r\n", secret1, sizeof(secret1));
t.stop(); d = t.read_ms(); t.reset(); t.start();
pc.printf("time: %dms\r\n",d);
pc.printf("make share secret 2\r\n");
t.start();
r = uECC_shared_secret(public1, private2, secret2, curve);
pc.printf("r: %04X\r\n",r);
dumphex("secret2:\r\n", secret2, sizeof(secret2));
t.stop(); d = t.read_ms(); t.reset(); t.start();
pc.printf("time: %dms\r\n",d);
pc.printf("\r\n\r\n");
wait(1);
}
int main() {
pc.baud(115200);
printf("\033[2J\033[0;0H"); // return to 0,0 and clear screen in VT100
pc.printf("\r\nmicroECC test\r\n");
#if defined(RNG_TEST)
// Test rand() functions is turly random.
for(int i=0; i<4; i++){
randtest();
pc.printf("\r\n");
}
#endif
#if(0)
for(int i=0; i<10; i++){
adctest();
wait(1);
}
#endif
uECC_set_rng(&RNG);
pc.printf("\r\n");
loop();
while(1) {
;
}
}