added concrete implementations of putc(), getc(), getchar() and gets()
[tangerine.git] / workbench / c / Mount.c
blob85667f6c4a6f479c6f9440c6692d166027ee6218
1 /*
2 sc link debug=line idir=include: nostackcheck opt data=far nostartup mountnew.c exit
3 (C) 1995-2001 AROS - The Amiga Research OS
4 (C) 2002-2005 Harry Sintonen
5 (C) 2005-2007 Pavel Fedin
6 $Id$
8 Desc: Mount CLI command
9 Lang: English
12 /******************************************************************************
14 NAME
16 Mount
18 USAGE
20 Mount <Device> <From>
22 SYNOPSIS
24 DEVICE/M, FROM/K
26 LOCATION
28 Sys:C
30 FUNCTION
32 Loads and mounts a device
34 INPUTS
36 DEVICE -- The device type to be mounted
37 FROM -- Search device in this mountlist
39 RESULT
41 Standard DOS error codes.
43 NOTES
45 EXAMPLE
47 Mount DEVS:FAT0
48 (Mounts a FAT device defined on SYS:Devs/FAT0 file)
50 BUGS
52 SEE ALSO
54 INTERNALS
56 HISTORY
58 ******************************************************************************/
60 #include <exec/devices.h>
61 #include <exec/io.h>
62 #include <exec/memory.h>
63 #include <exec/semaphores.h>
64 #include <exec/types.h>
65 #include <dos/dosextens.h>
66 #include <dos/exall.h>
67 #include <dos/filehandler.h>
68 #include <dos/rdargs.h>
69 #include <libraries/configvars.h>
70 #include <libraries/expansion.h>
71 #include <workbench/workbench.h>
72 #include <workbench/startup.h>
74 #include <proto/exec.h>
75 #include <proto/dos.h>
76 #include <proto/intuition.h>
77 #include <proto/utility.h>
78 #include <proto/icon.h>
79 #include <proto/expansion.h>
81 #ifndef __SASC
82 #ifdef __AROS__
83 #include <clib/arossupport_protos.h>
84 #else
85 #include <clib/debug_protos.h>
86 #endif
87 #else
88 typedef unsigned long IPTR;
89 #endif
91 #include <resources/filesysres.h>
92 #include <string.h>
93 #include <stdlib.h>
94 #include <stdio.h>
96 #define DEBUG_PATCHDOSNODE(x)
97 #define DEBUG_MOUNT(x)
98 #define DEBUG_MAKEDOSNODE(x)
99 #define DEBUG_CHECK(x)
101 #define MOUNTLIST "DEVS:MountList"
102 #define DOSDRIVERS "DEVS:DOSDrivers/"
103 #define STORAGEDRIVERS "SYS:Storage/DOSDrivers/"
104 #define PARAMSLENGTH (sizeof(struct DosEnvec) + sizeof(IPTR)*4)
106 enum
108 ERR_SPECIAL = 5000,
109 ERR_DEVICENOTFOUND,
110 ERR_INVALIDKEYWORD
113 const char *SearchTable[]=
116 "DEVS:DOSDrivers/",
117 #ifdef __MORPHOS__
118 "MOSSYS:DEVS/DOSDrivers/",
119 #endif
120 "SYS:Storage/DOSDrivers/",
121 #ifdef __MORPHOS__
122 "MOSSYS:Storage/DOSDrivers/",
123 #endif
124 NULL
128 * startup,control need to be handled differently.
131 enum
133 ARG_HANDLER,
134 ARG_EHANDLER,
135 ARG_FILESYSTEM,
136 ARG_DEVICE,
137 ARG_UNIT,
138 ARG_FLAGS,
139 ARG_BLOCKSIZE,
140 ARG_SURFACES,
141 ARG_BLOCKSPERTRACK,
142 ARG_SECTORSPERBLOCK,
143 ARG_RESERVED,
144 ARG_PREALLOC,
145 ARG_INTERLEAVE,
146 ARG_LOWCYL,
147 ARG_HIGHCYL,
148 ARG_BUFFERS,
149 ARG_BUFMEMTYPE,
150 ARG_MAXTRANSFER,
151 ARG_MASK,
152 ARG_BOOTPRI,
153 ARG_DOSTYPE,
154 ARG_BAUD,
155 ARG_CONTROL,
156 ARG_STACKSIZE,
157 ARG_PRIORITY,
158 ARG_GLOBVEC,
159 ARG_STARTUP,
160 ARG_ACTIVATE,
161 ARG_FORCELOAD,
162 NUM_ARGS
165 const UBYTE options[]=
166 "HANDLER/K,"
167 "EHANDLER/K,"
168 "FILESYSTEM/K,"
169 "DEVICE/K,"
170 "UNIT/K,"
171 "FLAGS/K,"
172 "SECTORSIZE=BLOCKSIZE/K,"
173 "SURFACES/K,"
174 "SECTORSPERTRACK=BLOCKSPERTRACK/K,"
175 "SECTORSPERBLOCK/K,"
176 "RESERVED/K,"
177 "PREALLOC/K,"
178 "INTERLEAVE/K,"
179 "LOWCYL/K,"
180 "HIGHCYL/K,"
181 "BUFFERS/K,"
182 "BUFMEMTYPE/K,"
183 "MAXTRANSFER/K,"
184 "MASK/K,"
185 "BOOTPRI/K,"
186 "DOSTYPE/K,"
187 "BAUD/K,"
188 "CONTROL/K,"
189 "STACKSIZE/K,"
190 "PRIORITY/K,"
191 "GLOBVEC/K,"
192 "STARTUP/K,"
193 "MOUNT=ACTIVATE/K,"
194 "FORCELOAD/K";
196 #ifdef __MORPHOS__
197 #define PROGNAME "Mount unofficial"
198 #define __stackparm __attribute__((varargs68k))
199 typedef struct Library *UtilityBase_t;
200 #else
201 #define PROGNAME "Mount"
202 typedef struct UtilityBase *UtilityBase_t;
203 #endif
205 #ifdef __PPC__
206 #define ARGS(ap) ap->overflow_arg_area
207 #else
208 #define ARGS(ap) (IPTR *)ap
209 #endif
211 #ifdef __AROS__
212 #define _WBenchMsg WBenchMsg
213 #endif
215 #ifdef AROS_FAST_BPTR
216 #define BSTR_EXTRA 1
217 #define BSTR_OFFSET 0
218 #define bstrcpy(dest, src, len) strcpy(dest, src)
219 #else
220 #define BSTR_EXTRA 2
221 #define BSTR_OFFSET 1
222 #define bstrcpy(dest, src, len) \
223 dest[0] = len; \
224 strcpy(&dest[1], src);
225 #endif
227 static const int __nocommandline;
228 const TEXT version[] = "\0$VER: " PROGNAME " 50.14 (10.1.2008)";
230 ULONG CheckDevice(char *name);
231 void InitParams(IPTR *params);
232 LONG readfile(STRPTR name, STRPTR *mem, LONG *size);
233 ULONG readmountlist(IPTR *params, STRPTR name, char *mountlist);
234 ULONG readmountfile(IPTR *params, STRPTR name);
235 void preparefile(STRPTR buf, LONG size);
236 LONG parsemountfile(IPTR *params, STRPTR buf, LONG size);
237 LONG parsemountlist(IPTR *params, STRPTR name, STRPTR buf, LONG size);
238 LONG mount(IPTR *params, STRPTR name);
239 void __stackparm ShowError(char *s, ...);
240 void ShowFault(LONG code, char *s, ...);
242 struct DosLibrary *DOSBase;
243 struct IntuitionBase *IntuitionBase;
244 UtilityBase_t UtilityBase;
245 struct Process *MyProcess;
247 ULONG StartupValue;
248 char *StartupString = NULL;
249 char *ControlString = NULL;
250 char *UnitString = NULL;
251 char *FlagsString = NULL;
252 ULONG StackSize;
253 ULONG Priority;
254 ULONG Activate;
255 int GlobalVec;
256 ULONG ForceLoad;
257 char *HandlerString;
258 char *DeviceString;
259 BOOL IsEHandler, IsFilesystem;
260 BOOL IsCli;
261 BOOL flagargs[NUM_ARGS];
262 extern struct WBStartup *_WBenchMsg;
264 int main(void)
266 STRPTR args[2];
267 IPTR *params;
268 LONG error = RETURN_FAIL;
269 struct RDArgs *rda;
270 char dirname[512];
272 if ((DOSBase = (struct DosLibrary *)OpenLibrary("dos.library",37))!=0)
274 if ((UtilityBase = (UtilityBase_t)OpenLibrary("utility.library",37)))
276 memset(&flagargs, 0, sizeof(flagargs));
277 IsEHandler = TRUE;
278 IsFilesystem = TRUE;
279 if (!_WBenchMsg)
281 memset(args,0,sizeof(args));
282 if ((rda = ReadArgs("DEVICE/M,FROM/K", (IPTR *)args, NULL)))
284 STRPTR *MyDevPtr;
285 int len;
287 error = 0;
289 MyDevPtr =(STRPTR *)args[0];
290 if (MyDevPtr)
292 while (*MyDevPtr)
294 DEBUG_MOUNT(Printf("Mount: Current DevName <%s>\n",
295 (ULONG)*MyDevPtr));
297 if ((params = AllocVec(PARAMSLENGTH, MEMF_PUBLIC | MEMF_CLEAR)))
299 StackSize = 8192;
300 Priority = 5;
301 GlobalVec = -1;
302 HandlerString = NULL;
303 DeviceString = NULL;
304 StartupString = NULL;
306 len = strlen(*MyDevPtr);
307 if ((*MyDevPtr)[len-1] == ':')
309 /* search for a devicename */
310 DEBUG_MOUNT(Printf("Mount: search for devname <%s>\n",
311 (ULONG)*MyDevPtr));
313 strcpy(dirname, *MyDevPtr);
314 dirname[len-1] = '\0';
316 if ((error=CheckDevice(dirname))!=RETURN_OK)
318 DEBUG_MOUNT(Printf("Mount: is already mounted..stop\n"));
320 else
322 if (args[1])
324 error=readmountlist(params, dirname, args[1]);
325 DEBUG_MOUNT(Printf("Mount: readmountlist(%s) returned %ld\n", args[1], error));
327 else
329 char **SearchPtr;
330 ULONG slen;
332 DEBUG_MOUNT(Printf("Mount: search device definition <%s>\n",
333 (ULONG)*MyDevPtr));
334 for (SearchPtr=(char**) SearchTable;
335 *SearchPtr;
336 SearchPtr++)
338 if(SetSignal(0L,SIGBREAKF_CTRL_C) & SIGBREAKF_CTRL_C)
340 error = RETURN_FAIL;
341 SetIoErr(ERROR_BREAK);
342 break;
345 slen = strlen(*SearchPtr);
346 strcpy(dirname, *SearchPtr);
347 dirname[slen] = '\0';
348 strcat(dirname, *MyDevPtr);
349 dirname[slen+len-1] = '\0';
350 DEBUG_MOUNT(Printf("Mount: try File <%s>\n", (ULONG)dirname));
352 error=readmountfile(params, dirname);
353 DEBUG_MOUNT(Printf("Mount: readmountfile returned %ld\n", error));
354 if (error != ERROR_OBJECT_NOT_FOUND)
355 break;
357 if (error == ERROR_OBJECT_NOT_FOUND)
359 DEBUG_MOUNT(Printf("Mount: try from mountlist\n"));
360 dirname[0] = '\0';
361 strcat(dirname, *MyDevPtr);
362 dirname[len-1] = '\0';
363 error=readmountlist(params, dirname, MOUNTLIST);
364 DEBUG_MOUNT(Printf("Mount: readmountlist(default) returned %ld\n", error));
369 else
371 /* search for a filename */
373 LONG err;
375 UBYTE stack_ap[sizeof(struct AnchorPath) + 3];
376 struct AnchorPath *MyAp = (struct AnchorPath *) (((ULONG) stack_ap + 3) & ~3);
378 DEBUG_MOUNT(Printf("Mount: search for mountfile <%s>\n",
379 (ULONG)*MyDevPtr));
381 memset(MyAp,0,sizeof(struct AnchorPath));
383 dirname[0] = '\0';
384 for (err = MatchFirst(*MyDevPtr,MyAp);
385 err == 0;
386 err = MatchNext(MyAp))
388 if (MyAp->ap_Flags & APF_DirChanged)
390 DEBUG_MOUNT(Printf("Mount: Changed directories...\n"));
393 if (NameFromLock(MyAp->ap_Current->an_Lock,
394 dirname,
395 sizeof(dirname)) == FALSE)
397 ShowFault(IoErr(), "Error on NameFromLock");
398 break;
400 if (AddPart(dirname,
401 &(MyAp->ap_Info.fib_FileName[0]),
402 sizeof(dirname)) == FALSE)
404 ShowFault(IoErr(), "Error on AddPart");
405 break;
407 if (MyAp->ap_Info.fib_DirEntryType > 0)
409 if (MyAp->ap_Flags & APF_DIDDIR)
411 DEBUG_MOUNT(Printf("Mount: Ascending from directory %s\n",
412 (ULONG)dirname));
414 else
416 DEBUG_MOUNT(Printf("Mount: The next dir is ... %s\n", (ULONG)dirname));
418 /* clear the completed directory flag */
419 MyAp->ap_Flags &= ~APF_DIDDIR;
422 else
424 /* Here is code for handling each particular file */
426 DEBUG_MOUNT(Printf("Mount: try File <%s>\n",
427 (ULONG)dirname));
429 memset(&flagargs, 0, sizeof(flagargs));
430 IsEHandler = TRUE;
431 IsFilesystem = TRUE;
432 error=readmountfile(params, dirname);
433 DEBUG_MOUNT(Printf("Mount: readmount file returned %ld\n", error));
436 /* This absolutely, positively must be called, all of the time. */
437 MatchEnd(MyAp);
439 if (err == ERROR_NO_MORE_ENTRIES)
441 SetIoErr(0);
443 else
445 /* if it was real error promote it - Piru */
446 error = err;
449 FreeVec(params);
451 else
453 error = ERROR_NO_FREE_STORE;
454 break;
456 MyDevPtr++;
459 FreeArgs(rda);
460 } /* if (rda != NULL) */
461 else
463 error = IoErr();
466 if (error && error != ERROR_NO_MORE_ENTRIES && error < ERR_SPECIAL)
468 ShowFault(error, "ERROR");
470 error = RETURN_FAIL;
472 else
474 error = error < ERR_SPECIAL ? RETURN_OK : RETURN_FAIL;
478 else
480 /* wb startup */
481 if (_WBenchMsg->sm_NumArgs >= 2)
483 if ((params = AllocVec(PARAMSLENGTH,
484 MEMF_PUBLIC | MEMF_CLEAR)))
486 int i;
488 for (i = 1; i < _WBenchMsg->sm_NumArgs; i++)
490 BPTR olddir;
492 DEBUG_MOUNT(kprintf("Mount: try File <%s>\n",
493 (ULONG) _WBenchMsg->sm_ArgList[i].wa_Name));
495 olddir = CurrentDir(_WBenchMsg->sm_ArgList[i].wa_Lock);
497 error=readmountfile(params, _WBenchMsg->sm_ArgList[i].wa_Name);
498 DEBUG_MOUNT(kprintf("Mount: readmountfile returned %ld\n", error));
499 if (error && error != ERROR_NO_MORE_ENTRIES && error < ERR_SPECIAL)
500 ShowFault(error, "ERROR");
502 (void) CurrentDir(olddir);
505 FreeVec(params);
507 else
509 error = ERROR_NO_FREE_STORE;
513 CloseLibrary((struct Library *)UtilityBase);
515 CloseLibrary((struct Library *)DOSBase);
518 return error;
521 /************************************************************************************************/
522 /************************************************************************************************/
523 ULONG CheckDevice(char *name)
525 struct DosList *dl;
526 ULONG Status;
528 DEBUG_CHECK(Printf("CheckDevice: <%s>\n",
529 name));
531 dl = LockDosList(LDF_DEVICES | LDF_VOLUMES | LDF_ASSIGNS | LDF_READ);
532 if ((dl = FindDosEntry(dl,name,LDF_DEVICES | LDF_VOLUMES | LDF_ASSIGNS)))
534 Status = ERROR_OBJECT_EXISTS;
536 else
538 Status = 0;
540 UnLockDosList(LDF_DEVICES | LDF_VOLUMES | LDF_ASSIGNS | LDF_READ);
542 DEBUG_CHECK(Printf("CheckDevice: object %sexist\n", Status ? "does" : "doesn't "));
544 return Status;
547 /************************************************************************************************/
548 /************************************************************************************************/
550 void InitParams(IPTR *params)
552 struct DosEnvec *vec;
554 memset(params,0, PARAMSLENGTH);
556 vec = (struct DosEnvec *)&params[4];
558 vec->de_TableSize = DE_BOOTBLOCKS;
559 vec->de_SizeBlock = 512 >> 2;
560 vec->de_Surfaces = 2;
561 vec->de_SectorPerBlock = 1;
562 vec->de_BlocksPerTrack = 11;
563 vec->de_Reserved = 2;
565 /* memset above
566 vec->de_SecOrg = 0;
567 vec->de_BootBlocks = 0;
568 vec->de_BootPri = 0;
569 vec->de_PreAlloc = 0;
570 vec->de_Interleave = 0;
571 vec->de_LowCyl = 0;
574 vec->de_HighCyl = 79;
575 vec->de_NumBuffers = 20; /* On AmigaOS 3.9 it's 5 */
576 vec->de_BufMemType = 3;
577 vec->de_Baud = 1200;
578 vec->de_MaxTransfer = 0x7fffffff;
579 vec->de_Mask = 0xfffffffe;
580 vec->de_DosType = ID_DOS_DISK;
582 StackSize = 8192;
583 Priority = 5;
584 GlobalVec = -1;
585 HandlerString = NULL;
586 DeviceString = NULL;
587 StartupString = NULL;
590 void FreeStuff(void)
592 if (UnitString)
594 FreeVec(UnitString);
595 UnitString = NULL;
597 if (FlagsString)
599 FreeVec(FlagsString);
600 FlagsString = NULL;
602 if (ControlString)
604 FreeVec(ControlString);
605 ControlString = NULL;
607 if (HandlerString)
609 FreeVec(HandlerString);
610 HandlerString = NULL;
612 if (DeviceString)
614 FreeVec(DeviceString);
615 DeviceString = NULL;
617 if (StartupString)
619 FreeVec(StartupString);
620 StartupString = NULL;
624 /************************************************************************************************/
625 /************************************************************************************************/
627 ULONG GetValue(char *buf, char **end)
629 int base;
630 char *c = buf;
632 /* I decided to leave this routine in order to prevent reading numbers starting from '0'
633 as octal. Probably this is not needed, or octal support would not do any harm, in this
634 case this routine is not needed at all - Pavel Fedin */
635 if ((c[0]=='-') || (c[1]=='+'))
636 c++;
637 if ((c[0] == '0') && (((c[1])=='x') || (c[1])=='X'))
638 base = 16;
639 else
640 base = 10;
641 return strtol(buf,end,base);
642 /* Left for reference - Pavel Fedin
643 ULONG Value;
644 ULONG Sign;
645 Value = 0;
646 Sign = 1;
647 if (buf[0]=='-')
649 Sign = -1;
650 buf++;
652 else
653 if (buf[0]=='+')
655 buf++;
658 if ((buf[0] == '0') && (((buf[1])=='x') || (buf[1])=='X'))
660 int num;
662 // base = hex
663 buf+=2;
664 while(*buf)
666 Value<<=4;
667 num=*buf++;
669 if((num >= 0x30) && (num <= 0x39))
671 num-=0x30;
672 Value+=num;
674 else
676 num |= 0x20;
678 if((num >= 0x61) && (num <= 0x66))
680 num-=(0x61-10);
681 Value+=num;
686 else
688 // base = dev
689 Value=atoi(buf);
691 return Value * Sign;
695 /************************************************************************************************/
696 /************************************************************************************************/
698 ULONG ReadMountArgs(IPTR *params, struct RDArgs *rda)
700 struct DosEnvec *vec;
701 STRPTR args[NUM_ARGS];
702 struct RDArgs *MyRDA;
703 ULONG result = RETURN_OK;
704 int i;
705 char *s = NULL;
707 DEBUG_MOUNT(Printf("ReadMountArgs:\n%s\n\n",(ULONG)&rda->RDA_Source.CS_Buffer[rda->RDA_Source.CS_CurChr]));
709 memset(&args, 0, sizeof(args));
711 if (!(MyRDA = ReadArgs((STRPTR)options, (IPTR *)args, rda)))
713 DEBUG_MOUNT(Printf("ReadMountArgs: ReadArgs failed\n"));
714 DEBUG_MOUNT(PrintFault(IoErr(),"ReadMountArgs"));
715 //return (ULONG) IoErr();
716 return ERR_INVALIDKEYWORD;
719 for (i = 0; i < NUM_ARGS; i++)
721 if (args[i] != NULL)
723 flagargs[i] = TRUE;
727 if (args[ARG_HANDLER] != NULL)
729 s = (STRPTR)args[ARG_HANDLER];
730 IsEHandler = FALSE;
731 IsFilesystem = FALSE;
733 else if (args[ARG_EHANDLER] != NULL)
735 s = (STRPTR)args[ARG_EHANDLER];
736 IsEHandler = TRUE;
737 IsFilesystem = FALSE;
739 else if (args[ARG_FILESYSTEM] != NULL)
741 s = (STRPTR)args[ARG_FILESYSTEM];
742 IsEHandler = TRUE;
743 IsFilesystem = TRUE;
744 } else
745 s = NULL;
746 if (s)
748 int len;
749 DEBUG_MOUNT(Printf("ReadMountArgs: Handler <%s>\n",s));
750 len = strlen(s);
751 if (HandlerString)
753 FreeVec(HandlerString);
755 if ((HandlerString = AllocVec(len + BSTR_EXTRA, MEMF_PUBLIC|MEMF_CLEAR)))
757 bstrcpy(HandlerString, s, len);
760 if (args[ARG_STACKSIZE] != NULL)
762 StackSize = GetValue(args[ARG_STACKSIZE], NULL);
765 if (args[ARG_PRIORITY] != NULL)
767 Priority = GetValue(args[ARG_PRIORITY], NULL);
770 if (args[ARG_GLOBVEC] != NULL)
772 GlobalVec = GetValue(args[ARG_GLOBVEC], NULL);
775 if (args[ARG_FORCELOAD] != NULL)
777 ForceLoad = GetValue((STRPTR)args[ARG_FORCELOAD], NULL);
780 if (args[ARG_ACTIVATE] != NULL)
782 Activate = GetValue(args[ARG_ACTIVATE], NULL);
785 if (args[ARG_DEVICE] != NULL)
787 int len;
789 DEBUG_MOUNT(Printf("ReadMountArgs: Device <%s>\n",args[ARG_DEVICE]));
791 len = strlen((STRPTR)args[ARG_DEVICE]);
793 if (DeviceString)
795 FreeVec(DeviceString);
797 if ((DeviceString = AllocVec(len+1,MEMF_PUBLIC|MEMF_CLEAR)))
799 //Printf("copying...\n");
801 strcpy(DeviceString, args[ARG_DEVICE]);
805 if (args[ARG_UNIT] != NULL)
807 if (UnitString)
809 FreeVec(UnitString);
810 UnitString = NULL;
812 params[2] = GetValue(args[ARG_UNIT], &s);
813 if (*s)
815 int len;
817 len = strlen(args[ARG_UNIT]);
819 DEBUG_MOUNT(Printf("ReadMountArgs: len %ld\n",len));
821 if ((UnitString = AllocVec(len + 1, MEMF_PUBLIC|MEMF_CLEAR)))
823 strcpy(UnitString, args[ARG_UNIT]);
824 params[2] = (IPTR)UnitString;
825 DEBUG_MOUNT(Printf("ReadMountArgs: Unit String <%s>\n", (STRPTR)params[2]));
827 else
829 result = ERROR_NO_FREE_STORE;
830 goto error;
833 else
834 DEBUG_MOUNT(Printf("ReadMountArgs: Unit Value %ld\n",params[2]));
836 if (args[ARG_FLAGS] != NULL)
838 // char *String;
840 DEBUG_MOUNT(Printf("ReadMountArgs: Flags <%s>\n",args[ARG_FLAGS]));
841 if (FlagsString)
843 FreeVec(FlagsString);
844 FlagsString = NULL;
847 String = args[ARG_FLAGS];
849 if ((*String >= 0x30) && (*String <= 0x39))
851 params[3] = GetValue(String);
852 DEBUG_MOUNT(Printf("ReadMountArgs: Flag Value %ld\n",params[3]));
854 else
856 params[3] = GetValue(args[ARG_FLAGS], &s);
857 if (*s)
859 int len;
861 len = strlen(args[ARG_FLAGS]);
863 DEBUG_MOUNT(Printf("ReadMountArgs: len %ld\n",len));
865 if ((FlagsString = AllocVec(len + 1, MEMF_PUBLIC|MEMF_CLEAR)))
867 strcpy(FlagsString, args[ARG_FLAGS]);
868 params[3] = (IPTR) FlagsString;
869 DEBUG_MOUNT(Printf("ReadMountArgs: Flags String <%s>\n",(STRPTR)params[3]));
871 else
873 result = ERROR_NO_FREE_STORE;
874 goto error;
877 else
878 DEBUG_MOUNT(Printf("ReadMountArgs: Flag Value %ld\n",params[3]));
881 vec = (struct DosEnvec *)&params[4];
883 if (args[ARG_BLOCKSIZE] != NULL)
885 vec->de_SizeBlock = GetValue(args[ARG_BLOCKSIZE], NULL) >> 2;
887 if (args[ARG_SURFACES] != NULL)
889 vec->de_Surfaces = GetValue(args[ARG_SURFACES], NULL);
891 if (args[ARG_SECTORSPERBLOCK] != NULL)
893 vec->de_SectorPerBlock = GetValue(args[ARG_SECTORSPERBLOCK], NULL);
895 if (args[ARG_BLOCKSPERTRACK] != NULL)
897 vec->de_BlocksPerTrack = GetValue(args[ARG_BLOCKSPERTRACK], NULL);
899 if (args[ARG_RESERVED] != NULL)
901 vec->de_Reserved = GetValue(args[ARG_RESERVED], NULL);
903 if (args[ARG_PREALLOC] != NULL)
905 vec->de_PreAlloc = GetValue(args[ARG_PREALLOC], NULL);
907 if (args[ARG_INTERLEAVE] != NULL)
909 vec->de_Interleave = GetValue(args[ARG_INTERLEAVE], NULL);
911 if (args[ARG_LOWCYL] != NULL)
913 vec->de_LowCyl = GetValue(args[ARG_LOWCYL], NULL);
915 if (args[ARG_HIGHCYL] != NULL)
917 vec->de_HighCyl = GetValue(args[ARG_HIGHCYL], NULL);
919 if (args[ARG_BUFFERS] != NULL)
921 vec->de_NumBuffers = GetValue(args[ARG_BUFFERS], NULL);
923 if (args[ARG_BUFMEMTYPE] != NULL)
925 vec->de_BufMemType = GetValue(args[ARG_BUFMEMTYPE], NULL);
927 if (args[ARG_BOOTPRI] != NULL)
929 vec->de_BootPri = GetValue(args[ARG_BOOTPRI], NULL);
931 if (args[ARG_BAUD] != NULL)
933 vec->de_Baud = GetValue(args[ARG_BAUD], NULL);
935 if (args[ARG_MAXTRANSFER] != NULL)
937 vec->de_MaxTransfer = GetValue(args[ARG_MAXTRANSFER], NULL);
939 if (args[ARG_MASK] != NULL)
941 vec->de_Mask = GetValue(args[ARG_MASK], NULL);
944 if (args[ARG_DOSTYPE] != NULL)
946 vec->de_DosType = (IPTR)GetValue(args[ARG_DOSTYPE], NULL);
949 if (args[ARG_CONTROL] != NULL)
951 int len;
952 DEBUG_MOUNT(Printf("ReadMountArgs: Control <%s>\n",args[ARG_CONTROL]));
953 if (ControlString)
955 FreeVec(ControlString);
956 ControlString = NULL;
958 len = strlen(args[ARG_CONTROL]);
959 if (len < 0x100)
961 if ((ControlString=AllocVec(len + BSTR_EXTRA, MEMF_PUBLIC|MEMF_CLEAR)))
963 bstrcpy(ControlString, args[ARG_CONTROL], len);
964 vec->de_Control = (IPTR)MKBADDR((char*)ControlString);
966 else
968 ShowError("Unable to allocate Control string");
969 result = ERROR_NO_FREE_STORE;
970 goto error;
973 else
975 result = ERROR_LINE_TOO_LONG;
976 SetIoErr(result);
977 // ShowError("Control string too long");
978 goto error;
982 if (args[ARG_STARTUP] != NULL)
984 // char *String;
986 DEBUG_MOUNT(Printf("ReadMountArgs: Startup <%s>\n",args[ARG_STARTUP]));
987 if (StartupString)
989 FreeVec(StartupString);
990 StartupString = NULL;
993 String = args[ARG_STARTUP];
994 if ((*String >= 0x30) && (*String <= 0x39))
996 StartupValue = GetValue(String);
998 else
1000 StartupValue = GetValue(args[ARG_STARTUP], &s);
1001 if (*s)
1003 int len;
1005 len = strlen(args[ARG_STARTUP]);
1007 DEBUG_MOUNT(Printf("ReadMountArgs: len %ld\n",len));
1009 if ((StartupString = AllocVec(len + 1, MEMF_PUBLIC|MEMF_CLEAR)))
1011 strcpy(StartupString,args[ARG_STARTUP]);
1013 else
1015 result = ERROR_NO_FREE_STORE;
1016 goto error;
1021 error:
1022 FreeArgs(MyRDA);
1024 return result;
1027 /************************************************************************************************/
1028 /************************************************************************************************/
1030 ULONG readmountlist(IPTR *params,
1031 STRPTR name,
1032 char *mountlist)
1034 STRPTR MountListBuf;
1035 LONG MountListBufSize;
1036 ULONG error;
1038 DEBUG_MOUNT(Printf("ReadMountList: find <%s> in mountlist <%s>\n",
1039 name,
1040 mountlist));
1042 error = readfile(mountlist,
1043 &MountListBuf,
1044 &MountListBufSize);
1045 if (error==RETURN_OK)
1047 preparefile(MountListBuf,
1048 MountListBufSize);
1051 InitParams(params);
1053 if ((error=parsemountlist(params,
1054 name,
1055 MountListBuf,
1056 MountListBufSize))==RETURN_OK)
1058 if ((error = mount(params,name))!=RETURN_OK)
1060 DEBUG_MOUNT(Printf("ReadMountList: mount failed error %ld\n",
1061 error));
1064 else
1066 switch (error)
1068 case ERR_DEVICENOTFOUND:
1069 case ERR_INVALIDKEYWORD:
1070 ShowError("Device '%s:' not found in file '%s'", name, mountlist);
1071 break;
1075 FreeStuff();
1076 FreeVec(MountListBuf);
1078 return error;
1081 /************************************************************************************************/
1082 /************************************************************************************************/
1084 ULONG readmountfile(IPTR *params, STRPTR filename)
1086 struct Library *IconBase;
1087 struct DiskObject *diskobj;
1088 char **myargv;
1089 STRPTR MountListBuf;
1090 LONG MountListBufSize;
1091 struct RDArgs rda;
1092 ULONG error = RETURN_FAIL;
1093 UBYTE *nameptr;
1094 int toollen;
1095 BOOL mountinfo=FALSE;
1096 char name[256+1];
1098 DEBUG_MOUNT(Printf("ReadMountFile: <%s>\n", (ULONG)filename));
1101 struct Process *me = (APTR) FindTask(NULL);
1102 APTR oldwinptr;
1103 BPTR lock;
1105 name[0] = '\0';
1107 oldwinptr = me->pr_WindowPtr;
1108 me->pr_WindowPtr = (APTR) -1;
1109 lock = Lock(filename, SHARED_LOCK);
1110 if (lock)
1112 struct FileInfoBlock fib;
1113 if (Examine(lock, &fib))
1115 nameptr = fib.fib_FileName;
1116 memmove(name, nameptr, strlen(nameptr) + 1);
1118 UnLock(lock);
1120 me->pr_WindowPtr = oldwinptr;
1122 if (name[0] == '\0')
1124 nameptr = FilePart(filename);
1125 strcpy(name,
1126 nameptr);
1130 DEBUG_MOUNT(Printf("ReadMountFile: mount <%s>\n", (ULONG)name));
1132 if ((error=CheckDevice(name))!=RETURN_OK)
1134 return error;
1137 InitParams(params);
1139 DEBUG_MOUNT(Printf("ReadMountFile: readfile\n"));
1141 error = readfile(filename,
1142 &MountListBuf,
1143 &MountListBufSize);
1144 if (error==RETURN_OK)
1146 DEBUG_MOUNT(Printf("ReadMountFile: preparsefile\n"));
1147 preparefile(MountListBuf, MountListBufSize);
1150 DEBUG_MOUNT(Printf("ReadMountFile: parsemountfile\n"));
1151 if ((error = parsemountfile(params, MountListBuf, MountListBufSize))!=RETURN_OK)
1153 DEBUG_MOUNT(Printf("ReadMountFile: parsemountfile error %ld\n", error));
1154 ShowFault(IoErr(), "Mountfile '%s' is invalid", filename);
1156 else
1158 mountinfo = TRUE;
1160 FreeVec(MountListBuf);
1162 else
1164 DEBUG_MOUNT(Printf("ReadMountFile: mountfile not found..search for <%s.info>\n",
1165 filename));
1168 if ((error==RETURN_OK) ||
1169 (error==ERROR_OBJECT_NOT_FOUND))
1171 DEBUG_MOUNT(Printf("ReadMountFile: look for icon\n"));
1173 if ((IconBase = OpenLibrary("icon.library", 37)))
1175 if ((diskobj = GetDiskObject(filename)))
1177 myargv =(char**) diskobj->do_ToolTypes;
1178 if (myargv)
1180 while (*myargv)
1182 char *ToolPtr;
1183 ToolPtr = *myargv;
1184 DEBUG_MOUNT(Printf("ReadMountFile: ToolType <%s>\n",
1185 ToolPtr));
1186 if ((ToolPtr[0] != '(') && (ToolPtr[0] != '*') &&
1187 !((ToolPtr[0] == 'I') && (ToolPtr[1] == 'M') && (ToolPtr[3] == '=')))
1189 char *ToolString;
1190 toollen = strlen(ToolPtr);
1191 if ((ToolString = AllocVec(toollen + 2,MEMF_ANY)))
1193 memcpy(ToolString,ToolPtr,toollen);
1194 ToolString[toollen] = '\n';
1195 ToolString[toollen+1] = '\0';
1196 memset(&rda,0,sizeof(struct RDArgs));
1197 rda.RDA_Source.CS_Buffer = ToolString;
1198 rda.RDA_Source.CS_Length = toollen+1;
1199 rda.RDA_Source.CS_CurChr = 0;
1200 rda.RDA_Flags = RDAF_NOPROMPT;
1201 if ((ReadMountArgs(params, &rda)==RETURN_OK))
1203 mountinfo = TRUE;
1205 else
1207 DEBUG_MOUNT(Printf("ReadMountFile: ReadArgs failed error %ld\n",
1208 error));
1210 FreeVec(ToolString);
1212 else
1214 error = ERROR_NO_FREE_STORE;
1215 break;
1218 else
1220 DEBUG_MOUNT(Printf("ReadMountFile: skipped\n"));
1222 myargv++;
1225 FreeDiskObject(diskobj);
1227 else
1230 CloseLibrary(IconBase);
1234 if (mountinfo)
1236 DEBUG_MOUNT(Printf("ReadMountFile: mount information exists\n"));
1238 if ((error = mount(params,name)) != RETURN_OK)
1240 DEBUG_MOUNT(Printf("ReadMountFile: mount failed error %ld\n",
1241 error));
1245 FreeStuff();
1247 return error;
1250 /************************************************************************************************/
1251 /************************************************************************************************/
1254 LONG readfile(STRPTR name, STRPTR *mem, LONG *size)
1256 BPTR ml;
1257 ULONG rest,sub;
1258 STRPTR buf;
1259 struct Process *me = (struct Process *) FindTask(NULL);
1260 APTR oldwinptr;
1262 oldwinptr = me->pr_WindowPtr;
1263 me->pr_WindowPtr = (APTR) -1;
1264 ml = Open(name, MODE_OLDFILE);
1265 me->pr_WindowPtr = oldwinptr;
1267 DEBUG_MOUNT(Printf("ReadFile: <%s>\n", (LONG) name));
1269 if (ml)
1271 if (Seek(ml, 0, OFFSET_END) != -1)
1273 *size = Seek(ml, 0, OFFSET_BEGINNING);
1275 if (*size != -1)
1277 *mem = (STRPTR)AllocVec(*size+2, MEMF_ANY);
1279 if (*mem)
1281 rest = *size;
1282 buf = *mem;
1284 for (;;)
1286 if (!rest)
1288 Close(ml);
1290 *buf++ = '\n';
1291 *buf = '\0';
1293 return 0;
1296 sub = Read(ml, buf, rest);
1298 if (sub == -1)
1300 break;
1303 rest -= sub;
1304 buf += sub;
1307 FreeVec(*mem);
1309 else
1311 SetIoErr(ERROR_NO_FREE_STORE);
1316 Close(ml);
1319 DEBUG_MOUNT(Printf("ReadFile: error %ld\n", IoErr()));
1320 return IoErr();
1323 /************************************************************************************************/
1324 /************************************************************************************************/
1327 void preparefile(STRPTR buf, LONG size)
1329 STRPTR end = buf + size;
1331 while (buf < end)
1333 /* Convert comments to spaces */
1334 if (buf + 1 < end && *buf == '/' && buf[1] == '*')
1336 *buf++ = ' ';
1337 *buf++ = ' ';
1339 while (buf < end)
1341 if (*buf == '*')
1343 *buf++ = ' ';
1345 if (buf >= end)
1347 break;
1350 if (*buf == '/')
1352 *buf++ = ' ';
1353 break;
1356 else
1358 *buf++=' ';
1362 continue;
1365 /* Skip strings */
1366 if (*buf=='\"')
1369 * skip first
1371 buf++;
1372 while (buf < end && *buf != '\"')
1374 buf++;
1377 * skip last "
1379 buf++;
1380 continue;
1383 /* Convert '\n' and ';' to spaces */
1384 if (*buf == '\n' || *buf == ';')
1386 *buf++ = ' ';
1387 continue;
1390 /* Convert '#' to \n */
1391 if (*buf == '#')
1393 *buf++ = '\n';
1394 continue;
1397 /* Skip all other characters */
1398 buf++;
1402 /************************************************************************************************/
1403 /************************************************************************************************/
1405 struct FileSysEntry *GetFileSysEntry(ULONG DosType)
1408 struct FileSysResource *MyFileSysRes;
1409 struct FileSysEntry *MyFileSysEntry;
1410 struct FileSysEntry *CurrentFileSysEntry;
1412 MyFileSysEntry = NULL;
1413 MyFileSysRes = OpenResource(FSRNAME);
1414 if (MyFileSysRes)
1416 Forbid();
1417 CurrentFileSysEntry = (struct FileSysEntry*) MyFileSysRes->fsr_FileSysEntries.lh_Head;
1418 while (CurrentFileSysEntry->fse_Node.ln_Succ)
1420 if (CurrentFileSysEntry->fse_DosType == DosType)
1422 if (MyFileSysEntry)
1424 if (CurrentFileSysEntry->fse_Version > MyFileSysEntry->fse_Version)
1426 MyFileSysEntry = CurrentFileSysEntry;
1429 else
1431 MyFileSysEntry = CurrentFileSysEntry;
1434 CurrentFileSysEntry =(struct FileSysEntry*) CurrentFileSysEntry->fse_Node.ln_Succ;
1436 Permit();
1438 return MyFileSysEntry;
1441 /************************************************************************************************/
1442 /************************************************************************************************/
1445 void PatchDosNode(struct DeviceNode *MyDeviceNode,
1446 ULONG DosType)
1448 struct FileSysEntry *MyFileSysEntry;
1449 ULONG MyPatchFlags;
1451 DEBUG_PATCHDOSNODE(Printf("MakeDosNode: DeviceNode 0x%lx\n",
1452 (ULONG)MyDeviceNode));
1454 if ((MyFileSysEntry=GetFileSysEntry(DosType)))
1456 MyPatchFlags = MyFileSysEntry->fse_PatchFlags;
1458 DEBUG_PATCHDOSNODE(Printf("PatchDosNode: FileSysEntry 0x%lx PatchFlags 0x%lx\n",
1459 (ULONG)MyFileSysEntry,
1460 MyPatchFlags));
1462 if (MyPatchFlags)
1464 ULONG *PatchDeviceNode;
1465 ULONG *PatchDeviceNodeEnd;
1466 ULONG *PatchFileSysEntry;
1468 PatchFileSysEntry =(ULONG*) &MyFileSysEntry->fse_Type;
1469 PatchDeviceNode =(ULONG*) &MyDeviceNode->dn_Type;
1470 PatchDeviceNodeEnd =(ULONG*) ((ULONG) MyDeviceNode + sizeof(struct DeviceNode));
1472 while (MyPatchFlags)
1474 if (MyPatchFlags & 1)
1476 *PatchDeviceNode = *PatchFileSysEntry;
1478 PatchDeviceNode++;
1479 PatchFileSysEntry++;
1481 if (PatchDeviceNode >= PatchDeviceNodeEnd)
1483 /* Savety */
1484 break;
1487 MyPatchFlags >>= 1;
1491 else
1493 /* Mount with no BootNode */
1494 DEBUG_PATCHDOSNODE(Printf("PatchDosNode: Can't get FileSysEntry..no bootnode\n"));
1499 /************************************************************************************************/
1500 /************************************************************************************************/
1504 #define DOSNAME_INDEX 0
1505 #define EXECNAME_INDEX 1
1506 #define UNIT_INDEX 2
1507 #define FLAGS_INDEX 3
1508 #define ENVIROMENT_INDEX 4
1510 struct DeviceNode *MyMakeDosNode(char *DosName, IPTR *ParameterPkt, char *StartupName)
1512 int DosNameSize;
1513 int ExecNameSize;
1514 int MyEnvSize = 0;
1515 struct DeviceNode *MyDeviceNode = NULL;
1516 struct FileSysStartupMsg *MyFileSysStartupMsg = NULL;
1517 struct DosEnvec *MyDosEnvec = NULL;
1518 char *MyString = NULL;
1519 ULONG Status = FALSE;
1520 DEBUG_MAKEDOSNODE(Printf("MakeDosNode: Pkt 0x%lx\n",(IPTR)ParameterPkt));
1522 if (ParameterPkt)
1524 DEBUG_MAKEDOSNODE(Printf("MakeDosNode: DosName <%s> DeviceName <%s> Unit ", DosName, ParameterPkt[EXECNAME_INDEX]));
1525 DEBUG_MAKEDOSNODE(if (UnitString)
1526 Printf("<%s>",ParameterPkt[UNIT_INDEX]);
1527 else
1528 Printf("%ld",ParameterPkt[UNIT_INDEX]);)
1529 DEBUG_MAKEDOSNODE(Printf(" Flags 0x%lx DE_TABLESIZE 0x%lx\n", ParameterPkt[FLAGS_INDEX], ParameterPkt[ENVIROMENT_INDEX]));
1531 else
1533 DEBUG_MAKEDOSNODE(Printf("MakeDosNode: DosName <%s> Startup <%s>\n", (IPTR)DosName, (IPTR)StartupName));
1536 DosNameSize = strlen(DosName);
1538 if (ParameterPkt)
1540 if (ParameterPkt[EXECNAME_INDEX])
1542 ExecNameSize = strlen((UBYTE *)ParameterPkt[EXECNAME_INDEX]);
1544 else
1546 ExecNameSize = 0;
1548 MyEnvSize = (ParameterPkt[ENVIROMENT_INDEX] + 1) * sizeof(IPTR);
1550 else
1552 ExecNameSize = StartupName ? strlen(StartupName) : 0;
1555 if ((MyDeviceNode = AllocVec(sizeof(struct DeviceNode), MEMF_PUBLIC | MEMF_CLEAR)))
1557 DEBUG_MAKEDOSNODE(Printf("MakeDosNode: MyDeviceNode 0x%lx\n", (ULONG)MyDeviceNode));
1559 MyDeviceNode->dn_StackSize = 600;
1560 MyDeviceNode->dn_Priority = 10;
1562 if ((MyString=AllocVec(((DosNameSize + BSTR_EXTRA + 4) & ~3) + ((ExecNameSize + BSTR_EXTRA + 4) & ~3), MEMF_PUBLIC | MEMF_CLEAR)))
1564 bstrcpy(MyString, DosName, DosNameSize);
1566 MyDeviceNode->dn_Name = MKBADDR(MyString);
1568 if (ParameterPkt)
1570 if ((MyFileSysStartupMsg = AllocVec(sizeof(struct FileSysStartupMsg), MEMF_PUBLIC | MEMF_CLEAR)))
1572 DEBUG_MAKEDOSNODE(Printf("MakeDosNode: MyFileSysStartupMsg 0x%lx\n", (IPTR)MyFileSysStartupMsg));
1574 if ((MyDosEnvec = AllocVec(MyEnvSize, MEMF_PUBLIC | MEMF_CLEAR)))
1576 char *ExecNamePtr;
1578 DEBUG_MAKEDOSNODE(Printf("MakeDosNode: MyDosEnvec 0x%lx\n", (IPTR)MyDosEnvec));
1579 ExecNamePtr = &MyString[(1 + DosNameSize + BSTR_EXTRA + 3) & ~3];
1581 /* .device name must absolutely **NOT** include the 0 in the
1582 * length!!
1584 * the string *MUST* be 0 terminated, however!
1586 if (ParameterPkt[EXECNAME_INDEX])
1588 bstrcpy(ExecNamePtr, (UBYTE *)ParameterPkt[EXECNAME_INDEX], ExecNameSize);
1590 else
1592 ExecNamePtr[0] = 0;
1593 #ifndef AROS_FAST_BPTR
1594 ExecNamePtr[1] = 0;
1595 #endif
1597 MyFileSysStartupMsg->fssm_Device = MKBADDR(ExecNamePtr);
1598 MyFileSysStartupMsg->fssm_Unit = ParameterPkt[UNIT_INDEX];
1599 MyFileSysStartupMsg->fssm_Flags = ParameterPkt[FLAGS_INDEX];
1600 MyFileSysStartupMsg->fssm_Environ = MKBADDR(MyDosEnvec);
1601 MyDeviceNode->dn_Startup = MKBADDR(MyFileSysStartupMsg);
1603 CopyMem(&ParameterPkt[ENVIROMENT_INDEX], MyDosEnvec, MyEnvSize);
1605 Status=TRUE;
1606 DEBUG_MAKEDOSNODE(Printf("MakeDosNode: done\n"));
1610 else
1612 if (StartupName && ExecNameSize)
1614 char *StartupNamePtr;
1616 StartupNamePtr = &MyString[(1 + DosNameSize + BSTR_EXTRA + 3) & ~3];
1617 bstrcpy(StartupNamePtr, StartupName, ExecNameSize);
1618 MyDeviceNode->dn_Startup = MKBADDR(StartupNamePtr);
1620 Status=TRUE;
1624 if (Status)
1626 DEBUG_MAKEDOSNODE(Printf("MakeDosNode: done\n"));
1627 return MyDeviceNode;
1629 else
1631 DEBUG_MAKEDOSNODE(Printf("MakeDosNode: failed\n"));
1632 FreeVec(MyFileSysStartupMsg);
1633 FreeVec(MyDeviceNode);
1634 FreeVec(MyString);
1635 return NULL;
1641 /************************************************************************************************/
1642 /************************************************************************************************/
1645 LONG parsemountfile(IPTR *params, STRPTR buf, LONG size)
1647 STRPTR args[NUM_ARGS];
1648 LONG error;
1649 struct RDArgs rda;
1651 DEBUG_MOUNT(Printf("ParseMountFile:\n"));
1653 memset(&args, 0, sizeof(args));
1654 memset(&rda,0,sizeof(struct RDArgs));
1656 rda.RDA_Source.CS_Buffer = buf;
1657 rda.RDA_Source.CS_Length = size;
1658 rda.RDA_Source.CS_CurChr = 0;
1659 rda.RDA_Flags = RDAF_NOPROMPT;
1661 DEBUG_MOUNT(Printf("ReadArgs..\n%s\n\n",(ULONG)rda.RDA_Source.CS_Buffer));
1663 if ((error=ReadMountArgs(params,
1664 &rda))!=RETURN_OK)
1666 DEBUG_MOUNT(Printf("Parse: ReadArgs failed\n"));
1668 return error;
1671 /************************************************************************************************/
1672 /************************************************************************************************/
1675 LONG parsemountlist(IPTR *params,
1676 STRPTR name,
1677 STRPTR buf,
1678 LONG size)
1680 STRPTR args[NUM_ARGS];
1681 UBYTE buffer[1024];
1682 LONG error=RETURN_OK, res;
1683 STRPTR end = buf + size;
1684 STRPTR s2;
1685 char *ptr;
1686 struct RDArgs rda;
1688 DEBUG_MOUNT(Printf("ParseMountList: <%s>\n",(ULONG)name));
1690 memset(&args,0,sizeof(args));
1691 memset(&rda,0,sizeof(struct RDArgs));
1693 rda.RDA_Source.CS_Buffer = buf;
1694 rda.RDA_Source.CS_Length = end - buf;
1695 rda.RDA_Source.CS_CurChr = 0;
1696 rda.RDA_Flags = RDAF_NOPROMPT;
1698 while (rda.RDA_Source.CS_CurChr < rda.RDA_Source.CS_Length)
1700 res = ReadItem(buffer, sizeof(buffer), &rda.RDA_Source);
1702 DEBUG_MOUNT(Printf("ParseMountList: buffer <%s>\n",(ULONG)buffer));
1703 DEBUG_MOUNT(Printf("ParseMountList: ReadItem res %ld\n",res));
1705 if (res == ITEM_ERROR)
1707 return IoErr();
1710 if (res == ITEM_NOTHING &&
1711 rda.RDA_Source.CS_CurChr == rda.RDA_Source.CS_Length)
1713 return 0;
1716 if (res != ITEM_QUOTED && res != ITEM_UNQUOTED)
1718 return 1;
1721 s2 = buffer;
1723 while (*s2)
1725 s2++;
1728 if (s2 == buffer || s2[-1] != ':')
1730 DEBUG_MOUNT(Printf("ParseMountList: failure\n"));
1731 return ERR_DEVICENOTFOUND;
1734 *--s2 = 0;
1736 if (!Strnicmp(name, buffer, s2 - buffer) &&
1737 (!name[s2 - buffer] || (name[s2 - buffer] == ':' || !name[s2 - buffer + 1])))
1739 DEBUG_MOUNT(Printf("ParseMountList: found\n"));
1741 /* Copy the string so we get proper case - Piru */
1742 memcpy(name, buffer, s2 - buffer);
1743 name[s2 - buffer] = '\0';
1745 ptr = name;
1746 while (*ptr)
1748 if (*ptr++ == ':')
1750 ptr[-1] = '\0';
1751 break;
1755 DEBUG_MOUNT(Printf("ReadArgs..\n%s\n\n",(ULONG)&rda.RDA_Source.CS_Buffer[rda.RDA_Source.CS_CurChr]));
1757 if ((error=ReadMountArgs(params,
1758 &rda))!=RETURN_OK)
1760 DEBUG_MOUNT(Printf("ParseMountList: ReadArgs failed\n"));
1761 //return IoErr();
1764 return error;
1767 while (rda.RDA_Source.CS_CurChr < rda.RDA_Source.CS_Length)
1769 if (rda.RDA_Source.CS_Buffer[rda.RDA_Source.CS_CurChr++] == '\n')
1771 DEBUG_MOUNT(Printf("ParseMountList: reach the end of the block\n"));
1772 break;
1777 DEBUG_MOUNT(Printf("ParseMountList: mount found nothing\n"));
1778 return ERR_DEVICENOTFOUND;
1781 /************************************************************************************************/
1782 /************************************************************************************************/
1784 LONG checkmount(IPTR *params)
1786 struct DosEnvec *vec;
1788 vec = (struct DosEnvec *)&params[4];
1790 params[1] = (IPTR) DeviceString;
1792 if (IsFilesystem && (!flagargs[ARG_DEVICE]
1793 || !flagargs[ARG_SURFACES] || !flagargs[ARG_BLOCKSPERTRACK]
1794 || !flagargs[ARG_LOWCYL] || !flagargs[ARG_HIGHCYL]))
1796 ShowError("Could not find some of the following keywords:\n"
1797 " Surfaces, BlocksPerTrack, LowCyl, HighCyl, Device");
1798 return ERR_INVALIDKEYWORD;
1800 /* bootpri -129 shouldn't be started and not automatic mounted..whatever that means */
1801 if ((vec->de_BootPri < -129) || (vec->de_BootPri > 127))
1803 ShowError("BootPri %ld is not allowed. Legal range is -128..127",vec->de_BootPri);
1804 return ERROR_BAD_NUMBER;
1807 if (flagargs[ARG_GLOBVEC])
1809 if ((GlobalVec != -1) && (GlobalVec != -2))
1811 ShowError("Globvec %ld is not supported. Only -1 and -2 are supported here", GlobalVec);
1812 return ERROR_BAD_NUMBER;
1816 if (flagargs[ARG_STARTUP] && !StartupString)
1818 if (StartupValue >= 0x100)
1820 ShowError("Startup uses a too large numerical number %ld",StartupValue);
1821 return ERROR_BAD_NUMBER;
1825 return RETURN_OK;
1828 /************************************************************************************************/
1829 /************************************************************************************************/
1831 LONG mount(IPTR *params, STRPTR name)
1833 struct DosEnvec *vec;
1834 LONG error = RETURN_OK;
1835 struct DeviceNode *dn;
1837 strupr(name);
1838 DEBUG_MOUNT(Printf("MountDev: <%s>\n",(ULONG)name));
1840 if ((error=checkmount(params))!=RETURN_OK)
1842 DEBUG_MOUNT(Printf("MountDev: checkmount failed\n"));
1843 return error;
1846 vec = (struct DosEnvec *)&params[4];
1848 DEBUG_MOUNT(Printf("MountDev: DosName <%s>\n",(ULONG)name));
1849 DEBUG_MOUNT(Printf("MountDev: Filesystem <%s>\n",(ULONG)HandlerString + BSTR_OFFSET));
1850 DEBUG_MOUNT(Printf("MountDev: Device <%s>\n",(ULONG)DeviceString));
1851 DEBUG_MOUNT(Printf("MountDev: TableSize %ld\n",vec->de_TableSize));
1852 DEBUG_MOUNT(Printf("MountDev: SizeBlock %ld\n",vec->de_SizeBlock));
1853 DEBUG_MOUNT(Printf("MountDev: SecOrg %ld\n",vec->de_SecOrg));
1854 DEBUG_MOUNT(Printf("MountDev: Surfaces %ld\n",vec->de_Surfaces));
1855 DEBUG_MOUNT(Printf("MountDev: SectorsPerBlock %ld\n",vec->de_SectorPerBlock));
1856 DEBUG_MOUNT(Printf("MountDev: BlocksPerTrack %ld\n",vec->de_BlocksPerTrack));
1857 DEBUG_MOUNT(Printf("MountDev: Reserved %ld\n",vec->de_Reserved));
1858 DEBUG_MOUNT(Printf("MountDev: PreAlloc %ld\n",vec->de_PreAlloc));
1859 DEBUG_MOUNT(Printf("MountDev: Interleave %ld\n",vec->de_Interleave));
1860 DEBUG_MOUNT(Printf("MountDev: LowCyl %ld\n",vec->de_LowCyl));
1861 DEBUG_MOUNT(Printf("MountDev: UpperCyl %ld\n",vec->de_HighCyl));
1862 DEBUG_MOUNT(Printf("MountDev: NumBuffers %ld\n",vec->de_NumBuffers));
1863 DEBUG_MOUNT(if (vec->de_TableSize >= DE_BUFMEMTYPE))
1864 DEBUG_MOUNT(Printf("MountDev: BufMemType 0x%lx\n",vec->de_BufMemType));
1865 DEBUG_MOUNT(Printf("MountDev: MaxTransfer 0x%lx\n",vec->de_MaxTransfer));
1866 DEBUG_MOUNT(if (vec->de_TableSize >= DE_MASK))
1867 DEBUG_MOUNT(Printf("MountDev: Mask 0x%lx\n",vec->de_Mask));
1868 DEBUG_MOUNT(if (vec->de_TableSize >= DE_BOOTPRI))
1869 DEBUG_MOUNT(Printf("MountDev: BootPri %ld\n",vec->de_BootPri));
1870 DEBUG_MOUNT(if (vec->de_TableSize >= DE_DOSTYPE))
1871 DEBUG_MOUNT(Printf("MountDev: DosType 0x%lx\n",vec->de_DosType));
1872 DEBUG_MOUNT(if (vec->de_TableSize >= DE_BAUD))
1873 DEBUG_MOUNT(Printf("MountDev: Baud %ld\n",vec->de_Baud));
1874 DEBUG_MOUNT(if (vec->de_TableSize >= DE_CONTROL))
1875 DEBUG_MOUNT(Printf("MountDev: Control 0x%lx\n",vec->de_Control));
1876 DEBUG_MOUNT(if (vec->de_TableSize >= DE_BOOTBLOCKS))
1877 DEBUG_MOUNT(Printf("MountDev: BootBlocks %ld\n",vec->de_BootBlocks));
1879 if ((dn=MyMakeDosNode(name, IsEHandler ? params : NULL, StartupString)))
1881 DEBUG_MOUNT(Printf("MountDev: DeviceNode 0x%lx\n",(ULONG)dn));
1883 dn->dn_StackSize = StackSize;
1884 dn->dn_Priority = Priority;
1885 dn->dn_GlobalVec = (BPTR)GlobalVec;
1887 if (!IsEHandler && !StartupString)
1889 dn->dn_Startup = (BPTR)StartupValue;
1892 if (IsFilesystem && ((ForceLoad==0) || (HandlerString==NULL)))
1894 DEBUG_MOUNT(Printf("MountDev: patchdosnode\n"));
1895 PatchDosNode(dn,vec->de_DosType);
1898 if (ForceLoad || dn->dn_SegList==NULL)
1900 DEBUG_MOUNT(Printf("MountDev: Load Handler\n"));
1901 dn->dn_Handler = MKBADDR(HandlerString);
1903 else
1906 * We don't need the HandlerString anymore...free it
1908 if (HandlerString)
1910 FreeVec(HandlerString);
1911 HandlerString = NULL;
1914 DEBUG_MOUNT(Printf("MountDev: Name %b\n",dn->dn_Name));
1915 DEBUG_MOUNT(Printf("MountDev: Handler 0x%lx <%b>\n",dn->dn_Handler,dn->dn_Handler));
1916 DEBUG_MOUNT(Printf("MountDev: SegList 0x%lx\n",dn->dn_SegList));
1917 DEBUG_MOUNT(Printf("MountDev: StackSize %ld\n",dn->dn_StackSize));
1918 DEBUG_MOUNT(Printf("MountDev: Priority %ld\n",dn->dn_Priority));
1919 if (!IsEHandler && StartupString)
1920 DEBUG_MOUNT(Printf("MountDev: Startup <%b>\n", dn->dn_Startup));
1921 else
1922 DEBUG_MOUNT(Printf("MountDev: Startup 0x%lx\n",dn->dn_Startup));
1923 DEBUG_MOUNT(Printf("MountDev: GlobalVec %ld\n",dn->dn_GlobalVec));
1925 if (dn->dn_SegList || dn->dn_Handler)
1927 if (AddDosEntry((struct DosList *)dn))
1929 DEBUG_MOUNT(Printf("MountDev: AddDosEntry worked\n"));
1931 * Don't free these anymore as they belong to the dosnode
1933 HandlerString = NULL;
1934 if (IsEHandler)
1936 UnitString = NULL;
1937 FlagsString = NULL;
1938 ControlString = NULL;
1940 if (Activate)
1942 DEBUG_MOUNT(Printf("Activating\n"));
1943 strcat(name, ":");
1944 DeviceProc(name);
1946 error = 0;
1948 else
1950 DEBUG_MOUNT(Printf("MountDev: AddDosEntry failed\n"));
1951 error = ERROR_INVALID_RESIDENT_LIBRARY;
1952 if (HandlerString)
1954 FreeVec(HandlerString);
1958 else
1960 DEBUG_MOUNT(Printf("MountDev: no loadseg and no handler specified\n"));
1961 error = ERROR_OBJECT_NOT_FOUND;
1964 else
1966 error = ERROR_NO_FREE_STORE;
1969 return error;
1972 void ShowError(char *s, ...)
1974 va_list ap;
1976 va_start(ap, s);
1977 if (IsCli)
1979 PutStr("ERROR: ");
1980 VPrintf(s, ARGS(ap));
1981 PutStr("\n");
1983 else
1985 struct EasyStruct es =
1987 sizeof(struct EasyStruct),
1989 "Mount Failure",
1991 "OK"
1994 IntuitionBase = (struct IntuitionBase *)OpenLibrary("intuition.library", 36);
1995 if (IntuitionBase)
1997 EasyRequestArgs(NULL, &es, NULL, ARGS(ap));
1998 CloseLibrary((struct Library *)IntuitionBase);
2001 va_end(ap);
2004 void ShowFault(LONG code, char *s, ...)
2006 char buf[256];
2007 va_list ap;
2008 int l;
2010 va_start(ap, s);
2011 l = vsnprintf(buf, sizeof(buf) - 2, s, ap);
2012 va_end(ap);
2013 strcpy(&buf[l], ": ");
2014 l += 2;
2015 Fault(code, NULL, &buf[l], sizeof(buf) - l);
2016 if (IsCli)
2018 PutStr(buf);
2019 PutStr("\n");
2021 else
2023 struct EasyStruct es =
2025 sizeof(struct EasyStruct),
2027 "Mount Failure",
2028 buf,
2029 "OK"
2032 IntuitionBase = (struct IntuitionBase *)OpenLibrary("intuition.library", 36);
2033 if (IntuitionBase)
2035 EasyRequestArgs(NULL, &es, NULL, NULL);
2036 CloseLibrary((struct Library *)IntuitionBase);