mirror of
https://github.com/aaru-dps/Aaru.git
synced 2025-12-16 19:24:25 +00:00
Support ISO9660 with a block size different from 2048 bytes. Fixes #410
This commit is contained in:
@@ -124,7 +124,8 @@ namespace Aaru.Filesystems
|
||||
|
||||
offset += entry.XattrLength;
|
||||
|
||||
if(entry.CdiSystemArea?.attributes.HasFlag(CdiAttributes.DigitalAudio) == true && entry.Extents.Count == 1)
|
||||
if(entry.CdiSystemArea?.attributes.HasFlag(CdiAttributes.DigitalAudio) == true &&
|
||||
entry.Extents.Count == 1)
|
||||
{
|
||||
try
|
||||
{
|
||||
@@ -568,7 +569,7 @@ namespace Aaru.Filesystems
|
||||
try
|
||||
{
|
||||
byte[] fullSector =
|
||||
_image.ReadSectorTag(extents[i].extent + currentExtentSector,
|
||||
_image.ReadSectorTag(((extents[i].extent + currentExtentSector) * _blockSize) / 2048,
|
||||
SectorTagType.CdSectorSubHeader);
|
||||
|
||||
ms.Write(fullSector, copy ? 0 : 4, 4);
|
||||
|
||||
@@ -58,6 +58,7 @@ namespace Aaru.Filesystems
|
||||
bool _useEvd;
|
||||
bool _usePathTable;
|
||||
bool _useTransTbl;
|
||||
ushort _blockSize;
|
||||
|
||||
public FileSystemType XmlFsType { get; private set; }
|
||||
public Encoding Encoding { get; private set; }
|
||||
|
||||
@@ -31,6 +31,8 @@
|
||||
// In the loving memory of Facunda "Tata" Suárez Domínguez, R.I.P. 2019/07/24
|
||||
// ****************************************************************************/
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using Aaru.Console;
|
||||
using Aaru.Decoders.CD;
|
||||
|
||||
@@ -40,61 +42,158 @@ namespace Aaru.Filesystems
|
||||
{
|
||||
byte[] ReadSector(ulong sector, bool interleaved = false, byte fileNumber = 0)
|
||||
{
|
||||
ulong realSector;
|
||||
uint sectorCount;
|
||||
|
||||
sectorCount = (uint)_blockSize / 2048;
|
||||
|
||||
if(_blockSize % 2048 > 0)
|
||||
sectorCount++;
|
||||
|
||||
realSector = (sector * _blockSize) / 2048;
|
||||
|
||||
ulong offset = (sector * _blockSize) % 2048;
|
||||
|
||||
byte[] data;
|
||||
|
||||
// TODO: No more exceptions
|
||||
try
|
||||
if(sectorCount == 1)
|
||||
{
|
||||
data = _image.ReadSectorLong(sector);
|
||||
// TODO: No more exceptions
|
||||
try
|
||||
{
|
||||
data = _image.ReadSectorLong(realSector);
|
||||
}
|
||||
catch
|
||||
{
|
||||
data = _image.ReadSector(realSector);
|
||||
}
|
||||
|
||||
if(_debug)
|
||||
{
|
||||
switch(data.Length)
|
||||
{
|
||||
case 2048:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin", "Sector {0}, Cooked, Mode 0/1 / Mode 2 Form 1",
|
||||
realSector);
|
||||
|
||||
break;
|
||||
case 2324:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin", "Sector {0}, Cooked, Mode 2 Form 2",
|
||||
realSector);
|
||||
|
||||
break;
|
||||
case 2336:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin",
|
||||
"Sector {0}, Cooked, Mode 2 Form {1}, File Number {2}, Channel Number {3}, Submode {4}, Coding Information {5}",
|
||||
realSector,
|
||||
((Mode2Submode)data[2]).HasFlag(Mode2Submode.Form2) ? 2 : 1,
|
||||
data[0], data[1], (Mode2Submode)data[2], data[3]);
|
||||
|
||||
break;
|
||||
case 2352 when data[0] != 0x00 || data[1] != 0xFF || data[2] != 0xFF || data[3] != 0xFF ||
|
||||
data[4] != 0xFF || data[5] != 0xFF || data[6] != 0xFF || data[7] != 0xFF ||
|
||||
data[8] != 0xFF || data[9] != 0xFF || data[10] != 0xFF || data[11] != 0x00:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin", "Sector {0}, Raw, Audio", realSector);
|
||||
|
||||
break;
|
||||
case 2352 when data[15] != 2:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin",
|
||||
"Sector {0} ({1:X2}:{2:X2}:{3:X2}), Raw, Mode {4}", realSector,
|
||||
data[12], data[13], data[14], data[15]);
|
||||
|
||||
break;
|
||||
case 2352:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin",
|
||||
"Sector {0} ({1:X2}:{2:X2}:{3:X2}), Raw, Mode 2 Form {4}, File Number {5}, Channel Number {6}, Submode {7}, Coding Information {8}",
|
||||
realSector, data[12], data[13], data[14],
|
||||
((Mode2Submode)data[18]).HasFlag(Mode2Submode.Form2) ? 2 : 1,
|
||||
data[16], data[17], (Mode2Submode)data[18], data[19]);
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if(_blockSize == 2048)
|
||||
return Sector.GetUserData(data, interleaved, fileNumber);
|
||||
|
||||
byte[] tmp = new byte[_blockSize];
|
||||
Array.Copy(Sector.GetUserData(data, interleaved, fileNumber), (int)offset, tmp, 0, _blockSize);
|
||||
|
||||
return tmp;
|
||||
}
|
||||
catch
|
||||
else
|
||||
{
|
||||
data = _image.ReadSector(sector);
|
||||
var ms = new MemoryStream();
|
||||
|
||||
for(uint i = 0; i < sectorCount; i++)
|
||||
{
|
||||
ulong dstSector = realSector + 1;
|
||||
|
||||
// TODO: No more exceptions
|
||||
try
|
||||
{
|
||||
data = _image.ReadSectorLong(dstSector);
|
||||
}
|
||||
catch
|
||||
{
|
||||
data = _image.ReadSector(dstSector);
|
||||
}
|
||||
|
||||
if(_debug)
|
||||
{
|
||||
switch(data.Length)
|
||||
{
|
||||
case 2048:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin",
|
||||
"Sector {0}, Cooked, Mode 0/1 / Mode 2 Form 1", dstSector);
|
||||
|
||||
break;
|
||||
case 2324:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin", "Sector {0}, Cooked, Mode 2 Form 2",
|
||||
dstSector);
|
||||
|
||||
break;
|
||||
case 2336:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin",
|
||||
"Sector {0}, Cooked, Mode 2 Form {1}, File Number {2}, Channel Number {3}, Submode {4}, Coding Information {5}",
|
||||
dstSector,
|
||||
((Mode2Submode)data[2]).HasFlag(Mode2Submode.Form2) ? 2 : 1,
|
||||
data[0], data[1], (Mode2Submode)data[2], data[3]);
|
||||
|
||||
break;
|
||||
case 2352 when data[0] != 0x00 || data[1] != 0xFF || data[2] != 0xFF || data[3] != 0xFF ||
|
||||
data[4] != 0xFF || data[5] != 0xFF || data[6] != 0xFF || data[7] != 0xFF ||
|
||||
data[8] != 0xFF || data[9] != 0xFF || data[10] != 0xFF || data[11] != 0x00:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin", "Sector {0}, Raw, Audio", dstSector);
|
||||
|
||||
break;
|
||||
case 2352 when data[15] != 2:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin",
|
||||
"Sector {0} ({1:X2}:{2:X2}:{3:X2}), Raw, Mode {4}",
|
||||
dstSector, data[12], data[13], data[14], data[15]);
|
||||
|
||||
break;
|
||||
case 2352:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin",
|
||||
"Sector {0} ({1:X2}:{2:X2}:{3:X2}), Raw, Mode 2 Form {4}, File Number {5}, Channel Number {6}, Submode {7}, Coding Information {8}",
|
||||
dstSector, data[12], data[13], data[14],
|
||||
((Mode2Submode)data[18]).HasFlag(Mode2Submode.Form2) ? 2 : 1,
|
||||
data[16], data[17], (Mode2Submode)data[18], data[19]);
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
byte[] sectorData = Sector.GetUserData(data, interleaved, fileNumber);
|
||||
|
||||
ms.Write(sectorData, 0, sectorData.Length);
|
||||
}
|
||||
|
||||
byte[] tmp = new byte[_blockSize];
|
||||
Array.Copy(Sector.GetUserData(ms.ToArray(), interleaved, fileNumber), 0, tmp, 0, _blockSize);
|
||||
|
||||
return tmp;
|
||||
}
|
||||
|
||||
if(!_debug)
|
||||
return Sector.GetUserData(data, interleaved, fileNumber);
|
||||
|
||||
switch(data.Length)
|
||||
{
|
||||
case 2048:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin", "Sector {0}, Cooked, Mode 0/1 / Mode 2 Form 1",
|
||||
sector);
|
||||
|
||||
break;
|
||||
case 2324:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin", "Sector {0}, Cooked, Mode 2 Form 2", sector);
|
||||
|
||||
break;
|
||||
case 2336:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin",
|
||||
"Sector {0}, Cooked, Mode 2 Form {1}, File Number {2}, Channel Number {3}, Submode {4}, Coding Information {5}",
|
||||
sector, ((Mode2Submode)data[2]).HasFlag(Mode2Submode.Form2) ? 2 : 1,
|
||||
data[0], data[1], (Mode2Submode)data[2], data[3]);
|
||||
|
||||
break;
|
||||
case 2352 when data[0] != 0x00 || data[1] != 0xFF || data[2] != 0xFF || data[3] != 0xFF ||
|
||||
data[4] != 0xFF || data[5] != 0xFF || data[6] != 0xFF || data[7] != 0xFF ||
|
||||
data[8] != 0xFF || data[9] != 0xFF || data[10] != 0xFF || data[11] != 0x00:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin", "Sector {0}, Raw, Audio", sector);
|
||||
|
||||
break;
|
||||
case 2352 when data[15] != 2:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin", "Sector {0} ({1:X2}:{2:X2}:{3:X2}), Raw, Mode {4}",
|
||||
sector, data[12], data[13], data[14], data[15]);
|
||||
|
||||
break;
|
||||
case 2352:
|
||||
AaruConsole.DebugWriteLine("ISO9660 Plugin",
|
||||
"Sector {0} ({1:X2}:{2:X2}:{3:X2}), Raw, Mode 2 Form {4}, File Number {5}, Channel Number {6}, Submode {7}, Coding Information {8}",
|
||||
sector, data[12], data[13], data[14],
|
||||
((Mode2Submode)data[18]).HasFlag(Mode2Submode.Form2) ? 2 : 1, data[16],
|
||||
data[17], (Mode2Submode)data[18], data[19]);
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
return Sector.GetUserData(data, interleaved, fileNumber);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -278,6 +278,8 @@ namespace Aaru.Filesystems
|
||||
|
||||
if(_highSierra)
|
||||
{
|
||||
_blockSize = hsvd.Value.logical_block_size;
|
||||
|
||||
pathTableData = ReadSingleExtent(0, hsvd.Value.path_table_size,
|
||||
Swapping.Swap(hsvd.Value.mandatory_path_table_msb));
|
||||
|
||||
@@ -288,6 +290,8 @@ namespace Aaru.Filesystems
|
||||
}
|
||||
else if(_cdi)
|
||||
{
|
||||
_blockSize = fsvd.Value.logical_block_size;
|
||||
|
||||
pathTableData = ReadSingleExtent(0, fsvd.Value.path_table_size, fsvd.Value.path_table_addr);
|
||||
|
||||
fsFormat = "CD-i";
|
||||
@@ -299,6 +303,8 @@ namespace Aaru.Filesystems
|
||||
}
|
||||
else
|
||||
{
|
||||
_blockSize = pvd.Value.logical_block_size;
|
||||
|
||||
pathTableData =
|
||||
ReadSingleExtent(0, pvd.Value.path_table_size, Swapping.Swap(pvd.Value.type_m_path_table));
|
||||
|
||||
|
||||
@@ -83,7 +83,7 @@ namespace Aaru.Filesystems
|
||||
entry.Extents.Count == 0)
|
||||
return Errno.NoError;
|
||||
|
||||
byte[] sector = _image.ReadSectorLong(entry.Extents[0].extent);
|
||||
byte[] sector = _image.ReadSectorLong((entry.Extents[0].extent * _blockSize) / 2048);
|
||||
|
||||
if(sector[15] != 2)
|
||||
return Errno.NoError;
|
||||
|
||||
Reference in New Issue
Block a user