From 6e2ddefbb5ffdcd5a36f4474b4004d07c698bec6 Mon Sep 17 00:00:00 2001 From: Timofey Solomko Date: Sat, 15 Jul 2017 20:47:57 +0300 Subject: [PATCH] Move tar long names parsing from entry to container --- Sources/TarContainer.swift | 38 ++++++++++++++++++++++++++++---------- Sources/TarEntry.swift | 11 +++-------- 2 files changed, 31 insertions(+), 18 deletions(-) diff --git a/Sources/TarContainer.swift b/Sources/TarContainer.swift index 47a445ff..c757395b 100644 --- a/Sources/TarContainer.swift +++ b/Sources/TarContainer.swift @@ -45,6 +45,30 @@ public class TarContainer: Container { } else { pointerData.index -= 1024 } + pointerData.index += 156 + let fileTypeIndicator = String(Character(UnicodeScalar(pointerData.byte()))) + if fileTypeIndicator == "K" || fileTypeIndicator == "L" { + pointerData.index -= 33 + + guard let octalSize = Int(try pointerData.nullSpaceEndedAsciiString(cutoff: 12)) + else { throw TarError.fieldIsNotNumber } + let size = octalSize.octalToDecimal() + pointerData.index += 376 + + let dataStartIndex = pointerData.index + let longPath = try pointerData.nullEndedAsciiString(cutoff: size) + + if fileTypeIndicator == "K" { + longLinkName = longPath + } else { + longName = longPath + } + pointerData.index = dataStartIndex + pointerData.index += size.roundTo512() + continue + } + pointerData.index -= 157 + let entry = try TarEntry(pointerData, lastGlobalExtendedHeader, lastLocalExtendedHeader, longName, longLinkName) switch entry.type { @@ -53,16 +77,10 @@ public class TarContainer: Container { case .localExtendedHeader: lastLocalExtendedHeader = String(data: entry.data(), encoding: .utf8) default: - if entry.isLongName { - longName = try DataWithPointer(data: entry.data()).nullEndedAsciiString(cutoff: entry.size) - } else if entry.isLongLinkName { - longLinkName = try DataWithPointer(data: entry.data()).nullEndedAsciiString(cutoff: entry.size) - } else { - output.append(entry) - lastLocalExtendedHeader = nil - longName = nil - longLinkName = nil - } + output.append(entry) + lastLocalExtendedHeader = nil + longName = nil + longLinkName = nil } } diff --git a/Sources/TarEntry.swift b/Sources/TarEntry.swift index cddf47b4..61bd42cb 100644 --- a/Sources/TarEntry.swift +++ b/Sources/TarEntry.swift @@ -165,9 +165,6 @@ public class TarEntry: ContainerEntry { private let dataObject: Data - let isLongName: Bool - let isLongLinkName: Bool - private let gnuLongName: String? private let gnuLongLinkName: String? @@ -249,8 +246,6 @@ public class TarEntry: ContainerEntry { // File type let fileTypeIndicator = String(Character(UnicodeScalar(pointerData.byte()))) - isLongLinkName = fileTypeIndicator == "K" - isLongName = fileTypeIndicator == "L" let fileType = EntryType(rawValue: fileTypeIndicator) ?? .vendorUnknownOrReserved type = fileType switch fileType { @@ -432,9 +427,9 @@ extension DataWithPointer { } -fileprivate extension Int { +extension Int { - fileprivate func octalToDecimal() -> Int { + func octalToDecimal() -> Int { var octal = self var decimal = 0, i = 0 while octal != 0 { @@ -446,7 +441,7 @@ fileprivate extension Int { return decimal } - fileprivate func roundTo512() -> Int { + func roundTo512() -> Int { let fractionNum = Double(self) / 512 let roundedNum = Int(ceil(fractionNum)) return roundedNum * 512