2012-08-22 3 views
1

이상한 이유로 인해 노드의 내장 CipherDecipher 클래스가 예상대로 작동하지 않습니다. documentationcipher.updateNode.js Crypto AES Cipher

"는 암호화 된 내용을 반환하고가 스트리밍으로 새로운 데이터를 여러 번 호출 할 수 있습니다."고 말한다

docscipher.final

는 "남아있는 암호화 된 내용을 반환합니다."고 명시

하지만, 내 테스트에서 당신 해야 전화 cipher.final 따라서 암호를 렌더링, 쓸모없는 모든 데이터를 객체 얻을, 당신은 새로운 Cipher 객체를 생성 할 필요가 다음 블록을 처리 할 수 ​​있습니다. 초기화 벡터 등의 비밀과, crypto.createCipher 또는 crypto.createCipheriv를 사용할 때 이런 것을

var secret = crypto.randomBytes(16) 
    , source = crypto.randomBytes(8) 
    , cipher = crypto.createCipher("aes128", secret) 
    , decipher = crypto.createDecipher("aes128", secret); 

var step = cipher.update(source); 
var end = decipher.update(step); 

assert.strictEqual(source.toString('binary'), end); // should not fail, but does 

참고.

var step = cipher.update(source) + cipher.final(); 
var end = decipher.update(step) + decipher.final(); 

그러나 이것은, 전술 한 바와 같이, 양 및 cipherdecipher 쓸모 렌더링 : 수정은 다음과 같이 라인들 (6, 7)를 대체한다.

이것은 노드의 기본 제공 암호화가 작동하는 방법이지만 분명히 아닙니다. 이 문제는 Node 또는 Node의 버그를 어떻게 사용합니까? 아니면 잘못된 것을 기대하고 있습니까? 직접 AES를 구현할 수는 있지만 시간이 많이 걸리고 성가시다. 암호화 또는 암호 해독이 필요할 때마다 새로운 Cipher 또는 Decipher 개체를 새로 만들어야합니까? 내가 하천의 일부로 그렇게한다면 비싼 것 같습니다.

답변

3

두 가지 문제가있었습니다. 첫 번째는 블록의 크기가 64 비트 또는 8 바이트가 될 것이라고 가정했기 때문에 "평문"을 만드는 데 사용됩니다. 실제로 AES의 내부는 128 비트 평문을 2 개의 64 비트 청크로 분할하고 거기에서부터 시작됩니다.

두 번째 문제는 위의 변경 사항을 적용한 후 정확한 청크 크기를 사용했지만 crypto 모듈이 자동 채우기를 적용하고 자동 채우기를 해제하면 두 번째 문제가 해결된다는 것입니다. 따라서, 작업 예제는 다음과 같습니다 :

var secret = crypto.randomBytes(16) 
    , source = crypto.randomBytes(16) 
    , cipher = crypto.createCipheriv("aes128", secret, secret); // or createCipher 
    , decipher = crypto.createDecipheriv("aes128", secret, secret); 

cipher.setAutoPadding(false); 
decipher.setAutoPadding(false); 

var step = cipher.update(source); 
var end = decipher.update(step); 

assert.strictEqual(source.toString('binary'), end); // does not fail 
+0

패딩 사용 중지가 안전하지 않습니다. –

+0

팁 주셔서 감사합니다.보안과 관련이없는 환경에서 보안 시스템의 프로토콜을 모방하려했기 때문에 문맥 상 중요하지 않습니다. – skeggse

+0

atuo 패딩 소금 –

2

AES는 16 바이트의 블록 크기를 사용합니다 (제안했던대로 2 배가 아닙니다). 또한 패딩이 활성화 된 경우 항상 패딩해야합니다. 그 이유는 패딩되지 않은 알고리즘이 패딩과 일반 텍스트의 마지막 바이트를 구분할 수 없기 때문입니다.

대개의 경우 암호 텍스트가 일반 텍스트와 동일한 크기가 아니어야합니다. doFinal()이 항상 호출되는지 확인하십시오. 자체 암호화 체계를 구현하는 경우 암호화/암호 해독을 위해이 방법으로 만 업데이트를 사용해야합니다.

0

행을 여러 번 호출하는 a node.js issue이 있습니다. 나는 그것이 해결되어 다음 릴리스에 반영되었을 것입니다.