[OpenBIOS] [commit] r816 - in trunk/openbios-devel: fs/ext2 fs/grubfs fs/hfs fs/hfsplus fs/iso9660 packages

repository service svn at openbios.org
Sat Jul 10 15:11:23 CEST 2010


Author: mcayland
Date: Sat Jul 10 15:11:22 2010
New Revision: 816
URL: http://tracker.coreboot.org/trac/openbios/changeset/816

Log:
Currently the dir word works by using /packages/misc-files to open a directory in a similar way to a file and then 
special-casing directory actions. This is wrong in that in order to list the contents of a directory, open-dev must return true 
for any device which contains a valid filesystem, regardless of whether or not the supplied arguments reference a valid path.

This causes us a problem because in order to implement multiple references in boot-device correctly, we have to fail if we open 
a specific device with invalid arguments (such as a non-existent file reference). This patch therefore makes the following changes:

1) Create a static method in each of the filesystem packages to implement dir
2) Enhance the partition/disk handlers to record the phandle of any detected filesystem during open
3) Create a new dir method in the partition/disk handlers which invokes the static dir method for the currently detected 
filesystem

Hence we can now open a raw device/partition and invoke dir on its filesystem without having to open a specific file-reference 
first. Following shortly is a patch to switch the main dir word over to use this new system.

Signed-off-by: Mark Cave-Ayland <mark.cave-ayland at siriusit.co.uk>

Modified:
   trunk/openbios-devel/fs/ext2/ext2_fs.c
   trunk/openbios-devel/fs/grubfs/grubfs_fs.c
   trunk/openbios-devel/fs/hfs/hfs_fs.c
   trunk/openbios-devel/fs/hfsplus/hfsp_fs.c
   trunk/openbios-devel/fs/iso9660/iso9660_fs.c
   trunk/openbios-devel/packages/disk-label.c
   trunk/openbios-devel/packages/mac-parts.c
   trunk/openbios-devel/packages/pc-parts.c
   trunk/openbios-devel/packages/sun-parts.c

Modified: trunk/openbios-devel/fs/ext2/ext2_fs.c
==============================================================================
--- trunk/openbios-devel/fs/ext2/ext2_fs.c	Sun Jul  4 15:37:00 2010	(r815)
+++ trunk/openbios-devel/fs/ext2/ext2_fs.c	Sat Jul 10 15:11:22 2010	(r816)
@@ -33,7 +33,7 @@
 
 DECLARE_NODE( ext2, 0, sizeof(ext2_info_t), "+/packages/ext2-files" );
 
-/*
+
 static const int days_month[12] =
 	{ 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };
 static const int days_month_leap[12] =
@@ -83,28 +83,6 @@
 		     year, month, day, hour, minute, second);
 }
 
-static void
-dir_fs ( file_desc_t *fd)
-{
-	ext2_COMMON *common = (ext2_COMMON *)fd;
-	struct ext2_dir_entry_2 *entry;
-	struct ext2_inode inode;
-
-	if (common->type != DIR)
-		return;
-
-	forth_printf("\n");
-	while ( (entry = ext2_readdir(common->dir)) ) {
-		ext2_get_inode(common->dir->volume, entry->inode, &inode);
-		forth_printf("% 10d ", inode.i_size);
-		print_date(inode.i_mtime);
-		if (S_ISDIR(inode.i_mode))
-			forth_printf("%s\\\n", entry->name);
-		else
-			forth_printf("%s\n", entry->name);
-	}
-}
-*/
 
 /************************************************************************/
 /*	Standard package methods					*/
@@ -233,6 +211,52 @@
 	PUSH( (ucell)strdup("ext2") );
 }
 
