support for hfs(+)-fs on a CD
Kay Sievers
kay.sievers at vrfy.org
Wed Jul 28 20:26:20 PDT 2004
Here is support for recognition of hfs and hfsplus filesystems on a main
block device, like a CD. Only the first partition is returned with the
probe.
Also introduced is a global change to the 64bit versions of stat(), so
I've changed back to the standard versions. David, could you chaeck if
your NTFS partition has still a label, cause your label last time, was
beyond the 2GB limit.
The usual, but boring screenshot is here:
http://vrfy.org/projects/hal/hfs-CD.png
Btw: How can I pass the DEBUG flag to volume_id instead of setting it in
the sources?
Thanks,
Kay
-------------- next part --------------
Index: configure.in
===================================================================
RCS file: /cvs/hal/hal/configure.in,v
retrieving revision 1.28
diff -u -r1.28 configure.in
--- configure.in 22 Jul 2004 19:40:19 -0000 1.28
+++ configure.in 29 Jul 2004 03:10:26 -0000
@@ -15,6 +15,7 @@
AC_PROG_MAKE_SET
AC_PROG_LN_S
AM_PATH_PYTHON
+AC_SYS_LARGEFILE
AC_ARG_WITH(init-scripts, [ --with-init-scripts=<os> Style of init scripts to install (redhat)])
AC_ARG_WITH(pid-file, [ --with-pid-file=<pidfile> PID file HAL daemon])
Index: hald/linux/block_class_device.c
===================================================================
RCS file: /cvs/hal/hal/hald/linux/block_class_device.c,v
retrieving revision 1.45
diff -u -r1.45 block_class_device.c
--- hald/linux/block_class_device.c 27 Jul 2004 20:26:50 -0000 1.45
+++ hald/linux/block_class_device.c 29 Jul 2004 03:10:28 -0000
@@ -58,7 +58,7 @@
#include "../hald_conf.h"
#include "class_device.h"
#include "common.h"
-
+
#include "volume_id/volume_id.h"
#include "linux_dvd_rw_utils.h"
Index: hald/linux/volume_id/volume_id.c
===================================================================
RCS file: /cvs/hal/hal/hald/linux/volume_id/volume_id.c,v
retrieving revision 1.14
diff -u -r1.14 volume_id.c
--- hald/linux/volume_id/volume_id.c 20 Jul 2004 17:27:16 -0000 1.14
+++ hald/linux/volume_id/volume_id.c 29 Jul 2004 03:10:28 -0000
@@ -47,7 +47,7 @@
} while (0)
#else
#define dbg(format, arg...) do {} while (0)
-#endif
+#endif /* DEBUG */
#define bswap16(x) (__u16)((((__u16)(x) & 0x00ffu) << 8) | \
(((__u32)(x) & 0xff00u) >> 8))
@@ -189,8 +189,9 @@
/* check if we need to read */
if ((off + len) > id->sbbuf_len) {
dbg("read sbbuf len:0x%lx", off + len);
- lseek64(id->fd, 0, SEEK_SET);
+ lseek(id->fd, 0, SEEK_SET);
buf_len = read(id->fd, id->sbbuf, off + len);
+ dbg("got 0x%x (%i) bytes", buf_len, buf_len);
id->sbbuf_len = buf_len;
if (buf_len < off + len)
return NULL;
@@ -212,7 +213,7 @@
if ((off < id->seekbuf_off) ||
((off + len) > (id->seekbuf_off + id->seekbuf_len))) {
dbg("read seekbuf off:0x%lx len:0x%x", off, len);
- if (lseek64(id->fd, off, SEEK_SET) == -1)
+ if (lseek(id->fd, off, SEEK_SET) == -1)
return NULL;
buf_len = read(id->fd, id->seekbuf, len);
dbg("got 0x%x (%i) bytes", buf_len, buf_len);
@@ -909,12 +910,17 @@
return 0;
}
-
#define HFS_SUPERBLOCK_OFFSET 0x400
#define HFS_NODE_LEAF 0xff
#define HFSPLUS_POR_CNID 1
static int probe_hfs_hfsplus(struct volume_id *id)
{
+ struct mac_driver_desc {
+ __u8 signature[2];
+ __u16 block_size;
+ __u32 block_count;
+ } __attribute__((__packed__)) *driver;
+
struct mac_partition {
__u8 signature[2];
__u16 res1;
@@ -922,7 +928,8 @@
__u32 start_block;
__u32 block_count;
__u8 name[32];
- } __attribute__((__packed__)) *part;
+ __u8 type[32];
+ } __attribute__((__packed__)) *part;
struct finder_info {
__u32 boot_folder;
@@ -1040,7 +1047,7 @@
unsigned int alloc_block_size;
unsigned int alloc_first_block;
unsigned int embed_first_block;
- unsigned int embed_off = 0;
+ unsigned int partition_off = 0;
struct hfsplus_bnode_descriptor *descr;
struct hfsplus_bheader_record *bnode;
struct hfsplus_catalog_key *key;
@@ -1050,16 +1057,37 @@
buf = get_buffer(id, 0, 0x200);
if (buf == NULL)
return -1;
-
+
part = (struct mac_partition *) buf;
if ((strncmp(part->signature, "PM", 2) == 0) &&
- (strncmp(part->name, "Apple", 5) == 0)) {
+ (strncmp(part->type, "Apple_partition_map", 19) == 0)) {
id->fs_type = MACPARTMAP;
id->fs_name = "mac_partition_map";
return 0;
}
- buf = get_buffer(id, HFS_SUPERBLOCK_OFFSET, 0x200);
+ driver = (struct mac_driver_desc *) buf;
+ if (strncmp(driver->signature, "ER", 2) == 0) {
+ /* we are on a main device, like a CD
+ * just try to probe the first partition from the map */
+ unsigned int bsize = be16_to_cpu(driver->block_size);
+ unsigned long start;
+
+ buf = get_buffer(id, 2 * bsize, 0x200);
+ if (buf == NULL)
+ return -1;
+ part = (struct mac_partition *) buf;
+
+ if (strncmp(part->signature, "PM", 2) == 0) {
+ start = be32_to_cpu(part->start_block) * bsize;
+ dbg("found '%s' partition entry pointing to 0x%lx",
+ part->type, start);
+
+ partition_off = start;
+ }
+ }
+
+ buf = get_buffer(id, partition_off + HFS_SUPERBLOCK_OFFSET, 0x200);
if (buf == NULL)
return -1;
@@ -1078,11 +1106,11 @@
embed_first_block = be16_to_cpu(hfs->embed_startblock);
dbg("embed_first_block 0x%x", embed_first_block);
- embed_off = (alloc_first_block * 512) +
- (embed_first_block * alloc_block_size);
- dbg("hfs wrapped hfs+ found at offset 0x%x", embed_off);
+ partition_off += (alloc_first_block * 512) +
+ (embed_first_block * alloc_block_size);
+ dbg("hfs wrapped hfs+ found at offset 0x%x", partition_off);
- buf = get_buffer(id, embed_off + HFS_SUPERBLOCK_OFFSET, 0x200);
+ buf = get_buffer(id, partition_off + HFS_SUPERBLOCK_OFFSET, 0x200);
if (buf == NULL)
return -1;
goto checkplus;
@@ -1110,7 +1138,7 @@
blocksize = be32_to_cpu(hfsplus->blocksize);
cat_block = be32_to_cpu(hfsplus->cat_file.extents[0].start_block);
cat_block_count = be32_to_cpu(hfsplus->cat_file.extents[0].block_count);
- cat_off = (cat_block * blocksize) + embed_off;
+ cat_off = (cat_block * blocksize) + partition_off;
cat_len = cat_block_count * blocksize;
dbg("catalog start 0x%x, len 0x%x", cat_off, cat_len);
@@ -1291,6 +1319,10 @@
if (attr_type == MFT_RECORD_ATTR_OBJECT_ID) {
dbg("found uuid");
+ /* Not sure about the on-disk format of MS's uuid's
+ * just assuming a byte stream, it should be unique
+ * anyway.
+ * Any authoritative information is welcome. */
val = &((__u8 *) attr)[val_off];
set_uuid(id, val, 16);
}
@@ -1369,9 +1401,9 @@
case ISO9660:
rc = probe_iso9660(id);
break;
+ case MACPARTMAP:
case HFS:
case HFSPLUS:
- case MACPARTMAP:
rc = probe_hfs_hfsplus(id);
break;
case UFS:
Index: hald/linux/volume_id/volume_id.h
===================================================================
RCS file: /cvs/hal/hal/hald/linux/volume_id/volume_id.h,v
retrieving revision 1.5
diff -u -r1.5 volume_id.h
--- hald/linux/volume_id/volume_id.h 10 Jul 2004 14:52:19 -0000 1.5
+++ hald/linux/volume_id/volume_id.h 29 Jul 2004 03:10:28 -0000
@@ -60,7 +60,7 @@
unsigned char *sbbuf;
unsigned int sbbuf_len;
unsigned char *seekbuf;
- unsigned int seekbuf_off;
+ unsigned long seekbuf_off;
unsigned int seekbuf_len;
int fd_close;
};
-------------- next part --------------
_______________________________________________
hal mailing list
hal at freedesktop.org
http://freedesktop.org/mailman/listinfo/hal
More information about the Hal
mailing list