이 기사에서는 Ruby 포장 및 압축 풀기 방법에 대해 알아볼 것입니다!
하지만 이러한 방법이 필요한 이유는 무엇입니까?
텍스트 작업은 바이너리 데이터 작업보다 훨씬 쉽습니다. .
텍스트를 사용하면 다음을 사용할 수 있습니다.
- 정규 표현식
scan
과 같은 메소드 &match
- gsub
그러나 이진 데이터로 작업하려면 몇 가지 추가 작업이 필요합니다. 여기에서 Array#pack 및 String#unpack 메서드가 작동합니다.
간단한 문자열로 시작하여 더 흥미로운 내용으로 넘어가는 몇 가지 예를 보여드리겠습니다.
문자열을 ASCII 값으로
이것은 문자열의 모든 문자를 10진수 값으로 변환합니다:
str = "AABBCC" str.unpack("c*") # [65, 65, 66, 66, 67, 67]
"c*"
주목 unpack
인수 .
이것은 unpack
을 알려주는 "형식 문자열"입니다. 데이터로 무엇을 할 것인가. 이 경우 c
한 문자를 가져와 정수 값으로 변환하는 것을 의미합니다(String#ord 메서드도 이 작업을 수행합니다).
별표 *
"모든 입력 데이터에 대해 이 형식을 반복하십시오"라고만 표시됩니다.
16진수를 문자열로 변환
H
pack
과 함께 사용 메소드는 16진수를 문자열로 변환합니다.
예 :
["414243"].pack("H*") # "ABC" "ABC".unpack("H*") # ["414243"]
16진수를 정수로 변환하는 방법
이 형식 문자열은 4바이트의 데이터를 사용하고 정수를 반환합니다. 한 가지 주의할 점은 이러한 바이트가 "리틀 엔디안" 형식이라는 것입니다.
예 :
"\xff\x00\x00\x00".unpack("l").first # 255
"\x90\xC0\xDD\x08".unpack("l").first # 148750480
first
를 사용했습니다. unpack
하기 때문에 여기에 있습니다. 배열을 반환합니다.
Unpack 방법으로 이진 파일 구문 분석
EXE, PNG 또는 GZIP과 같은 바이너리 파일을 어떻게 읽습니까?
이 파일을 일반 텍스트처럼 읽으면 임의의 데이터처럼 보이는 것을 볼 수 있습니다...
무작위가 아닙니다.
문서화된 구조가 있습니다. 이러한 많은 파일 형식 및 unpack
메소드는 해당 데이터를 읽고 유용한 것으로 변환하는 데 사용할 수 있는 것입니다.
예시입니다 :
binary_data = "\x05\x00\x68\x65\x6c\x6c\x6f" length, message = binary_data.unpack("Sa*") # [5, "hello"]
이 예에서 바이너리 데이터(1과 0보다 훨씬 더 간결한 16진수로 표시됨)에는 다음 문자열의 길이가 포함된 2바이트(16비트) 길이 필드가 있습니다. 그런 다음 문자열 자체가 있습니다.
바이너리 파일 및 바이너리 네트워크 프로토콜에 "길이" 필드가 있는 것은 매우 일반적입니다.
읽어야 할 바이트 수를 파서에 정확히 알려줍니다. .
네.
이 예에서 길이와 데이터를 모두 한 단계로 읽는다는 것을 알고 있습니다. 이는 단순하게 유지하기 위한 것입니다.
BinData Gem 사용 방법
바이너리 구조를 구문 분석하는 데 도움이 되도록 특별히 제작된 bindata gem도 있습니다.
예시입니다 :
class BinaryString < BinData::Record endian :little uint16 :len string :name, :read_length => :len end
read_length
주목 매개변수. 이렇게 하면 bindata가 필드에서 길이를 계산하도록 지시하므로 많은 작업을 절약할 수 있습니다. 🙂
따라서 바이너리 형식에 대한 파서를 작성하려면 다음 단계를 따르십시오.
- 이 형식에 대한 사양 찾기(공개되지 않은 경우 리버스 엔지니어링해야 하며 이는 그 자체로 전체 주제임)
- 파일의 모든 섹션에 대해 `bindata` 클래스 작성(일반적으로 먼저 메타데이터가 있는 헤더 섹션을 찾은 다음 여러 데이터 섹션을 찾음)
- 데이터를 읽고 원하는 대로 처리합니다(예:PNG에서 이미지 색상을 변경할 수 있음)
- 이익!
bindata
의 전체 예를 보려면 실제로 github에서 내 PNG 파서를 살펴보십시오.
Base64 인코딩
"Base64"라는 인코딩 유형이 있습니다. 이전에 URL에서 본 적이 있을 것입니다.
이렇게 생겼어요 :
U2VuZCByZWluZm9yY2VtZW50cw==
끝에 있는 이중 등호는 일반적으로 Base64
를 다루고 있음을 알리는 신호입니다. , 일부 입력은 등호가 없는 결과를 초래할 수 있습니다(패딩으로 사용됨).
그래서 내가 이 말을 하는 이유는...
그 자체로 알아두면 유용한 것 외에도?
문자열을 Base64
로 변환할 수 있습니다. pack
사용 방법.
여기에서 볼 수 있듯이 :
def encode64(bin) [bin].pack("m") end encode64 "abcd" # "YWJjZA==\n"
사실 이것은 Base64
에서 사용되는 정확한 방법입니다. 표준 라이브러리의 모듈입니다.
요약
이 게시물에서 pack
에 대해 배웠습니다. &unpack
이진 데이터로 작업하는 데 도움이 되는 메서드. 이것을 사용하여 바이너리 파일을 구문 분석하고 문자열을 ASCII 값으로 변환하며 Base64 인코딩에 사용할 수 있습니다.
공유 및 구독을 잊지 마세요. 이렇게 더 많은 블로그 게시물을 즐길 수 있습니다! 🙂