Rework ISO9660 filesystem to use ARC file architecture.

ISO filesystem doesn't depend anymore of boot volume/system volume

svn path=/trunk/; revision=42528
This commit is contained in:
Hervé Poussineau 2009-08-08 17:13:14 +00:00
parent 20c8af6fef
commit e307cb2881
3 changed files with 228 additions and 195 deletions

View file

@ -202,7 +202,7 @@ static BOOLEAN FsOpenVolume(ULONG DriveNumber, ULONGLONG StartSector, ULONGLONG
pFSVtbl = &Ext2Vtbl; pFSVtbl = &Ext2Vtbl;
break; break;
case FS_ISO9660: case FS_ISO9660:
pFSVtbl = &Iso9660Vtbl; pFSVtbl = &CompatArcVtbl;
break; break;
default: default:
pFSVtbl = NULL; pFSVtbl = NULL;
@ -638,8 +638,12 @@ LONG ArcOpen(CHAR* Path, OPENMODE OpenMode, ULONG* FileId)
} }
/* Try to detect the file system */ /* Try to detect the file system */
/* FIXME: we link there to old infrastructure... */ FileData[DeviceId].FileFuncTable = IsoMount(DeviceId);
FileData[DeviceId].FileFuncTable = &CompatFsFuncTable; if (!FileData[DeviceId].FileFuncTable)
{
/* FIXME: we link there to old infrastructure... */
FileData[DeviceId].FileFuncTable = &CompatFsFuncTable;
}
pDevice->DeviceId = DeviceId; pDevice->DeviceId = DeviceId;
} }

View file

