Search

'Cortex M4 SSL'에 해당되는 글 2건

  1. 2017.06.17 SSL/TLS embedded for IoT #6
  2. 2017.06.16 SSL/TLS embedded for IoT #5

SSL/TLS embedded for IoT #6

Embedded SSL 2017.06.17 17:19 Posted by Dwarp

SSL/TLS embedded for IoT


이 글은 embedded IoT device의 보안에 관한 글입니다.


embedded SSL/TLS 여섯번째입니다.



너무 몰아붙이나요? ㅎㅎ 아니겠죠 ㅎㅎ 저만 ㅠㅠ 여러분들은 시간날 때 보면 되니까 ㅠㅠ 암튼 전 주말이지만 기다리시는 분들이 계셔서 계속 진행합니다. 오늘은 W5500 iolibrary와 mbedTLS를 이어 붙이는 시간이 될 거에요. 하지만 그 전에 SSL/TLS라는 게 서버든 클라이언트든 있어야 하잖아요?


또 그러기 위해서는 뭔가... 그 뭐냐... 그그그그그.... Application!이 있어야 하겠죠? 제가 건망증이 좀 있습니다. 양해 좀 ㅎㅎ


우리가 지금 IoT 하고 있잖아요? 그래서 네트워크 어플리케이션으로 MQTT를 정하겠습니다. MQTT는 뭐냐고요? 그건 뭐..... IoT에 특화된 네트워크 프로토콜입니다. 찾아보시면 금방 자료 나와요. 전 라즈베리파이에 MQTT 서버를 SSL 모드로 열어놨습니다. 특별한 문제가 없으면 오픈해 놓으려고 하니 테스트 해보셔요. 아래는 제가 open 해놓은 MQTT Broker(서버) 주소 입니다.


<라즈베리 파이>


IP: 222.98.173.239

Port 일반 TCP: 1883

Port 보안 TCP: 1884

Port 일반 websocket: 8883

Port 보안 websocket: 8884


** 경고!!!!!!!! 아시겠지만 테스트 용도로만 사용하시고 상업적인 용도로 사용하지 마세요. 제가 손해봐서 그러는게 아닙니다. 여러분들이 고생합니다. ㅠㅠ 사전 경고 없이 서버가 꺼지거나 할 수 있는데 정작 저는 모를 수 있어요.



<제 책상의 라즈베리파이 MQTT 서버 - 언제나 꺼질 지 모르는 완벽한 불안정 속에 위치해 있다.>


** 리눅스에 MQTT 서버 설치/Open SSL 인증서 만드는 법 등 요청하시면 따로 포스팅 하겠습니다.


자 그럼 다시 코드로 넘어가겠습니다. mbedTLS와 관련하여 만들어야 할 함수가 존재하겠죠? 근데 뭐가 필요하죠? mbedTLS 코드를 다운로드 받으면 여러 예제가 있긴 하지만 보고 있으면 괴롭기만 할 뿐입니다. 괴로운건 ㅠㅠ 제가 이미 봤으니까 여러분들은 핵심만 가져가세요. (왜 남 좋은 일 하냐구요? 뭐 고마운신 분들은 댓글 주세요. 계좌번호 드릴테니까 돈 좀 주세요. 아니면 연봉 1억쯤 주시고 데려가서 노예로 쓰시면 됩니다.)


자! 쓸데없는 소리 그만하고 만들어야 할 함수를 설명하겠습니다.


wiz_mbedtls_ssl_init();

먼저 SSL이라고 피해갈 수 없겠죠? 초기화를 해야만 합니다. 각종 메모리 할당, callback 등록 등의 과정이 들어 있을 겁니다.


wiz_mbedtls_ssl_deinit();

뭐 이건 초기화의 반대네요. mbedtls가 malloc/free를 쓰는 이상 리소스 관리를 하지 않을 수가 없겠죠? init가 malloc을 했다면 deinit은 free를 주로 하겠네요.


