벌써 두번이나 했는데 매번 기억이 안 나서 몇번씩 시행착오를 한 관계로 잊어버리지 않기 위해서 기록한다.
Source code에 한글로 comment를 쓰기 좋아하는 사람들(사실 나도 간혹 그런다)이 꽤 많이 있는데, file의 character encoding만 잘 맞춘다면야 comment를 뭘로 쓰든 사실 별 상관이 없다. 오히려 자신의 제일 잘 구사할 수 있는 언어인 한국어로 설명을 달아놓는 것이 더 좋을 수도 있을 것이다. 그런데, 이건 encoding을 잘 맞출 때나 할 수 있는 얘기고, EUC-KR이나 CP949로 저장되어야 할 파일을 어찌어찌 하다가 UTF-8 같은 것으로 저장해버리는 일이 종종 생긴다. 흔히 editor가 EUC-KR로 encoding된 파일을 열 때 제대로 decoding을 하지 않은 채로 열고, 저장할 때는 그냥 UTF-8로 저장해 버리는 경우에 많이 발생하는 듯 하다. 어쨌거나 내가 최근 며칠 사이에 아주 자주 마주치는 상황은 아마도 그런 전차로 발생한 듯 한다.
어떻게 이런 일이 일어났는지는 뭐 알 수 없는 거고, 현재 상태만 설명하자면 이렇다.
- 파일의 실제 character set은 EUC-KR이다.
- 그런데 이 파일이 적절한 decoding과 다시 적절한 encoding 없이 바로 UTF-8로 저장되었다.
이것을 다음과 같은 과정을 거쳐서 복원 시도할 것이다.
- UTF-8을 decoding해서 latin1으로 표현된 파일을 얻는다.
- 이 파일을 EUC-KR로 decoding한 후에 다시 UTF-8로 encoding한 파일을 얻는다.
2번의 결과물을 보면 망가졌던 한글 character 중 대략 70% 정도는 복구할 수가 있다. 그리고 나머지는 사람의 두뇌를 이용해서 복구가 안된 글자들을 상상해서 끼워 맞추는 작업이 필요하다.
최초의 파일(file1.c)은 이렇다. (vim에서 열어 본 것. ~/.vimrc에서 fileencodings는 ucs-bom,utf-8,euc-kr,cp949,iso-2022-kr,latin1 로 설정되어 있음)
이것을 bvi로 열어서 해당하는 부분을 보면 아래와 같다.
첫번째 변환은 다음과 같이 한다.
iconv -f utf-8 -t latin1//IGNORE file1.c > file2.c
최초 파일(file1.c)을 utf-8로 인식하여 연 다음에 latin1으로 변환하라는 뜻인데, latin1은 사실 아무런 변환을 하지 않은 것과 같다. 따라서 우연히 utf-8로 잘못 저장된 내용을 복구한 것이 된다.
이 결과는 다음과 같다(file2.c)
vim에서는 같은 것처럼 보이지만, 처음은 encoding이 utf-8이었고, 지금은 latin1으로 인식한다.
bvi로 열면 다음과 같다. 분명 파일 내용은 바뀌어 있다.
여기에서 생각할 것은 이 파일은 encoding은 실제로는 euc-kr이라는 것이다. 적절한 code 변환 없이 저장되는 바람에 일부 byte들이 유실되었고 vim로 자동인식해서 열어봐도 그냥 latin1으로 표시될 뿐이다. 이 파일을 강제로 euc-kr로 인식시키고자 다시 iconv를 이용한다. 두번째 변환은 다음과 같다.
iconv -f euc-kr -t utf-8//IGNORE file2.c > file3.c
이 결과물(file3.c)은 제대로 utf-8로 저장된 파일이 된다.
vim에서 열면 아래와 같다.
bvi로 열면 아래와 같다.
마지막 결과를 잘 보면 한글 한 글자당 3 byte가 사용되는 제대로 된 utf-8 encoding인 것처럼 보인다. 물론 몇가지 글자들은 정보 유실 때문에 여전히 깨지기도 하고, 복원하는 과정에서 잉여 byte들이 끼어들어 뭔가 더 길어진 것처럼 보이기도 한다. 잘 인지되지 않는 글자들은 무시한다. 시간이 남는다면 유실되거나 추가된 byte들을 이러저리 만져보면서 완전한 원본을 만들어낼 수도 있겠으나, 나는 지금 이 글을 쓰면서도 이미 시간을 많이 소비했다. ㅋㅋ 나머지는 나의 한국어 실력을 믿기로 한다.