Hash
-
Cryptography hash('digest’라고도 함)는 텍스트 또는 데이터 파일에 대한 일종의 'signature'.
SHA, Secure Hash Algorithm
SHA-256
-
SHA 알고리즘의 한 종류로 256bit로 구성된 64자리 문자열 반환
-
2256 개의 경우의 수를 만들 수 있음
-
어떤 길이의 값을 입력하더라도 256bit의 고정된 결과값 출력
-
8bit → 1byte, 2byte → char
-
256bit → 32byte
-
-
단방향성으로 복호화 불가
-
16진법(hex)
val hash1 = MessageDigest
.getInstance("SHA-256")
.digest(origin.toByteArray())
.fold("", { str, it -> str + "%02x".format(it) })
// required "org.bouncycastle:bcprov-jdk15on"
val hash2 = MessageDigest
.getInstance("SHA-256")
.digest(origin.toByteArray())
.let { String(Hex.encode(it)) }
val hash3 = MessageDigest
.getInstance("SHA-256")
.digest(origin.toByteArray())
.let { BigInteger(1, it).toString(16).padStart(32, '0') }
MD5, Message-Digest algorithm 5
-
암호화 해시 함수
-
RFC 1321
crpyto
AES, Advanced Encryption Standard
-
대칭키를 쓰는 블럭 암호
AES 256
-
256 암호화 키 사용
-
aes-256-cbc로 생성하면 64byte 키값이 생성됨
salt=5B1CD0A0E6F91535 key=1F3CDAD3FDD397162A8431B24D67B65C7C4A0277BC07223C19B7CD711F4376F5 iv =BF9B3C014A9061CB7F33FF3451023ABE
-
블록암호화를 진행하기 위해 패딩 기법 필요
-
데이터를 특정크기로 맞추기 위해 채워넣는 방법
val c = Cipher.getInstance("AES/CBC/PKCS5Padding")
-
JDK에서는 지원하지 않음
-
JCE 설치
-
외부 디펜던시 추가
build.gradle.ktsdependencies { api("org.bouncycastle:bcprov-jdk15on:1.66") }
AesUtils.ktobject AesUtils { init { Security.addProvider(BouncyCastleProvider()) } fun encrypt256(data: String, hexAesKey: String): ByteArray { val keySpec = SecretKeySpec(hexAesKey.hexStringToByteArray(), "AES") val ivSpec = IvParameterSpec(ByteArray(16) { 0x00 }) return Cipher .getInstance("AES/CBC/PKCS7Padding", BouncyCastleProvider.PROVIDER_NAME) .apply { init(Cipher.ENCRYPT_MODE, keySpec, ivSpec) } .doFinal(data.toByteArray(StandardCharsets.UTF_8)) } }
-
PKCS#7 Padding
-
블럭의 빈 자리를 채우는 방법
-
일반적으로 PKCS#5, PKCS#7 사용
-
나무위키
PKCS#5 패딩은 PKCS#7 패딩과 구현 방식이 같지만 블럭의 크기가 8바이트로 고정된 것이다. AES는 128비트(16바이트) 블럭 알고리즘이기 때문에 사실 PKCS#5 패딩을 쓸 일이 없다. 그러나 PKCS#7 패딩과 구현 방식이 같아 보통 같은 구현을 돌려쓰는데다, Java에서 'AES/CBC/PKCS5Padding' 표기법만 허용하고 'AES/CBC/PKCS7Padding' 표기법은 지원하지 않다보니 오히려 AES에 PKCS#5 패딩을 쓰는 것이 맞는 줄 아는 경우가 많다.
Mode/IV
-
IV(Initialization Vector): 초기화 벡터
-
https://en.wikipedia.org/wiki/Block_cipher_mode_of_operation
-
블럭 암호화 순서 및 규칙에 대한 표준
-
CBC(Cipher-Block Chining)
-
최초 평문 1블럭과 IV를 XOR 연산하고 암호화
-
다음 편문 1블록은 앞에서 위에어 암호화된 결과 블럭에 XOR 연산하여 다시 암호화
-
이 과정을 끝까지 반복하는 것이 CBC
-
평문 마지막 블럭은 패딩된 블럭
-
-
ECB
-
IV를 사용하지 않고, 즉 XOR 연산 없이 각 블럭을 암호화
-
References
RSA
-
공개키 암호 방식(public-key cryptography)의 한 종류
-
비대칭키 사용
-
1978년 로널드 라이베스트(Ron Rivest), 아디 샤미르(Adi Shamir), 레너드 애들먼(Leonard Adleman)의 연구에 의해 체계화되었으며, 이들 이름을 따서 명명됨
MAC, Message Authenication Code
-
해싱보다는 알고리즘
-
대칭키/공개치 같은 암호화 알고리즘 보다 빠르다?
-
현재 메시지가 진짜임을 인증하는 것
-
reversible하지 않다
HMAC, Hash-based Message Authentication Code
HMAC-SHA256
-
절차
-
보내는 쪽에서 payload와 signature(payload + altorithm(
HMAC_SHA256
) + key)를 전달함 -
받는 쪽에서 전달 받은 payload로 signature를 만들어 전달 받은 signature와 동일한지 비교
-
-
해시 함수를 통과하기 전 데이터를 message라 함. (payload = message)
-
해시 함수를 통과한 데이터는 digest라 함. (signature = digest)
-
SHA-256 해시 알고리즘을 사용했으므로 다이제스트는 256 bytes