Mercurial > ecos
changeset 2298:474e1f0afb12
* src/synthdisk.c: Updated to match changes in io/disk package.
* src/synthdisk.c: Mildly reorganized to support changeable
media. Added synth_disk_change() function to allow us to fake a
disk change for testing purposes.
* cdl/synthdisk.cdl: Added testing config options, plus
define_proc to export CYGDAT_DEVS_DISK_CFG include file name.
* src/synthdisk.c: Updated to latest disk device specification.
| author | jlarmour |
|---|---|
| date | Thu, 21 Sep 2006 16:36:04 +0000 |
| parents | fa76da61c460 |
| children | 04006a2b020d |
| files | packages/devs/disk/synth/current/ChangeLog packages/devs/disk/synth/current/cdl/synthdisk.cdl packages/devs/disk/synth/current/src/synthdisk.c |
| diffstat | 3 files changed, 229 insertions(+), 52 deletions(-) [+] |
line wrap: on
line diff
--- a/packages/devs/disk/synth/current/ChangeLog +++ b/packages/devs/disk/synth/current/ChangeLog @@ -1,14 +1,33 @@ +2006-02-03 Nick Garnett <nickg@ecoscentric.com> + + * src/synthdisk.c: Updated to match changes in io/disk package. + 2004-07-01 Savin Zlobec <savin@elatec.si> * src/synthdisk.c: Updated to work with the new DISK_CHANNEL macro definition. -2004-01-15 Nick Garnett <nickg@calivar.com> +2004-04-15 Nick Garnett <nickg@ecoscentric.com> + + * src/synthdisk.c: Mildly reorganized to support changeable + media. Added synth_disk_change() function to allow us to fake a + disk change for testing purposes. + +2004-02-05 Nick Garnett <nickg@ecoscentric.com> + + * cdl/synthdisk.cdl: Added testing config options, plus + define_proc to export CYGDAT_DEVS_DISK_CFG include file name. + +2004-01-30 Nick Garnett <nickg@ecoscentric.com> + + * src/synthdisk.c: Updated to latest disk device specification. + +2004-01-15 Nick Garnett <nickg@ecoscentric.com> * cdl/synthdisk.cdl: * src/synthdisk.c: Added _FILENAME option for disk instances to map device to an - arbitrary cinfigured file. + arbitrary configured file. * src/synthdisk.c: Removed block_pos arguments from read and write calls: it is not necessary. @@ -31,7 +50,8 @@ 2003-08-19 Savin Zlobec <savin@elatec.si //####ECOSGPLCOPYRIGHTBEGIN#### // ------------------------------------------- // This file is part of eCos, the Embedded Configurable Operating System. -// Copyright (C) 2003 Savin Zlobec +// Copyright (C) 2003 Savin Zlobec +// Copyright (C) 2004, 2006 eCosCentric Limited // // eCos is free software; you can redistribute it and/or modify it under // the terms of the GNU General Public License as published by the Free
--- a/packages/devs/disk/synth/current/cdl/synthdisk.cdl +++ b/packages/devs/disk/synth/current/cdl/synthdisk.cdl @@ -8,7 +8,8 @@ #####ECOSGPLCOPYRIGHTBEGIN#### ## ------------------------------------------- ## This file is part of eCos, the Embedded Configurable Operating System. -## Copyright (C) 2003 Savin Zlobec +## Copyright (C) 2003 Savin Zlobec +## Copyright (C) 2004 eCosCentric Limited ## ## eCos is free software; you can redistribute it and/or modify it under ## the terms of the GNU General Public License as published by the Free @@ -52,6 +53,12 @@ cdl_package CYGPKG_DEVS_DISK_ECOSYNTH { active_if CYGPKG_IO_DISK active_if CYGPKG_HAL_SYNTH + define_proc { + puts $::cdl_system_header "/***** Synthdisk driver proc output start *****/" + puts $::cdl_system_header "#define CYGDAT_DEVS_DISK_CFG <pkgconf/devs_disk_ecosynth.h>" + puts $::cdl_system_header "/***** Synthdisk driver proc output end *****/" + } + cdl_component CYGVAR_DEVS_DISK_ECOSYNTH_DISK0 { display "Provide disk 0 device" flavor bool @@ -61,7 +68,7 @@ cdl_package CYGPKG_DEVS_DISK_ECOSYNTH { cdl_option CYGDAT_IO_DISK_ECOSYNTH_DISK0_NAME { display "Device name for ecosynth disk 0 device" flavor data - default_value {"\"/dev/disk0/\""} + default_value {"\"/dev/hd0/\""} description "This is the device name used to access this device in eCos. Note that the trailing slash character must be present." @@ -163,4 +170,48 @@ cdl_package CYGPKG_DEVS_DISK_ECOSYNTH { the set of global flags if present." } } + + cdl_component CYGPKG_DEVS_DISK_ECOSYNTH_TESTING { + display "Testing configuration" + default_value 1 + + cdl_option CYGDAT_DEVS_DISK_TEST_DEVICE { + display "Test device driver" + flavor data + default_value {"\"/dev/hd0/1\"" } + } + + cdl_option CYGDAT_DEVS_DISK_TEST_MOUNTPOINT { + display "Test filesystem mountpoint" + flavor data + default_value {"\"/dosfs\"" } + } + + cdl_option CYGDAT_DEVS_DISK_TEST_DIRECTORY { + display "Test directory on test device" + flavor data + default_value {"\"/test\"" } + } + + + cdl_option CYGDAT_DEVS_DISK_TEST_DEVICE2 { + display "Second Test device driver" + flavor data + default_value {"\"/dev/hd0/2\"" } + } + + cdl_option CYGDAT_DEVS_DISK_TEST_MOUNTPOINT2 { + display "Second Test filesystem mountpoint" + flavor data + default_value {"\"/dosfs2\"" } + } + + cdl_option CYGDAT_DEVS_DISK_TEST_DIRECTORY2 { + display "Test directory on second test device" + flavor data + default_value {"\"/test\"" } + } + + } + }
--- a/packages/devs/disk/synth/current/src/synthdisk.c +++ b/packages/devs/disk/synth/current/src/synthdisk.c @@ -8,7 +8,8 @@ //####ECOSGPLCOPYRIGHTBEGIN#### // ------------------------------------------- // This file is part of eCos, the Embedded Configurable Operating System. -// Copyright (C) 2003 Savin Zlobec. +// Copyright (C) 2003 Savin Zlobec +// Copyright (C) 2004, 2006 eCosCentric Limited // // eCos is free software; you can redistribute it and/or modify it under // the terms of the GNU General Public License as published by the Free @@ -76,6 +77,8 @@ typedef struct { char *filename; } synth_disk_info_t; +typedef struct { int dummy; } synth_controller_t; + // ---------------------------------------------------------------------------- static cyg_bool synth_disk_init(struct cyg_devtab_entry *tab); @@ -104,38 +107,42 @@ static Cyg_ErrNo synth_disk_lookup(struc struct cyg_devtab_entry *sub_tab, const char *name); -static DISK_FUNS(synth_disk_funs, - synth_disk_read, - synth_disk_write, - synth_disk_get_config, - synth_disk_set_config +DISK_FUNS(synth_disk_funs, + synth_disk_read, + synth_disk_write, + synth_disk_get_config, + synth_disk_set_config ); // ---------------------------------------------------------------------------- -#define SYNTH_DISK_INSTANCE(_number_,_mbr_supp_, _cyl_,_hpt_,_spt_) \ -static synth_disk_info_t synth_disk_info##_number_ = { \ - num: _number_, \ - cylinders_num: _cyl_, \ - heads_num: _hpt_, \ - sectors_num: _spt_, \ - size: CYGNUM_IO_DISK_ECOSYNTH_DISK##_number_##_SIZE, \ - filefd: -1, \ - filename: CYGDAT_IO_DISK_ECOSYNTH_DISK##_number_##_FILENAME \ -}; \ -DISK_CHANNEL(synth_disk_channel##_number_, \ - synth_disk_funs, \ - synth_disk_info##_number_, \ - _mbr_supp_, \ - 4 \ -); \ -BLOCK_DEVTAB_ENTRY(synth_disk_io##_number_, \ - CYGDAT_IO_DISK_ECOSYNTH_DISK##_number_##_NAME, \ - 0, \ - &cyg_io_disk_devio, \ - synth_disk_init, \ - synth_disk_lookup, \ - &synth_disk_channel##_number_ \ + +#define SYNTH_DISK_INSTANCE(_number_,_mbr_supp_, _cyl_,_hpt_,_spt_) \ +static synth_disk_info_t synth_disk_info##_number_ = { \ + num: _number_, \ + cylinders_num: _cyl_, \ + heads_num: _hpt_, \ + sectors_num: _spt_, \ + size: CYGNUM_IO_DISK_ECOSYNTH_DISK##_number_##_SIZE, \ + filefd: -1, \ + filename: CYGDAT_IO_DISK_ECOSYNTH_DISK##_number_##_FILENAME \ +}; \ +static synth_controller_t synth_controller_##_number_; \ +DISK_CONTROLLER( synth_disk_controller_##_number_, synth_controller_##_number_ ); \ +DISK_CHANNEL(synth_disk_channel##_number_, \ + synth_disk_funs, \ + synth_disk_info##_number_, \ + synth_disk_controller_##_number_, \ + _mbr_supp_, \ + 4 \ +); \ +BLOCK_DEVTAB_ENTRY(synth_disk_io##_number_, \ + CYGDAT_IO_DISK_ECOSYNTH_DISK##_number_##_NAME, \ + 0, \ + &cyg_io_disk_devio, \ + synth_disk_init, \ + synth_disk_lookup, \ + &synth_disk_channel##_number_ \ ); // ---------------------------------------------------------------------------- @@ -194,33 +201,45 @@ synth_disk_init(struct cyg_devtab_entry if (result) { - cyg_disk_identify_t ident; - - ident.serial[0] = '\0'; - ident.firmware_rev[0] = '\0'; - ident.model_num[0] = '\0'; - ident.lba_sectors_num = synth_info->size / 512; - ident.cylinders_num = synth_info->cylinders_num; - ident.heads_num = synth_info->heads_num; - ident.sectors_num = synth_info->sectors_num; if (!(chan->callbacks->disk_init)(tab)) return false; - if (ENOERR != (chan->callbacks->disk_connected)(tab, &ident)) - return false; } return result; } +// ---------------------------------------------------------------------------- + static Cyg_ErrNo -synth_disk_lookup(struct cyg_devtab_entry **tab, +synth_disk_lookup(struct cyg_devtab_entry **tab, struct cyg_devtab_entry *sub_tab, const char *name) { + Cyg_ErrNo res; disk_channel *chan = (disk_channel *) (*tab)->priv; - return (chan->callbacks->disk_lookup(tab, sub_tab, name)); + synth_disk_info_t *synth_info = (synth_disk_info_t *) chan->dev_priv; + cyg_disk_identify_t ident; + + ident.serial[0] = '\0'; + ident.firmware_rev[0] = '\0'; + ident.model_num[0] = '\0'; + ident.lba_sectors_num = synth_info->size / 512; + ident.cylinders_num = synth_info->cylinders_num; + ident.heads_num = synth_info->heads_num; + ident.sectors_num = synth_info->sectors_num; + ident.phys_block_size = 1; + ident.max_transfer = 2048; + + res = (chan->callbacks->disk_connected)(*tab, &ident); + + if( res == ENOERR ) + res = (chan->callbacks->disk_lookup(tab, sub_tab, name)); + + return res; } +// ---------------------------------------------------------------------------- + static Cyg_ErrNo synth_disk_read(disk_channel *chan, void *buf, @@ -238,12 +257,14 @@ synth_disk_read(disk_channel *chan, cyg_hal_sys_lseek(synth_info->filefd, block_num * chan->info->block_size, CYG_HAL_SYS_SEEK_SET); - cyg_hal_sys_read(synth_info->filefd, buf, len); + cyg_hal_sys_read(synth_info->filefd, buf, len*512); return ENOERR; } return -EIO; } +// ---------------------------------------------------------------------------- + static Cyg_ErrNo synth_disk_write(disk_channel *chan, const void *buf, @@ -261,13 +282,15 @@ synth_disk_write(disk_channel *chan, cyg_hal_sys_lseek(synth_info->filefd, block_num * chan->info->block_size, CYG_HAL_SYS_SEEK_SET); - cyg_hal_sys_write(synth_info->filefd, buf, len); + cyg_hal_sys_write(synth_info->filefd, buf, len*512); // cyg_hal_sys_fdatasync(synth_info->filefd); return ENOERR; } return -EIO; } +// ---------------------------------------------------------------------------- + static Cyg_ErrNo synth_disk_get_config(disk_channel *chan, cyg_uint32 key, @@ -282,18 +305,101 @@ synth_disk_get_config(disk_channel *chan return -EINVAL; } +// ---------------------------------------------------------------------------- + static Cyg_ErrNo synth_disk_set_config(disk_channel *chan, cyg_uint32 key, const void *xbuf, cyg_uint32 *len) { - + Cyg_ErrNo res = ENOERR; #ifdef DEBUG diag_printf("synth disk set config\n"); #endif - - return -EINVAL; + + switch ( key ) + { + case CYG_IO_SET_CONFIG_DISK_MOUNT: + // We have nothing to do here for this option. + break; + + case CYG_IO_SET_CONFIG_DISK_UMOUNT: + if( chan->info->mounts == 0 ) + { + // If this is the last unmount of this disk, then disconnect it from + // the driver system so the user can swap it out if he wants. + res = (chan->callbacks->disk_disconnected)(chan); + } + break; + + default: + res = -EINVAL; + break; + } + + return res; +} + +// ---------------------------------------------------------------------------- + +externC cyg_bool synth_disk_change( int unit, char *filename, int size, + int cyls, int heads, int sectors) +{ + struct cyg_devtab_entry *tab = &synth_disk_io0; + disk_channel *chan = (disk_channel *) tab->priv; + synth_disk_info_t *synth_info = (synth_disk_info_t *) chan->dev_priv; + int err = 0; + + if (!chan->init) + return false; + + synth_info->filename = filename; + synth_info->size = size; + synth_info->cylinders_num = cyls; + synth_info->heads_num = heads; + synth_info->sectors_num = sectors; + +#ifdef DEBUG + diag_printf("synth disk %d change size=%d\n", + synth_info->num, synth_info->size); +#endif + + err = cyg_hal_sys_close( synth_info->filefd ); + +#ifdef DEBUG + if( err != 0 ) + { + diag_printf("synth disk change, failed to close old image: %d\n",err); + } +#endif + + synth_info->filefd = cyg_hal_sys_open(synth_info->filename, + CYG_HAL_SYS_O_RDWR, + CYG_HAL_SYS_S_IRWXU|CYG_HAL_SYS_S_IRWXG|CYG_HAL_SYS_S_IRWXO); + + if (-ENOENT == synth_info->filefd) + { + synth_info->filefd = cyg_hal_sys_open(synth_info->filename, + CYG_HAL_SYS_O_RDWR|CYG_HAL_SYS_O_CREAT, 0644); + + if (synth_info->filefd >= 0) + { + unsigned char b = 0x00; + int i; + + for (i = 0; i < synth_info->size; i++) + cyg_hal_sys_write(synth_info->filefd, &b, 1); + } + } + + if (synth_info->filefd < 0) + { + CYG_ASSERT(false, "Can't open/create disk image file"); + return false; + } + + return true; } // ----------------------------------------------------------------------------
