CPP aes128 str mode Encryption Decryption Using openssl library
Programming/C,CPP,CS 2016. 9. 5. 13:41CPP aes128 cbc mode Encryption Decryption
AES
Encryption Block :
128 비트
192 비트
256 비트
Mode :
1. ECB ( Electric Code Book )
http://jo.centis1504.net/wp-content/uploads/2010/11/Encryption-ECB_MODE.swf
2. CBC ( Cipher Block Chaining )
http://jo.centis1504.net/wp-content/uploads/2010/11/Encryption-CBC_MODE.swf
3. OFB ( Output Feed Back )
http://jo.centis1504.net/wp-content/uploads/2010/11/Encryption-OFB_MODE.swf
4. CFB ( Cipher Feed Back )
5. CTR ( CounTeR )
모드별 설명은
관련 자료 참고 : http://www.parkjonghyuk.net/lecture/modernCrypto/lecturenote/chap04.pdf
구현에서는 CTR 모드로 구현하였다.
개발 환경 : Windows 7 64bit, VS 2013
최신버전으로 직접 빌드하시려면 아래의 링크를 참조하시기 바랍니다.
귀찮으신 분은 빌드된 버전을 사용합시다.
"openssl-1.0.1f_vc_no-idea no-mdc2 no-rc5_build.zip" 는 no-idea no-mdc2 no-rc5 로 빌드된, 특허문제가 해결 된 바이너리입니다.
압축 해제 후 파일을 프로젝트 폴더로 이동
프로젝트속성 > VC++ 디렉터리 > 디렉터리 설정 (포함 디렉터리, 라이브러리 디렉터리)
별도의 클래스를 만들어 사용 하였습니다.
#pragma once #include#include #include #include struct ctr_state { unsigned char ivec[AES_BLOCK_SIZE]; unsigned int num; unsigned char ecount[AES_BLOCK_SIZE]; }; class CAESCTR { public: AES_KEY key; int BYTES_SIZE = 1024; int KEY_SIZE = 128; unsigned char ckey[32]; unsigned char iv[8]; int init_ctr(struct ctr_state *state, const unsigned char iv[8]); void encrypt(unsigned char *indata, unsigned char *outdata, int bytes_read); void encrypt(CString& indata, CString& outdata, int bytes_read); CAESCTR(); CAESCTR::CAESCTR(unsigned char* iv, unsigned char* ckey); ~CAESCTR(); };
#include "stdafx.h" #include "AESCTR.h" int CAESCTR::init_ctr(struct ctr_state *state, const unsigned char iv[8]){ state->num = 0; memset(state->ecount, 0, AES_BLOCK_SIZE); memset(state->ivec + 8, 0, 8); memcpy(state->ivec, iv, 8); return 0; } // encrypt twice == decrypt void CAESCTR::encrypt(unsigned char *indata, unsigned char *outdata, int bytes_read){ int i = 0; int mod_len = 0; AES_set_encrypt_key(ckey, KEY_SIZE, &key); if (bytes_read < BYTES_SIZE){ struct ctr_state state; init_ctr(&state, iv); AES_ctr128_encrypt(indata, outdata, bytes_read, &key, state.ivec, state.ecount, &state.num); return; } // loop block size = [ BYTES_SIZE ] for (i = BYTES_SIZE; i <= bytes_read; i += BYTES_SIZE){ struct ctr_state state; init_ctr(&state, iv); AES_ctr128_encrypt(indata, outdata, BYTES_SIZE, &key, state.ivec, state.ecount, &state.num); indata += BYTES_SIZE; outdata += BYTES_SIZE; } mod_len = bytes_read % BYTES_SIZE; if (mod_len != 0){ struct ctr_state state; init_ctr(&state, iv); AES_ctr128_encrypt(indata, outdata, mod_len, &key, state.ivec, state.ecount, &state.num); } } void CAESCTR::encrypt(CString& instr, CString& outstr, int bytes_read){ int i = 0; int mod_len = 0; unsigned char *indata; unsigned char *outdata; indata = (unsigned char *)malloc(instr.GetLength() + 1); outdata = (unsigned char *)malloc(instr.GetLength() + 1); strncpy((char*)indata, (LPSTR)(LPCSTR)instr, instr.GetLength()); indata[instr.GetLength()] = NULL; AES_set_encrypt_key(ckey, KEY_SIZE, &key); if (bytes_read < BYTES_SIZE){ struct ctr_state state; init_ctr(&state, iv); AES_ctr128_encrypt(indata, outdata, bytes_read, &key, state.ivec, state.ecount, &state.num); outdata[instr.GetLength()] = NULL; outstr = outdata; return; } // loop block size = [ BYTES_SIZE ] for (i = BYTES_SIZE; i <= bytes_read; i += BYTES_SIZE){ struct ctr_state state; init_ctr(&state, iv); AES_ctr128_encrypt(indata, outdata, BYTES_SIZE, &key, state.ivec, state.ecount, &state.num); indata += BYTES_SIZE; outdata += BYTES_SIZE; } mod_len = bytes_read % BYTES_SIZE; if (mod_len != 0){ struct ctr_state state; init_ctr(&state, iv); AES_ctr128_encrypt(indata, outdata, mod_len, &key, state.ivec, state.ecount, &state.num); } outdata[instr.GetLength()] = NULL; outstr = outdata; } CAESCTR::CAESCTR() { unsigned char temp_iv[8] = { 0x66, 0x61, 0x63, 0x65, 0x73, 0x65, 0x61, 0x00 }; memcpy(iv, temp_iv, 8); unsigned char temp_ckey[32] = { 0x12, 0x34, 0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x34, 0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12, 0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12, 0x34, 0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12, 0x34, 0x56 }; // 32bytes = AES256, 16bytes = AES128 memcpy(ckey, temp_ckey, 32); } CAESCTR::CAESCTR(unsigned char* iv, unsigned char* ckey) { memcpy(this->iv, iv, 8); memcpy(this->ckey, ckey, 32); } CAESCTR::~CAESCTR() { }
그리고, 프로젝트 속성에서
구성 속성 > 문자 집합 > 설정 안 함
으로 하여서 사용하였습니다.
사용예시
void CPasswordEncoderDlg::OnEnChangeEdit1() { // TODO: RICHEDIT 컨트롤인 경우, 이 컨트롤은 // CDialogEx::OnInitDialog() 함수를 재지정 //하고 마스크에 OR 연산하여 설정된 ENM_CHANGE 플래그를 지정하여 CRichEditCtrl().SetEventMask()를 호출하지 않으면 // 이 알림 메시지를 보내지 않습니다. // TODO: 여기에 컨트롤 알림 처리기 코드를 추가합니다. CAESCTR m_AESCTR; CString editText; m_Edit1.GetWindowTextA(editText); int editTextLength = editText.GetLength(); unsigned char* editTextCharSeq; editTextCharSeq = (unsigned char *)malloc(editTextLength+1); strncpy((char*)editTextCharSeq, (LPSTR)(LPCSTR)editText, editTextLength); editTextCharSeq[editTextLength] = NULL; unsigned char* outTextCharSeq; outTextCharSeq = (unsigned char *)malloc(editTextLength + 1); m_AESCTR.encrypt(editTextCharSeq, outTextCharSeq, editTextLength); outTextCharSeq[editTextLength] = NULL; editText = outTextCharSeq; m_Edit2.SetWindowTextA(editText); m_AESCTR.encrypt(editText, editText, editTextLength); m_Edit3.SetWindowTextA(editText); free(editTextCharSeq); free(outTextCharSeq); }
'Programming > C,CPP,CS' 카테고리의 다른 글
openssl AES encrypt (AES_ctr128_encrypt) (0) | 2016.09.19 |
---|---|
openssl AES Mode : ECB, CBC, CFB, OFB, CTR (0) | 2016.09.05 |
CDateTimeCtrl 사용법 (0) | 2016.08.25 |
Apache License, Version 2.0 (0) | 2016.08.22 |
Log4cxx ChainSaw Appender (0) | 2016.08.22 |