diff options
| author | Andrew Morton <akpm@osdl.org> | 2004-03-11 16:12:15 -0800 |
|---|---|---|
| committer | Linus Torvalds <torvalds@ppc970.osdl.org> | 2004-03-11 16:12:15 -0800 |
| commit | e3459dfb5bf954c69a3ff663218633e5b93c3a60 (patch) | |
| tree | 546224f3ff9379386e23b27016281cecffbe5d08 /include/linux | |
| parent | 202775d67e0e440323c92c099a3f996c4ab12f6c (diff) | |
[PATCH] read-only support for UFS2
From: Niraj Kumar <niraj17@iitbombay.org>
This patch adds read-only support for ufs2 (used in FreeBSD 5.x) variant of
ufs filesystem. For filesystem specific tools, see
http://ufs-linux.sourceforge.com .
Diffstat (limited to 'include/linux')
| -rw-r--r-- | include/linux/ufs_fs.h | 170 | ||||
| -rw-r--r-- | include/linux/ufs_fs_i.h | 1 |
2 files changed, 155 insertions, 16 deletions
diff --git a/include/linux/ufs_fs.h b/include/linux/ufs_fs.h index cc3ddd5f680f..507187f51c58 100644 --- a/include/linux/ufs_fs.h +++ b/include/linux/ufs_fs.h @@ -22,6 +22,9 @@ * HP/UX hfs filesystem support added by * Martin K. Petersen <mkp@mkp.net>, August 1999 * + * UFS2 (of FreeBSD 5.x) support added by + * Niraj Kumar <niraj17@iitbombay.org> , Jan 2004 + * */ #ifndef __LINUX_UFS_FS_H @@ -43,8 +46,50 @@ #define UFS_SECTOR_SIZE 512 #define UFS_SECTOR_BITS 9 -#define UFS_MAGIC 0x00011954 -#define UFS_CIGAM 0x54190100 /* byteswapped MAGIC */ +#define UFS_MAGIC 0x00011954 +#define UFS2_MAGIC 0x19540119 +#define UFS_CIGAM 0x54190100 /* byteswapped MAGIC */ + +/* Copied from FreeBSD */ +/* + * Each disk drive contains some number of filesystems. + * A filesystem consists of a number of cylinder groups. + * Each cylinder group has inodes and data. + * + * A filesystem is described by its super-block, which in turn + * describes the cylinder groups. The super-block is critical + * data and is replicated in each cylinder group to protect against + * catastrophic loss. This is done at `newfs' time and the critical + * super-block data does not change, so the copies need not be + * referenced further unless disaster strikes. + * + * For filesystem fs, the offsets of the various blocks of interest + * are given in the super block as: + * [fs->fs_sblkno] Super-block + * [fs->fs_cblkno] Cylinder group block + * [fs->fs_iblkno] Inode blocks + * [fs->fs_dblkno] Data blocks + * The beginning of cylinder group cg in fs, is given by + * the ``cgbase(fs, cg)'' macro. + * + * Depending on the architecture and the media, the superblock may + * reside in any one of four places. For tiny media where every block + * counts, it is placed at the very front of the partition. Historically, + * UFS1 placed it 8K from the front to leave room for the disk label and + * a small bootstrap. For UFS2 it got moved to 64K from the front to leave + * room for the disk label and a bigger bootstrap, and for really piggy + * systems we check at 256K from the front if the first three fail. In + * all cases the size of the superblock will be SBLOCKSIZE. All values are + * given in byte-offset form, so they do not imply a sector size. The + * SBLOCKSEARCH specifies the order in which the locations should be searched. + */ +#define SBLOCK_FLOPPY 0 +#define SBLOCK_UFS1 8192 +#define SBLOCK_UFS2 65536 +#define SBLOCK_PIGGY 262144 +#define SBLOCKSIZE 8192 +#define SBLOCKSEARCH \ + { SBLOCK_UFS2, SBLOCK_UFS1, SBLOCK_FLOPPY, SBLOCK_PIGGY, -1 } /* HP specific MAGIC values */ @@ -120,6 +165,11 @@ #define UFS_CG_OLD 0x00000000 #define UFS_CG_44BSD 0x00002000 #define UFS_CG_SUN 0x00001000 +/* filesystem type encoding */ +#define UFS_TYPE_MASK 0x00010000 /* mask for the following */ +#define UFS_TYPE_UFS1 0x00000000 +#define UFS_TYPE_UFS2 0x00010000 + /* fs_inodefmt options */ #define UFS_42INODEFMT -1 @@ -132,7 +182,7 @@ #define UFS_MOUNT_ONERROR_UMOUNT 0x00000004 #define UFS_MOUNT_ONERROR_REPAIR 0x00000008 -#define UFS_MOUNT_UFSTYPE 0x00000FF0 +#define UFS_MOUNT_UFSTYPE 0x0000FFF0 #define UFS_MOUNT_UFSTYPE_OLD 0x00000010 #define UFS_MOUNT_UFSTYPE_44BSD 0x00000020 #define UFS_MOUNT_UFSTYPE_SUN 0x00000040 @@ -141,6 +191,7 @@ #define UFS_MOUNT_UFSTYPE_OPENSTEP 0x00000200 #define UFS_MOUNT_UFSTYPE_SUNx86 0x00000400 #define UFS_MOUNT_UFSTYPE_HP 0x00000800 +#define UFS_MOUNT_UFSTYPE_UFS2 0x00001000 #define ufs_clear_opt(o,opt) o &= ~UFS_MOUNT_##opt #define ufs_set_opt(o,opt) o |= UFS_MOUNT_##opt @@ -173,7 +224,8 @@ * They calc file system addresses of cylinder group data structures. */ #define ufs_cgbase(c) (uspi->s_fpg * (c)) -#define ufs_cgstart(c) (ufs_cgbase(c) + uspi->s_cgoffset * ((c) & ~uspi->s_cgmask)) +#define ufs_cgstart(c) ((uspi)->fs_magic == UFS2_MAGIC ? ufs_cgbase(c) : \ + (ufs_cgbase(c) + uspi->s_cgoffset * ((c) & ~uspi->s_cgmask))) #define ufs_cgsblock(c) (ufs_cgstart(c) + uspi->s_sblkno) /* super blk */ #define ufs_cgcmin(c) (ufs_cgstart(c) + uspi->s_cblkno) /* cg block */ #define ufs_cgimin(c) (ufs_cgstart(c) + uspi->s_iblkno) /* inode blk */ @@ -227,8 +279,14 @@ #define UFS_MAXNAMLEN 255 #define UFS_MAXMNTLEN 512 +#define UFS2_MAXMNTLEN 468 +#define UFS2_MAXVOLLEN 32 /* #define UFS_MAXCSBUFS 31 */ #define UFS_LINK_MAX 32000 +/* +#define UFS2_NOCSPTRS ((128 / sizeof(void *)) - 4) +*/ +#define UFS2_NOCSPTRS 28 /* * UFS_DIR_PAD defines the directory entries boundaries @@ -262,6 +320,14 @@ struct ufs_csum { __u32 cs_nifree; /* number of free inodes */ __u32 cs_nffree; /* number of free frags */ }; +struct ufs2_csum_total { + __u64 cs_ndir; /* number of directories */ + __u64 cs_nbfree; /* number of free blocks */ + __u64 cs_nifree; /* number of free inodes */ + __u64 cs_nffree; /* number of free frags */ + __u64 cs_numclusters; /* number of free clusters */ + __u64 cs_spare[3]; /* future expansion */ +}; /* * This is the actual superblock, as it is laid out on the disk. @@ -333,7 +399,7 @@ struct ufs_super_block { __u32 fs_ncyl; /* cylinders in file system */ /* these fields can be computed from the others */ __u32 fs_cpg; /* cylinders per group */ - __u32 fs_ipg; /* inodes per group */ + __u32 fs_ipg; /* inodes per cylinder group */ __u32 fs_fpg; /* blocks per group * fs_frag */ /* this data must be re-computed after crashes */ struct ufs_csum fs_cstotal; /* cylinder summary information */ @@ -342,13 +408,39 @@ struct ufs_super_block { __s8 fs_clean; /* file system is clean flag */ __s8 fs_ronly; /* mounted read-only flag */ __s8 fs_flags; /* currently unused flag */ - __s8 fs_fsmnt[UFS_MAXMNTLEN]; /* name mounted on */ -/* these fields retain the current block allocation info */ - __u32 fs_cgrotor; /* last cg searched */ - __u32 fs_csp[UFS_MAXCSBUFS]; /* list of fs_cs info buffers */ - __u32 fs_maxcluster; - __u32 fs_cpc; /* cyl per cycle in postbl */ - __u16 fs_opostbl[16][8]; /* old rotation block list head */ + union { + struct { + __s8 fs_fsmnt[UFS_MAXMNTLEN];/* name mounted on */ + __u32 fs_cgrotor; /* last cg searched */ + __u32 fs_csp[UFS_MAXCSBUFS];/*list of fs_cs info buffers */ + __u32 fs_maxcluster; + __u32 fs_cpc; /* cyl per cycle in postbl */ + __u16 fs_opostbl[16][8]; /* old rotation block list head */ + } fs_u1; + struct { + __s8 fs_fsmnt[UFS2_MAXMNTLEN]; /* name mounted on */ + __u8 fs_volname[UFS2_MAXVOLLEN]; /* volume name */ + __u64 fs_swuid; /* system-wide uid */ + __s32 fs_pad; /* due to alignment of fs_swuid */ + __u32 fs_cgrotor; /* last cg searched */ + __u32 fs_ocsp[UFS2_NOCSPTRS]; /*list of fs_cs info buffers */ + __u32 fs_contigdirs;/*# of contiguously allocated dirs */ + __u32 fs_csp; /* cg summary info buffer for fs_cs */ + __u32 fs_maxcluster; + __u32 fs_active;/* used by snapshots to track fs */ + __s32 fs_old_cpc; /* cyl per cycle in postbl */ + __s32 fs_maxbsize;/*maximum blocking factor permitted */ + __s64 fs_sparecon64[17];/*old rotation block list head */ + __s64 fs_sblockloc; /* byte offset of standard superblock */ + struct ufs2_csum_total fs_cstotal;/*cylinder summary information*/ + struct ufs_timeval fs_time; /* last time written */ + __s64 fs_size; /* number of blocks in fs */ + __s64 fs_dsize; /* number of data blocks in fs */ + __u64 fs_csaddr; /* blk addr of cyl grp summary area */ + __s64 fs_pendingblocks;/* blocks in process of being freed */ + __s32 fs_pendinginodes;/*inodes in process of being freed */ + } fs_u2; + } fs_u11; union { struct { __s32 fs_sparecon[53];/* reserved for future constants */ @@ -441,6 +533,16 @@ struct ufs_cylinder_group { __u32 cg_nclusterblks; /* number of clusters this cg */ __u32 cg_sparecon[13]; /* reserved for future use */ } cg_44; + struct { + __u32 cg_clustersumoff;/* (u_int32) counts of avail clusters */ + __u32 cg_clusteroff; /* (u_int8) free cluster map */ + __u32 cg_nclusterblks;/* number of clusters this cg */ + __u32 cg_niblk; /* number of inode blocks this cg */ + __u32 cg_initediblk; /* last initialized inode */ + __u32 cg_sparecon32[3];/* reserved for future use */ + __u64 cg_time; /* time last written */ + __u64 cg_sparecon[3]; /* reserved for future use */ + } cg_u2; __u32 cg_sparecon[16]; /* reserved for future use */ } cg_u; __u8 cg_space[1]; /* space for cylinder group maps */ @@ -497,6 +599,39 @@ struct ufs_inode { } ui_u3; }; +#define UFS_NXADDR 2 /* External addresses in inode. */ +struct ufs2_inode { + __u16 ui_mode; /* 0: IFMT, permissions; see below. */ + __s16 ui_nlink; /* 2: File link count. */ + __u32 ui_uid; /* 4: File owner. */ + __u32 ui_gid; /* 8: File group. */ + __u32 ui_blksize; /* 12: Inode blocksize. */ + __u64 ui_size; /* 16: File byte count. */ + __u64 ui_blocks; /* 24: Bytes actually held. */ + struct ufs_timeval ui_atime; /* 32: Last access time. */ + struct ufs_timeval ui_mtime; /* 40: Last modified time. */ + struct ufs_timeval ui_ctime; /* 48: Last inode change time. */ + struct ufs_timeval ui_birthtime; /* 56: Inode creation time. */ + __s32 ui_mtimensec; /* 64: Last modified time. */ + __s32 ui_atimensec; /* 68: Last access time. */ + __s32 ui_ctimensec; /* 72: Last inode change time. */ + __s32 ui_birthnsec; /* 76: Inode creation time. */ + __s32 ui_gen; /* 80: Generation number. */ + __u32 ui_kernflags; /* 84: Kernel flags. */ + __u32 ui_flags; /* 88: Status flags (chflags). */ + __s32 ui_extsize; /* 92: External attributes block. */ + __s64 ui_extb[UFS_NXADDR];/* 96: External attributes block. */ + union { + struct { + __s64 ui_db[UFS_NDADDR]; /* 112: Direct disk blocks. */ + __s64 ui_ib[UFS_NINDIR];/* 208: Indirect disk blocks.*/ + } ui_addr; + __u8 ui_symlink[2*4*(UFS_NDADDR+UFS_NINDIR)];/* 0x28 fast symlink */ + } ui_u2; + __s64 ui_spare[3]; /* 232: Reserved; currently unused */ +}; + + /* FreeBSD has these in sys/stat.h */ /* ui_flags that can be set by a file owner */ #define UFS_UF_SETTABLE 0x0000ffff @@ -517,8 +652,8 @@ struct ufs_inode { * than the size of fragment. */ struct ufs_buffer_head { - unsigned fragment; /* first fragment */ - unsigned count; /* number of fragments */ + __u64 fragment; /* first fragment */ + __u64 count; /* number of fragments */ struct buffer_head * bh[UFS_MAXFRAG]; /* buffers */ }; @@ -551,6 +686,8 @@ struct ufs_sb_private_info { __u32 s_cgmask; /* used to calc mod fs_ntrak */ __u32 s_size; /* number of blocks (fragments) in fs */ __u32 s_dsize; /* number of data blocks in fs */ + __u64 s_u2_size; /* ufs2: number of blocks (fragments) in fs */ + __u64 s_u2_dsize; /*ufs2: number of data blocks in fs */ __u32 s_ncg; /* number of cylinder groups */ __u32 s_bsize; /* size of basic blocks */ __u32 s_fsize; /* size of fragments */ @@ -577,7 +714,7 @@ struct ufs_sb_private_info { __u32 s_ntrak; /* tracks per cylinder */ __u32 s_nsect; /* sectors per track */ __u32 s_spc; /* sectors per cylinder */ - __u32 s_ipg; /* inodes per group */ + __u32 s_ipg; /* inodes per cylinder group */ __u32 s_fpg; /* fragments per group */ __u32 s_cpc; /* cyl per cycle in postbl */ __s32 s_contigsumsize;/* size of cluster summary array, 44bsd */ @@ -605,6 +742,7 @@ struct ufs_sb_private_info { __u32 s_bpfmask; /* bits per fragment mask */ __u32 s_maxsymlinklen;/* upper limit on fast symlinks' size */ + __s32 fs_magic; /* filesystem magic */ }; /* @@ -758,7 +896,7 @@ extern void ufs_free_inode (struct inode *inode); extern struct inode * ufs_new_inode (struct inode *, int); /* inode.c */ -extern int ufs_frag_map (struct inode *, int); +extern u64 ufs_frag_map (struct inode *, int); extern void ufs_read_inode (struct inode *); extern void ufs_put_inode (struct inode *); extern void ufs_write_inode (struct inode *, int); diff --git a/include/linux/ufs_fs_i.h b/include/linux/ufs_fs_i.h index 1b7586441822..c4ef0dfa9f46 100644 --- a/include/linux/ufs_fs_i.h +++ b/include/linux/ufs_fs_i.h @@ -17,6 +17,7 @@ struct ufs_inode_info { union { __u32 i_data[15]; __u8 i_symlink[4*15]; + __u64 u2_i_data[15]; } i_u1; __u32 i_flags; __u32 i_gen; |
