mirror of
https://github.com/9fans/plan9port.git
synced 2025-01-12 11:10:07 +00:00
hfs (David Swasey)
This commit is contained in:
parent
eba172d68e
commit
d63163af35
6 changed files with 2000 additions and 1 deletions
|
@ -77,6 +77,7 @@ Block* diskread(Disk *disk, u32int, u64int offset);
|
|||
int disksync(Disk *disk);
|
||||
|
||||
Fsys* fsysopenffs(Disk*);
|
||||
Fsys* fsysopenhfs(Disk*);
|
||||
Fsys* fsysopenkfs(Disk*);
|
||||
Fsys* fsysopenext2(Disk*);
|
||||
Fsys* fsysopenfat(Disk*);
|
||||
|
|
|
@ -6,6 +6,8 @@ This software was developed as part of a project at MIT:
|
|||
Copyright (c) 2005 Russ Cox,
|
||||
Massachusetts Institute of Technology
|
||||
|
||||
HFS Support Copyright (c) 2007 David Swasey
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining
|
||||
a copy of this software and associated documentation files (the
|
||||
"Software"), to deal in the Software without restriction, including
|
||||
|
|
|
@ -10,6 +10,7 @@ int allowall;
|
|||
static Fsys *(*opentab[])(Disk*) =
|
||||
{
|
||||
fsysopenffs,
|
||||
fsysopenhfs,
|
||||
fsysopenkfs,
|
||||
fsysopenext2,
|
||||
fsysopenfat,
|
||||
|
|
1785
src/libdiskfs/hfs.c
Normal file
1785
src/libdiskfs/hfs.c
Normal file
File diff suppressed because it is too large
Load diff
210
src/libdiskfs/hfs.h
Normal file
210
src/libdiskfs/hfs.h
Normal file
|
@ -0,0 +1,210 @@
|
|||
/*
|
||||
Supports HFS Plus and HFSX file systems with or without an HFS
|
||||
wrapper.
|
||||
|
||||
Apple technical note 1150 documents the file system:
|
||||
|
||||
http://developer.apple.com/technotes/tn/tn1150.html
|
||||
|
||||
Briefly an hfs file system comprises a volume header, an
|
||||
optional journal, and a set of forks.
|
||||
|
||||
Most fs metadata resides in forks including a block allocation
|
||||
bitmap, a tree storing extents (q.v.) for forks and bad disk
|
||||
blocks, and a tree storing catalog (file and directory)
|
||||
information.
|
||||
|
||||
An extent comprises a starting block number and block count.
|
||||
The fs maintains a list of k*NEXTENTS extents for each fork.
|
||||
These are used to map fork block numbers to disk block
|
||||
numbers. A fork's initial extents are in its catalog record
|
||||
or (for fs forks) the volume header. The rest are in the
|
||||
extents tree.
|
||||
|
||||
Fs trees are layed out (in a fork) as an array of fixed-size
|
||||
nodes. A node comprises a header, a sorted list of
|
||||
variable-size records, and trailing record offsets. The
|
||||
records in interior nodes map keys to (child) node numbers.
|
||||
The records in leaf nodes map keys to data. The nodes at each
|
||||
level in a tree are also sorted via (sibling) node numbers
|
||||
stored in each node header.
|
||||
*/
|
||||
|
||||
typedef struct Extent Extent;
|
||||
typedef struct Fork Fork;
|
||||
typedef struct Inode Inode;
|
||||
typedef struct Tree Tree;
|
||||
typedef struct Node Node;
|
||||
typedef struct Treeref Treeref;
|
||||
typedef struct Key Key;
|
||||
typedef struct Extentkey Extentkey;
|
||||
typedef struct Name Name;
|
||||
typedef struct Catalogkey Catalogkey;
|
||||
typedef struct Hfs Hfs;
|
||||
|
||||
enum
|
||||
{
|
||||
Hfssig = 0x4244,
|
||||
Hfsplussig = 0x482B,
|
||||
Hfsxsig = 0x4858,
|
||||
Hfsplusmagic = (Hfsplussig<<16)|4,
|
||||
Hfsxmagic = (Hfsxsig<<16)|5,
|
||||
|
||||
NAMELEN = 255,
|
||||
UTFNAMELEN = NAMELEN*UTFmax,
|
||||
|
||||
NEXTENTS = 8,
|
||||
|
||||
Dfork = 0, Rfork = 255,
|
||||
|
||||
/* fixed cnids */
|
||||
RootpId = 1, RootId, ExtentsId, CatalogId,
|
||||
BadblockId, AllocId, MinuserId = 16,
|
||||
|
||||
/* size of a few structures on disk */
|
||||
Extentlen = 8, /* Extent */
|
||||
Ndlen = 14, /* Node */
|
||||
Folderlen = 88, Filelen = 248, /* Inode */
|
||||
|
||||
/* values in Node.type */
|
||||
LeafNode = -1, IndexNode, HeaderNode, MapNode,
|
||||
|
||||
/* catalog record types */
|
||||
Folder = 1, File, FolderThread, FileThread,
|
||||
|
||||
/* permissions in Inode.mode */
|
||||
IEXEC = 00100,
|
||||
IWRITE = 0200,
|
||||
IREAD = 0400,
|
||||
ISTXT = 01000,
|
||||
ISGID = 02000,
|
||||
ISUID = 04000,
|
||||
|
||||
/* type in Inode.mode */
|
||||
IFMT = 0170000,
|
||||
IFIFO = 0010000,
|
||||
IFCHR = 0020000,
|
||||
IFDIR = 0040000,
|
||||
IFBLK = 0060000,
|
||||
IFREG = 0100000,
|
||||
IFLNK = 0120000,
|
||||
IFSOCK = 0140000,
|
||||
IFWHT = 0160000,
|
||||
};
|
||||
|
||||
struct Extent
|
||||
{
|
||||
u32int start; /* first block in extent */
|
||||
u32int count; /* number of blocks in extent */
|
||||
};
|
||||
|
||||
struct Fork
|
||||
{
|
||||
u32int cnid; /* catalog node id (in memory only) */
|
||||
int type; /* Dfork or Rfork (in memory only) */
|
||||
u64int size; /* size in bytes */
|
||||
u32int nblocks;
|
||||
Extent extent[NEXTENTS]; /* initial extents */
|
||||
};
|
||||
|
||||
/*
|
||||
* In-core catalog record for a file or folder.
|
||||
*/
|
||||
struct Inode
|
||||
{
|
||||
u32int cnid;
|
||||
u32int mtime; /* modification */
|
||||
u32int ctime; /* attribute modification */
|
||||
u32int atime; /* access */
|
||||
u32int uid;
|
||||
u32int gid;
|
||||
int mode;
|
||||
u32int special;
|
||||
union{
|
||||
u32int nentries; /* directories */
|
||||
struct{ /* files */
|
||||
Fork dfork;
|
||||
/*Fork rfork;*/
|
||||
};
|
||||
};
|
||||
};
|
||||
|
||||
struct Tree
|
||||
{
|
||||
int nodesize; /* node size in bytes */
|
||||
u32int nnodes; /* number of nodes in tree */
|
||||
u32int root; /* node number of the tree's root */
|
||||
int height;
|
||||
int maxkeylen; /* maximum key size in bytes */
|
||||
int indexkeylen; /* 0 or length of index node keys */
|
||||
int sensitive; /* are key strings case sensitive */
|
||||
Hfs *fs;
|
||||
Fork *fork;
|
||||
};
|
||||
|
||||
struct Node
|
||||
{
|
||||
int type; /* type of this node */
|
||||
u32int next; /* next related node or 0 */
|
||||
int nrec; /* number of records in this node */
|
||||
};
|
||||
|
||||
struct Treeref
|
||||
{
|
||||
Tree *tree;
|
||||
u32int cnid; /* tree->fork->cnid, for debugging prints */
|
||||
|
||||
Block *block; /* a node in the tree */
|
||||
u32int nno;
|
||||
Node node;
|
||||
|
||||
int rno; /* a record in the node */
|
||||
int klen;
|
||||
uchar *key;
|
||||
int dlen;
|
||||
uchar *data;
|
||||
};
|
||||
|
||||
struct Key
|
||||
{
|
||||
int (*_cmp)(uchar *k, int len, int *order, Key *key);
|
||||
void *priv;
|
||||
};
|
||||
|
||||
struct Extentkey
|
||||
{
|
||||
u32int cnid;
|
||||
int type;
|
||||
u32int bno;
|
||||
};
|
||||
|
||||
struct Name
|
||||
{
|
||||
int len;
|
||||
Rune name[NAMELEN]; /* only len runes on disk */
|
||||
};
|
||||
|
||||
struct Catalogkey
|
||||
{
|
||||
u32int parent;
|
||||
union{
|
||||
Name name;
|
||||
uchar *b; /* not yet decoded */
|
||||
};
|
||||
};
|
||||
|
||||
struct Hfs
|
||||
{
|
||||
u32int blocksize;
|
||||
u32int nblock;
|
||||
u32int nfree; /* for debugging */
|
||||
int hasbadblocks;
|
||||
Fork alloc; /* block allocation bitmap */
|
||||
Fork extentsfork;
|
||||
Fork catalogfork;
|
||||
Tree extents; /* Extentkey -> Extent[NEXTENT] */
|
||||
Tree catalog; /* Catalogkey -> Catalogkey + Inode */
|
||||
int wrapper; /* HFS wrapper used? */
|
||||
Disk *disk;
|
||||
Fsys *fsys;
|
||||
};
|
|
@ -67,5 +67,5 @@ diskpartabandon(Disk *d)
|
|||
{
|
||||
if(d->_read != diskpartread)
|
||||
abort();
|
||||
d->subdisk = nil;
|
||||
((DiskPart*)d)->subdisk = nil;
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue