mirror of
https://github.com/dmolony/DiskBrowser.git
synced 2025-02-18 05:30:29 +00:00
tidying
This commit is contained in:
parent
e135b65948
commit
8db6489649
@ -15,16 +15,19 @@ import com.bytezone.diskbrowser.utilities.Utility;
|
|||||||
abstract class CatalogEntry implements AppleFileSource
|
abstract class CatalogEntry implements AppleFileSource
|
||||||
// -----------------------------------------------------------------------------------//
|
// -----------------------------------------------------------------------------------//
|
||||||
{
|
{
|
||||||
|
Disk disk;
|
||||||
ProdosDisk parentDisk;
|
ProdosDisk parentDisk;
|
||||||
DirectoryHeader parentDirectory;
|
|
||||||
String name;
|
String name;
|
||||||
int storageType;
|
int storageType;
|
||||||
|
|
||||||
LocalDateTime created;
|
LocalDateTime created;
|
||||||
int version;
|
int version;
|
||||||
int minVersion;
|
int minVersion;
|
||||||
int access;
|
int access;
|
||||||
|
|
||||||
List<DiskAddress> dataBlocks = new ArrayList<> ();
|
List<DiskAddress> dataBlocks = new ArrayList<> ();
|
||||||
Disk disk;
|
DirectoryHeader parentDirectory;
|
||||||
|
|
||||||
// ---------------------------------------------------------------------------------//
|
// ---------------------------------------------------------------------------------//
|
||||||
CatalogEntry (ProdosDisk parentDisk, byte[] entryBuffer)
|
CatalogEntry (ProdosDisk parentDisk, byte[] entryBuffer)
|
||||||
@ -32,8 +35,10 @@ abstract class CatalogEntry implements AppleFileSource
|
|||||||
{
|
{
|
||||||
this.parentDisk = parentDisk;
|
this.parentDisk = parentDisk;
|
||||||
this.disk = parentDisk.getDisk ();
|
this.disk = parentDisk.getDisk ();
|
||||||
|
|
||||||
name = HexFormatter.getString (entryBuffer, 1, entryBuffer[0] & 0x0F);
|
name = HexFormatter.getString (entryBuffer, 1, entryBuffer[0] & 0x0F);
|
||||||
storageType = (entryBuffer[0] & 0xF0) >> 4;
|
storageType = (entryBuffer[0] & 0xF0) >> 4;
|
||||||
|
|
||||||
created = Utility.getAppleDate (entryBuffer, 24);
|
created = Utility.getAppleDate (entryBuffer, 24);
|
||||||
version = entryBuffer[28] & 0xFF;
|
version = entryBuffer[28] & 0xFF;
|
||||||
minVersion = entryBuffer[29] & 0xFF;
|
minVersion = entryBuffer[29] & 0xFF;
|
||||||
@ -63,8 +68,8 @@ abstract class CatalogEntry implements AppleFileSource
|
|||||||
public boolean contains (DiskAddress da)
|
public boolean contains (DiskAddress da)
|
||||||
// ---------------------------------------------------------------------------------//
|
// ---------------------------------------------------------------------------------//
|
||||||
{
|
{
|
||||||
for (DiskAddress sector : dataBlocks)
|
for (DiskAddress diskAddress : dataBlocks)
|
||||||
if (sector.matches (da))
|
if (diskAddress.matches (da))
|
||||||
return true;
|
return true;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -88,6 +88,7 @@ public interface ProdosConstants
|
|||||||
"CMD", "OVL", "UD2", "UD3", "UD4", "BAT", "UD6", "UD7", //
|
"CMD", "OVL", "UD2", "UD3", "UD4", "BAT", "UD6", "UD7", //
|
||||||
"PRG", "P16", "INT", "IVR", "BAS", "VAR", "REL", "SYS" };
|
"PRG", "P16", "INT", "IVR", "BAS", "VAR", "REL", "SYS" };
|
||||||
|
|
||||||
|
static int BLOCK_SIZE = 0x200;
|
||||||
static int ENTRY_SIZE = 0x27;
|
static int ENTRY_SIZE = 0x27;
|
||||||
static int ENTRIES_PER_BLOCK = 0x0D;
|
static int ENTRIES_PER_BLOCK = 0x0D;
|
||||||
static int BLOCK_ENTRY_SIZE = ENTRY_SIZE * ENTRIES_PER_BLOCK;
|
static int BLOCK_ENTRY_SIZE = ENTRY_SIZE * ENTRIES_PER_BLOCK;
|
||||||
|
@ -1,6 +1,8 @@
|
|||||||
package com.bytezone.diskbrowser.prodos.write;
|
package com.bytezone.diskbrowser.prodos.write;
|
||||||
|
|
||||||
import static com.bytezone.diskbrowser.prodos.write.ProdosDisk.ENTRY_SIZE;
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.BLOCK_SIZE;
|
||||||
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.ENTRIES_PER_BLOCK;
|
||||||
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.ENTRY_SIZE;
|
||||||
import static com.bytezone.diskbrowser.utilities.Utility.getAppleDate;
|
import static com.bytezone.diskbrowser.utilities.Utility.getAppleDate;
|
||||||
import static com.bytezone.diskbrowser.utilities.Utility.putAppleDate;
|
import static com.bytezone.diskbrowser.utilities.Utility.putAppleDate;
|
||||||
import static com.bytezone.diskbrowser.utilities.Utility.readShort;
|
import static com.bytezone.diskbrowser.utilities.Utility.readShort;
|
||||||
@ -12,8 +14,6 @@ import java.time.LocalDateTime;
|
|||||||
public class DirectoryHeader
|
public class DirectoryHeader
|
||||||
// -----------------------------------------------------------------------------------//
|
// -----------------------------------------------------------------------------------//
|
||||||
{
|
{
|
||||||
static final int BLOCK_SIZE = 512;
|
|
||||||
|
|
||||||
ProdosDisk disk;
|
ProdosDisk disk;
|
||||||
byte[] buffer;
|
byte[] buffer;
|
||||||
int ptr;
|
int ptr;
|
||||||
@ -25,7 +25,7 @@ public class DirectoryHeader
|
|||||||
byte minVersion = 0x00;
|
byte minVersion = 0x00;
|
||||||
byte access = (byte) 0xE3;
|
byte access = (byte) 0xE3;
|
||||||
byte entryLength = ENTRY_SIZE;
|
byte entryLength = ENTRY_SIZE;
|
||||||
byte entriesPerBlock = 0x0D;
|
byte entriesPerBlock = ENTRIES_PER_BLOCK;
|
||||||
int fileCount;
|
int fileCount;
|
||||||
|
|
||||||
// ---------------------------------------------------------------------------------//
|
// ---------------------------------------------------------------------------------//
|
||||||
@ -44,6 +44,7 @@ public class DirectoryHeader
|
|||||||
storageType = (byte) ((buffer[ptr] & 0xF0) >>> 4);
|
storageType = (byte) ((buffer[ptr] & 0xF0) >>> 4);
|
||||||
int nameLength = buffer[ptr] & 0x0F;
|
int nameLength = buffer[ptr] & 0x0F;
|
||||||
fileName = new String (buffer, ptr + 1, nameLength);
|
fileName = new String (buffer, ptr + 1, nameLength);
|
||||||
|
|
||||||
creationDate = getAppleDate (buffer, ptr + 0x18);
|
creationDate = getAppleDate (buffer, ptr + 0x18);
|
||||||
version = buffer[ptr + 0x1C];
|
version = buffer[ptr + 0x1C];
|
||||||
minVersion = buffer[ptr + 0x1D];
|
minVersion = buffer[ptr + 0x1D];
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package com.bytezone.diskbrowser.prodos.write;
|
package com.bytezone.diskbrowser.prodos.write;
|
||||||
|
|
||||||
import static com.bytezone.diskbrowser.prodos.write.ProdosDisk.BLOCK_SIZE;
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.BLOCK_SIZE;
|
||||||
import static com.bytezone.diskbrowser.prodos.write.ProdosDisk.UNDERLINE;
|
import static com.bytezone.diskbrowser.prodos.write.ProdosDisk.UNDERLINE;
|
||||||
import static com.bytezone.diskbrowser.utilities.Utility.getAppleDate;
|
import static com.bytezone.diskbrowser.utilities.Utility.getAppleDate;
|
||||||
import static com.bytezone.diskbrowser.utilities.Utility.putAppleDate;
|
import static com.bytezone.diskbrowser.utilities.Utility.putAppleDate;
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package com.bytezone.diskbrowser.prodos.write;
|
package com.bytezone.diskbrowser.prodos.write;
|
||||||
|
|
||||||
import static com.bytezone.diskbrowser.prodos.write.ProdosDisk.BLOCK_SIZE;
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.BLOCK_SIZE;
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------------//
|
// -----------------------------------------------------------------------------------//
|
||||||
public class IndexBlock
|
public class IndexBlock
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
package com.bytezone.diskbrowser.prodos.write;
|
package com.bytezone.diskbrowser.prodos.write;
|
||||||
|
|
||||||
import static com.bytezone.diskbrowser.prodos.write.ProdosDisk.BLOCK_SIZE;
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.BLOCK_SIZE;
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------------//
|
// -----------------------------------------------------------------------------------//
|
||||||
public class MasterIndexBlock
|
public class MasterIndexBlock
|
||||||
|
@ -1,6 +1,8 @@
|
|||||||
package com.bytezone.diskbrowser.prodos.write;
|
package com.bytezone.diskbrowser.prodos.write;
|
||||||
|
|
||||||
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.BLOCK_SIZE;
|
||||||
import static com.bytezone.diskbrowser.prodos.ProdosConstants.ENTRIES_PER_BLOCK;
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.ENTRIES_PER_BLOCK;
|
||||||
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.ENTRY_SIZE;
|
||||||
import static com.bytezone.diskbrowser.prodos.ProdosConstants.FILE_TYPE_DIRECTORY;
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.FILE_TYPE_DIRECTORY;
|
||||||
import static com.bytezone.diskbrowser.prodos.ProdosConstants.SUBDIRECTORY;
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.SUBDIRECTORY;
|
||||||
import static com.bytezone.diskbrowser.prodos.ProdosConstants.SUBDIRECTORY_HEADER;
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.SUBDIRECTORY_HEADER;
|
||||||
@ -20,9 +22,9 @@ public class ProdosDisk
|
|||||||
{
|
{
|
||||||
static final String UNDERLINE = "------------------------------------------------\n";
|
static final String UNDERLINE = "------------------------------------------------\n";
|
||||||
|
|
||||||
static final int BLOCK_SIZE = 512;
|
// static final int BLOCK_SIZE = 512;
|
||||||
private static final int CATALOG_SIZE = 4;
|
private static final int CATALOG_SIZE = 4;
|
||||||
static final int ENTRY_SIZE = 0x27;
|
// static final int ENTRY_SIZE = 0x27;
|
||||||
private static final int BITS_PER_BLOCK = 8 * BLOCK_SIZE;
|
private static final int BITS_PER_BLOCK = 8 * BLOCK_SIZE;
|
||||||
static final String[] storageTypes =
|
static final String[] storageTypes =
|
||||||
{ "Deleted", "Seedling", "Sapling", "Tree", "", "", "", "", "", "", "", "", "",
|
{ "Deleted", "Seedling", "Sapling", "Tree", "", "", "", "", "", "", "", "", "",
|
||||||
@ -117,7 +119,8 @@ public class ProdosDisk
|
|||||||
|
|
||||||
// ---------------------------------------------------------------------------------//
|
// ---------------------------------------------------------------------------------//
|
||||||
public FileEntry addFile (String path, byte type, int auxType, LocalDateTime created,
|
public FileEntry addFile (String path, byte type, int auxType, LocalDateTime created,
|
||||||
LocalDateTime modified, byte[] dataBuffer) throws DiskFullException
|
LocalDateTime modified, byte[] dataBuffer)
|
||||||
|
throws DiskFullException, VolumeCatalogFullException
|
||||||
// ---------------------------------------------------------------------------------//
|
// ---------------------------------------------------------------------------------//
|
||||||
{
|
{
|
||||||
// split the full path into an array of subdirectories and a file name
|
// split the full path into an array of subdirectories and a file name
|
||||||
@ -233,7 +236,8 @@ public class ProdosDisk
|
|||||||
}
|
}
|
||||||
|
|
||||||
// ---------------------------------------------------------------------------------//
|
// ---------------------------------------------------------------------------------//
|
||||||
private FileEntry createSubdirectory (int blockNo, String name) throws DiskFullException
|
private FileEntry createSubdirectory (int blockNo, String name)
|
||||||
|
throws DiskFullException, VolumeCatalogFullException
|
||||||
// ---------------------------------------------------------------------------------//
|
// ---------------------------------------------------------------------------------//
|
||||||
{
|
{
|
||||||
FileEntry fileEntry = findFreeSlot (blockNo);
|
FileEntry fileEntry = findFreeSlot (blockNo);
|
||||||
@ -296,7 +300,7 @@ public class ProdosDisk
|
|||||||
int allocateNextBlock () throws DiskFullException
|
int allocateNextBlock () throws DiskFullException
|
||||||
// ---------------------------------------------------------------------------------//
|
// ---------------------------------------------------------------------------------//
|
||||||
{
|
{
|
||||||
int nextBlock = getFreeBlock ();
|
int nextBlock = volumeBitMap.nextSetBit (0);
|
||||||
if (nextBlock < 0)
|
if (nextBlock < 0)
|
||||||
throw new DiskFullException ("Disk Full");
|
throw new DiskFullException ("Disk Full");
|
||||||
|
|
||||||
@ -306,17 +310,15 @@ public class ProdosDisk
|
|||||||
}
|
}
|
||||||
|
|
||||||
// ---------------------------------------------------------------------------------//
|
// ---------------------------------------------------------------------------------//
|
||||||
private int getFreeBlock ()
|
private FileEntry findFreeSlot (int blockNo)
|
||||||
|
throws DiskFullException, VolumeCatalogFullException
|
||||||
// ---------------------------------------------------------------------------------//
|
// ---------------------------------------------------------------------------------//
|
||||||
{
|
{
|
||||||
return volumeBitMap.nextSetBit (0);
|
// check for Volume Directory Header full
|
||||||
}
|
if (blockNo == 2 && volumeDirectoryHeader.fileCount == 51)
|
||||||
|
throw new VolumeCatalogFullException ("Volume Directory is full"); // stupid
|
||||||
|
|
||||||
// ---------------------------------------------------------------------------------//
|
// get the subdirectory header before the blockNo can change
|
||||||
private FileEntry findFreeSlot (int blockNo) throws DiskFullException
|
|
||||||
// ---------------------------------------------------------------------------------//
|
|
||||||
{
|
|
||||||
// get the subdirectory header before the blockNo possibly changes
|
|
||||||
SubdirectoryHeader subdirectoryHeader = subdirectoryHeaders.get (blockNo);
|
SubdirectoryHeader subdirectoryHeader = subdirectoryHeaders.get (blockNo);
|
||||||
|
|
||||||
int lastBlockNo = 0; // used for linking directory blocks
|
int lastBlockNo = 0; // used for linking directory blocks
|
||||||
@ -338,27 +340,20 @@ public class ProdosDisk
|
|||||||
blockNo = readShort (buffer, offset + 2); // next block
|
blockNo = readShort (buffer, offset + 2); // next block
|
||||||
} while (blockNo > 0);
|
} while (blockNo > 0);
|
||||||
|
|
||||||
|
if (subdirectoryHeader == null) // this should be impossible
|
||||||
|
throw new VolumeCatalogFullException ("Volume Directory is full");
|
||||||
|
|
||||||
// no free slots, so add a new catalog block
|
// no free slots, so add a new catalog block
|
||||||
blockNo = allocateNextBlock ();
|
blockNo = allocateNextBlock ();
|
||||||
|
|
||||||
// update file entry size (if not the Volume Directory)
|
|
||||||
if (subdirectoryHeader != null)
|
|
||||||
{
|
|
||||||
FileEntry fileEntry =
|
|
||||||
new FileEntry (this, buffer, subdirectoryHeader.parentPointer * BLOCK_SIZE
|
|
||||||
+ (subdirectoryHeader.parentEntry - 1) * ENTRY_SIZE + 4);
|
|
||||||
fileEntry.read ();
|
|
||||||
fileEntry.blocksUsed++;
|
|
||||||
fileEntry.eof += BLOCK_SIZE;
|
|
||||||
fileEntry.modifiedDate = LocalDateTime.now ();
|
|
||||||
fileEntry.write ();
|
|
||||||
}
|
|
||||||
|
|
||||||
// update links
|
// update links
|
||||||
int ptr = blockNo * BLOCK_SIZE;
|
int ptr = blockNo * BLOCK_SIZE;
|
||||||
writeShort (buffer, lastBlockNo * BLOCK_SIZE + 2, blockNo); // point to next block
|
writeShort (buffer, lastBlockNo * BLOCK_SIZE + 2, blockNo); // point to next block
|
||||||
writeShort (buffer, ptr, lastBlockNo); // point to previous block
|
writeShort (buffer, ptr, lastBlockNo); // point to previous block
|
||||||
|
|
||||||
|
// update parent's file entry size (this is the subdirectory file entry
|
||||||
|
subdirectoryHeader.updateParentFileEntry ();
|
||||||
|
|
||||||
return new FileEntry (this, buffer, ptr + 4); // first slot in new block
|
return new FileEntry (this, buffer, ptr + 4); // first slot in new block
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,10 +1,13 @@
|
|||||||
package com.bytezone.diskbrowser.prodos.write;
|
package com.bytezone.diskbrowser.prodos.write;
|
||||||
|
|
||||||
import static com.bytezone.diskbrowser.prodos.write.ProdosDisk.ENTRY_SIZE;
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.BLOCK_SIZE;
|
||||||
|
import static com.bytezone.diskbrowser.prodos.ProdosConstants.ENTRY_SIZE;
|
||||||
import static com.bytezone.diskbrowser.prodos.write.ProdosDisk.UNDERLINE;
|
import static com.bytezone.diskbrowser.prodos.write.ProdosDisk.UNDERLINE;
|
||||||
import static com.bytezone.diskbrowser.utilities.Utility.readShort;
|
import static com.bytezone.diskbrowser.utilities.Utility.readShort;
|
||||||
import static com.bytezone.diskbrowser.utilities.Utility.writeShort;
|
import static com.bytezone.diskbrowser.utilities.Utility.writeShort;
|
||||||
|
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------------//
|
// -----------------------------------------------------------------------------------//
|
||||||
public class SubdirectoryHeader extends DirectoryHeader
|
public class SubdirectoryHeader extends DirectoryHeader
|
||||||
// -----------------------------------------------------------------------------------//
|
// -----------------------------------------------------------------------------------//
|
||||||
@ -23,6 +26,19 @@ public class SubdirectoryHeader extends DirectoryHeader
|
|||||||
access = (byte) 0xC3;
|
access = (byte) 0xC3;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ---------------------------------------------------------------------------------//
|
||||||
|
void updateParentFileEntry ()
|
||||||
|
// ---------------------------------------------------------------------------------//
|
||||||
|
{
|
||||||
|
FileEntry fileEntry = new FileEntry (disk, buffer,
|
||||||
|
parentPointer * BLOCK_SIZE + (parentEntry - 1) * ENTRY_SIZE + 4);
|
||||||
|
fileEntry.read ();
|
||||||
|
fileEntry.blocksUsed++;
|
||||||
|
fileEntry.eof += BLOCK_SIZE;
|
||||||
|
fileEntry.modifiedDate = LocalDateTime.now ();
|
||||||
|
fileEntry.write ();
|
||||||
|
}
|
||||||
|
|
||||||
// ---------------------------------------------------------------------------------//
|
// ---------------------------------------------------------------------------------//
|
||||||
@Override
|
@Override
|
||||||
void read ()
|
void read ()
|
||||||
|
@ -0,0 +1,9 @@
|
|||||||
|
package com.bytezone.diskbrowser.prodos.write;
|
||||||
|
|
||||||
|
public class VolumeCatalogFullException extends Exception
|
||||||
|
{
|
||||||
|
public VolumeCatalogFullException (String message)
|
||||||
|
{
|
||||||
|
super (message);
|
||||||
|
}
|
||||||
|
}
|
@ -10,6 +10,7 @@ import java.util.List;
|
|||||||
import com.bytezone.diskbrowser.prodos.write.DiskFullException;
|
import com.bytezone.diskbrowser.prodos.write.DiskFullException;
|
||||||
import com.bytezone.diskbrowser.prodos.write.FileEntry;
|
import com.bytezone.diskbrowser.prodos.write.FileEntry;
|
||||||
import com.bytezone.diskbrowser.prodos.write.ProdosDisk;
|
import com.bytezone.diskbrowser.prodos.write.ProdosDisk;
|
||||||
|
import com.bytezone.diskbrowser.prodos.write.VolumeCatalogFullException;
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------------//
|
// -----------------------------------------------------------------------------------//
|
||||||
public class NuFX
|
public class NuFX
|
||||||
@ -152,6 +153,11 @@ public class NuFX
|
|||||||
{
|
{
|
||||||
System.out.println ("disk full: " + diskSize); // go round again
|
System.out.println ("disk full: " + diskSize); // go round again
|
||||||
}
|
}
|
||||||
|
catch (VolumeCatalogFullException e)
|
||||||
|
{
|
||||||
|
e.printStackTrace ();
|
||||||
|
return null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user