+/* static method, ( pathstr len ihandle -- ) */
+static void
+ext2_files_dir( ext2_info_t *dummy )
+{
+	ext2_COMMON *common;
+	ext2_VOLUME *volume;
+	struct ext2_dir_entry_2 *entry;
+	struct ext2_inode inode;
+	int fd;
+
+	ihandle_t ih = POP();
+	char *path = pop_fstr_copy();
+
+	fd = open_ih( ih );
+	if ( fd == -1 ) {
+		free( path );
+		return;
+	}
+
+	volume = ext2_mount(fd);
+	if (!volume) {
+		return;
+	}
+
+	common = (ext2_COMMON*)malloc(sizeof(ext2_COMMON));
+	common->dir = ext2_opendir(volume, path);
+
+	forth_printf("\n");
+	while ( (entry = ext2_readdir(common->dir)) ) {
+		ext2_get_inode(common->dir->volume, entry->inode, &inode);
+		forth_printf("% 10d ", inode.i_size);
+		print_date(inode.i_mtime);
+		if (S_ISDIR(inode.i_mode))
+			forth_printf("%s\\\n", entry->name);
+		else
+			forth_printf("%s\n", entry->name);
+	}
+
+	ext2_closedir( common->dir );
+	ext2_umount( volume );
+
+	close_io( fd );
+
+	free( common );
+	free( path );
+}
 
 /* static method, ( pos.d ih -- flag? ) */
 static void
@@ -265,6 +289,7 @@
 	{ "read",	ext2_files_read		},
 	{ "seek",	ext2_files_seek		},
 	{ "load",	ext2_files_load		},
+	{ "dir",	ext2_files_dir		},
 
 	/* special */
 	{ "get-path",	ext2_files_get_path	},

Modified: trunk/openbios-devel/fs/grubfs/grubfs_fs.c
==============================================================================
--- trunk/openbios-devel/fs/grubfs/grubfs_fs.c	Sun Jul  4 15:37:00 2010	(r815)
+++ trunk/openbios-devel/fs/grubfs/grubfs_fs.c	Sat Jul 10 15:11:22 2010	(r816)
@@ -356,6 +356,15 @@
 	RET ( 0 );
 }
 
+/* static method, ( pathstr len ihandle -- ) */
+static void
+grubfs_files_dir( grubfs_info_t *mi )
+{
+	forth_printf("dir method not implemented for grubfs filesystem\n");
+	POP();
+	POP();
+	POP();
+}
 
 static void
 grubfs_initializer( grubfs_info_t *dummy )
@@ -370,6 +379,7 @@
 	{ "read",	grubfs_files_read	},
 	{ "seek",	grubfs_files_seek	},
 	{ "load",	grubfs_files_load	},
+	{ "dir",	grubfs_files_dir	},
 
 	/* special */
 	{ "get-path",	grubfs_files_get_path	},

Modified: trunk/openbios-devel/fs/hfs/hfs_fs.c
==============================================================================
--- trunk/openbios-devel/fs/hfs/hfs_fs.c	Sun Jul  4 15:37:00 2010	(r815)
+++ trunk/openbios-devel/fs/hfs/hfs_fs.c	Sat Jul 10 15:11:22 2010	(r816)
@@ -144,7 +144,6 @@
 	return mi->common->file;
 }
 
-/*
 
 static const int days_month[12] =
 	{ 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };
@@ -195,6 +194,7 @@
 		     year, month, day, hour, minute, second);
 }
 
+/*
 static void
 dir_fs( file_desc_t *fd )
 {
@@ -485,6 +485,83 @@
 	PUSH ((ucell)volname);
 }
 
+/* static method, ( pathstr len ihandle -- ) */
+static void
+hfs_files_dir( hfs_info_t *dummy )
+{
+	hfsvol *volume;
+	hfscommon *common;
+	hfsdirent ent;
+	const char *s;
+	char buf[256], *tmppath;
+	int fd;
+
+	ihandle_t ih = POP();
+	char *path = pop_fstr_copy();
+
+	fd = open_ih( ih );
+	if ( fd == -1 ) {
+		free( path );
+		return;
+	}
+
+	volume = hfs_mount(fd, 0);
+	if (!volume) {
+		return;
+	}
+
+	common = malloc(sizeof(hfscommon));
+
+	if (strcmp(path, "\\") == 0) {
+		common->dir = hfs_opendir(volume, ":");
+	} else {
+		if (path[strlen(path) - 1] == '\\') {
+			path[strlen(path) - 1] = 0;
+		}
+
+		tmppath = path;
+		for( tmppath-- ;; ) {
+			int n;
+	
+			s = ++tmppath;
+			tmppath = strchr(s, '\\');
+			if( !tmppath || !tmppath[1])
+				break;
+			n = MIN( sizeof(buf)-1, (path-s) );
+			if( !n )
+				continue;
+	
+			strncpy( buf, s, n );
+			buf[n] = 0;
+			if( hfs_chdir(volume, buf) ) {
+				free(common);
+				free(path);
+				return;
+			}
+		}
+
+		common->dir = hfs_opendir(volume, s);
+	}
+
+	forth_printf("\n");
+	while( !hfs_readdir(common->dir, &ent) ) {
+		forth_printf("% 10d ", ent.u.file.dsize);
+		print_date(ent.mddate);
+		if( ent.flags & HFS_ISDIR )
+			forth_printf("%s\\\n", ent.name);
+		else
+			forth_printf("%s\n", ent.name);
+	}
+
+	hfs_closedir( common->dir );
+	hfs_umount( volume );
+
+	close_io( fd );
+
+	free( common );
+	free( path );
+}
+
 /* static method, ( pos.d ih -- flag? ) */
 static void
 hfs_files_probe( hfs_info_t *dummy )
@@ -515,6 +592,7 @@
 	{ "read",	hfs_files_read	},
 	{ "seek",	hfs_files_seek	},
 	{ "load",	hfs_files_load	},
+	{ "dir",	hfs_files_dir	},
 
 	/* special */
 	{ "open-nwrom",	 	hfs_files_open_nwrom 	},

Modified: trunk/openbios-devel/fs/hfsplus/hfsp_fs.c
==============================================================================
--- trunk/openbios-devel/fs/hfsplus/hfsp_fs.c	Sun Jul  4 15:37:00 2010	(r815)
+++ trunk/openbios-devel/fs/hfsplus/hfsp_fs.c	Sat Jul 10 15:11:22 2010	(r816)
@@ -24,6 +24,7 @@
 #include "unicode.h"
 #include "blockiter.h"
 #include "libc/diskio.h"
+#include "libc/vsprintf.h"
 
 #define MAC_OS_ROM_CREATOR	0x63687270	/* 'chrp' */
 #define MAC_OS_ROM_TYPE		0x74627869	/* 'tbxi' */
@@ -432,6 +433,16 @@
 	PUSH ((ucell)volname);
 }
 
+/* static method, ( pathstr len ihandle -- ) */
+static void
+hfsp_files_dir( hfsp_info_t *dummy )
+{
+	forth_printf("dir method not implemented for HFS+ filesystem\n");
+	POP();
+	POP();
+	POP();
+}
+
 /* static method, ( pos.d ih -- flag? ) */
 static void
 hfsp_files_probe( hfsp_info_t *dummy )
@@ -449,7 +460,6 @@
 	RET (ret);
 }
 
-
 static void
 hfsp_initializer( hfsp_info_t *dummy )
 {
@@ -463,6 +473,7 @@
 	{ "read",	hfsp_files_read		},
 	{ "seek",	hfsp_files_seek		},
 	{ "load",	hfsp_files_load		},
+	{ "dir",	hfsp_files_dir		},
 
 	/* special */
 	{ "open-nwrom",	 	hfsp_files_open_nwrom 	},

Modified: trunk/openbios-devel/fs/iso9660/iso9660_fs.c
==============================================================================
--- trunk/openbios-devel/fs/iso9660/iso9660_fs.c	Sun Jul  4 15:37:00 2010	(r815)
+++ trunk/openbios-devel/fs/iso9660/iso9660_fs.c	Sat Jul 10 15:11:22 2010	(r816)
@@ -156,17 +156,37 @@
 	PUSH( size );
 }
 
+/* static method, ( pathstr len ihandle -- ) */
 static void