wiz_mbedtls_ssl_handshake();

handshake를 처음에 설명드렸는지 안했는지 기억이 안납니다. ㅎ 암튼 SSL은 암호화된 통신을 하기 전에 서버와 클라이언트 사이의 암호화 방법을 결정하고 인증서를 교환하는 등의 과정을 거칩니다. 이 과정을 handshake라고 부르는데요 이 과정도 약간 프로그래밍을 해줘야 합니다. 대놓고 mbedtls_ssl_handshake()라는 함수를 사용해도 되지만 전 일단 감싸주려고 합니다. 처리해야 할 것도 약간 있구요.


wiz_mbedtls_ssl_random();

거의 모든 보안 알고리즘들은 난수를 필요로 합니다. 완벽한 난수일 수록 좋지요. 어쨌든 mbedTLS도 random 함수를 callback으로 묶어줘야 합니다. 없으면 기본적으로 내장된 rand()함수를 사용하게 프로그래밍 되어 있겠지만 음.. analog 입력을 받아(open 상태로) 그거라도 SEED를 줘서 rand()를 돌리는 게 훨씬 좋을 것 같습니다.


wiz_mbedtls_ssl_send();

기본적인 send()라고 보시면 됩니다. 일반적인 socket프로그램을 사용하면 mbedtls option질로 안 만들어도 되는 함수가 되겠지만 iolibrary는 일반적인 socket 프로그래밍 방식과는 약간 차이가 있기 때문에 iolibrary의 send를 한 번 감싸준 함수입니다.


wiz_mbedtls_ssl_recv();

wiz_mbed_ssl_send() 함수와 같은 역할입니다. 기본적인 recv함수 입니다.


wiz_mbedtls_ssl_recvtimeout();

동작은 wiz_mbedtls_ssl_recv와 같지만 time out 값을 지정해 시간내 응답이 없으면 TIME_OUT ERROR를 발생시키기 위한 목적입니다. wiz_mbedtls_ssl_recv와 wiz_mbedtls_ssl_recvtimeout 둘 중 하나만 콜벡으로 등록하면 된다고 기억하고 있지만 어쨌든 둘 다 만들어 봅시다.


아~~ 오늘은 토요일이라서 하기 싫다~~~ 그냥 소주나 한잔 먹고 싶다~


그래서 오늘은 이만 여기까지 쓰겠습니다. ㅎㅎ 다음 시간에는 함수 구현해 봅시다~~


안녕~

저작자 표시
신고

'Embedded SSL' 카테고리의 다른 글

SSL/TLS embedded for IoT #8  (0) 2017.06.27
SSL/TLS embedded for IoT #7  (0) 2017.06.19
SSL/TLS embedded for IoT #6  (0) 2017.06.17
SSL/TLS embedded for IoT #5  (0) 2017.06.16
SSL/TLS embedded for IoT #4  (0) 2017.06.15
SSL/TLS embedded for IoT #3  (6) 2016.12.28

SSL/TLS embedded for IoT #5

Embedded SSL 2017.06.16 16:37 Posted by Dwarp

SSL/TLS embedded for IoT


이 글은 embedded IoT device의 보안에 관한 글입니다.


embedded SSL/TLS 다섯번째입니다.


업로드가 느려 죄송한 마음에 하나 더 포스팅을 하도록 하겠습니다. 계속 본격적이라고 해놓고는 SSL 포팅은 맛도 못봤기 때문에 이번 시간에 SSL 포팅 바로 전까지 마무리하고 이후에는 SSL 포팅과 application을 진행하도록 하겠습니다.


저번 시간에는 main에 W5500만 초기화하는 코드를 넣었습니다. 이제는 W5500을 초기화 하고 network 정보를 입력할 시간입니다.


W5500HardwareDriver.c에 W5500Initialize() 함수를 추가해 줄 거에요.


