From: <ga...@us...> - 2009-04-28 08:39:31
|
Revision: 5355 http://jnode.svn.sourceforge.net/jnode/?rev=5355&view=rev Author: galatnm Date: 2009-04-28 08:39:26 +0000 (Tue, 28 Apr 2009) Log Message: ----------- Renaming Modified Paths: -------------- trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusParams.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusFileSystem.java trunk/fs/src/fs/org/jnode/fs/hfsplus/Superblock.java trunk/fs/src/fs/org/jnode/fs/hfsplus/catalog/Catalog.java trunk/fs/src/fs/org/jnode/fs/hfsplus/catalog/CatalogFile.java trunk/fs/src/fs/org/jnode/fs/hfsplus/catalog/CatalogFolder.java trunk/fs/src/fs/org/jnode/fs/hfsplus/catalog/CatalogKey.java trunk/fs/src/fs/org/jnode/fs/hfsplus/catalog/CatalogThread.java Added Paths: ----------- trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusBSDInfo.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusDirectory.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusEntry.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusFile.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusForkData.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusObject.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusSystemChecker.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsUnicodeString.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsUtils.java Removed Paths: ------------- trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusBSDInfo.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusDirectory.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusEntry.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusFile.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusForkData.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusObject.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSUnicodeString.java trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSUtils.java Deleted: trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusBSDInfo.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusBSDInfo.java 2009-04-28 07:28:05 UTC (rev 5354) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusBSDInfo.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -1,5 +0,0 @@ -package org.jnode.fs.hfsplus; - -public class HFSPlusBSDInfo { - -} Deleted: trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusDirectory.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusDirectory.java 2009-04-28 07:28:05 UTC (rev 5354) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusDirectory.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -1,255 +0,0 @@ -/* - * $Id$ - * - * Copyright (C) 2003-2009 JNode.org - * - * This library is free software; you can redistribute it and/or modify it - * under the terms of the GNU Lesser General Public License as published - * by the Free Software Foundation; either version 2.1 of the License, or - * (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY - * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public - * License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this library; If not, write to the Free Software Foundation, Inc., - * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - */ - -package org.jnode.fs.hfsplus; - -import java.io.FileNotFoundException; -import java.io.IOException; -import java.util.Iterator; -import java.util.LinkedList; -import java.util.List; - -import org.apache.log4j.Logger; -import org.jnode.fs.FSDirectory; -import org.jnode.fs.FSEntry; -import org.jnode.fs.ReadOnlyFileSystemException; -import org.jnode.fs.hfsplus.catalog.Catalog; -import org.jnode.fs.hfsplus.catalog.CatalogFile; -import org.jnode.fs.hfsplus.catalog.CatalogFolder; -import org.jnode.fs.hfsplus.catalog.CatalogKey; -import org.jnode.fs.hfsplus.catalog.CatalogNodeId; -import org.jnode.fs.hfsplus.tree.LeafRecord; -import org.jnode.fs.spi.FSEntryTable; - -public class HFSPlusDirectory extends HFSPlusEntry implements FSDirectory { - - private static final Logger log = Logger.getLogger(HFSPlusDirectory.class); - - /** Table of entries of our parent */ - private FSEntryTable entries; - - private CatalogFolder folder; - - public HFSPlusDirectory(HfsPlusFileSystem fs, HFSPlusDirectory parent, String name, - LeafRecord record) { - super(fs, parent, name, record); - this.folder = new CatalogFolder(record.getData()); - this.entries = FSEntryTable.EMPTY_TABLE; - } - - @Override - public FSEntry addDirectory(String name) throws IOException { - log.debug("<<< BEGIN addDirectory " + name + " >>>"); - if (fs.isReadOnly()) { - throw new ReadOnlyFileSystemException(); - } - - if (getEntry(name) != null) { - throw new IOException("File or Directory already exists" + name); - } - FSEntry newEntry = createDirectoryEntry(name); - setFreeEntry(newEntry); - log.debug("<<< END addDirectory " + name + " >>>"); - return newEntry; - } - - @Override - public FSEntry addFile(String name) throws IOException { - log.debug("<<< BEGIN addFile " + name + " >>>"); - if (fs.isReadOnly()) { - throw new ReadOnlyFileSystemException(); - } - if (getEntry(name) != null) { - throw new IOException("File or directory already exists: " + name); - } - FSEntry newEntry = createFileEntry(name); - setFreeEntry(newEntry); - - log.debug("<<< END addFile " + name + " >>>"); - return newEntry; - } - - private final FSEntry createFileEntry(final String name) throws IOException { - /*if (fs.isReadOnly()) { - throw new ReadOnlyFileSystemException(); - } - Catalog catalog = fs.getCatalog(); - Superblock volumeHeader = ((HfsPlusFileSystem) getFileSystem()).getVolumeHeader(); - LeafRecord fileRecord = catalog.createNode(name, this.folder - .getFolderId(), new CatalogNodeId(volumeHeader.getNextCatalogId()), CatalogFile.RECORD_TYPE_FILE); - - HFSPlusEntry newEntry = new HFSPlusFile(fs, this, name, folderRecord); - newEntry.setDirty(); - volumeHeader.setFileCount(volumeHeader.getFileCount() + 1); - log.debug("New volume header :\n" + volumeHeader.toString());*/ - - return null; - } - - @Override - public void flush() throws IOException { - log.debug("<<< BEGIN flush >>>"); - if (fs.isReadOnly()) { - throw new ReadOnlyFileSystemException(); - } - boolean flushEntries = isEntriesLoaded() && entries.isDirty(); - if (isDirty() || flushEntries) { - writeEntries(entries); - // entries.resetDirty(); - resetDirty(); - } - log.debug("<<< END flush >>>"); - } - - @Override - public FSEntry getEntry(String name) throws IOException { - checkEntriesLoaded(); - return entries.get(name); - } - - @Override - public Iterator<? extends FSEntry> iterator() throws IOException { - return entries.iterator(); - } - - public int rename(String oldName, String newName) { - return entries.rename(oldName, newName); - } - - @Override - public void remove(String name) throws IOException { - if (fs.isReadOnly()) { - throw new ReadOnlyFileSystemException(); - } - if (entries.remove(name) >= 0) { - setDirty(); - flush(); - return; - } else { - throw new FileNotFoundException(name); - } - } - - // Helper methods - - /** - * BE CAREFULL : don't call this method from the constructor of this class - * because it call the method readEntries of the child classes that are not - * yet initialized (constructed). - */ - protected final void checkEntriesLoaded() { - if (!isEntriesLoaded()) { - log.debug("checkEntriesLoaded : loading"); - try { - if (rights.canRead()) { - entries = readEntries(); - } else { - // the next time, we will call checkEntriesLoaded() - // we will retry to load entries - entries = FSEntryTable.EMPTY_TABLE; - log.debug("checkEntriesLoaded : can't read, using EMPTY_TABLE"); - } - resetDirty(); - } catch (IOException e) { - log.fatal("unable to read directory entries", e); - // the next time, we will call checkEntriesLoaded() - // we will retry to load entries - entries = FSEntryTable.EMPTY_TABLE; - } - } - log.debug("<<< END checkEntriesLoaded >>>"); - } - - /** - * Have we already loaded our entries from device ? - * - * @return if the entries are already loaded from the device - */ - private final boolean isEntriesLoaded() { - return (entries != FSEntryTable.EMPTY_TABLE); - } - - /** - * - * @return - * @throws IOException - */ - private final FSEntryTable readEntries() throws IOException { - List<FSEntry> pathList = new LinkedList<FSEntry>(); - HfsPlusFileSystem fs = (HfsPlusFileSystem) getFileSystem(); - if (fs.getVolumeHeader().getFolderCount() > 0) { - LeafRecord[] records = fs.getCatalog().getRecords(folder.getFolderId()); - for (LeafRecord rec : records) { - if (rec.getType() == CatalogFolder.RECORD_TYPE_FOLDER || - rec.getType() == CatalogFile.RECORD_TYPE_FILE) { - String name = ((CatalogKey) rec.getKey()).getNodeName().getUnicodeString(); - HFSPlusEntry e = new HFSPlusDirectory(fs, this, name, rec); - pathList.add(e); - } - } - } - return new FSEntryTable(((HfsPlusFileSystem) getFileSystem()), pathList); - } - - private void writeEntries(final FSEntryTable entries) throws IOException { - // TODO Auto-generated method stub - } - - /** - * - * @param name - * @return - * @throws IOException - */ - private final FSEntry createDirectoryEntry(final String name) throws IOException { - if (fs.isReadOnly()) { - throw new ReadOnlyFileSystemException(); - } - Catalog catalog = fs.getCatalog(); - Superblock volumeHeader = ((HfsPlusFileSystem) getFileSystem()).getVolumeHeader(); - LeafRecord folderRecord = catalog.createNode(name, this.folder.getFolderId(), - new CatalogNodeId(volumeHeader.getNextCatalogId()), CatalogFolder.RECORD_TYPE_FOLDER_THREAD); - folder.setValence(folder.getValence() + 1); - - HFSPlusEntry newEntry = new HFSPlusDirectory(fs, this, name, folderRecord); - newEntry.setDirty(); - volumeHeader.setFolderCount(volumeHeader.getFolderCount() + 1); - log.debug("New volume header :\n" + volumeHeader.toString()); - - return newEntry; - } - - /** - * Find a free entry and set it with the given entry - * - * @param newEntry - * @throws IOException - */ - private final void setFreeEntry(FSEntry newEntry) throws IOException { - checkEntriesLoaded(); - if (entries.setFreeEntry(newEntry) >= 0) { - log.debug("setFreeEntry: free entry found !"); - setDirty(); - flush(); - return; - } - } - -} Deleted: trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusEntry.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusEntry.java 2009-04-28 07:28:05 UTC (rev 5354) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusEntry.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -1,167 +0,0 @@ -/* - * $Id$ - * - * Copyright (C) 2003-2009 JNode.org - * - * This library is free software; you can redistribute it and/or modify it - * under the terms of the GNU Lesser General Public License as published - * by the Free Software Foundation; either version 2.1 of the License, or - * (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY - * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public - * License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this library; If not, write to the Free Software Foundation, Inc., - * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - */ - -package org.jnode.fs.hfsplus; - -import java.io.IOException; - -import org.jnode.fs.FSAccessRights; -import org.jnode.fs.FSDirectory; -import org.jnode.fs.FSEntry; -import org.jnode.fs.FSFile; -import org.jnode.fs.FileSystem; -import org.jnode.fs.hfsplus.catalog.CatalogFile; -import org.jnode.fs.hfsplus.catalog.CatalogFolder; -import org.jnode.fs.hfsplus.tree.LeafRecord; -import org.jnode.fs.spi.AbstractFSEntry; -import org.jnode.fs.spi.UnixFSAccessRights; - -public class HFSPlusEntry implements FSEntry { - - protected HfsPlusFileSystem fs; - protected HFSPlusDirectory parent; - protected String name; - protected LeafRecord record; - private int type; - - protected boolean valid; - protected boolean dirty; - protected FSAccessRights rights; - private long lastModified; - - /** - * - * @param fs - * @param parent - * @param name - * @param record - */ - public HFSPlusEntry(HfsPlusFileSystem fs, HFSPlusDirectory parent, String name, - LeafRecord record) { - this.fs = fs; - this.parent = parent; - this.name = name; - this.record = record; - this.type = getFSEntryType(); - this.rights = new UnixFSAccessRights(fs); - this.lastModified = System.currentTimeMillis(); - } - - private int getFSEntryType() { - int mode = record.getType(); - if ("/".equals(name)) { - return AbstractFSEntry.ROOT_ENTRY; - } else if (mode == CatalogFolder.RECORD_TYPE_FOLDER) { - return AbstractFSEntry.DIR_ENTRY; - } else if (mode == CatalogFile.RECORD_TYPE_FILE) { - return AbstractFSEntry.FILE_ENTRY; - } else { - return AbstractFSEntry.OTHER_ENTRY; - } - } - - @Override - public FSAccessRights getAccessRights() throws IOException { - return rights; - } - - @Override - public FSDirectory getDirectory() throws IOException { - if (!isDirectory()) { - throw new IOException("It is not a Directory"); - } - return (HFSPlusDirectory) this; - } - - @Override - public FSFile getFile() throws IOException { - if (!isFile()) { - throw new IOException("It is not a file"); - } - return (HFSPlusFile) this; - } - - @Override - public long getLastModified() throws IOException { - // TODO Auto-generated method stub - return lastModified; - } - - @Override - public String getName() { - return name; - } - - @Override - public FSDirectory getParent() { - return parent; - } - - @Override - public boolean isDirectory() { - return (type == AbstractFSEntry.DIR_ENTRY || type == AbstractFSEntry.ROOT_ENTRY); - } - - @Override - public boolean isDirty() throws IOException { - return dirty; - } - - public void setDirty() { - dirty = true; - } - - public void resetDirty() { - dirty = false; - } - - @Override - public boolean isFile() { - return (type == AbstractFSEntry.FILE_ENTRY); - } - - @Override - public void setLastModified(long lastModified) throws IOException { - this.lastModified = lastModified; - } - - @Override - public void setName(String newName) throws IOException { - if (type == AbstractFSEntry.ROOT_ENTRY) { - throw new IOException("Cannot change name of root directory"); - } - if (parent.rename(name, newName) < 0) { - throw new IOException("Cannot change name"); - } - - this.name = newName; - } - - @Override - public FileSystem<?> getFileSystem() { - return fs; - } - - @Override - public boolean isValid() { - return valid; - } - -} Deleted: trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusFile.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusFile.java 2009-04-28 07:28:05 UTC (rev 5354) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusFile.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -1,72 +0,0 @@ -/* - * $Id$ - * - * Copyright (C) 2003-2009 JNode.org - * - * This library is free software; you can redistribute it and/or modify it - * under the terms of the GNU Lesser General Public License as published - * by the Free Software Foundation; either version 2.1 of the License, or - * (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY - * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public - * License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this library; If not, write to the Free Software Foundation, Inc., - * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - */ - -package org.jnode.fs.hfsplus; - -import java.io.IOException; -import java.nio.ByteBuffer; - -import org.jnode.fs.FSFile; -import org.jnode.fs.hfsplus.catalog.CatalogFile; -import org.jnode.fs.hfsplus.extent.ExtentDescriptor; -import org.jnode.fs.hfsplus.tree.LeafRecord; - -public class HFSPlusFile extends HFSPlusEntry implements FSFile { - - private CatalogFile file; - - public HFSPlusFile(HfsPlusFileSystem fs, HFSPlusDirectory parent, String name, LeafRecord record) { - super(fs, parent, name, record); - this.file = new CatalogFile(record.getData()); - } - - @Override - public void flush() throws IOException { - - } - - @Override - public final long getLength() { - return file.getDatas().getTotalSize(); - } - - @Override - public final void read(final long fileOffset, final ByteBuffer dest) throws IOException { - HfsPlusFileSystem fs = (HfsPlusFileSystem) getFileSystem(); - for (ExtentDescriptor d : file.getDatas().getExtents()) { - if (!d.isEmpty()) { - long firstOffset = d.getStartOffset(fs.getVolumeHeader().getBlockSize()); - fs.getApi().read(firstOffset, dest); - } - } - } - - @Override - public void write(final long fileOffset, final ByteBuffer src) throws IOException { - // TODO Auto-generated method stub - - } - - public void setLength(final long length) throws IOException { - // TODO Auto-generated method stub - - } - -} Deleted: trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusForkData.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusForkData.java 2009-04-28 07:28:05 UTC (rev 5354) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusForkData.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -1,128 +0,0 @@ -/* - * $Id$ - * - * Copyright (C) 2003-2009 JNode.org - * - * This library is free software; you can redistribute it and/or modify it - * under the terms of the GNU Lesser General Public License as published - * by the Free Software Foundation; either version 2.1 of the License, or - * (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY - * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public - * License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this library; If not, write to the Free Software Foundation, Inc., - * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - */ - -package org.jnode.fs.hfsplus; - -import org.jnode.fs.hfsplus.extent.ExtentDescriptor; -import org.jnode.util.BigEndian; - -public class HFSPlusForkData { - public static final int FORK_DATA_LENGTH = 80; - private static final int EXTENT_OFFSET = 16; - /** The size in bytes of the valid data in the fork. */ - private long totalSize; - /** */ - private int clumpSize; - /** The total of allocation blocks use by the extents in the fork. */ - private int totalBlock; - /** The first eight extent descriptors for the fork. */ - private ExtentDescriptor[] extents; - - /** - * Create fork data from existing informations. - * - * @param src - * @param offset - */ - public HFSPlusForkData(final byte[] src, final int offset) { - byte[] data = new byte[FORK_DATA_LENGTH]; - System.arraycopy(src, offset, data, 0, FORK_DATA_LENGTH); - totalSize = BigEndian.getInt64(data, 0); - clumpSize = BigEndian.getInt32(data, 8); - totalBlock = BigEndian.getInt32(data, 12); - extents = new ExtentDescriptor[8]; - for (int i = 0; i < 8; i++) { - extents[i] = - new ExtentDescriptor(data, EXTENT_OFFSET + - (i * ExtentDescriptor.EXTENT_DESCRIPTOR_LENGTH)); - } - } - - /** - * - * Create a new empty fork data object. - * - * @param totalSize - * @param clumpSize - * @param totalBlock - */ - public HFSPlusForkData(long totalSize, int clumpSize, int totalBlock) { - this.totalSize = totalSize; - this.clumpSize = clumpSize; - this.totalBlock = totalBlock; - this.extents = new ExtentDescriptor[8]; - for (int i = 0; i < extents.length; i++) { - extents[i] = new ExtentDescriptor(); - } - } - - public byte[] write(byte[] dest, int destOffSet) { - byte[] data = new byte[FORK_DATA_LENGTH]; - BigEndian.setInt64(data, 0, totalSize); - BigEndian.setInt32(data, 8, clumpSize); - BigEndian.setInt32(data, 12, totalBlock); - for (int i = 0; i < extents.length; i++) { - extents[i].write(data, EXTENT_OFFSET + (i * ExtentDescriptor.EXTENT_DESCRIPTOR_LENGTH)); - } - System.arraycopy(data, 0, dest, destOffSet, FORK_DATA_LENGTH); - return dest; - } - - public final String toString() { - StringBuffer s = new StringBuffer(); - s.append("Total size : ").append(totalSize).append("\n"); - s.append("Clump size : ").append(clumpSize).append("\n"); - s.append("Total Blocks : ").append(totalBlock).append("\n"); - for (int i = 0; i < extents.length; i++) { - s.append("Extent[" + i + "]: " + extents[i].toString()); - } - return s.toString(); - } - - public long getTotalSize() { - return totalSize; - } - - public int getClumpSize() { - return clumpSize; - } - - public int getTotalBlocks() { - return totalBlock; - } - - public ExtentDescriptor getExtent(int index) { - return extents[index]; - } - - /** - * - * @param index - * @param desc - */ - public final void addDescriptor(int index, ExtentDescriptor desc) { - extents[index] = desc; - } - - public ExtentDescriptor[] getExtents() { - return extents; - } - -} Deleted: trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusObject.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusObject.java 2009-04-28 07:28:05 UTC (rev 5354) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusObject.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -1,39 +0,0 @@ -/* - * $Id$ - * - * Copyright (C) 2003-2009 JNode.org - * - * This library is free software; you can redistribute it and/or modify it - * under the terms of the GNU Lesser General Public License as published - * by the Free Software Foundation; either version 2.1 of the License, or - * (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY - * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public - * License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this library; If not, write to the Free Software Foundation, Inc., - * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - */ - -package org.jnode.fs.hfsplus; - -import org.jnode.fs.FSObject; - -public class HFSPlusObject implements FSObject { - protected HfsPlusFileSystem fs; - - public HFSPlusObject(final HfsPlusFileSystem fileSystem) { - this.fs = fileSystem; - } - - public final HfsPlusFileSystem getFileSystem() { - return fs; - } - - public final boolean isValid() { - return false; - } -} Modified: trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusParams.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusParams.java 2009-04-28 07:28:05 UTC (rev 5354) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusParams.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -20,6 +20,9 @@ package org.jnode.fs.hfsplus; +import java.io.IOException; + +import org.jnode.driver.ApiNotFoundException; import org.jnode.fs.FileSystemException; public class HFSPlusParams { @@ -66,82 +69,85 @@ } /** + * Initialize default sizes (allocation, catalog node, etc...) * - * @param blockDeviceSize - * @param sectorSize - * + * @param fs * @throws FileSystemException - * + * @throws IOException */ - public void initializeDefaultsValues(long blockDeviceSize, long sectorSize) - throws FileSystemException { - long clumpSize = 0; - this.blockDeviceSize = blockDeviceSize; - if (resourceClumpBlocks == 0) { - if (blockSize > DEFAULT_BLOCK_SIZE) { - clumpSize = round(RESOURCE_CLUMP_FACTOR * DEFAULT_BLOCK_SIZE, blockSize); + public void initializeDefaultsValues(HfsPlusFileSystem fs) + throws FileSystemException, IOException { + try { + long clumpSize = 0; + this.blockDeviceSize = fs.getApi().getLength(); + if (resourceClumpBlocks == 0) { + if (blockSize > DEFAULT_BLOCK_SIZE) { + clumpSize = round(RESOURCE_CLUMP_FACTOR * DEFAULT_BLOCK_SIZE, blockSize); + } else { + clumpSize = RESOURCE_CLUMP_FACTOR * blockSize; + } } else { - clumpSize = RESOURCE_CLUMP_FACTOR * blockSize; + clumpSize = clumpSizeCalculation(resourceClumpBlocks); } - } else { - clumpSize = clumpSizeCalculation(resourceClumpBlocks); - } - resourceClumpSize = (int) clumpSize; - if (dataClumpBlocks == 0) { - if (blockSize > DEFAULT_BLOCK_SIZE) { - clumpSize = round(DATA_CLUMP_FACTOR * DEFAULT_BLOCK_SIZE, blockSize); + resourceClumpSize = (int) clumpSize; + if (dataClumpBlocks == 0) { + if (blockSize > DEFAULT_BLOCK_SIZE) { + clumpSize = round(DATA_CLUMP_FACTOR * DEFAULT_BLOCK_SIZE, blockSize); + } else { + clumpSize = DATA_CLUMP_FACTOR * blockSize; + } } else { - clumpSize = DATA_CLUMP_FACTOR * blockSize; + clumpSize = clumpSizeCalculation(dataClumpBlocks); } - } else { - clumpSize = clumpSizeCalculation(dataClumpBlocks); - } - if (blockSize < OPTIMAL_BLOCK_SIZE || blockDeviceSize < 0x40000000) { - catalogNodeSize = 4096; - } - long sectorCount = blockDeviceSize / sectorSize; - if (catalogClumpBlocks == 0) { - clumpSize = getBTreeClumpSize(blockSize, catalogNodeSize, sectorCount, true); - } else { - clumpSize = clumpSizeCalculation(catalogClumpBlocks); - if (clumpSize % catalogNodeSize != 0) { - throw new FileSystemException("clump size is not a multiple of node size"); + if (blockSize < OPTIMAL_BLOCK_SIZE || blockDeviceSize < 0x40000000) { + catalogNodeSize = 4096; } - } - catalogClumpSize = (int) clumpSize; - if (extentClumpBlocks == 0) { - clumpSize = getBTreeClumpSize(blockSize, extentNodeSize, sectorCount, false); - } else { - clumpSize = clumpSizeCalculation(extentClumpBlocks); - } - extentClumpSize = (int) clumpSize; + long sectorCount = blockDeviceSize / fs.getFSApi().getSectorSize(); + if (catalogClumpBlocks == 0) { + clumpSize = getBTreeClumpSize(blockSize, catalogNodeSize, sectorCount, true); + } else { + clumpSize = clumpSizeCalculation(catalogClumpBlocks); + if (clumpSize % catalogNodeSize != 0) { + throw new FileSystemException("clump size is not a multiple of node size"); + } + } + catalogClumpSize = (int) clumpSize; + if (extentClumpBlocks == 0) { + clumpSize = getBTreeClumpSize(blockSize, extentNodeSize, sectorCount, false); + } else { + clumpSize = clumpSizeCalculation(extentClumpBlocks); + } + extentClumpSize = (int) clumpSize; - if (attributeClumpBlocks == 0) { - clumpSize = 0; - } else { - clumpSize = clumpSizeCalculation(attributeClumpBlocks); - if (clumpSize % attributeNodeSize != 0) { - throw new FileSystemException("clump size is not a multiple of attribute node size"); + if (attributeClumpBlocks == 0) { + clumpSize = 0; + } else { + clumpSize = clumpSizeCalculation(attributeClumpBlocks); + if (clumpSize % attributeNodeSize != 0) { + throw new FileSystemException( + "clump size is not a multiple of attribute node size"); + } } - } - attributeClumpSize = (int) clumpSize; + attributeClumpSize = (int) clumpSize; - long totalBlocks = this.getBlockCount(); - long minClumpSize = this.getBlockCount() >> 3; - if ((totalBlocks & 7) == 0) { - ++minClumpSize; - } - if (bitmapClumpBlocks == 0) { - clumpSize = minClumpSize; - } else { - clumpSize = clumpSizeCalculation(bitmapClumpBlocks); - if (clumpSize < minClumpSize) { - throw new FileSystemException("bitmap clump size is too small."); + long totalBlocks = this.getBlockCount(); + long minClumpSize = this.getBlockCount() >> 3; + if ((totalBlocks & 7) == 0) { + ++minClumpSize; } + if (bitmapClumpBlocks == 0) { + clumpSize = minClumpSize; + } else { + clumpSize = clumpSizeCalculation(bitmapClumpBlocks); + if (clumpSize < minClumpSize) { + throw new FileSystemException("bitmap clump size is too small."); + } + } + allocationClumpSize = (int) clumpSize; + } catch (ApiNotFoundException e) { + throw new FileSystemException("Unable initialize default values.", e); } - allocationClumpSize = (int) clumpSize; - } private int[] extentClumpTable = new int[] {4, 4, 4, 5, 5, 6, 7, 8, 9, 11, 14, 16, 20, 25, 32}; @@ -151,13 +157,13 @@ /** * Get the file clump size for Extent and catalog B-Tree files. * - * @param blockSize - * @param nodeSize - * @param sectors + * @param blockSize Size of a block. + * @param nodeSize Size of a node. + * @param sectors Number of sector for the device. * @param catalog If true, calculate catalog clump size. In the other case, * calculate extent clump size. * - * @return + * @return B-Tree clump size. */ private long getBTreeClumpSize(int blockSize, int nodeSize, long sectors, boolean catalog) { int size = Math.max(blockSize, nodeSize); Deleted: trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSUnicodeString.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSUnicodeString.java 2009-04-28 07:28:05 UTC (rev 5354) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSUnicodeString.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -1,81 +0,0 @@ -/* - * $Id$ - * - * Copyright (C) 2003-2009 JNode.org - * - * This library is free software; you can redistribute it and/or modify it - * under the terms of the GNU Lesser General Public License as published - * by the Free Software Foundation; either version 2.1 of the License, or - * (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY - * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public - * License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this library; If not, write to the Free Software Foundation, Inc., - * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - */ - -package org.jnode.fs.hfsplus; - -import org.jnode.util.BigEndian; - -public class HFSUnicodeString { - /** Length of string in characters. */ - private int length; - - private String string; - - /** - * Create HFSUnicodeString from existing data. - * - * @param src byte array contains data. - * @param offset start of data in the array. - */ - public HFSUnicodeString(final byte[] src, final int offset) { - length = BigEndian.getInt16(src, offset); - byte[] data = new byte[2 + (length * 2)]; - System.arraycopy(src, offset, data, 0, 2); - length = BigEndian.getInt16(data, 0); - data = new byte[length * 2]; - System.arraycopy(src, offset + 2, data, 0, length * 2); - char[] result = new char[length]; - for (int i = 0; i < length; ++i) { - result[i] = BigEndian.getChar(data, i * 2); - } - string = new String(result); - } - - /** - * - * @param string - */ - public HFSUnicodeString(String string) { - this.string = string; - this.length = string.length(); - } - - public final int getLength() { - return length; - } - - public final String getUnicodeString() { - return string; - } - - public final byte[] getBytes() { - char[] result = new char[length]; - string.getChars(0, length, result, 0); - byte[] name = new byte[length * 2]; - for (int i = 0; i < length; ++i) { - BigEndian.setChar(name, i * 2, result[i]); - } - byte[] data = new byte[(length * 2) + 2]; - BigEndian.setInt16(data, 0, length); - System.arraycopy(name, 0, data, 2, name.length); - return data; - } - -} Deleted: trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSUtils.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSUtils.java 2009-04-28 07:28:05 UTC (rev 5354) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSUtils.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -1,72 +0,0 @@ -/* - * $Id$ - * - * Copyright (C) 2003-2009 JNode.org - * - * This library is free software; you can redistribute it and/or modify it - * under the terms of the GNU Lesser General Public License as published - * by the Free Software Foundation; either version 2.1 of the License, or - * (at your option) any later version. - * - * This library is distributed in the hope that it will be useful, but - * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY - * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public - * License for more details. - * - * You should have received a copy of the GNU Lesser General Public License - * along with this library; If not, write to the Free Software Foundation, Inc., - * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. - */ - -package org.jnode.fs.hfsplus; - -import java.text.SimpleDateFormat; -import java.util.Calendar; -import java.util.Date; - -public class HFSUtils { - - /** - * Difference in second between 01/01/1970 00:00:00 (java reference time) - * and 01/01/1904 00:00:00 (HFS reference time). - */ - public static final long MAC_DATE_CONVERSION = 2082844800L; - - /** - * Convert time from/to java time to/from mac time. - * - * @param time in seconds since reference date. - * @param encode if {code true}, convert from java to mac, otherwise - * convert from mac to java. - * - * @return the converted time - */ - public static long getDate(long time, boolean encode) { - time = (encode) ? time + MAC_DATE_CONVERSION : time - MAC_DATE_CONVERSION; - return time; - } - - /** - * - * @param time a date/time in seconds since the UNIX epoch. - * @param dateFormat the date/time format string - * @return the date/time formatted as a String - */ - public static String printDate(final long time, final String dateFormat) { - Calendar cal = Calendar.getInstance(); - cal.setTimeInMillis(getDate(time, false) * 1000); - SimpleDateFormat sdf = new SimpleDateFormat(dateFormat); - return sdf.format(cal.getTime()); - } - - /** - * Returns current date and time in mac format. - * - * @return current date and time. - */ - public static int getNow() { - Calendar now = Calendar.getInstance(); - now.setTime(new Date()); - return (int) HFSUtils.getDate(now.getTimeInMillis() / 1000, true); - } -} Copied: trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusBSDInfo.java (from rev 5353, trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusBSDInfo.java) =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusBSDInfo.java (rev 0) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusBSDInfo.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -0,0 +1,5 @@ +package org.jnode.fs.hfsplus; + +public class HfsPlusBSDInfo { + +} Copied: trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusDirectory.java (from rev 5353, trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusDirectory.java) =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusDirectory.java (rev 0) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusDirectory.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -0,0 +1,255 @@ +/* + * $Id$ + * + * Copyright (C) 2003-2009 JNode.org + * + * This library is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published + * by the Free Software Foundation; either version 2.1 of the License, or + * (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this library; If not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +package org.jnode.fs.hfsplus; + +import java.io.FileNotFoundException; +import java.io.IOException; +import java.util.Iterator; +import java.util.LinkedList; +import java.util.List; + +import org.apache.log4j.Logger; +import org.jnode.fs.FSDirectory; +import org.jnode.fs.FSEntry; +import org.jnode.fs.ReadOnlyFileSystemException; +import org.jnode.fs.hfsplus.catalog.Catalog; +import org.jnode.fs.hfsplus.catalog.CatalogFile; +import org.jnode.fs.hfsplus.catalog.CatalogFolder; +import org.jnode.fs.hfsplus.catalog.CatalogKey; +import org.jnode.fs.hfsplus.catalog.CatalogNodeId; +import org.jnode.fs.hfsplus.tree.LeafRecord; +import org.jnode.fs.spi.FSEntryTable; + +public class HfsPlusDirectory extends HfsPlusEntry implements FSDirectory { + + private static final Logger log = Logger.getLogger(HfsPlusDirectory.class); + + /** Table of entries of our parent */ + private FSEntryTable entries; + + private CatalogFolder folder; + + public HfsPlusDirectory(HfsPlusFileSystem fs, HfsPlusDirectory parent, String name, + LeafRecord record) { + super(fs, parent, name, record); + this.folder = new CatalogFolder(record.getData()); + this.entries = FSEntryTable.EMPTY_TABLE; + } + + @Override + public FSEntry addDirectory(String name) throws IOException { + log.debug("<<< BEGIN addDirectory " + name + " >>>"); + if (fs.isReadOnly()) { + throw new ReadOnlyFileSystemException(); + } + + if (getEntry(name) != null) { + throw new IOException("File or Directory already exists" + name); + } + FSEntry newEntry = createDirectoryEntry(name); + setFreeEntry(newEntry); + log.debug("<<< END addDirectory " + name + " >>>"); + return newEntry; + } + + @Override + public FSEntry addFile(String name) throws IOException { + log.debug("<<< BEGIN addFile " + name + " >>>"); + if (fs.isReadOnly()) { + throw new ReadOnlyFileSystemException(); + } + if (getEntry(name) != null) { + throw new IOException("File or directory already exists: " + name); + } + FSEntry newEntry = createFileEntry(name); + setFreeEntry(newEntry); + + log.debug("<<< END addFile " + name + " >>>"); + return newEntry; + } + + private final FSEntry createFileEntry(final String name) throws IOException { + /*if (fs.isReadOnly()) { + throw new ReadOnlyFileSystemException(); + } + Catalog catalog = fs.getCatalog(); + Superblock volumeHeader = ((HfsPlusFileSystem) getFileSystem()).getVolumeHeader(); + LeafRecord fileRecord = catalog.createNode(name, this.folder + .getFolderId(), new CatalogNodeId(volumeHeader.getNextCatalogId()), CatalogFile.RECORD_TYPE_FILE); + + HFSPlusEntry newEntry = new HFSPlusFile(fs, this, name, folderRecord); + newEntry.setDirty(); + volumeHeader.setFileCount(volumeHeader.getFileCount() + 1); + log.debug("New volume header :\n" + volumeHeader.toString());*/ + + return null; + } + + @Override + public void flush() throws IOException { + log.debug("<<< BEGIN flush >>>"); + if (fs.isReadOnly()) { + throw new ReadOnlyFileSystemException(); + } + boolean flushEntries = isEntriesLoaded() && entries.isDirty(); + if (isDirty() || flushEntries) { + writeEntries(entries); + // entries.resetDirty(); + resetDirty(); + } + log.debug("<<< END flush >>>"); + } + + @Override + public FSEntry getEntry(String name) throws IOException { + checkEntriesLoaded(); + return entries.get(name); + } + + @Override + public Iterator<? extends FSEntry> iterator() throws IOException { + return entries.iterator(); + } + + public int rename(String oldName, String newName) { + return entries.rename(oldName, newName); + } + + @Override + public void remove(String name) throws IOException { + if (fs.isReadOnly()) { + throw new ReadOnlyFileSystemException(); + } + if (entries.remove(name) >= 0) { + setDirty(); + flush(); + return; + } else { + throw new FileNotFoundException(name); + } + } + + // Helper methods + + /** + * BE CAREFULL : don't call this method from the constructor of this class + * because it call the method readEntries of the child classes that are not + * yet initialized (constructed). + */ + protected final void checkEntriesLoaded() { + if (!isEntriesLoaded()) { + log.debug("checkEntriesLoaded : loading"); + try { + if (rights.canRead()) { + entries = readEntries(); + } else { + // the next time, we will call checkEntriesLoaded() + // we will retry to load entries + entries = FSEntryTable.EMPTY_TABLE; + log.debug("checkEntriesLoaded : can't read, using EMPTY_TABLE"); + } + resetDirty(); + } catch (IOException e) { + log.fatal("unable to read directory entries", e); + // the next time, we will call checkEntriesLoaded() + // we will retry to load entries + entries = FSEntryTable.EMPTY_TABLE; + } + } + log.debug("<<< END checkEntriesLoaded >>>"); + } + + /** + * Have we already loaded our entries from device ? + * + * @return if the entries are already loaded from the device + */ + private final boolean isEntriesLoaded() { + return (entries != FSEntryTable.EMPTY_TABLE); + } + + /** + * + * @return + * @throws IOException + */ + private final FSEntryTable readEntries() throws IOException { + List<FSEntry> pathList = new LinkedList<FSEntry>(); + HfsPlusFileSystem fs = (HfsPlusFileSystem) getFileSystem(); + if (fs.getVolumeHeader().getFolderCount() > 0) { + LeafRecord[] records = fs.getCatalog().getRecords(folder.getFolderId()); + for (LeafRecord rec : records) { + if (rec.getType() == CatalogFolder.RECORD_TYPE_FOLDER || + rec.getType() == CatalogFile.RECORD_TYPE_FILE) { + String name = ((CatalogKey) rec.getKey()).getNodeName().getUnicodeString(); + HfsPlusEntry e = new HfsPlusDirectory(fs, this, name, rec); + pathList.add(e); + } + } + } + return new FSEntryTable(((HfsPlusFileSystem) getFileSystem()), pathList); + } + + private void writeEntries(final FSEntryTable entries) throws IOException { + // TODO Auto-generated method stub + } + + /** + * + * @param name + * @return + * @throws IOException + */ + private final FSEntry createDirectoryEntry(final String name) throws IOException { + if (fs.isReadOnly()) { + throw new ReadOnlyFileSystemException(); + } + Catalog catalog = fs.getCatalog(); + Superblock volumeHeader = ((HfsPlusFileSystem) getFileSystem()).getVolumeHeader(); + LeafRecord folderRecord = catalog.createNode(name, this.folder.getFolderId(), + new CatalogNodeId(volumeHeader.getNextCatalogId()), CatalogFolder.RECORD_TYPE_FOLDER_THREAD); + folder.setValence(folder.getValence() + 1); + + HfsPlusEntry newEntry = new HfsPlusDirectory(fs, this, name, folderRecord); + newEntry.setDirty(); + volumeHeader.setFolderCount(volumeHeader.getFolderCount() + 1); + log.debug("New volume header :\n" + volumeHeader.toString()); + + return newEntry; + } + + /** + * Find a free entry and set it with the given entry + * + * @param newEntry + * @throws IOException + */ + private final void setFreeEntry(FSEntry newEntry) throws IOException { + checkEntriesLoaded(); + if (entries.setFreeEntry(newEntry) >= 0) { + log.debug("setFreeEntry: free entry found !"); + setDirty(); + flush(); + return; + } + } + +} Copied: trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusEntry.java (from rev 5353, trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusEntry.java) =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusEntry.java (rev 0) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusEntry.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -0,0 +1,167 @@ +/* + * $Id$ + * + * Copyright (C) 2003-2009 JNode.org + * + * This library is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published + * by the Free Software Foundation; either version 2.1 of the License, or + * (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this library; If not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +package org.jnode.fs.hfsplus; + +import java.io.IOException; + +import org.jnode.fs.FSAccessRights; +import org.jnode.fs.FSDirectory; +import org.jnode.fs.FSEntry; +import org.jnode.fs.FSFile; +import org.jnode.fs.FileSystem; +import org.jnode.fs.hfsplus.catalog.CatalogFile; +import org.jnode.fs.hfsplus.catalog.CatalogFolder; +import org.jnode.fs.hfsplus.tree.LeafRecord; +import org.jnode.fs.spi.AbstractFSEntry; +import org.jnode.fs.spi.UnixFSAccessRights; + +public class HfsPlusEntry implements FSEntry { + + protected HfsPlusFileSystem fs; + protected HfsPlusDirectory parent; + protected String name; + protected LeafRecord record; + private int type; + + protected boolean valid; + protected boolean dirty; + protected FSAccessRights rights; + private long lastModified; + + /** + * + * @param fs + * @param parent + * @param name + * @param record + */ + public HfsPlusEntry(HfsPlusFileSystem fs, HfsPlusDirectory parent, String name, + LeafRecord record) { + this.fs = fs; + this.parent = parent; + this.name = name; + this.record = record; + this.type = getFSEntryType(); + this.rights = new UnixFSAccessRights(fs); + this.lastModified = System.currentTimeMillis(); + } + + private int getFSEntryType() { + int mode = record.getType(); + if ("/".equals(name)) { + return AbstractFSEntry.ROOT_ENTRY; + } else if (mode == CatalogFolder.RECORD_TYPE_FOLDER) { + return AbstractFSEntry.DIR_ENTRY; + } else if (mode == CatalogFile.RECORD_TYPE_FILE) { + return AbstractFSEntry.FILE_ENTRY; + } else { + return AbstractFSEntry.OTHER_ENTRY; + } + } + + @Override + public FSAccessRights getAccessRights() throws IOException { + return rights; + } + + @Override + public FSDirectory getDirectory() throws IOException { + if (!isDirectory()) { + throw new IOException("It is not a Directory"); + } + return (HfsPlusDirectory) this; + } + + @Override + public FSFile getFile() throws IOException { + if (!isFile()) { + throw new IOException("It is not a file"); + } + return (HfsPlusFile) this; + } + + @Override + public long getLastModified() throws IOException { + // TODO Auto-generated method stub + return lastModified; + } + + @Override + public String getName() { + return name; + } + + @Override + public FSDirectory getParent() { + return parent; + } + + @Override + public boolean isDirectory() { + return (type == AbstractFSEntry.DIR_ENTRY || type == AbstractFSEntry.ROOT_ENTRY); + } + + @Override + public boolean isDirty() throws IOException { + return dirty; + } + + public void setDirty() { + dirty = true; + } + + public void resetDirty() { + dirty = false; + } + + @Override + public boolean isFile() { + return (type == AbstractFSEntry.FILE_ENTRY); + } + + @Override + public void setLastModified(long lastModified) throws IOException { + this.lastModified = lastModified; + } + + @Override + public void setName(String newName) throws IOException { + if (type == AbstractFSEntry.ROOT_ENTRY) { + throw new IOException("Cannot change name of root directory"); + } + if (parent.rename(name, newName) < 0) { + throw new IOException("Cannot change name"); + } + + this.name = newName; + } + + @Override + public FileSystem<?> getFileSystem() { + return fs; + } + + @Override + public boolean isValid() { + return valid; + } + +} Copied: trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusFile.java (from rev 5353, trunk/fs/src/fs/org/jnode/fs/hfsplus/HFSPlusFile.java) =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusFile.java (rev 0) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusFile.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -0,0 +1,72 @@ +/* + * $Id$ + * + * Copyright (C) 2003-2009 JNode.org + * + * This library is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published + * by the Free Software Foundation; either version 2.1 of the License, or + * (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY + * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this library; If not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +package org.jnode.fs.hfsplus; + +import java.io.IOException; +import java.nio.ByteBuffer; + +import org.jnode.fs.FSFile; +import org.jnode.fs.hfsplus.catalog.CatalogFile; +import org.jnode.fs.hfsplus.extent.ExtentDescriptor; +import org.jnode.fs.hfsplus.tree.LeafRecord; + +public class HfsPlusFile extends HfsPlusEntry implements FSFile { + + private CatalogFile file; + + public HfsPlusFile(HfsPlusFileSystem fs, HfsPlusDirectory parent, String name, LeafRecord record) { + super(fs, parent, name, record); + this.file = new CatalogFile(record.getData()); + } + + @Override + public void flush() throws IOException { + + } + + @Override + public final long getLength() { + return file.getDatas().getTotalSize(); + } + + @Override + public final void read(final long fileOffset, final ByteBuffer dest) throws IOException { + HfsPlusFileSystem fs = (HfsPlusFileSystem) getFileSystem(); + for (ExtentDescriptor d : file.getDatas().getExtents()) { + if (!d.isEmpty()) { + long firstOffset = d.getStartOffset(fs.getVolumeHeader().getBlockSize()); + fs.getApi().read(firstOffset, dest); + } + } + } + + @Override + public void write(final long fileOffset, final ByteBuffer src) throws IOException { + // TODO Auto-generated method stub + + } + + public void setLength(final long length) throws IOException { + // TODO Auto-generated method stub + + } + +} Modified: trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusFileSystem.java =================================================================== --- trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusFileSystem.java 2009-04-28 07:28:05 UTC (rev 5354) +++ trunk/fs/src/fs/org/jnode/fs/hfsplus/HfsPlusFileSystem.java 2009-04-28 08:39:26 UTC (rev 5355) @@ -21,7 +21,6 @@ package org.jnode.fs.hfsplus; import java.io.IOException; -import java.nio.ByteBuffer; import org.apache.log4j.Logger; import org.jnode.driver.ApiNotFoundException; @@ -35,11 +34,11 @@ import org.jnode.fs.hfsplus.tree.LeafRecord; import org.jnode.fs.spi.AbstractFileSystem; -public class HfsPlusFileSystem extends AbstractFileSystem<HFSPlusEntry> { +public class HfsPlusFileSystem extends AbstractFileSystem<HfsPlusEntry> { private final Logger log = Logger.getLogger(getClass()); /** HFS volume header */ - private Superblock sb; + private Superblock volumeHeader; /** Catalog special file for this instance */ private Catalog catalog; @@ -61,18 +60,18 @@ * @throws FileSystemException */ public final void read() throws FileSystemException { - sb = new Superblock(this, false); - log.debug(sb.toString()); - if (!sb.isAttribute(Superblock.HFSPLUS_VOL_UNMNT_BIT)) { + volumeHeader = new Superblock(this, false); + log.debug(volumeHeader.toString()); + if (!volumeHeader.isAttribute(Superblock.HFSPLUS_VOL_UNMNT_BIT)) { log.info(getDevice().getId() + " Filesystem has not been cleanly unmounted, mounting it readonly"); setReadOnly(true); } - if (sb.isAttribute(Superblock.HFSPLUS_VOL_SOFTLOCK_BIT)) { + if (volumeHeader.isAttribute(Superblock.HFSPLUS_VOL_SOFTLOCK_BIT)) { log.info(getDevice().getId() + " Filesystem is marked locked, mounting it readonly"); setReadOnly(true); } - if (sb.isAttribute(Superblock.HFSPLUS_VOL_JOURNALED_BIT)) { + if (volumeHeader.isAttribute(Superblock.HFSPLUS_VOL_JOURNALED_BIT)) { log .info(getDevice().getId() + " Filesystem is journaled, write access is not supported. Mounting it readonly"); @@ -96,11 +95,11 @@ } @Override - protected final HFSPlusEntry createRootEntry() throws IOException { + protected final HfsPlusEntry createRootEntry() throws IOException { log.info("Create root entry."); LeafRecord record = catalog.getRecord(CatalogNodeId.HFSPLUS_POR_CNID); if (record != null) { - return new HFSPlusDirectory(this, null, "/", record); + return new HfsPlusDirectory(this, null, "/", record); } log.error("Root entry : No record found."); return null; @@ -112,7 +111,7 @@ * @see org.jnode.fs.FileSystem#getFreeSpace() */ public final long getFreeSpace() { - return sb.getFreeBlocks() * sb.getBlockSize(); + return volumeHeader.getFreeBlocks() * volumeHeader.getBlockSize(); } /* @@ -121,7 +120,7 @@ * @see org.jnode.fs.FileSystem#getTotalSpace() */ public final long getTotalSpace() { - return sb.getTotalBlocks() * sb.getBlockSize(); + return volumeHeader.getTotalBlocks() * volumeHeader.getBlockSize(); } /* @@ -138,41 +137,36 @@ } public final Superblock getVolumeHeader() { - return sb; + return volumeHeader; } /** + * Create a new HFS+ file system. * - * @param params + * @param params creation parameters * * @throws FileSystemException */ public void create(HFSPlusParams params) throws FileSystemException { - sb = new Superblock(this, true); + volumeHeader = new Superblock(this, true); try { - params.initializeDefaultsValues(this.getApi().getLength(), this.getFSApi() - .getSectorSize()); - sb.create(params); - log.debug(sb.toString()); - // --... [truncated message content] |