@ -1,6 +1,7 @@
/* /*
* FreeLoader * FreeLoader
* Copyright (C) 1998-2003 Brian Palmer <brianp@sginet.com> * Copyright (C) 1998-2003 Brian Palmer <brianp@sginet.com>
* Copyright (C) 2009 Hervé Poussineau <hpoussin@reactos.org>
* *
* This program is free software; you can redistribute it and/or modify * This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by * it under the terms of the GNU General Public License as published by
@ -22,39 +23,6 @@
#define SECTORSIZE 2048 #define SECTORSIZE 2048
static ULONG IsoRootSector; // Starting sector of the root directory
static ULONG IsoRootLength; // Length of the root directory
ULONG IsoDriveNumber = 0;
BOOLEAN IsoOpenVolume(UCHAR DriveNumber, ULONGLONG VolumeStartSector, ULONGLONG PartitionSectorCount)
{
PPVD Pvd = (PPVD)DISKREADBUFFER;
DPRINTM(DPRINT_FILESYSTEM, "IsoOpenVolume() DriveNumber = 0x%x VolumeStartSector = 16\n", DriveNumber);
// Store the drive number
IsoDriveNumber = DriveNumber;
IsoRootSector = 0;
IsoRootLength = 0;
if (!MachDiskReadLogicalSectors(DriveNumber, 16, 1, Pvd))
{
FileSystemError("Failed to read the PVD.");
return FALSE;
}
IsoRootSector = Pvd->RootDirRecord.ExtentLocationL;
IsoRootLength = Pvd->RootDirRecord.DataLengthL;
DPRINTM(DPRINT_FILESYSTEM, "IsoRootSector = %u IsoRootLegth = %u\n", IsoRootSector, IsoRootLength);
return TRUE;
}
static BOOLEAN IsoSearchDirectoryBufferForFile(PVOID DirectoryBuffer, ULONG DirectoryLength, PCHAR FileName, PISO_FILE_INFO IsoFileInfoPointer) static BOOLEAN IsoSearchDirectoryBufferForFile(PVOID DirectoryBuffer, ULONG DirectoryLength, PCHAR FileName, PISO_FILE_INFO IsoFileInfoPointer)
{ {
PDIR_RECORD Record; PDIR_RECORD Record;
@ -119,16 +87,18 @@ static BOOLEAN IsoSearchDirectoryBufferForFile(PVOID DirectoryBuffer, ULONG Dire
/* /*
* IsoBufferDirectory() * IsoBufferDirectory()
* This function allocates a buffer, reads the specified directory * This function allocates a buffer, reads the specified directory
* and returns a pointer to that buffer. The function returns NULL * and returns a pointer to that buffer into pDirectoryBuffer. The
* if allocation or read fails. The directory is specified by its * function returns an ARC error code. The directory is specified
* starting sector and length. * by its starting sector and length.
*/ */
static PVOID IsoBufferDirectory(ULONG DirectoryStartSector, ULONG DirectoryLength) static LONG IsoBufferDirectory(ULONG DeviceId, ULONG DirectoryStartSector, ULONG DirectoryLength,
PVOID* pDirectoryBuffer)
{ {
PVOID DirectoryBuffer; PVOID DirectoryBuffer;
PVOID Ptr; ULONG SectorCount;
ULONG SectorCount; LARGE_INTEGER Position;
ULONG i; ULONG Count;
ULONG ret;
DPRINTM(DPRINT_FILESYSTEM, "IsoBufferDirectory() DirectoryStartSector = %d DirectoryLength = %d\n", DirectoryStartSector, DirectoryLength); DPRINTM(DPRINT_FILESYSTEM, "IsoBufferDirectory() DirectoryStartSector = %d DirectoryLength = %d\n", DirectoryStartSector, DirectoryLength);
@ -140,26 +110,29 @@ static PVOID IsoBufferDirectory(ULONG DirectoryStartSector, ULONG DirectoryLengt
// //
DPRINTM(DPRINT_FILESYSTEM, "Trying to allocate (DirectoryLength) %d bytes.\n", DirectoryLength); DPRINTM(DPRINT_FILESYSTEM, "Trying to allocate (DirectoryLength) %d bytes.\n", DirectoryLength);
DirectoryBuffer = MmHeapAlloc(DirectoryLength); DirectoryBuffer = MmHeapAlloc(DirectoryLength);
if (!DirectoryBuffer)
if (DirectoryBuffer == NULL) return ENOMEM;
{
return NULL;
}
// //
// Now read directory contents into DirectoryBuffer // Now read directory contents into DirectoryBuffer
// //
for (i = 0, Ptr = DirectoryBuffer; i < SectorCount; i++, Ptr = (PVOID)((ULONG_PTR)Ptr + SECTORSIZE)) Position.HighPart = 0;
Position.LowPart = DirectoryStartSector * SECTORSIZE;
ret = ArcSeek(DeviceId, &Position, SeekAbsolute);
if (ret != ESUCCESS)
{ {
if (!MachDiskReadLogicalSectors(IsoDriveNumber, DirectoryStartSector + i, 1, (PVOID)DISKREADBUFFER)) MmHeapFree(DirectoryBuffer);
{ return ret;
MmHeapFree(DirectoryBuffer); }
return NULL; ret = ArcRead(DeviceId, DirectoryBuffer, SectorCount * SECTORSIZE, &Count);
} if (ret != ESUCCESS || Count != SectorCount * SECTORSIZE)
RtlCopyMemory(Ptr, (PVOID)DISKREADBUFFER, SECTORSIZE); {
MmHeapFree(DirectoryBuffer);
return EIO;
} }
return DirectoryBuffer; *pDirectoryBuffer = DirectoryBuffer;
return ESUCCESS;
} }
@ -167,11 +140,12 @@ static PVOID IsoBufferDirectory(ULONG DirectoryStartSector, ULONG DirectoryLengt
* IsoLookupFile() * IsoLookupFile()
* This function searches the file system for the * This function searches the file system for the
* specified filename and fills in an ISO_FILE_INFO structure * specified filename and fills in an ISO_FILE_INFO structure
* with info describing the file, etc. returns true * with info describing the file, etc. returns ARC error code
* if the file exists or false otherwise
*/ */
static BOOLEAN IsoLookupFile(PCSTR FileName, PISO_FILE_INFO IsoFileInfoPointer) static LONG IsoLookupFile(PCSTR FileName, ULONG DeviceId, PISO_FILE_INFO IsoFileInfoPointer)
{ {
UCHAR Buffer[SECTORSIZE];
PPVD Pvd = (PPVD)Buffer;
UINT32 i; UINT32 i;
ULONG NumberOfPathParts; ULONG NumberOfPathParts;
CHAR PathPart[261]; CHAR PathPart[261];
@ -179,19 +153,34 @@ static BOOLEAN IsoLookupFile(PCSTR FileName, PISO_FILE_INFO IsoFileInfoPointer)
ULONG DirectorySector; ULONG DirectorySector;
ULONG DirectoryLength; ULONG DirectoryLength;
ISO_FILE_INFO IsoFileInfo; ISO_FILE_INFO IsoFileInfo;
LARGE_INTEGER Position;
ULONG Count;
LONG ret;
DPRINTM(DPRINT_FILESYSTEM, "IsoLookupFile() FileName = %s\n", FileName); DPRINTM(DPRINT_FILESYSTEM, "IsoLookupFile() FileName = %s\n", FileName);
RtlZeroMemory(IsoFileInfoPointer, sizeof(ISO_FILE_INFO)); RtlZeroMemory(IsoFileInfoPointer, sizeof(ISO_FILE_INFO));
//
// Read The Primary Volume Descriptor
//
Position.HighPart = 0;
Position.LowPart = 16 * SECTORSIZE;
ret = ArcSeek(DeviceId, &Position, SeekAbsolute);
if (ret != ESUCCESS)
return ret;
ret = ArcRead(DeviceId, Pvd, SECTORSIZE, &Count);
if (ret != ESUCCESS || Count < sizeof(PVD))
return EIO;
DirectorySector = Pvd->RootDirRecord.ExtentLocationL;
DirectoryLength = Pvd->RootDirRecord.DataLengthL;
// //
// Figure out how many sub-directories we are nested in // Figure out how many sub-directories we are nested in
// //
NumberOfPathParts = FsGetNumPathParts(FileName); NumberOfPathParts = FsGetNumPathParts(FileName);
DirectorySector = IsoRootSector;
DirectoryLength = IsoRootLength;
// //
// Loop once for each part // Loop once for each part
// //
@ -213,11 +202,9 @@ static BOOLEAN IsoLookupFile(PCSTR FileName, PISO_FILE_INFO IsoFileInfoPointer)
// //
// Buffer the directory contents // Buffer the directory contents
// //
DirectoryBuffer = IsoBufferDirectory(DirectorySector, DirectoryLength); ret = IsoBufferDirectory(DeviceId, DirectorySector, DirectoryLength, &DirectoryBuffer);
if (DirectoryBuffer == NULL) if (ret != ESUCCESS)
{ return ret;
return FALSE;
}
// //
// Search for file name in directory // Search for file name in directory
@ -225,7 +212,7 @@ static BOOLEAN IsoLookupFile(PCSTR FileName, PISO_FILE_INFO IsoFileInfoPointer)
if (!IsoSearchDirectoryBufferForFile(DirectoryBuffer, DirectoryLength, PathPart, &IsoFileInfo)) if (!IsoSearchDirectoryBufferForFile(DirectoryBuffer, DirectoryLength, PathPart, &IsoFileInfo))
{ {
MmHeapFree(DirectoryBuffer); MmHeapFree(DirectoryBuffer);
return FALSE; return ENOENT;
} }
MmHeapFree(DirectoryBuffer); MmHeapFree(DirectoryBuffer);
@ -244,78 +231,101 @@ static BOOLEAN IsoLookupFile(PCSTR FileName, PISO_FILE_INFO IsoFileInfoPointer)
RtlCopyMemory(IsoFileInfoPointer, &IsoFileInfo, sizeof(ISO_FILE_INFO)); RtlCopyMemory(IsoFileInfoPointer, &IsoFileInfo, sizeof(ISO_FILE_INFO));
return TRUE; return ESUCCESS;
} }
LONG IsoClose(ULONG FileId)
/*
* IsoOpenFile()
* Tries to open the file 'name' and returns true or false
* for success and failure respectively
*/
FILE* IsoOpenFile(PCSTR FileName)
{ {
ISO_FILE_INFO TempFileInfo; PISO_FILE_INFO FileHandle = FsGetDeviceSpecific(FileId);
PISO_FILE_INFO FileHandle;
DPRINTM(DPRINT_FILESYSTEM, "IsoOpenFile() FileName = %s\n", FileName); MmHeapFree(FileHandle);
if (!IsoLookupFile(FileName, &TempFileInfo)) return ESUCCESS;
{ }
return NULL;
} LONG IsoGetFileInformation(ULONG FileId, FILEINFORMATION* Information)
{
PISO_FILE_INFO FileHandle = FsGetDeviceSpecific(FileId);
DPRINTM(DPRINT_FILESYSTEM, "IsoGetFileInformation() FileSize = %d\n", FileHandle->FileSize);
DPRINTM(DPRINT_FILESYSTEM, "IsoGetFileInformation() FilePointer = %d\n", FileHandle->FilePointer);
RtlZeroMemory(Information, sizeof(FILEINFORMATION));
Information->EndingAddress.LowPart = FileHandle->FileSize;
Information->CurrentAddress.LowPart = FileHandle->FilePointer;
return ESUCCESS;
}
LONG IsoOpen(CHAR* Path, OPENMODE OpenMode, ULONG* FileId)
{
ISO_FILE_INFO TempFileInfo;
PISO_FILE_INFO FileHandle;
ULONG DeviceId;
LONG ret;
if (OpenMode != OpenReadOnly)
return EACCES;
DeviceId = FsGetDeviceId(*FileId);
DPRINTM(DPRINT_FILESYSTEM, "IsoOpen() FileName = %s\n", Path);
if (*Path == '\\')
Path++;
RtlZeroMemory(&TempFileInfo, sizeof(TempFileInfo));
ret = IsoLookupFile(Path, DeviceId, &TempFileInfo);
if (ret != ESUCCESS)
return ENOENT;
FileHandle = MmHeapAlloc(sizeof(ISO_FILE_INFO)); FileHandle = MmHeapAlloc(sizeof(ISO_FILE_INFO));
if (!FileHandle)
if (FileHandle == NULL) return ENOMEM;
{
return NULL;
}
RtlCopyMemory(FileHandle, &TempFileInfo, sizeof(ISO_FILE_INFO)); RtlCopyMemory(FileHandle, &TempFileInfo, sizeof(ISO_FILE_INFO));
return (FILE*)FileHandle; FsSetDeviceSpecific(*FileId, FileHandle);
return ESUCCESS;
} }
LONG IsoRead(ULONG FileId, VOID* Buffer, ULONG N, ULONG* Count)
/*
* IsoReadFile()
* Reads BytesToRead from open file and
* returns the number of bytes read in BytesRead
*/
BOOLEAN IsoReadFile(FILE *FileHandle, ULONG BytesToRead, ULONG* BytesRead, PVOID Buffer)
{ {
PISO_FILE_INFO IsoFileInfo = (PISO_FILE_INFO)FileHandle; PISO_FILE_INFO FileHandle = FsGetDeviceSpecific(FileId);
UCHAR SectorBuffer[SECTORSIZE];
LARGE_INTEGER Position;
ULONG DeviceId;
ULONG FilePointer;
ULONG SectorNumber; ULONG SectorNumber;
ULONG OffsetInSector; ULONG OffsetInSector;
ULONG LengthInSector; ULONG LengthInSector;
ULONG NumberOfSectors; ULONG NumberOfSectors;
ULONG i; ULONG BytesRead;
LONG ret;
DPRINTM(DPRINT_FILESYSTEM, "IsoReadFile() BytesToRead = %d Buffer = 0x%x\n", BytesToRead, Buffer); DPRINTM(DPRINT_FILESYSTEM, "IsoRead() Buffer = %p, N = %lu\n", Buffer, N);
if (BytesRead != NULL) DeviceId = FsGetDeviceId(FileId);
{ *Count = 0;
*BytesRead = 0;
}
// //
// If they are trying to read past the // If they are trying to read past the
// end of the file then return success // end of the file then return success
// with BytesRead == 0 // with Count == 0
// //
if (IsoFileInfo->FilePointer >= IsoFileInfo->FileSize) FilePointer = FileHandle->FilePointer;
if (FilePointer >= FileHandle->FileSize)
{ {
return TRUE; return ESUCCESS;
} }
// //
// If they are trying to read more than there is to read // If they are trying to read more than there is to read
// then adjust the amount to read // then adjust the amount to read
// //
if ((IsoFileInfo->FilePointer + BytesToRead) > IsoFileInfo->FileSize) if (FilePointer + N > FileHandle->FileSize)
{ {
BytesToRead = (IsoFileInfo->FileSize - IsoFileInfo->FilePointer); N = FileHandle->FileSize - FilePointer;
} }
// //
@ -332,7 +342,7 @@ BOOLEAN IsoReadFile(FILE *FileHandle, ULONG BytesToRead, ULONG* BytesRead, PVOID
// | | // | |
// +---------------+--------------------+ // +---------------+--------------------+
// | // |
// BytesToRead -------+ // N -----------------+
// //
// 1 - The first calculation (and read) will align // 1 - The first calculation (and read) will align
// the file pointer with the next sector // the file pointer with the next sector
@ -351,129 +361,154 @@ BOOLEAN IsoReadFile(FILE *FileHandle, ULONG BytesToRead, ULONG* BytesRead, PVOID
// Only do the first read if we // Only do the first read if we
// aren't aligned on a cluster boundary // aren't aligned on a cluster boundary
// //
if (IsoFileInfo->FilePointer % SECTORSIZE) if (FilePointer % SECTORSIZE)
{ {
// //
// Do the math for our first read // Do the math for our first read
// //
SectorNumber = IsoFileInfo->FileStart + (IsoFileInfo->FilePointer / SECTORSIZE); SectorNumber = FileHandle->FileStart + (FilePointer / SECTORSIZE);
OffsetInSector = IsoFileInfo->FilePointer % SECTORSIZE; OffsetInSector = FilePointer % SECTORSIZE;
LengthInSector = (BytesToRead > (SECTORSIZE - OffsetInSector)) ? (SECTORSIZE - OffsetInSector) : BytesToRead; LengthInSector = (N > (SECTORSIZE - OffsetInSector)) ? (SECTORSIZE - OffsetInSector) : N;
// //
// Now do the read and update BytesRead, BytesToRead, FilePointer, & Buffer // Now do the read and update Count, N, FilePointer, & Buffer
// //
if (!MachDiskReadLogicalSectors(IsoDriveNumber, SectorNumber, 1, (PVOID)DISKREADBUFFER)) Position.HighPart = 0;
Position.LowPart = SectorNumber * SECTORSIZE;
ret = ArcSeek(DeviceId, &Position, SeekAbsolute);
if (ret != ESUCCESS)
{ {
return FALSE; return ret;
} }
RtlCopyMemory(Buffer, (PVOID)((ULONG_PTR)DISKREADBUFFER + OffsetInSector), LengthInSector); ret = ArcRead(DeviceId, SectorBuffer, SECTORSIZE, &BytesRead);
if (BytesRead != NULL) if (ret != ESUCCESS || BytesRead != SECTORSIZE)
{ {
*BytesRead += LengthInSector; return EIO;
} }
BytesToRead -= LengthInSector; RtlCopyMemory(Buffer, SectorBuffer + OffsetInSector, LengthInSector);
IsoFileInfo->FilePointer += LengthInSector; *Count += LengthInSector;
N -= LengthInSector;
FilePointer += LengthInSector;
Buffer = (PVOID)((ULONG_PTR)Buffer + LengthInSector); Buffer = (PVOID)((ULONG_PTR)Buffer + LengthInSector);
} }
// //
// Do the math for our second read (if any data left) // Do the math for our second read (if any data left)
// //
if (BytesToRead > 0) if (N > 0)
{ {
// //
// Determine how many full clusters we need to read // Determine how many full clusters we need to read
// //
NumberOfSectors = (BytesToRead / SECTORSIZE); NumberOfSectors = (N / SECTORSIZE);
for (i = 0; i < NumberOfSectors; i++) SectorNumber = FileHandle->FileStart + (FilePointer / SECTORSIZE);
//
// Now do the read and update Count, N, FilePointer, & Buffer
//
Position.HighPart = 0;
Position.LowPart = SectorNumber * SECTORSIZE;
ret = ArcSeek(DeviceId, &Position, SeekAbsolute);
if (ret != ESUCCESS)
{ {
SectorNumber = IsoFileInfo->FileStart + (IsoFileInfo->FilePointer / SECTORSIZE); return ret;
//
// Now do the read and update BytesRead, BytesToRead, FilePointer, & Buffer
//
if (!MachDiskReadLogicalSectors(IsoDriveNumber, SectorNumber, 1, (PVOID)DISKREADBUFFER))
{
return FALSE;
}
RtlCopyMemory(Buffer, (PVOID)DISKREADBUFFER, SECTORSIZE);
if (BytesRead != NULL)
{
*BytesRead += SECTORSIZE;
}
BytesToRead -= SECTORSIZE;
IsoFileInfo->FilePointer += SECTORSIZE;
Buffer = (PVOID)((ULONG_PTR)Buffer + SECTORSIZE);
} }
ret = ArcRead(DeviceId, Buffer, NumberOfSectors * SECTORSIZE, &BytesRead);
if (ret != ESUCCESS || BytesRead != NumberOfSectors * SECTORSIZE)
{
return EIO;
}
*Count += NumberOfSectors * SECTORSIZE;
N -= NumberOfSectors * SECTORSIZE;
FilePointer += NumberOfSectors * SECTORSIZE;
Buffer = (PVOID)((ULONG_PTR)Buffer + NumberOfSectors * SECTORSIZE);
} }
// //
// Do the math for our third read (if any data left) // Do the math for our third read (if any data left)
// //
if (BytesToRead > 0) if (N > 0)
{ {
SectorNumber = IsoFileInfo->FileStart + (IsoFileInfo->FilePointer / SECTORSIZE); SectorNumber = FileHandle->FileStart + (FilePointer / SECTORSIZE);
// //
// Now do the read and update BytesRead, BytesToRead, FilePointer, & Buffer // Now do the read and update Count, N, FilePointer, & Buffer
// //
if (!MachDiskReadLogicalSectors(IsoDriveNumber, SectorNumber, 1, (PVOID)DISKREADBUFFER)) Position.HighPart = 0;
Position.LowPart = SectorNumber * SECTORSIZE;
ret = ArcSeek(DeviceId, &Position, SeekAbsolute);
if (ret != ESUCCESS)
{ {
return FALSE; return ret;
} }
RtlCopyMemory(Buffer, (PVOID)DISKREADBUFFER, BytesToRead); ret = ArcRead(DeviceId, SectorBuffer, SECTORSIZE, &BytesRead);
if (BytesRead != NULL) if (ret != ESUCCESS || BytesRead != SECTORSIZE)
{ {
*BytesRead += BytesToRead; return EIO;
} }
IsoFileInfo->FilePointer += BytesToRead; RtlCopyMemory(Buffer, SectorBuffer, N);
BytesToRead -= BytesToRead; *Count += N;
Buffer = (PVOID)((ULONG_PTR)Buffer + BytesToRead); FilePointer += N;
} }
DPRINTM(DPRINT_FILESYSTEM, "IsoReadFile() done\n"); DPRINTM(DPRINT_FILESYSTEM, "IsoRead() done\n");
return TRUE; return ESUCCESS;
} }
LONG IsoSeek(ULONG FileId, LARGE_INTEGER* Position, SEEKMODE SeekMode)
ULONG IsoGetFileSize(FILE *FileHandle)
{ {
PISO_FILE_INFO IsoFileHandle = (PISO_FILE_INFO)FileHandle; PISO_FILE_INFO FileHandle = FsGetDeviceSpecific(FileId);
DPRINTM(DPRINT_FILESYSTEM, "IsoGetFileSize() FileSize = %d\n", IsoFileHandle->FileSize); DPRINTM(DPRINT_FILESYSTEM, "IsoSeek() NewFilePointer = %lu\n", Position->LowPart);
return IsoFileHandle->FileSize; if (SeekMode != SeekAbsolute)
return EINVAL;
if (Position->HighPart != 0)
return EINVAL;
if (Position->LowPart >= FileHandle->FileSize)
return EINVAL;
FileHandle->FilePointer = Position->LowPart;
return ESUCCESS;
} }
VOID IsoSetFilePointer(FILE *FileHandle, ULONG NewFilePointer) const DEVVTBL Iso9660FuncTable =
{ {
PISO_FILE_INFO IsoFileHandle = (PISO_FILE_INFO)FileHandle; IsoClose,
IsoGetFileInformation,
DPRINTM(DPRINT_FILESYSTEM, "IsoSetFilePointer() NewFilePointer = %d\n", NewFilePointer); IsoOpen,
IsoRead,
IsoFileHandle->FilePointer = NewFilePointer; IsoSeek,
}
ULONG IsoGetFilePointer(FILE *FileHandle)
{
PISO_FILE_INFO IsoFileHandle = (PISO_FILE_INFO)FileHandle;
DPRINTM(DPRINT_FILESYSTEM, "IsoGetFilePointer() FilePointer = %d\n", IsoFileHandle->FilePointer);
return IsoFileHandle->FilePointer;
}
const FS_VTBL Iso9660Vtbl = {
IsoOpenVolume,
IsoOpenFile,
NULL,
IsoReadFile,
IsoGetFileSize,
IsoSetFilePointer,
IsoGetFilePointer,
}; };
const DEVVTBL* IsoMount(ULONG DeviceId)
{
UCHAR Buffer[SECTORSIZE];
PPVD Pvd = (PPVD)Buffer;
LARGE_INTEGER Position;
ULONG Count;
LONG ret;
//
// Read The Primary Volume Descriptor
//
Position.HighPart = 0;
Position.LowPart = 16 * SECTORSIZE;
ret = ArcSeek(DeviceId, &Position, SeekAbsolute);
if (ret != ESUCCESS)
return NULL;
ret = ArcRead(DeviceId, Pvd, SECTORSIZE, &Count);
if (ret != ESUCCESS || Count < sizeof(PVD))
return NULL;
//
// Check if PVD is valid. If yes, return ISO9660 function table
//
if (Pvd->VdType == 1 && RtlCompareMemory(Pvd->StandardId, "CD001", 5) == 5)
return &Iso9660FuncTable;
else
return NULL;
}

View file

@ -99,14 +99,8 @@ typedef struct
ULONG DriveNumber; ULONG DriveNumber;
} ISO_FILE_INFO, * PISO_FILE_INFO; } ISO_FILE_INFO, * PISO_FILE_INFO;
BOOLEAN IsoOpenVolume(UCHAR DriveNumber, ULONGLONG VolumeStartSector, ULONGLONG PartitionSectorCount);
FILE* IsoOpenFile(PCSTR FileName);
BOOLEAN IsoReadFile(FILE *FileHandle, ULONG BytesToRead, ULONG* BytesRead, PVOID Buffer);
ULONG IsoGetFileSize(FILE *FileHandle);
VOID IsoSetFilePointer(FILE *FileHandle, ULONG NewFilePointer);
ULONG IsoGetFilePointer(FILE *FileHandle);
extern const FS_VTBL Iso9660Vtbl; extern const FS_VTBL Iso9660Vtbl;
const DEVVTBL* IsoMount(ULONG DeviceId);
#endif // #defined __FAT_H #endif // #defined __FAT_H