void W5500Initialize(void)
{
	unsigned char temp;
	unsigned int randSeed = 0;
	unsigned char W5500FifoSize[2][8] = {{2,8,1,1,1,1,1,1,},{2,8,1,1,1,1,1,1}};
	W5500DeSelect();

	/* spi function register */
	reg_wizchip_spi_cbfunc(W5500ReadByte, W5500WriteByte);

	/* CS function register */
	reg_wizchip_cs_cbfunc(W5500Select,W5500DeSelect);

	if(ctlwizchip(CW_INIT_WIZCHIP,(void*)W5500FifoSize) == -1)
	{
		printf("W5500 initialized fail.\r\n");
	}

//	do{//check phy status.
//		if(ctlwizchip(CW_GET_PHYLINK,(void*)&temp) == -1){
//			printf("Unknown PHY link status.\r\n");
//		}
//	}while(temp == PHY_LINK_OFF);
}


하단에 주석처리해 놓은 부분은 Ethernet LINK가 성립되길 기다리는 구문있데 있어도 되고 없어도 됩니다.

W5500HardwareDriver.h에도 함수 추가해 주시는 거 잊지 마시구요 ^^

그리고 나면 이 함수로 초기화를 시켜줄 수 있을 거에요.


이 다음에는 네트워크 정보를 입력해야겠죠? iolibrary에 있는 wizchip_setnetinfo() 함수를 사용할 거에요. 뭐 간단합니다. 아래와 같은 방식으로 사용하시면 됩니다. 구조체 선언하고 쓰면 됩니다.


wiz_NetInfo gWIZNETINFO = { .mac = {0x00,0x08,0xdc,0xff,0x11,0xff}, .ip = {192, 168, 0, 222}, .sn = {255, 255, 255, 0}, .gw = {192, 168, 0, 1}, .dns = {8,8,8,8}, .dhcp = NETINFO_STATIC}; wizchip_setnetinfo(&gWIZNETINFO);


각각에 맞는 네트워크 정보를 넣으셔야 하는데 공유기 있으시면 192.168.0.XXX로 하는 네트워크 정보를 넣으시면 되겠죠? 아니면 DHCP(IP 자동할당)을 사용하셔도 되는데 프로그램을 추가하셔야 해요. 일단은 고정 IP로 각자 집이나 회사에 가지고 있는 공유기 밑에 붙여보도록 합시다. 대부분의 공유기 default 값이 ip는 192.168.0.XXX subnet mask는 255.255.255.0, 그리고 gate way는 공유기 주소니까 192.168.0.1이 될거에요. dns는 그다지 상관없으니 구글꺼 쓰죠 뭐 8.8.8.8입니다. 그리고 mac은 남는 네트워크 카드나 PC 등등에서 빼오셔야 합니다. 내부망 통신은 상관없지만 외부망 통신하실 때 문제가 생깁니다.


이렇게 모두 설정하셨으면 main에 합쳐봅시다.


#include "W5500HardwareDriver.h"
#include "wizchip_conf.h"

wiz_NetInfo gWIZNETINFO = { .mac = {0x00,0x08,0xdc,0xff,0x11,0xff},
							.ip = {192, 168, 0, 222},
							.sn = {255, 255, 255, 0},
							.gw = {192, 168, 0, 1},
							.dns = {8, 8, 8, 8},
							.dhcp = NETINFO_STATIC};

int main(void)
{
	W5500HardwareInitilize();	//hardware init

	W5500Initialize();			//w5500 init

	wizchip_setnetinfo(&gWIZNETINFO);	//set network information
	
    while(1)
    {
    }
}


여기까지 다 했으면 F7번이나 컴파일 버튼을 눌러서 컴파일을 해봅시다. 에러가 없나요? 전 없군요. 그래서 다운로드 해보겠습니다.

음! 잘 되는 것 같군요. 그러면 network가 되는지  Ping 명령으로 확인해 볼까요? 설마 모르시려나? CMD 창에서 ping 192.168.XX.XXX -t 엔터


