From 4ef5a61ad5a63a18110e18b1b7b4e966d4986553 Mon Sep 17 00:00:00 2001 From: neil Date: Thu, 21 Aug 2008 21:30:51 +0000 Subject: [PATCH] Reapplication of sonic's patches originally done in r29201 and r29210: - FFS handler moved to better place - Tracks remaining locks on offline volumes correctly - Fills in id_VolumeNode correctly - Keeps track of current DOS VolumeNode git-svn-id: https://svn.aros.org/svn/aros/trunk/AROS@29216 fb15a70f-31f2-0310-bbcc-cdcc74a49acc --- rom/devs/filesys/afs/afshandler.h | 4 ++ rom/devs/filesys/afs/arosdevice.c | 2 +- rom/devs/filesys/afs/filehandles.h | 1 + rom/devs/filesys/afs/filehandles1.c | 45 +++++++++---- rom/devs/filesys/afs/filehandles3.c | 2 +- rom/devs/filesys/afs/main.c | 39 +++++++---- rom/devs/filesys/afs/misc.c | 10 +-- rom/devs/filesys/afs/mmakefile.src | 5 +- rom/devs/filesys/afs/os.h | 1 + rom/devs/filesys/afs/os_aros_support.c | 119 ++++++++++++--------------------- rom/devs/filesys/afs/os_aros_support.h | 3 +- rom/devs/filesys/afs/os_unix_support.c | 5 ++ rom/devs/filesys/afs/os_unix_support.h | 1 + rom/devs/filesys/afs/volumes.h | 1 + 14 files changed, 124 insertions(+), 114 deletions(-) diff --git a/rom/devs/filesys/afs/afshandler.h b/rom/devs/filesys/afs/afshandler.h index 471359571..d39d4877f 100644 --- a/rom/devs/filesys/afs/afshandler.h +++ b/rom/devs/filesys/afs/afshandler.h @@ -20,6 +20,10 @@ struct AFSBase struct IOFileSys *iofs; /* to be aborted iofs or NULL */ struct List device_list; /* list of mounted devices (struct Volume) */ struct timerequest *timer_request; + ULONG timer_flags; }; +#define TIMER_ACTIVE 0x00000001 +#define TIMER_RESTART 0x00000002 + #endif diff --git a/rom/devs/filesys/afs/arosdevice.c b/rom/devs/filesys/afs/arosdevice.c index 567f0792d..2a2048f7e 100644 --- a/rom/devs/filesys/afs/arosdevice.c +++ b/rom/devs/filesys/afs/arosdevice.c @@ -4,7 +4,7 @@ */ #ifndef DEBUG -#define DEBUG 1 +#define DEBUG 0 #endif #include diff --git a/rom/devs/filesys/afs/filehandles.h b/rom/devs/filesys/afs/filehandles.h index d90fdae5a..162f8e635 100644 --- a/rom/devs/filesys/afs/filehandles.h +++ b/rom/devs/filesys/afs/filehandles.h @@ -26,6 +26,7 @@ struct AfsHandle ULONG filesize; // size of file in bytes ULONG dirpos; // current position for ExamineAll struct Volume *volume; // the volume the handle refers to + struct DosList *volumenode; }; #endif diff --git a/rom/devs/filesys/afs/filehandles1.c b/rom/devs/filesys/afs/filehandles1.c index a721b9178..38eb3de0b 100644 --- a/rom/devs/filesys/afs/filehandles1.c +++ b/rom/devs/filesys/afs/filehandles1.c @@ -291,23 +291,39 @@ void addHandle(struct AfsHandle *ah) { } /* remove handle from locklist */ -void remHandle(struct AfsHandle *ah) { -struct AfsHandle *old; +void remHandle(struct AFSBase *afsbase, struct AfsHandle *ah) { +struct AfsHandle *old = NULL; - if (ah->volume->locklist==ah) + D(bug("[afs 0x%08lX] Removing handle 0x%08lX\n", ah->volume, ah)); + if (ah->volume->volumenode == ah->volumenode) { + D(bug("[afs 0x%08lX] Lock's volume is online\n", ah->volume)); + if (ah->volume->locklist==ah) ah->volume->locklist=ah->next; - else - { + else old=ah->volume->locklist; - while (old) - { - if (old->next==ah) - { - old->next=ah->next; - return; - } - old=old->next; + } +#ifdef __AROS__ + else { + D(bug("[afs 0x%08lX] Lock's volume is offline\n", ah->volume)); + if (ah->volumenode->dol_misc.dol_volume.dol_LockList == ah) + if (ah->next) + ah->volumenode->dol_misc.dol_volume.dol_LockList = ah->next; + else { + D(bug("[afs 0x%08lX] Last lock removed, removing VolumeNode\n", ah->volume)); + remDosNode(afsbase, ah->volumenode); } + else + old = ah->volumenode->dol_misc.dol_volume.dol_LockList; + } +#endif + while (old) + { + if (old->next==ah) + { + old->next=ah->next; + return; + } + old=old->next; } } @@ -358,6 +374,7 @@ struct AfsHandle *ah; ah->current.offset = 0; ah->filesize = OS_BE2LONG(fileblock->buffer[BLK_BYTE_SIZE(volume)]); ah->volume = volume; + ah->volumenode = volume->volumenode; addHandle(ah); } else @@ -581,7 +598,7 @@ ULONG fileblocknum = -1; void closef(struct AFSBase *afsbase, struct AfsHandle *ah) { D(bug("[afs] closef(%lu)\n",ah->header_block)); - remHandle(ah); + remHandle(afsbase, ah); FreeMem(ah,sizeof(struct AfsHandle)); } diff --git a/rom/devs/filesys/afs/filehandles3.c b/rom/devs/filesys/afs/filehandles3.c index ae7231867..7e8fb3e73 100644 --- a/rom/devs/filesys/afs/filehandles3.c +++ b/rom/devs/filesys/afs/filehandles3.c @@ -4,7 +4,7 @@ */ #ifndef DEBUG -#define DEBUG 1 +#define DEBUG 0 #endif #include diff --git a/rom/devs/filesys/afs/main.c b/rom/devs/filesys/afs/main.c index 629d35604..8f00ec645 100644 --- a/rom/devs/filesys/afs/main.c +++ b/rom/devs/filesys/afs/main.c @@ -34,11 +34,17 @@ static VOID startFlushTimer(struct AFSBase *afsbase) struct timerequest *request; /* Set up delay for next flush */ - request = afsbase->timer_request; - request->tr_node.io_Command = TR_ADDREQUEST; - request->tr_time.tv_secs = 1; - request->tr_time.tv_micro = 0; - SendIO((struct IORequest *)afsbase->timer_request); + if (afsbase->timer_flags & TIMER_ACTIVE) { + afsbase->timer_flags |= TIMER_RESTART; + } else { + D(bug("[afs] Starting timer\n")); + request = afsbase->timer_request; + request->tr_node.io_Command = TR_ADDREQUEST; + request->tr_time.tv_secs = 1; + request->tr_time.tv_micro = 0; + SendIO((struct IORequest *)afsbase->timer_request); + afsbase->timer_flags = TIMER_ACTIVE; + } } /******************************************* @@ -54,13 +60,17 @@ LONG retval; afsbase->port.mp_SigBit = SIGBREAKB_CTRL_F; afsbase->port.mp_Flags = PA_SIGNAL; - startFlushTimer(afsbase); + afsbase->timer_flags = 0; for (;;) { while ((iofs=(struct IOFileSys *)GetMsg(&afsbase->port))!=NULL) { /* Flush dirty blocks on all volumes */ if (iofs->IOFS.io_Message.mn_Node.ln_Type == NT_REPLYMSG) { + afsbase->timer_flags &= ~TIMER_ACTIVE; + if (afsbase->timer_flags & TIMER_RESTART) + startFlushTimer(afsbase); + else { struct Volume *volume, *tail; struct BlockCache *blockbuffer; @@ -78,14 +88,20 @@ LONG retval; writeBlock(afsbase, volume, blockbuffer, -1); blockbuffer->flags &= ~BCF_WRITE; } + if (volume->ioh.flags & IOHF_MOTOR_OFF) { + D(bug("[afs 0x%08lX] turning off motor\n", volume)); + motorOff(afsbase, &volume->ioh); + volume->ioh.flags &= ~IOHF_MOTOR_OFF; + } } volume = (struct Volume *)volume->ln.ln_Succ; } - startFlushTimer(afsbase); + } } else { - D(bug("[afs] got command %lu\n",iofs->IOFS.io_Command)); + DB2(bug("[afs] got command %lu\n",iofs->IOFS.io_Command)); + startFlushTimer(afsbase); error=0; afshandle = (struct AfsHandle *)iofs->IOFS.io_Unit; switch (iofs->IOFS.io_Command) @@ -144,6 +160,9 @@ LONG retval; iofs->io_Union.io_INHIBIT.io_Inhibit ); break; + case FSA_CLOSE : + closef(afsbase, afshandle); + break; default: if (mediumPresent(&afshandle->volume->ioh)) { @@ -158,9 +177,6 @@ LONG retval; iofs->io_Union.io_OPEN.io_FileMode ); break; - case FSA_CLOSE : - closef(afsbase, afshandle); - break; case FSA_READ : iofs->io_Union.io_READ.io_Length=readf ( @@ -348,7 +364,6 @@ LONG retval; switch (iofs->IOFS.io_Command) { case FSA_OPEN : /* locateObject, findupdate, findinput */ - case FSA_CLOSE : case FSA_READ : case FSA_WRITE : case FSA_SEEK : diff --git a/rom/devs/filesys/afs/misc.c b/rom/devs/filesys/afs/misc.c index 64a31d5f8..2f8f9167e 100644 --- a/rom/devs/filesys/afs/misc.c +++ b/rom/devs/filesys/afs/misc.c @@ -83,7 +83,7 @@ LONG getDiskInfo(struct Volume *volume, struct InfoData *id) { id->id_NumBlocksUsed = volume->usedblockscount; id->id_BytesPerBlock = volume->dosflags==0 ? BLOCK_SIZE(volume)-24 : BLOCK_SIZE(volume); id->id_DiskType = volume->dostype | volume->dosflags; - id->id_VolumeNode = 0; /* I think this is useless in AROS */ + id->id_VolumeNode = volume->volumenode; id->id_InUse = (LONG)TRUE; /* if we are here the device should be in use! */ return 0; } @@ -97,12 +97,12 @@ LONG getDiskInfo(struct Volume *volume, struct InfoData *id) { Output: 0 = no error ********************************************/ LONG inhibit(struct AFSBase *afsbase, struct Volume *volume, ULONG forbid) { - D(bug("[FFS] inhibit(%ld)\n", forbid)); + D(bug("[afs 0x%08lX] inhibit(%ld)\n", volume, forbid)); if (forbid) { if (volume->inhibitcounter++ == 0) { - D(bug("[FFS] inhibiting\n")); + D(bug("[afs 0x%08lX] inhibiting\n", volume)); /* if (exclusiveLocks(&volume->locklist)) return DOSFALSE; */ if (mediumPresent(&volume->ioh)) { @@ -115,10 +115,10 @@ LONG inhibit(struct AFSBase *afsbase, struct Volume *volume, ULONG forbid) { { if (--volume->inhibitcounter == 0) { - D(bug("[FFS] uninhibiting\n")); + D(bug("[afs 0x%08lX] uninhibiting\n", volume)); if (diskPresent(afsbase, &volume->ioh)) { - D(bug("[FFS] media inserted\n")); + D(bug("[afs 0x%08lX] media inserted\n", volume)); newMedium(afsbase, volume); volume->ioh.ioflags |= IOHF_DISK_IN; } diff --git a/rom/devs/filesys/afs/mmakefile.src b/rom/devs/filesys/afs/mmakefile.src index 0c77864c0..65c33df48 100644 --- a/rom/devs/filesys/afs/mmakefile.src +++ b/rom/devs/filesys/afs/mmakefile.src @@ -20,11 +20,10 @@ else FILES := endif -#MM- workbench-fs-complete : workbench-fs-afs -#MM- workbench-fs-afs : includes linklibs +#MM- kernel-fs-afs : includes linklibs USER_CFLAGS := -DDEBUG=0 -%build_module mmake=workbench-fs-afs \ +%build_module mmake=kernel-fs-afs \ modname=afs modtype=device modsuffix=handler \ files="arosdevice $(FILES)" uselibs="arosc" diff --git a/rom/devs/filesys/afs/os.h b/rom/devs/filesys/afs/os.h index d1157eeda..2eff379b5 100644 --- a/rom/devs/filesys/afs/os.h +++ b/rom/devs/filesys/afs/os.h @@ -19,6 +19,7 @@ struct Volume; LONG osMediumInit(struct AFSBase *, struct Volume *, struct BlockCache *); void osMediumFree(struct AFSBase *, struct Volume *, LONG); +void remDosNode(struct AFSBase *afsbase, struct DosList *dl); LONG readDisk(struct AFSBase *, struct Volume *, ULONG, ULONG, APTR); LONG writeDisk(struct AFSBase *, struct Volume *, ULONG, ULONG, APTR); UBYTE diskPresent(struct AFSBase *, struct IOHandle *); diff --git a/rom/devs/filesys/afs/os_aros_support.c b/rom/devs/filesys/afs/os_aros_support.c index 82c3027a8..b998c30aa 100644 --- a/rom/devs/filesys/afs/os_aros_support.c +++ b/rom/devs/filesys/afs/os_aros_support.c @@ -136,10 +136,15 @@ char string[32]; BSTR bname; UBYTE i; + if (volume->volumenode) { + D(bug("[afs 0x%08lX] VolumeNode is already present!\n", volume)); + return DOSTRUE; + } bname = volume->devicelist.dl_Name; for (i=0; idol_Ext.dol_AROS.dol_Device, dl->dol_Ext.dol_AROS.dol_Unit)); if ((dl->dol_Ext.dol_AROS.dol_Device == volume->device) && (dl->dol_Ext.dol_AROS.dol_Unit == NULL)) { @@ -154,6 +160,7 @@ UBYTE i; { dl->dol_Ext.dol_AROS.dol_Unit = (struct Unit *)&volume->ah; volume->locklist = dl->dol_misc.dol_volume.dol_LockList; + dl->dol_misc.dol_volume.dol_LockList = NULL; } } else @@ -166,6 +173,7 @@ UBYTE i; /* if not create a new doslist */ if (dl == NULL) { + D(bug("[afs 0x%08lX] Creating new VolumeNode\n", volume)); doslist = MakeDosEntry(string,DLT_VOLUME); if (doslist == NULL) return DOSFALSE; @@ -180,7 +188,9 @@ UBYTE i; AddDosEntry(doslist); /* if we re-use "volume" clear locklist */ volume->locklist = NULL; + dl = doslist; } + volume->volumenode = dl; //SendEvent(afsbase, IECLASS_DISKINSERTED); return DOSTRUE; } @@ -192,8 +202,6 @@ UBYTE i; set dol_LockList Input : volume - volume to remove Output: - - Note : displays a message if volume couldn't - be found in the system ********************************************/ void remDosVolume(struct AFSBase *afsbase, struct Volume *volume) { struct DosList *doslist; @@ -202,42 +210,36 @@ BSTR bname; char string[32]; UBYTE i; - //SendEvent(afsbase, IECLASS_DISKREMOVED); - if (volume->dostype == 0x444F5300) - { - bname = volume->devicelist.dl_Name; - if (bname != NULL) + dl = volume->volumenode; + if (dl) { + if (volume->locklist != NULL) { - for (i=0; ilocklist != NULL) - { - dl->dol_misc.dol_volume.dol_LockList = volume->locklist; - dl->dol_Ext.dol_AROS.dol_Unit = NULL; - } - else - { - D(bug("[afs] Removing\n")); - RemDosEntry(dl); - FreeDosEntry(dl); - } - } - else - showText(afsbase, "doslist not in chain"); - UnLockDosList(LDF_WRITE | LDF_VOLUMES); - } + D(bug("[afs 0x%08lX] VolumeNode in use, keeping as offline\n", volume)); + dl->dol_misc.dol_volume.dol_LockList = volume->locklist; + dl->dol_Ext.dol_AROS.dol_Unit = NULL; + } + else + { + D(bug("[afs 0x%08lX] Removing VolumeNode\n", volume)); + remDosNode(afsbase, dl); } + volume->volumenode = NULL; } } +/******************************************* + Name : remDosNode + Descr.: removes a DOS volume node + Input : dl - volume to remove + Output: - +********************************************/ +void remDosNode(struct AFSBase *afsbase, struct DosList *dl) +{ + RemDosEntry(dl); + FreeDosEntry(dl); +// SendEvent(afsbase, IECLASS_DISKREMOVED); +} + LONG osMediumInit (struct AFSBase *afsbase, struct Volume *volume, struct BlockCache *block) { @@ -352,8 +354,6 @@ UBYTE diskPresent(struct AFSBase *afsbase, struct IOHandle *ioh) { return ioh->ioreq->iotd_Req.io_Actual == 0; } -int timercode(struct Custom *, struct IOHandle *, APTR, struct ExecBase *); - struct IOHandle *openBlockDevice(struct AFSBase *afsbase, struct IOHandle *ioh) { @@ -367,11 +367,7 @@ struct IOHandle *openBlockDevice(struct AFSBase *afsbase, struct IOHandle *ioh) ioh->cmdwrite = CMD_WRITE; ioh->cmdseek = TD_SEEK; ioh->cmdformat = TD_FORMAT; - ioh->vbl_int.is_Code = (void(*)())&timercode; - ioh->vbl_int.is_Data = ioh; ioh->afsbase = afsbase; - if (StrCmp(ioh->blockdevice, "trackdisk.device")) - ioh->ioflags |= IOHF_TRACKDISK; if (diskPresent(afsbase, ioh)) ioh->ioflags |= IOHF_DISK_IN; checkAddChangeInt(afsbase, ioh); @@ -408,19 +404,17 @@ struct IOHandle *ioh; while (volume->ln.ln_Succ != NULL) { ioh = &volume->ioh; - if (ioh->ioflags & IOHF_MOTOR_OFF) - { - motorOff(afsbase, ioh); - ioh->ioflags &= ~IOHF_MOTOR_OFF; - } - else if ((ioh->ioflags & IOHF_MEDIA_CHANGE) && (!volume->inhibitcounter)) + if ((ioh->ioflags & IOHF_MEDIA_CHANGE) && (!volume->inhibitcounter)) { + D(bug("[afs 0x%08lX] Media change signalled\n", volume)); if (diskPresent(afsbase, ioh)) { if (!(ioh->ioflags & IOHF_DISK_IN)) { - if (!volume->inhibitcounter) + if (!volume->inhibitcounter) { + D(bug("[afs 0x%08lX] Media inserted\n", volume)); newMedium(afsbase, volume); + } ioh->ioflags |= IOHF_DISK_IN; } } @@ -510,7 +504,6 @@ BOOL flush(struct AFSBase *afsbase, struct Volume *volume) { volume->ioh.ioreq->iotd_Req.io_Command = CMD_UPDATE; DoIO((struct IORequest *)&volume->ioh.ioreq->iotd_Req); clearCache(afsbase, volume->blockcache); - /* turn off motor */ return DOSTRUE; } @@ -543,12 +536,7 @@ UQUAD offset; ioh->ioreq->iotd_Req.io_Offset = 0xFFFFFFFF & offset; ioh->ioreq->iotd_Req.io_Actual = offset>>32; retval = DoIO((struct IORequest *)&ioh->ioreq->iotd_Req); - if (ioh->ioflags & IOHF_TRACKDISK) - { - ioh->moff_time = 100; - if (ioh->moff_time <= 0) - AddIntServer(INTB_VERTB, &ioh->vbl_int); - } + ioh->flags |= IOHF_MOTOR_OFF; } else { @@ -566,7 +554,7 @@ BOOL retry = TRUE; while (retry) { - D(bug("[afs] readDisk: reading blocks %lu to %lu\n", start, start+count-1)); + DB2(bug("[afs] readDisk: reading blocks %lu to %lu\n", start, start+count-1)); result = readwriteDisk(afsbase, volume, start, count, data, volume->ioh.cmdread); if (result == 0) retry = FALSE; @@ -583,7 +571,7 @@ BOOL retry = TRUE; while (retry) { - D(bug("[afs] writeDisk: writing blocks %lu to %lu\n", start, start+count-1)); + DB2(bug("[afs] writeDisk: writing blocks %lu to %lu\n", start, start+count-1)); result = readwriteDisk(afsbase, volume, start, count, data, volume->ioh.cmdwrite); if (result == 0) retry = FALSE; @@ -596,27 +584,6 @@ BOOL retry = TRUE; #undef SysBase -AROS_UFH4(int, timercode, - AROS_UFHA(struct Custom *, custom, A0), - AROS_UFHA(struct IOHandle *, ioh, A1), - AROS_UFHA(APTR, is_Code, A5), - AROS_UFHA(struct ExecBase *, SysBase, A6)) -{ - AROS_USERFUNC_INIT - if (--ioh->moff_time == 0) - { - ioh->ioflags |= IOHF_MOTOR_OFF; - Signal - ( - ioh->afsbase->port.mp_SigTask, - 1<afsbase->port.mp_SigBit - ); - RemIntServer(INTB_VERTB, &ioh->vbl_int); - } - return 0; - AROS_USERFUNC_EXIT -} - AROS_UFH3(VOID, changeIntCode, AROS_UFHA(struct IOHandle *, ioh, A1), AROS_UFHA(APTR, is_Code, A5), diff --git a/rom/devs/filesys/afs/os_aros_support.h b/rom/devs/filesys/afs/os_aros_support.h index 8a009aca6..acf46938e 100644 --- a/rom/devs/filesys/afs/os_aros_support.h +++ b/rom/devs/filesys/afs/os_aros_support.h @@ -40,14 +40,13 @@ struct IOHandle { UWORD cmdwrite; UWORD cmdseek; UWORD cmdformat; - UBYTE moff_time; }; #define IOHF_MOTOR_OFF (1<<0) #define IOHF_MEDIA_CHANGE (1<<1) #define IOHF_DISK_IN (1<<2) -#define IOHF_TRACKDISK (1<<3) void checkDeviceFlags(struct AFSBase *); +void motorOff(struct AFSBase *afsbase, struct IOHandle *ioh); #endif diff --git a/rom/devs/filesys/afs/os_unix_support.c b/rom/devs/filesys/afs/os_unix_support.c index 9689d949f..76c2f6178 100644 --- a/rom/devs/filesys/afs/os_unix_support.c +++ b/rom/devs/filesys/afs/os_unix_support.c @@ -152,6 +152,11 @@ void osMediumFree(struct AFSBase *afsbase, struct Volume *volume, LONG all) { printf("%s: Don't know what to do here\n", __FUNCTION__); } +void remDosNode(struct AFSBase *afsbase, struct DosList *dl) +{ + printf("%s: Don't know what to do here\n", __FUNCTION__); +} + /********************************* OS Functions *****************************/ /* exec */ void *AllocMem(ULONG size, ULONG flags) { diff --git a/rom/devs/filesys/afs/os_unix_support.h b/rom/devs/filesys/afs/os_unix_support.h index 6f9f25dd7..2228b8be8 100644 --- a/rom/devs/filesys/afs/os_unix_support.h +++ b/rom/devs/filesys/afs/os_unix_support.h @@ -30,6 +30,7 @@ typedef short BOOL; struct AFSBase {}; struct Device {}; struct DeviceList {}; +struct DosList {}; struct DriveGeometry {}; struct Interrupt {}; struct List {}; diff --git a/rom/devs/filesys/afs/volumes.h b/rom/devs/filesys/afs/volumes.h index 95b7daa54..1d92dcc83 100644 --- a/rom/devs/filesys/afs/volumes.h +++ b/rom/devs/filesys/afs/volumes.h @@ -14,6 +14,7 @@ struct Volume { struct Node ln; struct Device *device; /* the handler this volume uses */ struct DeviceList devicelist; + struct DosList *volumenode; ULONG SizeBlock; /* Block size in words */ struct AfsHandle *locklist; -- 2.11.4.GIT