Shell에서 문자열의 이진 표현을 얻는 방법은 무엇입니까?

Shell에서 문자열의 이진 표현을 얻는 방법은 무엇입니까?

openssl dgst -sha1 -binary바이너리 형식으로 문자열의 해시 값을 가져오는 데 사용하고 있습니다 .

( -binary내 버전의 openssl이 기본적으로 각 해시 값 출력 앞에 "stdout"을 추가하고 이를 방지하는 데 도움이 되므로 추가 처리를 위해 해시 결과를 이진 형식으로 저장하는 것이 더 쉽기 때문에 플래그를 사용하고 있습니다(따라서 사용할 때 작동함 ). -binary각 문자열에서 xxd -p" "를 수동으로 제거하는 대신 16진수 값)stdout

openssl dgst -sha1 -binary따라서 Cygwin 콘솔의 "Hello!" 바이너리 출력 문자열은 다음과 같습니다.

이제 이 결과를 사용하여 새 변수를 만들고 값이 이진 형식이 아닌 다른 변수(예: "World")와 연결합니다. 이제 내 새 변수는 다음과 같습니다.

_▒ "Q▒%▒a▒▒▒▒. & c ▒0n▒q▒▒vh & 8iworld

그런 다음 이 연결 문자열에 대한 또 다른 해시를 생성하고 이를 기본 Java 해싱 라이브러리()를 사용하여 얻은 해시와 비교합니다 MessageDigest. 그런데 이 단계에서 쉘과 자바를 통해 얻은 해시 값이 일치하지 않는다(자바 측에서 생성한 것과 정확히 동일한 값을 얻어야 한다).

따라서 저는 Java 해시 출력과 일치하도록 "World" 문자열도 이진 형식이어야 한다고 생각했습니다(연결된 이진 값에 대한 해시를 생성하는 한 모든 해시가 일치하기 때문입니다). 그러나 쉘에서 "World" 문자열을 바이너리 형식으로 변환하는 방법을 모르겠습니다. 어떤 아이디어가 있나요?

답변1

넌 저장할 수 없어바이너리변수에 있는 데이터(바이너리 데이터는 일반적으로 유효한 문자를 형성하지만 특별하지 않은 바이트 값뿐만 아니라 임의의 바이트 값이 있는 데이터를 나타냄), 변수에 바이트 값을 저장하는 것이 지원되지 않기 bash때문에 bash(0 문자열을 전달할 수 없음을 기억하세요) NUL로 구분된 문자열이기 때문에 이와 같은 명령 인수에 사용됩니다.

zsh하지만 들어갈 수는 있습니다. 또한 명령 대체는 후행 줄 바꿈(0xa 바이트, Cygwin에서는 다를 수 있음)을 제거하므로 read여기서 사용하는 것이 가장 좋습니다 .

$ echo 323 | openssl dgst -sha1 -binary | hd
00000000  3a 8b 03 4a 5d 00 e9 07  b2 9e 0a 61 b3 54 db 45  |:..J]......a.T.E|
00000010  63 4b 37 b0                                       |cK7.|
00000014

0바이트와 개행 문자(0xa)가 어떻게 모두 포함되어 있는지 확인하세요.

$ echo 323 | openssl dgst -sha1 -binary | IFS= LC_ALL=C read -ru0 -k20 var &&
  var=${var}World
$ printf %s $var | hd
00000000  3a 8b 03 4a 5d 00 e9 07  b2 9e 0a 61 b3 54 db 45  |:..J]......a.T.E|
00000010  63 4b 37 b0 57 6f 72 6c  64                       |cK7.World|
00000019

이 변수는 내장 명령( printf...)에만 전달할 수 있다는 점을 다시 한 번 참고하세요.

이제 원하는 것이 다시 해시하는 것뿐이라면,

(echo 323 | openssl dgst -sha1 -binary; printf %s World) |
  openssl dgst -sha1 -binary

변수는 필요하지 않습니다.

관련 정보