응? 안되네요? 왜 안되죠? 뭐죠? 멘붕멘붕. 멘붕... 멘붕은 안하지요 대신 디버그를 할 뿐 ㅋ.


음 디버그를 해보니 항상 HAL_GetTick()이 0을 반환하는 군요 ㅎㅎ Time 관련된 함수가 넘어가질 않고 있었습니다. STM에서 왜 그랬느지 모르겠지만 HAL_GetTick, HAL_IncTick 등을 weak으로 선언해서 모든 HAL library에 사용하고 있습니다. 음.. 어쨌든 그러면 uwTick이라는 global 변수가 1씩 증가하게 해야겠습니다. HAL_IncTick은 Systick을 활용하도록 설계되어 있는 것 같은데 전 OS가 Systick을 사용하도록 하게 하고 싶습니다. 그렇다면 간단하게 weak으로 선언되어 있는 HAL_Tick을 override 시킵시다. 재선언 하는 것이지요. 그래서 uwTick이 아닌 OS의 Tick 값을 가져오도록 하겠습니다. 우후훗


점점 짬뽕이 되어 가고 있군요 ㅠㅠ SSL하다가 OS까지 오신 여러분 환영합니다. ㅠㅠ 그래도 힘내세요 ㅎㅎ 하다보면 이정도는 껌입니다.


자 그럼 main.c로 돌아가서 아래 코드를 추가해줍니다.

uint32_t HAL_GetTick(void)
{
	return CoGetOSTime();
}


지금 사용하는 CoOS는 CoGetOSTime()이라는 함수로 OS tick을 리턴합니다. 그럼 Main.c 전체는 다음과 같아질 거에요.


#include "W5500HardwareDriver.h"
#include "wizchip_conf.h"

wiz_NetInfo gWIZNETINFO = { .mac = {0x00,0x08,0xdc,0xff,0x11,0xff},
							.ip = {192, 168, 77, 123},
							.sn = {255, 255, 255, 0},
							.gw = {192, 168, 77, 1},
							.dns = {8, 8, 8, 8},
							.dhcp = NETINFO_STATIC};

int main(void)
{
	CoInitOS();

	W5500HardwareInitilize();	//hardware init

	W5500Initialize();			//w5500 init

	wizchip_setnetinfo(&gWIZNETINFO);	//set network information

	//CoStartOS();

	while(1)
    {
    }
}

uint32_t HAL_GetTick(void)
{
	return CoGetOSTime();
}


여기서 주의할 것은 CoInitOS() 인데요. 이 함수에서 Systick을 Enable 해줘요. 그래서 가장 처음에 call 했습니다.


그럼 컴파일/다운로드 하시고 Ping이 가는지 확인해 볼까요? 설마 모르시려나? CMD 창에서 ping 192.168.XX.XXX -t 엔터


!!!!!!!!!!!!! 여기서 IP 여러분 것으로 바꾸세요~ !!!!!!!!!!!!!



음... 으흐흐흐 잘 되는 군요..


이제는 정말 SSL 포팅만 남은 것 같습니다.



앞으로는 임베디드에서 보기 힘들었던 malloc, free뿐만 아니라 함수포인터 그리고 OS 개념들이 난무할거에요. 하아....

(여러분들은 한 번만 하면 되지 전 수십번은 한 것 같아요 ㅠㅠ 하아...)


암튼 주말은 푹 쉬시고 다음 주에 다시 달려봅시다.


화이팅!!! 하아....



저작자 표시
신고

'Embedded SSL' 카테고리의 다른 글

SSL/TLS embedded for IoT #7  (0) 2017.06.19
SSL/TLS embedded for IoT #6  (0) 2017.06.17
SSL/TLS embedded for IoT #5  (0) 2017.06.16
SSL/TLS embedded for IoT #4  (0) 2017.06.15
SSL/TLS embedded for IoT #3  (6) 2016.12.28
SSL/TLS embedded for IoT #2  (0) 2016.12.27