Make file opens safer and more consistent

This commit is contained in:
Matt Nadareski
2025-01-04 23:52:16 -05:00
parent 58a7558dd8
commit 281375f8e9
12 changed files with 96 additions and 49 deletions

View File

@@ -29,7 +29,8 @@ namespace SabreTools.DatFiles.Formats
public override void ParseFile(string filename, int indexId, bool keep, bool statsOnly = false, bool throwOnError = false) public override void ParseFile(string filename, int indexId, bool keep, bool statsOnly = false, bool throwOnError = false)
{ {
// Prepare all internal variables // Prepare all internal variables
var sr = new StreamReader(System.IO.File.OpenRead(filename), new UTF8Encoding(false)); var fs = System.IO.File.Open(filename, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
var sr = new StreamReader(fs, new UTF8Encoding(false));
var jtr = new JsonTextReader(sr); var jtr = new JsonTextReader(sr);
var source = new Source(indexId, filename); var source = new Source(indexId, filename);
long sourceIndex = ItemsDB.AddSource(source); long sourceIndex = ItemsDB.AddSource(source);

View File

@@ -787,7 +787,7 @@ namespace SabreTools.DatTools
// Otherwise, just open the filestream // Otherwise, just open the filestream
else else
{ {
stream = System.IO.File.OpenRead(file); stream = System.IO.File.Open(file, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
} }
// If the stream is null, then continue // If the stream is null, then continue

View File

@@ -53,7 +53,7 @@ namespace SabreTools.FileTypes.Aaru
/// <param name="filename">Filename respresenting the AaruFormat file</param> /// <param name="filename">Filename respresenting the AaruFormat file</param>
public static AaruFormat? Create(string filename) public static AaruFormat? Create(string filename)
{ {
using FileStream fs = File.OpenRead(filename); using Stream fs = File.Open(filename, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
return Create(fs); return Create(fs);
} }

View File

@@ -228,10 +228,11 @@ namespace SabreTools.FileTypes.Archives
{ {
gzipEntryRom.Filename = gamename; gzipEntryRom.Filename = gamename;
using BinaryReader br = new(File.OpenRead(Filename)); using Stream stream = File.Open(Filename, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
br.BaseStream.Seek(-8, SeekOrigin.End); stream.Seek(-8, SeekOrigin.End);
gzipEntryRom.CRC = br.ReadBytesBigEndian(4); gzipEntryRom.CRC = stream.ReadBytes(4);
gzipEntryRom.Size = br.ReadInt32BigEndian(); Array.Reverse(gzipEntryRom.CRC);
gzipEntryRom.Size = stream.ReadInt32BigEndian();
} }
// Otherwise, use the stream directly // Otherwise, use the stream directly
else else
@@ -298,14 +299,12 @@ namespace SabreTools.FileTypes.Archives
} }
// Get the Romba-specific header data // Get the Romba-specific header data
BinaryReader br = new(File.OpenRead(Filename)); Stream stream = File.Open(Filename, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
byte[] header = br.ReadBytes(12); // Get preamble header for checking byte[] header = stream.ReadBytes(12); // Get preamble header for checking
br.ReadBytes(16); // headermd5 _ = stream.ReadBytes(16); // headermd5
br.ReadBytes(4); // headercrc _ = stream.ReadBytes(4); // headercrc
br.ReadUInt64(); // headersz _ = stream.ReadUInt64(); // headersz
#if NET40_OR_GREATER stream.Dispose();
br.Dispose();
#endif
// If the header is not correct, return a blank rom // If the header is not correct, return a blank rom
bool correct = true; bool correct = true;
@@ -363,14 +362,12 @@ namespace SabreTools.FileTypes.Archives
byte[] headermd5; // MD5 byte[] headermd5; // MD5
byte[] headercrc; // CRC byte[] headercrc; // CRC
ulong headersz; // Int64 size ulong headersz; // Int64 size
BinaryReader br = new(File.OpenRead(Filename)); Stream stream = File.Open(Filename, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
header = br.ReadBytes(12); header = stream.ReadBytes(12);
headermd5 = br.ReadBytes(16); headermd5 = stream.ReadBytes(16);
headercrc = br.ReadBytes(4); headercrc = stream.ReadBytes(4);
headersz = br.ReadUInt64(); headersz = stream.ReadUInt64();
#if NET40_OR_GREATER stream.Dispose();
br.Dispose();
#endif
// If the header is not correct, return a blank rom // If the header is not correct, return a blank rom
bool correct = true; bool correct = true;
@@ -421,7 +418,8 @@ namespace SabreTools.FileTypes.Archives
inputFile = Path.GetFullPath(inputFile); inputFile = Path.GetFullPath(inputFile);
// Get the file stream for the file and write out // Get the file stream for the file and write out
return Write(File.OpenRead(inputFile), outDir, baseFile); using Stream inputStream = File.Open(inputFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
return Write(inputStream, outDir, baseFile);
} }
/// <inheritdoc/> /// <inheritdoc/>

View File

@@ -194,7 +194,7 @@ namespace SabreTools.FileTypes.Archives
try try
{ {
SharpCompress.Archives.Rar.RarArchive ra = SharpCompress.Archives.Rar.RarArchive.Open(File.OpenRead(Filename)); SharpCompress.Archives.Rar.RarArchive ra = SharpCompress.Archives.Rar.RarArchive.Open(File.Open(Filename, FileMode.Open, FileAccess.Read, FileShare.ReadWrite));
foreach (RarArchiveEntry entry in ra.Entries.Where(e => e != null && !e.IsDirectory)) foreach (RarArchiveEntry entry in ra.Entries.Where(e => e != null && !e.IsDirectory))
{ {
// Create a blank item for the entry // Create a blank item for the entry
@@ -294,8 +294,18 @@ namespace SabreTools.FileTypes.Archives
/// <inheritdoc/> /// <inheritdoc/>
public override bool Write(string inputFile, string outDir, BaseFile? baseFile) public override bool Write(string inputFile, string outDir, BaseFile? baseFile)
{ {
// Check that the input file exists
if (!File.Exists(inputFile))
{
_logger.Warning($"File '{inputFile}' does not exist!");
return false;
}
inputFile = Path.GetFullPath(inputFile);
// Get the file stream for the file and write out // Get the file stream for the file and write out
return Write(File.OpenRead(inputFile), outDir, baseFile); using Stream inputStream = File.Open(inputFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
return Write(inputStream, outDir, baseFile);
} }
/// <inheritdoc/> /// <inheritdoc/>

View File

@@ -378,8 +378,18 @@ namespace SabreTools.FileTypes.Archives
/// <inheritdoc/> /// <inheritdoc/>
public override bool Write(string inputFile, string outDir, BaseFile? baseFile) public override bool Write(string inputFile, string outDir, BaseFile? baseFile)
{ {
// Check that the input file exists
if (!File.Exists(inputFile))
{
_logger.Warning($"File '{inputFile}' does not exist!");
return false;
}
inputFile = Path.GetFullPath(inputFile);
// Get the file stream for the file and write out // Get the file stream for the file and write out
return Write(File.OpenRead(inputFile), outDir, baseFile); using Stream inputStream = File.Open(inputFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
return Write(inputStream, outDir, baseFile);
} }
/// <inheritdoc/> /// <inheritdoc/>
@@ -638,7 +648,7 @@ namespace SabreTools.FileTypes.Archives
int index = inputIndexMap[key]; int index = inputIndexMap[key];
// Open the input file for reading // Open the input file for reading
Stream freadStream = File.OpenRead(inputFiles[index]); Stream freadStream = File.Open(inputFiles[index], FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
ulong istreamSize = (ulong)new FileInfo(inputFiles[index]).Length; ulong istreamSize = (ulong)new FileInfo(inputFiles[index]).Length;
DateTime dt = DateTime.Now; DateTime dt = DateTime.Now;
@@ -720,7 +730,7 @@ namespace SabreTools.FileTypes.Archives
if (index < 0) if (index < 0)
{ {
// Open the input file for reading // Open the input file for reading
Stream freadStream = File.OpenRead(inputFiles[-index - 1]); Stream freadStream = File.Open(inputFiles[-index - 1], FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
ulong istreamSize = (ulong)(new FileInfo(inputFiles[-index - 1]).Length); ulong istreamSize = (ulong)(new FileInfo(inputFiles[-index - 1]).Length);
DateTime dt = DateTime.Now; DateTime dt = DateTime.Now;

View File

@@ -187,7 +187,7 @@ namespace SabreTools.FileTypes.Archives
try try
{ {
TarArchive ta = TarArchive.Open(File.OpenRead(Filename!)); TarArchive ta = TarArchive.Open(File.Open(Filename!, FileMode.Open, FileAccess.Read, FileShare.ReadWrite));
foreach (TarArchiveEntry entry in ta.Entries.Where(e => e != null && !e.IsDirectory)) foreach (TarArchiveEntry entry in ta.Entries.Where(e => e != null && !e.IsDirectory))
{ {
// Create a blank item for the entry // Create a blank item for the entry
@@ -283,8 +283,18 @@ namespace SabreTools.FileTypes.Archives
/// <inheritdoc/> /// <inheritdoc/>
public override bool Write(string inputFile, string outDir, BaseFile? baseFile) public override bool Write(string inputFile, string outDir, BaseFile? baseFile)
{ {
// Check that the input file exists
if (!File.Exists(inputFile))
{
_logger.Warning($"File '{inputFile}' does not exist!");
return false;
}
inputFile = Path.GetFullPath(inputFile);
// Get the file stream for the file and write out // Get the file stream for the file and write out
return Write(File.OpenRead(inputFile), outDir, baseFile); using Stream inputStream = File.Open(inputFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
return Write(inputStream, outDir, baseFile);
} }
/// <inheritdoc/> /// <inheritdoc/>
@@ -492,7 +502,10 @@ namespace SabreTools.FileTypes.Archives
usableDate = dt; usableDate = dt;
// Copy the input stream to the output // Copy the input stream to the output
tarFile.AddEntry(baseFiles[index].Filename!, File.OpenRead(inputFiles[index]), size: baseFiles[index].Size ?? 0, modified: usableDate); tarFile.AddEntry(baseFiles[index].Filename!,
File.Open(inputFiles[index], FileMode.Open, FileAccess.Read, FileShare.ReadWrite),
size: baseFiles[index].Size ?? 0,
modified: usableDate);
} }
} }
@@ -554,7 +567,10 @@ namespace SabreTools.FileTypes.Archives
usableDate = dt; usableDate = dt;
// Copy the input file to the output // Copy the input file to the output
tarFile.AddEntry(baseFiles[-index - 1].Filename!, File.OpenRead(inputFiles[-index - 1]), size: baseFiles[-index - 1].Size ?? 0, modified: usableDate); tarFile.AddEntry(baseFiles[-index - 1].Filename!,
File.Open(inputFiles[-index - 1], FileMode.Open, FileAccess.Read, FileShare.ReadWrite),
size: baseFiles[-index - 1].Size ?? 0,
modified: usableDate);
} }
// Otherwise, copy the file from the old archive // Otherwise, copy the file from the old archive

View File

@@ -70,7 +70,7 @@ namespace SabreTools.FileTypes.Archives
// Decompress the _filename stream // Decompress the _filename stream
FileStream outstream = File.Create(Path.Combine(outDir, Path.GetFileNameWithoutExtension(Filename)!)); FileStream outstream = File.Create(Path.Combine(outDir, Path.GetFileNameWithoutExtension(Filename)!));
var xz = new XZStream(File.OpenRead(Filename!)); var xz = new XZStream(File.Open(Filename!, FileMode.Open, FileAccess.Read, FileShare.ReadWrite));
xz.CopyTo(outstream); xz.CopyTo(outstream);
// Dispose of the streams // Dispose of the streams
@@ -156,7 +156,7 @@ namespace SabreTools.FileTypes.Archives
{ {
// Open the entry stream // Open the entry stream
string realEntry = Path.GetFileNameWithoutExtension(Filename); string realEntry = Path.GetFileNameWithoutExtension(Filename);
var stream = new XZStream(File.OpenRead(Filename)); var stream = new XZStream(File.Open(Filename, FileMode.Open, FileAccess.Read, FileShare.ReadWrite));
// Return the stream // Return the stream
return (stream, realEntry); return (stream, realEntry);
@@ -206,15 +206,16 @@ namespace SabreTools.FileTypes.Archives
{ {
xzEntryRom.Filename = gamename; xzEntryRom.Filename = gamename;
using BinaryReader br = new(File.OpenRead(Filename!)); using Stream fs = File.Open(Filename!, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
br.BaseStream.Seek(-8, SeekOrigin.End); fs.Seek(-8, SeekOrigin.End);
xzEntryRom.CRC = br.ReadBytesBigEndian(4); xzEntryRom.CRC = fs.ReadBytes(4);
xzEntryRom.Size = br.ReadInt32BigEndian(); Array.Reverse(xzEntryRom.CRC);
xzEntryRom.Size = fs.ReadInt32BigEndian();
} }
// Otherwise, use the stream directly // Otherwise, use the stream directly
else else
{ {
var xzStream = new XZStream(File.OpenRead(Filename!)); var xzStream = new XZStream(File.Open(Filename!, FileMode.Open, FileAccess.Read, FileShare.ReadWrite));
xzEntryRom = FileTypeTool.GetInfo(xzStream, _hashTypes); xzEntryRom = FileTypeTool.GetInfo(xzStream, _hashTypes);
xzEntryRom.Filename = gamename; xzEntryRom.Filename = gamename;
xzStream.Dispose(); xzStream.Dispose();
@@ -310,7 +311,8 @@ namespace SabreTools.FileTypes.Archives
inputFile = Path.GetFullPath(inputFile); inputFile = Path.GetFullPath(inputFile);
// Get the file stream for the file and write out // Get the file stream for the file and write out
return Write(File.OpenRead(inputFile), outDir, baseFile); using Stream inputStream = File.Open(inputFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
return Write(inputStream, outDir, baseFile);
} }
/// <inheritdoc/> /// <inheritdoc/>

View File

@@ -556,8 +556,18 @@ namespace SabreTools.FileTypes.Archives
/// <inheritdoc/> /// <inheritdoc/>
public override bool Write(string inputFile, string outDir, BaseFile? baseFile) public override bool Write(string inputFile, string outDir, BaseFile? baseFile)
{ {
// Check that the input file exists
if (!File.Exists(inputFile))
{
_logger.Warning($"File '{inputFile}' does not exist!");
return false;
}
inputFile = Path.GetFullPath(inputFile);
// Get the file stream for the file and write out // Get the file stream for the file and write out
return Write(File.OpenRead(inputFile), outDir, baseFile); using Stream inputStream = File.Open(inputFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
return Write(inputStream, outDir, baseFile);
} }
/// <inheritdoc/> /// <inheritdoc/>
@@ -809,7 +819,7 @@ namespace SabreTools.FileTypes.Archives
int index = inputIndexMap[key]; int index = inputIndexMap[key];
// Open the input file for reading // Open the input file for reading
Stream freadStream = File.OpenRead(inputFiles[index]); Stream freadStream = File.Open(inputFiles[index], FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
ulong istreamSize = (ulong)(new FileInfo(inputFiles[index]).Length); ulong istreamSize = (ulong)(new FileInfo(inputFiles[index]).Length);
DateTime dt = DateTime.Now; DateTime dt = DateTime.Now;
@@ -891,7 +901,7 @@ namespace SabreTools.FileTypes.Archives
if (index < 0) if (index < 0)
{ {
// Open the input file for reading // Open the input file for reading
Stream freadStream = File.OpenRead(inputFiles[-index - 1]); Stream freadStream = File.Open(inputFiles[-index - 1], FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
ulong istreamSize = (ulong)(new FileInfo(inputFiles[-index - 1]).Length); ulong istreamSize = (ulong)(new FileInfo(inputFiles[-index - 1]).Length);
DateTime dt = DateTime.Now; DateTime dt = DateTime.Now;

View File

@@ -22,7 +22,7 @@ namespace SabreTools.FileTypes.CHD
/// <param name="filename">Filename respresenting the CHD file</param> /// <param name="filename">Filename respresenting the CHD file</param>
public static CHDFile? Create(string filename) public static CHDFile? Create(string filename)
{ {
using var fs = File.OpenRead(filename); using Stream fs = File.Open(filename, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
return Create(fs); return Create(fs);
} }

View File

@@ -123,7 +123,7 @@ namespace SabreTools.FileTypes
/// <param name="hashes">Hashes to include in the information</param> /// <param name="hashes">Hashes to include in the information</param>
/// <param name="keepReadOpen">Indicates if the underlying read stream should be kept open</param> /// <param name="keepReadOpen">Indicates if the underlying read stream should be kept open</param>
/// <returns>Populated BaseFile object if success, empty one on error</returns> /// <returns>Populated BaseFile object if success, empty one on error</returns>
public static BaseFile GetInfo(Stream? input, long size, HashType[]? hashes, bool keepReadOpen) public static BaseFile GetInfo(Stream? input, long size, HashType[] hashes, bool keepReadOpen)
{ {
// If we have no stream // If we have no stream
if (input == null) if (input == null)

View File

@@ -189,7 +189,7 @@ namespace SabreTools.FileTypes
// If we had a file, open and return the stream // If we had a file, open and return the stream
if (!string.IsNullOrEmpty(match)) if (!string.IsNullOrEmpty(match))
{ {
var stream = File.OpenRead(match); Stream stream = File.Open(match, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
return (stream, match); return (stream, match);
} }
@@ -266,8 +266,8 @@ namespace SabreTools.FileTypes
/// <inheritdoc/> /// <inheritdoc/>
public bool Write(string inputFile, string outDir, BaseFile? baseFile) public bool Write(string inputFile, string outDir, BaseFile? baseFile)
{ {
FileStream fs = File.OpenRead(inputFile); using Stream inputStream = File.Open(inputFile, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
return Write(fs, outDir, baseFile); return Write(inputStream, outDir, baseFile);
} }
/// <inheritdoc/> /// <inheritdoc/>