-iso9660_files_dir( iso9660_info_t *mi )
+iso9660_files_dir( iso9660_info_t *dummy )
 {
+	iso9660_VOLUME *volume;
+	iso9660_COMMON *common;
 	struct iso_directory_record *idr;
 	char name_buf[256];
+	int fd;
  
-	if (mi->common->type != DIR)
+	ihandle_t ih = POP();
+	char *path = pop_fstr_copy();
+
+	fd = open_ih( ih );
+	if ( fd == -1 ) {
+		free( path );
 		return;
+	}
+ 
+	volume = iso9660_mount( fd );
+	if ( volume == NULL ) {
+		free ( path );
+		close_io( fd );
+		return;
+	}
+
+	common = malloc(sizeof(iso9660_COMMON));
+	common->dir = iso9660_opendir( volume, path );
 
 	forth_printf("\n");
-	while ( (idr = iso9660_readdir(mi->common->dir)) ) {
+	while ( (idr = iso9660_readdir(common->dir)) ) {
  
 		forth_printf("% 10d ", isonum_733(idr->size));
 		forth_printf("%d-%02d-%02d %02d:%02d:%02d ",
@@ -174,12 +194,20 @@
 			     idr->date[1], /* month */
                              idr->date[2], /* day */
 			     idr->date[3], idr->date[4], idr->date[5]);
-		iso9660_name(mi->common->dir->volume, idr, name_buf);
+		iso9660_name(common->dir->volume, idr, name_buf);
 		if (idr->flags[0] & 2)
 			forth_printf("%s\\\n", name_buf);
 		else
 			forth_printf("%s\n", name_buf);
 	}
+
+	iso9660_closedir( common->dir );
+	iso9660_umount( volume );
+
+	close_io( fd );
+
+	free( common );
+	free( path );
 }
 
 /* static method, ( pos.d ih -- flag? ) */

Modified: trunk/openbios-devel/packages/disk-label.c
==============================================================================
--- trunk/openbios-devel/packages/disk-label.c	Sun Jul  4 15:37:00 2010	(r815)
+++ trunk/openbios-devel/packages/disk-label.c	Sat Jul 10 15:11:22 2010	(r816)
@@ -41,6 +41,7 @@
 	int		type;		/* partition type or -1 */
 
 	ihandle_t	part_ih;
+	phandle_t	filesystem_ph;
 } dlabel_info_t;
 
 DECLARE_NODE( dlabel, 0, sizeof(dlabel_info_t), "/packages/disk-label" );
@@ -72,6 +73,7 @@
 	di->part_ih = 0;
 
 	/* Find parent methods */
+	di->filesystem_ph = 0;
 	di->parent_seek_xt = find_parent_method("seek");
 	di->parent_tell_xt = find_parent_method("tell");
         di->parent_read_xt = find_parent_method("read");	
@@ -115,6 +117,9 @@
 		ph = POP_ph();
 		if( ph ) {
 			/* If we have been asked to open a particular file, interpose the filesystem package with the passed filename as an argument */
+			di->filesystem_ph = ph;
+
+			DPRINTF("Located filesystem with ph " FMT_ucellx "\n", ph);
 			DPRINTF("path: %s length: %d\n", path, strlen(path));
 
 			if (strlen(path)) {
@@ -205,6 +210,24 @@
 	}
 }
 
+/* ( pathstr len -- ) */
+static void
+dlabel_dir( dlabel_info_t *di )
+{
+	if ( di->filesystem_ph ) {
+		PUSH( my_self() );
+		push_str("dir");
+		PUSH( di->filesystem_ph );
+		fword("find-method");
+		POP();
+		fword("execute");
+ 	} else {
+		forth_printf("disk-label: Unable to determine filesystem\n");
+		POP();
+		POP();
+	}
+}
+
 NODE_METHODS( dlabel ) = {
 	{ "open",	dlabel_open 	},
 	{ "close",	dlabel_close 	},
@@ -213,6 +236,7 @@
 	{ "write",	dlabel_write 	},
 	{ "seek",	dlabel_seek 	},
 	{ "tell",	dlabel_tell 	},
+	{ "dir",	dlabel_dir 	},
 };
 
 void

Modified: trunk/openbios-devel/packages/mac-parts.c
==============================================================================
--- trunk/openbios-devel/packages/mac-parts.c	Sun Jul  4 15:37:00 2010	(r815)
+++ trunk/openbios-devel/packages/mac-parts.c	Sat Jul 10 15:11:22 2010	(r816)
@@ -181,7 +181,6 @@
 				ret = -1;
 				goto out;
 			}
-
 		}
 		/* not found */
 		if (firstHFS != -1) {
@@ -341,12 +340,34 @@
 	load(my_self());
 }
 
+/* ( pathstr len -- ) */
+static void
+macparts_dir( macparts_info_t *di )
+{
+	/* On PPC Mac, the first partition chosen according to the CHRP boot
+	specification (i.e. marked as bootable) may not necessarily contain 
+	a valid FS */
+	if ( di->filesystem_ph ) {
+		PUSH( my_self() );
+		push_str("dir");
+		PUSH( di->filesystem_ph );
+		fword("find-method");
+		POP();
+		fword("execute");
+	} else {
+		forth_printf("mac-parts: Unable to determine filesystem\n");
+		POP();
+		POP();
+	}
+}
+
 NODE_METHODS( macparts ) = {
 	{ "probe",	macparts_probe 		},
 	{ "open",	macparts_open 		},
 	{ "seek",	macparts_seek 		},
 	{ "read",	macparts_read 		},
 	{ "load",	macparts_load 		},
+	{ "dir",	macparts_dir 		},
 	{ "get-info",	macparts_get_info 	},
 	{ "block-size",	macparts_block_size 	},
 	{ NULL,		macparts_initialize	},

Modified: trunk/openbios-devel/packages/pc-parts.c
==============================================================================
--- trunk/openbios-devel/packages/pc-parts.c	Sun Jul  4 15:37:00 2010	(r815)
+++ trunk/openbios-devel/packages/pc-parts.c	Sat Jul 10 15:11:22 2010	(r816)
@@ -365,6 +365,23 @@
 	load(my_self());
 }
 
+/* ( pathstr len -- ) */
+static void
+pcparts_dir( pcparts_info_t *di )
+{
+	if ( di->filesystem_ph ) {
+		PUSH( my_self() );
+		push_str("dir");
+		PUSH( di->filesystem_ph );
+		fword("find-method");
+		POP();
+		fword("execute");
+	} else {
+		forth_printf("pc-parts: Unable to determine filesystem\n");
+		POP();
+		POP();
+	}
+}
 
 NODE_METHODS( pcparts ) = {
 	{ "probe",	pcparts_probe 		},
@@ -372,6 +389,7 @@
 	{ "seek",	pcparts_seek 		},
 	{ "read",	pcparts_read 		},
 	{ "load",	pcparts_load 		},
+	{ "dir",	pcparts_dir 		},
 	{ "get-info",	pcparts_get_info 	},
 	{ "block-size",	pcparts_block_size 	},
 	{ NULL,		pcparts_initialize	},

Modified: trunk/openbios-devel/packages/sun-parts.c
==============================================================================
--- trunk/openbios-devel/packages/sun-parts.c	Sun Jul  4 15:37:00 2010	(r815)
+++ trunk/openbios-devel/packages/sun-parts.c	Sat Jul 10 15:11:22 2010	(r816)
@@ -297,6 +297,23 @@
 	load(my_self());
 }
 
+/* ( pathstr len -- ) */
+static void
+sunparts_dir( sunparts_info_t *di )
+{
+	if ( di->filesystem_ph) {
+		PUSH( my_self() );
+		push_str("dir");
+		PUSH( di->filesystem_ph );
+		fword("find-method");
+		POP();
+		fword("execute");
+	} else {
+		forth_printf("sun-parts: Unable to determine filesystem\n");
+		POP();
+		POP();
+	}
+}
 
 NODE_METHODS( sunparts ) = {
 	{ "probe",	sunparts_probe 		},
@@ -306,6 +323,7 @@
 	{ "seek",	sunparts_seek 		},
 	{ "read",	sunparts_read 		},
 	{ "load",	sunparts_load	 	},
+	{ "dir",	sunparts_dir 		},
 	{ NULL,		sunparts_initialize	},
 };
 



More information about the OpenBIOS mailing list