|
BOM을 반드시 사용할 필요는 없으며,
사용할 경우 문서의 가장 앞에 등장해야 한다.
유니코드는 8비트, 16비트 혹은 32비트 정수 단위로 인코딩할 수 있다.
16비트 및 32비트 표현의 경우,
알 수 없는 출처로부터 텍스트를 읽는 컴퓨터는 데이터를 어떤 바이트 순서로 인코딩했는지 알아야 한다.
BOM은 문서의 나머지 부분과 같은 방식으로 인코딩되며 바이트 순서가 바뀔 경우 비문자인 유니코드 코드 포인트가 되므로,
이 텍스트를 읽는 프로세스는 문서 외적인 정보 없이도 처음 몇 바이트를 검사함으로써 엔디언을 확인할 수 있다.
이후 수신자는 필요할 경우 바이트 순서를 자신의 엔디안에 맞게 바꾸며,
이 이후의 처리에는 더 이상 BOM이 필요하지 않다.
BOM의 바이트열은 유니코드 인코딩마다 다르며,
이들이 다른 인코딩으로 저장된 문서의 가장 앞에 등장할 가능성은 적다.
그러므로, 문서의 가장 앞에 인코딩된 BOM을 추가함으로써 텍스트가 유니코드임을 나타내고 그 인코딩 방식을 명시할 수 있다. BOM 문자를 이 방식으로 사용하는 것을 "유니코드 시그니처"라 한다.[2]
사용법[편집]
BOM 문자가 데이터 스트림 중간에 등장할 경우,
유니코드에서는 이를
"폭과 줄 바꿈 없는 공백"(단어 문자 사이에서 줄바꿈을 방지함)
로 해석해야 한다고 명시하고 있다.
유니코드 3.2에서는 이 용례를
단어 결합자 (U+2060)로 대체하는 것을 권장하며,[1]
이로 인해 U+FEFF는 BOM의 용도로만 사용할 수 있게 되었다.
UTF-8[편집]
BOM의 UTF-8 표현은 (16진) 바이트열인 0xEF,0xBB,0xBF이다.
유니코드 표준은 UTF-8에 BOM을 허용하지만,[3]
이는 필수가 아니며 권장 사항도 아니다.[4]
UTF-8에서 바이트 순서는 어떤 의미도 없으므로,[5]
UTF-8 내에서는 문서의 가장 앞에서 문서가 UTF-8로 인코딩되었거나,
BOM이 있는 문서가 UTF-8로 변환된 것을 표시하는 이외의 용도는 없다.
또한 표준에서는 BOM이 존재하는 경우 다른 인코딩으로 변환했다가 되돌릴 때 정보가 손실되지 않고, 이에 의존하는 코드가 계속 작동하도록 제거하지 않는 것을 권장한다.[6][7] IETF는 프로토콜이 (a) 항상 UTF-8을 사용하거나, (b) 인코딩 방식을 다른 방법으로 나타낼 수 있는 경우, "U+FEFF를 시그니처로 사용하는 것을 금지해야(SHOULD forbid) 한다"고 명시한다.[8]
BOM을 사용하지 않는 텍스트는 유니코드를 인식하지 못하는 일부 소프트웨어와 하위 호환된다. 이러한 예로는 문자열 리터럴에 ASCII가 아닌 바이트를 허용하지만 파일의 가장 앞에서는 금지하는 프로그래밍 언어가 있다.
UTF-8은 올바른 UTF-8 문자열을 이루지 않는 바이트 조합이 모든 조합 중 큰 비율을 차지한다는 점에서 "성긴" 인코딩이라고 할 수 있다. 이진 데이터와 다른 인코딩으로 작성된 텍스트는 UTF-8로 올바르지 않은 바이트열을 포함할 가능성이 크며, 이에 대한 현실적인 예외는 텍스트가 완전히 ASCII 범위의 바이트로만 작성되었을 때뿐이다. 최근의 모든 인코딩은 ASCII 범위의 바이트로 ASCII 문자를 표현하므로, ASCII만 포함하는 텍스트는 이를 작성한 시스템에서 무슨 인코딩을 사용했는지와 무관하게 UTF-8로 해석해도 문제가 없다. 이러한 사항으로 인해 휴리스틱 접근을 이용해 BOM 없이도 UTF-8을 사용하고 있는지 높은 신뢰도로 판정할 수 있다.
마이크로소프트의 컴파일러[9]와 인터프리터나 메모장 등 마이크로소프트 윈도우의 여러 소프트웨어는 휴리스틱을 이용하는 대신 BOM을 필수적인 매직 넘버로 취급한다. 이러한 프로그램은 UTF-8로 텍스트를 저장할 때 BOM을 추가하며, BOM이 있거나 파일에 ASCII만 포함되어 있는 경우가 아니라면 UTF-8을 해석하지 못한다. 버전 5.1까지의 파워셸은 UTF-8 XML 문서를 저장할 때 BOM을 추가했지만, PowerShell Core 6에서는 일부 명령에 -Encoding 스위치로 utf8NoBOM을 추가해 문서를 BOM 없이 저장할 수 있도록 하였다. 구글 독스 역시 문서를 다운로드 가능한 플레인 텍스트로 변환할 때 BOM을 추가한다.
UTF-16[편집]
UTF-16에서,
BOM(U+FEFF)은 파일의 첫 번째 문자로 배치되어
그 파일의 모든 16비트 코드 단위의 엔디언(바이트 순서)을 나타낼 수 있다.
이 스트림을 잘못된 엔디언으로 읽으려고 하면 바이트가 뒤집혀 문자 U+FFFE를 읽을 수 있으며,
이는 유니코드에서 텍스트에 등장해서는 안 되는 "비문자"(non-character)로 정의되어 있다.
이들은 모두 올바른 UTF-8이 아니므로,
이러한 파일은 UTF-8로 인코딩되지 않았음을 알 수 있다.
IANA에 등록된 문자 집합인 UTF-16BE와 UTF-16LE의 경우,
이 문자 집합의 이름으로 이미 바이트 순서가 결정되기 때문에
바이트 순서 표식을 사용해서는 안 된다.
이런 문서 내의 어떤 위치에든 BOM이 있을 경우 "폭과 줄 바꿈 없는 공백"으로 해석한다.
BOM이 없더라도 텍스트가 UTF-16인지 및 어떤 엔디언을 사용했는지를 ASCII 문자를 이용해(즉, 0x20에서 0x7E 범위 혹은 0x0A(LF)와 0x0D(CR) 바이트에 인접한 0 바이트) 추측할 수 있다. 이러한 문자가 많이(즉, 무작위로 등장하는 경우보다 훨씬 자주) 등장할 경우 문서가 높은 확률로 UTF-16임을, 0이 짝수 번째로 등장하는지 홀수 번째로 등장하는지를 확인해 이 문서의 엔디언을 추론할 수 있다. 그러나 이 방법은 오진의 가능성이 있다.
유니코드 표준의 '적합성' (3.10장) 중 D98항에서는 "UTF-16 인코딩 스킴은 BOM으로 시작하거나 시작하지 않을 수 있다. 그러나, BOM이 없고 고수준의 프로토콜이 존재하지 않을 경우 UTF-16 인코딩 스킴의 바이트 순서는 빅 엔디언이다."라고 명시하고 있다. 고수준의 프로토콜이 언제 적용되는지는 해석의 여지가 있다. 예를 들어, 리틀 엔디언을 사용하는 컴퓨터에 저장된 파일은 암시적으로 UTF-16LE로 인코딩되었다고 할 수 있다. 이런 이유로 빅 엔디언 추정 조항은 무시되는 경우가 많다. HTML5에 사용된 W3C/WHATWG 인코딩 표준에서는 "utf-16"이나 "utf-16le"로 표시된 콘텐츠를 리틀 엔디언으로 해석하는 것으로 명시하지만,[10] 바이트 순서 표식이 있을 경우 이 BOM을 다른 모든 사항보다 우선한다.[11]
UTF-16을 바이트 기반 인코딩으로 해석하는 프로그램은 무의미한 문자열을 표시하지만,
UTF-16 표현의 하위 바이트가 ASCII 코드와 같으므로 ASCII 문자는 알아볼 수 있다.
상위 바이트 0은 공백이나 점 등 일정한 문자로 표시되거나 아예 표시되지 않을 수도 있다.
UTF-32[편집]
UTF-32에도 BOM을 사용할 수는 있지만,
이 인코딩은 전송에 거의 사용되지 않는다.
이 이외에는 UTF-16과 동일한 규칙이 적용된다.
리틀 엔디언 UTF-32에서의 BOM 패턴은 리틀 엔디언 UTF-16에서 BOM 다음에 널 문자가 오는 것과 같으며, 이와 같이 서로 다른 인코딩에서 BOM 패턴이 같은 경우는 드물다. BOM을 이용해 인코딩을 추론하는 경우 문서가 UTF-32인지 널 문자로 시작하는지를 결정해야 한다.
인코딩에 따른 바이트 순서 표식[편집]
아래 표는 BOM 문자가 다양한 인코딩에서 바이트열로 어떻게 표현되는지와 이를 구식 인코딩(CP1252, C0 제어 문자의 경우 캐럿 표기)에서 어떻게 출력되는지를 정리한 것이다.
인코딩16진수 표현10진수 표현CP1252 문자로 된 바이트
UTF-8[a] | EF BB BF | 239 187 191 |  |
UTF-16 (BE) | FE FF | 254 255 | þÿ |
UTF-16 (LE) | FF FE | 255 254 | ÿþ |
UTF-32 (BE) | 00 00 FE FF | 0 0 254 255 | ^@^@þÿ (^@은 널 문자) |
UTF-32 (LE) | FF FE 00 00 | 255 254 0 0 | þÿ^@^@ (^@은 널 문자) |
UTF-7[a] | 2B 2F 76 382B 2F 76 39 2B 2F 76 2B 2B 2F 76 2F[b][13][14] | 43 47 118 5643 47 118 57 43 47 118 43 43 47 118 47 | +/v8+/v9 +/v+ +/v/ |
UTF-1[a] | F7 64 4C | 247 100 76 | ÷dL |
UTF-EBCDIC[a] | DD 73 66 73 | 221 115 102 115 | Ýsfs |
SCSU[a] | 0E FE FF[c] | 14 254 255 | ^Nþÿ (^N은 시프트 아웃 문자) |
BOCU-1[a] | FB EE 28 | 251 238 40 | ûî( |
GB-18030[a] | 84 31 95 33 | 132 49 149 51 | „1•3 |
첫댓글 유니코드/ 위키 https://ko.wikipedia.org/wiki/%EB%B0%94%EC%9D%B4%ED%8A%B8_%EC%88%9C%EC%84%9C_%ED%91%9C%EC%8B%9D
부호화 형식별로
UTF-7
UTF-8
CESU-8
UTF-16
UTF-32
UTF-EBCDIC
SCSU
퓨니코드
GB18030
UCS
양방향 텍스트
BOM
한중일 통합 한자
유니코드 범위 목록
유니코드 등가성
유니코드와 HTML
유니코드와 전자 우편
유니코드 글꼴
뭐 아무튼 범위를 알아봐야겠다 그리고,
바이트 순서 마크(표식). BOM.
바이트 순서 마크(표식). BOM.
유니코드 문자 U+FEFF를 쓴다. 인코딩 방식에 따라서 FF FE로 표기하기도 하나, 실제로 해석할 때에는 U+FEFF로 읽는다. 그리고 U+FFFE에는 문자가 처음부터 배당되지 않았기에, U+FFFE가 실제로 쓰일 일은 없어서 U+FEFF가 U+FFFE와 혼동될 여지가 앞으로도 없다.
유니코드의 아랍 문자용 블럭인 Arabic Presentation Forms-B에 끼어 있다.
정식 이름은 ZERO WIDTH NO-BREAK SPACE이다. 공백의 일종이지만 원래 용도 대신 BOM으로 쓰며, zero width non-breaking space의 역할은 U+2060인 WORD JOINER가 대신한다.
이 문자는 보통 UTF-16으로 된 파일의 엔디언이 올바르게 판단될 수 있도록 하기 위해서 파일의 맨 앞에 삽입된다. 실제로 UTF-16의 처리 방식은 순서에 따라 빅 엔디언(big endian, be)과 리틀 엔디언(little endian, le) 2가지가 있다. 두 방식 다 나름의 장점이 있기 때문에 아직도 둘 다 쓴다.
@칡 흰 UTF-8은 엔디언 문제가 없는데도 일부 텍스트 에디터는 강제로 U+FEFF 문자를 삽입해서 문제를 일으키기도 한다. 다만 유니코드 보급율이 느리다보니 일반 유저를 대상으로 하는 텍스트 에디터들의 경우 BOM이 없으면 일단 완성형(및 각 언어별 코드페이지)으로 읽고보는 식으로 처리하는 경우가 상당수. 그러다보니 UTF-8 문서에도 BOM을 넣어두는게 편한 게 사실이다.[1] 그리고 UTF-8에서 BOM은 EF BB BF와 같이 표기된다.
그런데 이게 유닉스 쪽까지 포함한다면 얘기가 달라진다. PHP의 경우 읽어들이는 내용이 PHP 소스로 되어 있으면 PHP로 실행하기 시작하고, 일반 텍스트로 되어 있으면 텍스트로 읽어들이기 시작하는데 PHP는 BOM을 인식하지 못한다. 그래서 일반 텍스트로 알고 보냈는데 하필 BOM으로 시작하는 바람에, PHP가 시작되니 오작동을 일으키는 것. 이외에 콘솔에서 텍스트 파일 합치는 데도 애로사항이 생길 수 있는 등, 개발자 입장에서는 BOM을 자동으로 넣어주는 프로그램이 오히려 욕먹는다.
@칡 흰 이런 경우 저장 시 BOM을 추가할지 말지 선택할 수 있는 에디터 또는 IDE로 문서를 저장해야 한다. Notepad++, IntelliJ IDEA, Visual Studio Code, EditPlus 등의 개발 툴은 UTF-8에 BOM을 추가할지 여부를 선택할 수 있다.
대표적으로 BOM을 자동 삽입하는 텍스트 에디터가 Microsoft Windows의 보조 프로그램인 메모장이다. Windows 쪽 에디터 프로그램들은 BOM이 없으면 UTF-8이라는 것을 인식하지 못하는 경우가 종종 발생한다. 다만 Windows 10 1903부터 기본 인코딩이 기존의 ANSI(=MBCS)에서 BOM 없는 UTF-8으로 바뀌었으며, 저장 시에 BOM을 붙일지 선택할 수 있게 바뀌었다. Visual Studio에서는 소스 파일의 인코딩을 UTF-8 BOM으로 설정하면 한글이 정상 출력되지만, UTF-8으로 설정하면 파일을 ANSI로 인식해 에디터와 콘솔에서 한글이 전부 깨진 채로 나온다.
@칡 흰 윈도우에서 한글을 출력시키기 위해 UTF-8에 BOM을 붙여 저장한 파일의 경우, 유닉스 계통 컴파일러(GCC, LLVM/Clang 등)와 공유해서 사용하면 BOM의 존재로 인하여 오작동을 일으킬 수도 있다.
쓸 데 없는 짓만 한다는, 욕을 먹는 놈이 되지 말자 ㅋ 한쿡의 글짜는 띄어쓰기를 자 ㄹ해야 함ㅋㅋㅋㅋ 언제나 호갱은 알지 못할 불만과 불평이 있다.
눈에 보이지 않는 특정 바이트를 넣는다.