From 904db9632cfaabd9a65effddd49e5c228ec25041 Mon Sep 17 00:00:00 2001 From: Denis Molony Date: Mon, 23 Jul 2018 06:52:41 +1000 Subject: [PATCH] handle invalid block numbers --- .../disk/AbstractFormattedDisk.java | 6 +- .../bytezone/diskbrowser/disk/AppleDisk.java | 14 +- .../bytezone/diskbrowser/gui/DataPanel.java | 4 +- .../diskbrowser/gui/DiskLayoutImage.java | 4 +- .../diskbrowser/prodos/FileEntry.java | 120 ++++++++++-------- .../diskbrowser/prodos/ProdosConstants.java | 1 + .../diskbrowser/prodos/ProdosDisk.java | 2 - .../diskbrowser/prodos/ProdosIndexSector.java | 7 +- 8 files changed, 86 insertions(+), 72 deletions(-) diff --git a/src/com/bytezone/diskbrowser/disk/AbstractFormattedDisk.java b/src/com/bytezone/diskbrowser/disk/AbstractFormattedDisk.java index 8b98e8c..d685bef 100755 --- a/src/com/bytezone/diskbrowser/disk/AbstractFormattedDisk.java +++ b/src/com/bytezone/diskbrowser/disk/AbstractFormattedDisk.java @@ -293,10 +293,10 @@ public abstract class AbstractFormattedDisk implements FormattedDisk @Override public void setSectorType (int block, SectorType type) { - if (block >= sectorTypes.length) - System.out.println ("Invalid block number: " + block); - else + if (block < sectorTypes.length) sectorTypes[block] = type; + else + System.out.println ("setSectorType: Invalid block number: " + block); } // Override this so that the correct sector type can be displayed diff --git a/src/com/bytezone/diskbrowser/disk/AppleDisk.java b/src/com/bytezone/diskbrowser/disk/AppleDisk.java index 6032d69..ec258b4 100755 --- a/src/com/bytezone/diskbrowser/disk/AppleDisk.java +++ b/src/com/bytezone/diskbrowser/disk/AppleDisk.java @@ -29,7 +29,7 @@ public class AppleDisk implements Disk private final int tracks; // usually 35 for floppy disks private int sectors; // 8 or 16 - private int blocks; // 280 or 560 + private int blocks; // 280 or 560 for floppy disks, higher for HD private final int trackSize; // 4096 public int sectorSize; // 256 or 512 @@ -460,9 +460,10 @@ public class AppleDisk implements Disk { if (!isValidAddress (block)) { - System.out.printf ("Invalid block : %d of %d%n", block, this.blocks); + System.out.printf ("getDiskAddress: Invalid block : %d of %d%n", block, + this.blocks); return null; - // return new AppleDiskAddress (this, 0); this was looping 26/07/2016 + // return new AppleDiskAddress (this, 0); // this was looping 26/07/2016 } return new AppleDiskAddress (this, block); } @@ -483,9 +484,10 @@ public class AppleDisk implements Disk @Override public boolean isValidAddress (int block) { - if (block < 0 || block >= this.blocks) - return false; - return true; + // if (block < 0 || block >= this.blocks) + // return false; + // return true; + return block >= 0 && block < this.blocks; } @Override diff --git a/src/com/bytezone/diskbrowser/gui/DataPanel.java b/src/com/bytezone/diskbrowser/gui/DataPanel.java index 0b97597..b490d79 100755 --- a/src/com/bytezone/diskbrowser/gui/DataPanel.java +++ b/src/com/bytezone/diskbrowser/gui/DataPanel.java @@ -394,8 +394,8 @@ class DataPanel extends JTabbedPane if (sectors.size () == 1) { DiskAddress da = sectors.get (0); - // if (da != null) - setDataSource (event.getFormattedDisk ().getFormattedSector (da)); + if (da != null) + setDataSource (event.getFormattedDisk ().getFormattedSector (da)); } else setDataSource (new SectorList (event.getFormattedDisk (), sectors)); diff --git a/src/com/bytezone/diskbrowser/gui/DiskLayoutImage.java b/src/com/bytezone/diskbrowser/gui/DiskLayoutImage.java index d144d3b..83592b7 100644 --- a/src/com/bytezone/diskbrowser/gui/DiskLayoutImage.java +++ b/src/com/bytezone/diskbrowser/gui/DiskLayoutImage.java @@ -78,8 +78,8 @@ class DiskLayoutImage extends DiskPanel implements Scrollable, RedoListener if (sectors != null && sectors.size () > 0) { DiskAddress da = sectors.size () == 1 ? sectors.get (0) : sectors.get (1); - // if (da != null) - scrollRectToVisible (layoutDetails.getLocation (da)); + if (da != null) + scrollRectToVisible (layoutDetails.getLocation (da)); } repaint (); } diff --git a/src/com/bytezone/diskbrowser/prodos/FileEntry.java b/src/com/bytezone/diskbrowser/prodos/FileEntry.java index f36dc75..92bbad5 100755 --- a/src/com/bytezone/diskbrowser/prodos/FileEntry.java +++ b/src/com/bytezone/diskbrowser/prodos/FileEntry.java @@ -8,6 +8,7 @@ import com.bytezone.diskbrowser.applefile.*; import com.bytezone.diskbrowser.appleworks.AppleworksADBFile; import com.bytezone.diskbrowser.appleworks.AppleworksSSFile; import com.bytezone.diskbrowser.appleworks.AppleworksWPFile; +import com.bytezone.diskbrowser.disk.Disk; import com.bytezone.diskbrowser.disk.DiskAddress; import com.bytezone.diskbrowser.gui.DataSource; import com.bytezone.diskbrowser.utilities.HexFormatter; @@ -31,11 +32,18 @@ class FileEntry extends CatalogEntry implements ProdosConstants private final List indexBlocks = new ArrayList (); private boolean invalid; private FileEntry link; + // private final int maxBlocks; + + private final Disk appleDisk; public FileEntry (ProdosDisk fDisk, byte[] entryBuffer, DirectoryHeader parent, int parentBlock) { super (fDisk, entryBuffer); + + // maxBlocks = fDisk.getDisk ().getTotalBlocks (); + appleDisk = fDisk.getDisk (); + assert parent != null; this.parentDirectory = parent; this.catalogBlock = this.disk.getDiskAddress (parentBlock); @@ -49,9 +57,6 @@ class FileEntry extends CatalogEntry implements ProdosConstants modified = HexFormatter.getAppleDate (entryBuffer, 0x21); // headerPointer = HexFormatter.unsignedShort (entryBuffer, 0x25); - if (isGSOSFile ()) // I think this is wrong - System.out.printf ("************************************ %s is GS/OS%n", name); - switch (storageType) { case SEEDLING: @@ -59,18 +64,18 @@ class FileEntry extends CatalogEntry implements ProdosConstants break; case SAPLING: - if (isGSOSFile ()) // not sure why this exists - traverseGEOSIndex (keyPtr); - else - addDataBlocks (storageType, keyPtr); + // if (isGSOSFile ()) // not sure why this exists + // traverseGEOSIndex (keyPtr); + // else + addDataBlocks (storageType, keyPtr); break; case TREE: masterIndexBlock = disk.getDiskAddress (keyPtr); - if (isGSOSFile ()) // not sure why this exists - traverseGEOSMasterIndex (keyPtr); - else - addDataBlocks (storageType, keyPtr); + // if (isGSOSFile ()) // not sure why this exists + // traverseGEOSMasterIndex (keyPtr); + // else + addDataBlocks (storageType, keyPtr); break; case GSOS_EXTENDED_FILE: @@ -166,7 +171,10 @@ class FileEntry extends CatalogEntry implements ProdosConstants byte[] buffer = disk.readSector (blockPtr); for (int i = 0; i < 256; i++) - blocks.add ((buffer[i] & 0xFF) | ((buffer[i + 0x100] & 0xFF) << 8)); + { + int blockNo = (buffer[i] & 0xFF) | ((buffer[i + 0x100] & 0xFF) << 8); + blocks.add (disk.isValidAddress (blockNo) ? blockNo : 0); + } } return blocks; @@ -186,53 +194,56 @@ class FileEntry extends CatalogEntry implements ProdosConstants List blocks = new ArrayList (highest + 1); for (int i = 0; i <= highest; i++) - blocks.add ((buffer[i] & 0xFF) | ((buffer[i + 256] & 0xFF) << 8)); + { + int blockNo = (buffer[i] & 0xFF) | ((buffer[i + 256] & 0xFF) << 8); + blocks.add (disk.isValidAddress (blockNo) ? blockNo : 0); + } return blocks; } // should be removed - private boolean isGSOSFile () - { - // return ((fileType & 0xF0) == 0x80); - if ((fileType & 0xF0) == 0x80) - System.out.println ("GS/OS file: " + name); - return false; - } + // private boolean isGSOSFile () + // { + // // return ((fileType & 0xF0) == 0x80); + // if ((fileType & 0xF0) == 0x80) + // System.out.println ("GS/OS file: " + name); + // return false; + // } // should be removed - private void traverseGEOSMasterIndex (int keyPtr) - { - byte[] buffer = disk.readSector (keyPtr); // master index - for (int i = 0; i < 0x80; i++) - { - int block = HexFormatter.intValue (buffer[i], buffer[i + 256]); - if (block == 0) - break; - if (block == 0xFFFF) - continue; - traverseGEOSIndex (block); - } - } + // private void traverseGEOSMasterIndex (int keyPtr) + // { + // byte[] buffer = disk.readSector (keyPtr); // master index + // for (int i = 0; i < 0x80; i++) + // { + // int block = HexFormatter.intValue (buffer[i], buffer[i + 256]); + // if (block == 0) + // break; + // if (block == 0xFFFF) + // continue; + // traverseGEOSIndex (block); + // } + // } // should be removed - private void traverseGEOSIndex (int keyPtr) - { - parentDisk.setSectorType (keyPtr, parentDisk.indexSector); - indexBlocks.add (disk.getDiskAddress (keyPtr)); - byte[] buffer = disk.readSector (keyPtr); - - for (int i = 0; i < 0x80; i++) - { - int block = HexFormatter.intValue (buffer[i], buffer[i + 256]); - if (block == 0) - break; - if (block == 0xFFFF) - continue; - parentDisk.setSectorType (block, parentDisk.dataSector); - dataBlocks.add (disk.getDiskAddress (block)); - } - } + // private void traverseGEOSIndex (int keyPtr) + // { + // parentDisk.setSectorType (keyPtr, parentDisk.indexSector); + // indexBlocks.add (disk.getDiskAddress (keyPtr)); + // byte[] buffer = disk.readSector (keyPtr); + // + // for (int i = 0; i < 0x80; i++) + // { + // int block = HexFormatter.intValue (buffer[i], buffer[i + 256]); + // if (block == 0) + // break; + // if (block == 0xFFFF) + // continue; + // parentDisk.setSectorType (block, parentDisk.dataSector); + // dataBlocks.add (disk.getDiskAddress (block)); + // } + // } @Override public DataSource getDataSource () @@ -249,7 +260,8 @@ class FileEntry extends CatalogEntry implements ProdosConstants if (fileType == FILE_TYPE_TEXT && auxType > 0) // random access file return getRandomAccessTextFile (); - byte[] buffer = isGSOSFile () ? getGEOSBuffer () : getBuffer (); + // byte[] buffer = isGSOSFile () ? getGEOSBuffer () : getBuffer (); + byte[] buffer = getBuffer (); byte[] exactBuffer = getExactBuffer (buffer); try @@ -388,11 +400,9 @@ class FileEntry extends CatalogEntry implements ProdosConstants file = new FileSystemTranslator (name, exactBuffer); break; - case FILE_TYPE_PASCAL_VOLUME: - file = new DefaultAppleFile (name, exactBuffer); - break; - case FILE_TYPE_FINDER: + case FILE_TYPE_PASCAL_VOLUME: + case FILE_TYPE_GEO: file = new DefaultAppleFile (name, exactBuffer); break; diff --git a/src/com/bytezone/diskbrowser/prodos/ProdosConstants.java b/src/com/bytezone/diskbrowser/prodos/ProdosConstants.java index 285f758..8d5ddeb 100755 --- a/src/com/bytezone/diskbrowser/prodos/ProdosConstants.java +++ b/src/com/bytezone/diskbrowser/prodos/ProdosConstants.java @@ -11,6 +11,7 @@ public interface ProdosConstants int FILE_TYPE_ASP = 0x1B; int FILE_TYPE_DESCRIPTOR_TABLE = 0x42; int FILE_TYPE_GWP = 0x50; + int FILE_TYPE_GEO = 0x82; int FILE_TYPE_IIGS_SOURCE = 0xB0; int FILE_TYPE_IIGS_OBJECT = 0xB1; // int FILE_TYPE_FORKED_FILE = 0xB3; // S16 diff --git a/src/com/bytezone/diskbrowser/prodos/ProdosDisk.java b/src/com/bytezone/diskbrowser/prodos/ProdosDisk.java index 08ad9df..b7617cd 100755 --- a/src/com/bytezone/diskbrowser/prodos/ProdosDisk.java +++ b/src/com/bytezone/diskbrowser/prodos/ProdosDisk.java @@ -94,8 +94,6 @@ public class ProdosDisk extends AbstractFormattedDisk if (storageType == 0) // deleted or unused continue; - System.out.println ("here"); - byte[] entry = new byte[ProdosConstants.ENTRY_SIZE]; System.arraycopy (sectorBuffer, ptr, entry, 0, ProdosConstants.ENTRY_SIZE); diff --git a/src/com/bytezone/diskbrowser/prodos/ProdosIndexSector.java b/src/com/bytezone/diskbrowser/prodos/ProdosIndexSector.java index d67f179..942235e 100755 --- a/src/com/bytezone/diskbrowser/prodos/ProdosIndexSector.java +++ b/src/com/bytezone/diskbrowser/prodos/ProdosIndexSector.java @@ -25,8 +25,11 @@ class ProdosIndexSector extends AbstractSector text.append ( String.format ("%02X %02X %02X", i, buffer[i], buffer[i + 256])); if (buffer[i] != 0 || buffer[i + 256] != 0) - text.append (String.format (" %s%n", - "block " + HexFormatter.intValue (buffer[i], buffer[i + 256]))); + { + int blockNo = HexFormatter.intValue (buffer[i], buffer[i + 256]); + String valid = disk.isValidAddress (blockNo) ? "" : " *** invalid ***"; + text.append (String.format (" %s%s%n", "block " + blockNo, valid)); + } else text.append ("\n"); }