단 하나의 tar 파일이 도구에 따라 8가지로 갈라진다

The Hardest Tarball?

GNU tar 명령 한 번으로 만든 tarball이 도구마다 전혀 다르게 풀린다. pax 헤더로 하드 링크에 size=512를 넣는 트릭 때문에 GNU tar, bsdtar, 7-Zip, Java Commons Compress, PHP PharData, RubyGems, R는 각기 다른 결과를 내고 .NET과 Julia, uv는 아예 거부한다. 저자는 이런 까다로운 tarball 134개를 모은 tar-minefield 테스트 스위트를 공개했다.

R는 완전히 다른 접근을 한다. 하드 링크가 아니라 empty에 크기를 잘못 적용해, 아카이브 끝 표시에서 가져온 512바이트의 널 문자로 empty를 추출한다.
  1. Joker_vD

    > 이제 POSIX는 하드 링크에 대한 데이터 블록이 pax 아카이브에 "포함될 수 있다"고 말하지만, 이것의 함의는 완전히 명확하지 않다.

    어떻게 그럴 수 있죠? 데이터 블록이 포함된다면, 그것들은 해당 하드 링크 뒤에 있는 파일의 의도된 내용입니다. 그것들은 파일의 이전 내용을 덮어써야 합니다.

    > 그러면 하드 링크 뒤의 512바이트는 그 데이터이고, 우리가 아카이브한 것처럼 빈 헤더가 아니라는 건가요?

    네, 정확합니다.

    > 어떻게 하드 링크가 이전 대응 파일과 다른 내용을 가질 수 있나요?

    아주 간단합니다: 아카이브가 생성되는 동안 두 개의 서로 다른 하드 링크 뒤에 있는 파일이 변경되었고, 아카이브 유틸리티가 이를 감지하여 원래 파일을 되감아 덮어쓰는 대신(테이프에서는 불가능하다는 거 아시죠) 파일의 새 내용을 두 번째 하드 링크의 내용으로 포함시켰습니다. 적어도 저는 이것이 이 허용의 근거였고 추출 시 의도된 동작이라고 생각합니다.

  2. JdeBP

    눈에 띄는 tar 구현이 하나 빠졌습니다. paxmirabilis는 tar, cpio, pax를 하나로 합친 멀티콜 바이너리입니다. 실제로 Debian에서 pax로 얻는 것이 바로 이것입니다.

    * https://mbsd.evolvis.org/pax.htm

    * https://manpages.debian.org/trixie/pax/index.html

    아니요, libarchive의 bsdtar가 아닙니다. BSD 세계에는 tar가 하나 이상 있습니다.

  3. bartvk

    이 사람, 정말 영웅이네요. 이 "가장 어려운 tarball"이 어떻게 생겼는지 보여주는 작은 그래픽까지 포함시켰어요.

    맨 아래에는 훨씬 더 많은 엣지 케이스로 가는 링크가 있습니다.

    이 아름다운 글이 생각나네요: "Parsing JSON is a Minefield"

    https://news.ycombinator.com/item?id=16897061

  4. molticrystal

    >NET, Julia 그리고 uv의 tar-codec - 이 구현들은 tarball을 거부합니다. 기술적으로 POSIX를 준수하지 않더라도 이것이 할 수 있는 최선이라고 생각합니다.

    이것이 가장 안전한 선택이긴 하지만 가장 도움이 되지도 않습니다. 저는 항상 아카이브에서 아무것도 얻지 못하는 것보다 뭔가를 얻는 쪽을 선호합니다. 아카이브의 손상/불규칙성 때문에 데이터 검사가 막혀서는 안 되고, 경고와 추출할 수 있는 것에 대한 주의사항을 붙여 폴백하는 방법만 있으면 됩니다.

  5. zahlman

    > 이 tarball은 제 테스트 스위트 haampie/tar-minefield에서 수집하고 분류 중인 134개의 까다로운 tarball 중 하나입니다.

    분명히 "tarpit"이 더 자연스러운 이름 아닐까요?

이 날의 다른 글

2026-11-10