diff options
author | github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> | 2022-09-14 18:29:56 +0300 |
---|---|---|
committer | GitHub <noreply@github.com> | 2022-09-14 18:29:56 +0300 |
commit | 66a9136f6b7e65945af92bd8769bdfa80fcde741 (patch) | |
tree | 682cd16004e62059bbe3eaf9fda012dbe74e603d /src | |
parent | 83e16f49899e204b07c2b78e2a6a50f18f8c2664 (diff) |
[release/7.0] Fix prefix writing on TarHeaderWrite (#75373)
* Fix buffer too small error on prefix
* Add test
* Remove var usage
* Remove assert
* Update src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntry.Tests.cs
* Add more lengths and improve test
* Add missing using
Co-authored-by: David Cantu <dacantu@microsoft.com>
Diffstat (limited to 'src')
-rw-r--r-- | src/libraries/System.Formats.Tar/src/System/Formats/Tar/TarHeader.Write.cs | 9 | ||||
-rw-r--r-- | src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntry.Tests.cs | 53 |
2 files changed, 56 insertions, 6 deletions
diff --git a/src/libraries/System.Formats.Tar/src/System/Formats/Tar/TarHeader.Write.cs b/src/libraries/System.Formats.Tar/src/System/Formats/Tar/TarHeader.Write.cs index e1166a06681..43fe79ce7dc 100644 --- a/src/libraries/System.Formats.Tar/src/System/Formats/Tar/TarHeader.Write.cs +++ b/src/libraries/System.Formats.Tar/src/System/Formats/Tar/TarHeader.Write.cs @@ -374,12 +374,9 @@ namespace System.Formats.Tar if (_name.Length > FieldLengths.Name) { - int prefixBytesLength = Math.Min(_name.Length - FieldLengths.Name, FieldLengths.Name); - Span<byte> remaining = prefixBytesLength <= 256 ? - stackalloc byte[prefixBytesLength] : - new byte[prefixBytesLength]; - - int encoded = Encoding.ASCII.GetBytes(_name.AsSpan(FieldLengths.Name), remaining); + int prefixBytesLength = Math.Min(_name.Length - FieldLengths.Name, FieldLengths.Prefix); + Span<byte> remaining = stackalloc byte[prefixBytesLength]; + int encoded = Encoding.ASCII.GetBytes(_name.AsSpan(FieldLengths.Name, prefixBytesLength), remaining); Debug.Assert(encoded == remaining.Length); checksum += WriteLeftAlignedBytesAndGetChecksum(remaining, buffer.Slice(FieldLocations.Prefix, FieldLengths.Prefix)); diff --git a/src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntry.Tests.cs b/src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntry.Tests.cs index b0c78298f2b..2808914db4e 100644 --- a/src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntry.Tests.cs +++ b/src/libraries/System.Formats.Tar/tests/TarWriter/TarWriter.WriteEntry.Tests.cs @@ -3,6 +3,7 @@ using System.Collections.Generic; using System.IO; +using System.Linq; using Xunit; namespace System.Formats.Tar.Tests @@ -299,5 +300,57 @@ namespace System.Formats.Tar.Tests } } } + + [Theory] + [InlineData(TarEntryFormat.V7)] + // [InlineData(TarEntryFormat.Ustar)] https://github.com/dotnet/runtime/issues/75360 + [InlineData(TarEntryFormat.Pax)] + [InlineData(TarEntryFormat.Gnu)] + public void WriteLongName(TarEntryFormat format) + { + var r = new Random(); + foreach (int length in new[] { 99, 100, 101, 199, 200, 201, 254, 255, 256 }) + { + string name = string.Concat(Enumerable.Range(0, length).Select(_ => (char)('a' + r.Next(26)))); + WriteLongNameCore(format, name); + } + } + + private void WriteLongNameCore(TarEntryFormat format, string maxPathComponent) + { + TarEntry entry; + MemoryStream ms = new(); + using (TarWriter writer = new(ms, true)) + { + TarEntryType entryType = format == TarEntryFormat.V7 ? TarEntryType.V7RegularFile : TarEntryType.RegularFile; + entry = InvokeTarEntryCreationConstructor(format, entryType, maxPathComponent); + writer.WriteEntry(entry); + + entry = InvokeTarEntryCreationConstructor(format, entryType, Path.Join(maxPathComponent, maxPathComponent)); + writer.WriteEntry(entry); + } + + ms.Position = 0; + using TarReader reader = new(ms); + + entry = reader.GetNextEntry(); + string expectedName = GetExpectedNameForFormat(format, maxPathComponent); + Assert.Equal(expectedName, entry.Name); + + entry = reader.GetNextEntry(); + expectedName = GetExpectedNameForFormat(format, Path.Join(maxPathComponent, maxPathComponent)); + Assert.Equal(expectedName, entry.Name); + + Assert.Null(reader.GetNextEntry()); + + string GetExpectedNameForFormat(TarEntryFormat format, string expectedName) + { + if (format is TarEntryFormat.V7 && expectedName.Length > 100) // V7 truncates names at 100 characters. + { + return expectedName.Substring(0, 100); + } + return expectedName; + } + } } } |