# HG changeset patch # User asl # Date 1154683081 0 # Node ID 32d66e0b0050e530c317943a3d64bd264d78c0d0 # Parent f2a958322096eb5923ba490e5455dd374039bba5 * src/ramfs.c (find_direntry): Don't search off the end of the directory node into hyperspace. * src/ramfs.c (ramfs_getinfo): Support for block usage call. * tests/ramfs1.c (main): Add file system block usage test. diff --git a/packages/fs/ram/current/ChangeLog b/packages/fs/ram/current/ChangeLog --- a/packages/fs/ram/current/ChangeLog +++ b/packages/fs/ram/current/ChangeLog @@ -1,3 +1,10 @@ +2006-06-25 Andrew Lunn + + * src/ramfs.c (find_direntry): Don't search off the end of the + directory node into hyperspace. + * src/ramfs.c (ramfs_getinfo): Support for block usage call. + * tests/ramfs1.c (main): Add file system block usage test. + 2006-05-17 Andy Jackson * tests/ramfs1.c (createfile): Fix compile warnings. diff --git a/packages/fs/ram/current/src/ramfs.c b/packages/fs/ram/current/src/ramfs.c --- a/packages/fs/ram/current/src/ramfs.c +++ b/packages/fs/ram/current/src/ramfs.c @@ -1210,11 +1210,11 @@ static ramfs_dirent *find_direntry( ramf ramfs_dirent *d; cyg_uint8 *buf; size_t size; - + // look for a first name fragment for(;;) { - err = findbuffer_node( dir, pos, &buf, &size, false ); + err = findbuffer_node( dir, pos, &buf, &size, false ); if( err != ENOERR || size == 0) return NULL; @@ -1223,7 +1223,10 @@ static ramfs_dirent *find_direntry( ramf if( size < sizeof(ramfs_dirent) || !d->inuse || !d->first ) { pos += sizeof(ramfs_dirent); - continue; + if ( pos < dir->size ) + continue; + // End if directory, didn't find it. + return NULL; } break; @@ -1248,17 +1251,17 @@ static ramfs_dirent *find_direntry( ramf fraglen = d->fraglen; // compare strings, if different, look for another - if( memcmp( frag, d->name, fraglen ) != 0 ) - break; - + if( memcmp( frag, d->name, fraglen ) != 0 ) { + break; + } frag += fraglen; // If we are at the last fragment, then the whole name string // has matched and we have a successful search. - if( d->last ) - return first; - + if( d->last ) + return first; + // Otherwise move on to next entry in chain err = findbuffer_node( dir, d->next, &buf, &size, false ); if( err != ENOERR ) @@ -1977,7 +1980,7 @@ static int ramfs_stat ( cyg_mtab_ent // ------------------------------------------------------------------------- // ramfs_getinfo() -// Getinfo. Currently only support pathconf(). +// Getinfo. Currently only support pathconf() and filesystem usage. static int ramfs_getinfo ( cyg_mtab_entry *mte, cyg_dir dir, const char *name, int key, void *buf, int len ) @@ -1996,7 +1999,26 @@ static int ramfs_getinfo ( cyg_mtab_ent case FS_INFO_CONF: err = ramfs_pathconf( ds.node, (struct cyg_pathconf_info *)buf ); break; - +#if defined(CYGSEM_FILEIO_BLOCK_USAGE) && defined(CYGPKG_FS_RAM_BLOCKS_ARRAY) + // When using malloc for storage this does not make much + // sense, so only implement this when using pre-allocated + // blocks + case FS_INFO_BLOCK_USAGE: { + struct cyg_fs_block_usage *usage = (struct cyg_fs_block_usage *) buf; + ramfs_block *b; + + usage->total_blocks = CYGNUM_FS_RAM_BLOCKS_ARRAY_SIZE; + usage->free_blocks = 0; + // Iterate over the free list to count its size + b = block_free_list; + while(b) { + usage->free_blocks++; + b=*(ramfs_block **)b; + } + usage->block_size = CYGNUM_RAMFS_BLOCK_SIZE; + return ENOERR; + } +#endif default: err = EINVAL; } diff --git a/packages/fs/ram/current/tests/ramfs1.c b/packages/fs/ram/current/tests/ramfs1.c --- a/packages/fs/ram/current/tests/ramfs1.c +++ b/packages/fs/ram/current/tests/ramfs1.c @@ -61,6 +61,7 @@ #include #include #include +#include #include // base kernel types #include // tracing macros @@ -415,6 +416,9 @@ int main( int argc, char **argv ) { int err; int existingdirents=-1; +#if defined(CYGSEM_FILEIO_BLOCK_USAGE) && defined(CYGPKG_FS_RAM_BLOCKS_ARRAY) + struct cyg_fs_block_usage usage; +#endif CYG_TEST_INIT(); @@ -431,7 +435,16 @@ int main( int argc, char **argv ) listdir( "/", true, -1, &existingdirents ); if ( existingdirents < 2 ) CYG_TEST_FAIL("Not enough dir entries\n"); - + // -------------------------------------------------------------- +#if defined(CYGSEM_FILEIO_BLOCK_USAGE) && defined(CYGPKG_FS_RAM_BLOCKS_ARRAY) + err = cyg_fs_getinfo("/", FS_INFO_BLOCK_USAGE, &usage, sizeof(usage)); + if( err < 0 ) SHOW_RESULT( cyg_fs_getinfo, err ); + diag_printf(": total size: %6lld blocks, %10lld bytes\n", + usage.total_blocks, usage.total_blocks * usage.block_size); + diag_printf(": free size: %6lld blocks, %10lld bytes\n", + usage.free_blocks, usage.free_blocks * usage.block_size); + diag_printf(": block size: %6u bytes\n", usage.block_size); +#endif // -------------------------------------------------------------- createfile( "/foo", 202 ); @@ -552,6 +565,16 @@ int main( int argc, char **argv ) listdir( "..", true, existingdirents+3, NULL ); // -------------------------------------------------------------- +#if defined(CYGSEM_FILEIO_BLOCK_USAGE) && defined(CYGPKG_FS_RAM_BLOCKS_ARRAY) + err = cyg_fs_getinfo("/", FS_INFO_BLOCK_USAGE, &usage, sizeof(usage)); + if( err < 0 ) SHOW_RESULT( cyg_fs_getinfo, err ); + diag_printf(": total size: %6lld blocks, %10lld bytes\n", + usage.total_blocks, usage.total_blocks * usage.block_size); + diag_printf(": free size: %6lld blocks, %10lld bytes\n", + usage.free_blocks, usage.free_blocks * usage.block_size); + diag_printf(": block size: %6u bytes\n", usage.block_size); +#endif + // -------------------------------------------------------------- diag_printf(": unlink tinky\n"); err = unlink( "tinky" );