Menu

#363 Fix incorrect fields in UNIX TAR format

open
nobody
None
5
2021-05-16
2021-05-15
Shell
No

Several posts on Ru.Board forum address problems in TAR archives created by 7-Zip. One of such problems is that device number fields in UStar format are filled with binary zeros, while the standard expects ASCII data. The problem is caused by the following lines in COutArchive::WriteHeaderReal (TarOut.cpp):

memset(record, 0, NFileHeader::kRecordSize);
/* skipped some lines of code */
if (item.DeviceMajorDefined) RETURN_IF_NOT_TRUE(WriteOctal_8(cur, item.DeviceMajor)); cur += 8;
if (item.DeviceMinorDefined) RETURN_IF_NOT_TRUE(WriteOctal_8(cur, item.DeviceMinor)); cur += 8;

I suggest a patch for fixing that (it has already been suggested for 7-Zip-zstd). The most obvious one is to fill these fields anyway:
RETURN_IF_NOT_TRUE(WriteOctal_8(cur,item.DeviceMajorDefined ? item.DeviceMajor : 0)); cur += 8;
RETURN_IF_NOT_TRUE(WriteOctal_8(cur,item.DeviceMinorDefined ? item.DeviceMinor : 0)); cur += 8;

The operator ?: can also be rewritten as follows:
(item.DeviceMinorDefined ? ~0 : 0) & item.DeviceMinor
which has an efficient x86 assembly implementation with SBB.

Discussion

  • Shell

    Shell - 2021-05-15

    Maybe the filling can be specified differently instead:
    memset(record, 0, NFileHeader::kNameSize);
    memset(record, '0', NFileHeader::kRecordSize-NFileHeader::kNameSize);
    /* do the job */
    memset(record, 0, NFileHeader::kRecordSize-(cur-record));
    RINOK(WriteBytes(record, NFileHeader::kRecordSize));

     
  • Igor Pavlov

    Igor Pavlov - 2021-05-16

    when I call tar in ubuntu linux with the command:

    tar -cvf linux.tar 1.txt
    

    It also writes binary zeros to these fields.
    So 7-Zip is consistent with tar program for these fields.

     

    Last edit: Igor Pavlov 2021-05-16

Log in to post a comment.

Want the latest updates on software, tech news, and AI?
Get latest updates about software, tech news, and AI from SourceForge directly in your inbox once a month.