2 Copyright © 1995-2011, The AROS Development Team. All rights reserved.
10 #include <dos/dosextens.h>
11 #include <intuition/intuition.h>
12 #include <exec/ports.h>
13 #include <aros/debug.h>
15 #define CATCOMP_NUMBERS
17 #include "dos_intern.h"
20 /*****************************************************************************
23 #include <proto/dos.h>
25 AROS_LH4(BOOL
, ErrorReport
,
28 AROS_LHA(LONG
, code
, D1
),
29 AROS_LHA(LONG
, type
, D2
),
30 AROS_LHA(IPTR
, arg1
, D3
),
31 AROS_LHA(struct MsgPort
*, device
, D4
),
34 struct DosLibrary
*, DOSBase
, 80, Dos
)
37 Displays a requester with Retry/Cancel buttons for an error.
38 IoErr() is set to "code".
42 code -- The error to put up the requester for
43 type -- Type of request
45 REPORT_LOCK -- arg1 is a lock (BPTR).
46 REPORT_FH -- arg1 is a filehandle (BPTR).
47 REPORT_VOLUME -- arg1 is a volumenode (C pointer).
48 REPORT_INSERT -- arg1 is the string for the volumename
50 arg1 -- Argument according to type (see above)
51 device -- Optional handler task address (obsolete!)
54 DOSFALSE - user has selected "Retry"
55 DOSTRUE - user has selected "Cancel" or code wasn't understood or
56 pr_WindowPtr is -1 or if an attempt to open the requester fails.
68 *****************************************************************************/
72 struct Process
*me
= (struct Process
*) FindTask(NULL
);
74 BOOL want_volume
= FALSE
;
75 BOOL want_device
= FALSE
;
76 STRPTR volname
= NULL
;
77 STRPTR devname
= NULL
;
78 struct DeviceList
*dl
= NULL
;
86 struct MsgPort
*msgport
;
87 struct PacketHelperStruct phs
;
89 ASSERT_VALID_PROCESS(me
);
91 /* do nothing if errors are disabled */
92 if (me
->pr_WindowPtr
== (APTR
) -1) {
98 /* first setup the error format and work out which args we need */
100 /* Volume FOO: is not validated */
101 case ERROR_DISK_NOT_VALIDATED
:
102 format
= DosGetString(MSG_STRING_DISK_NOT_VALIDATED
);
106 /* Volume FOO: is write protected */
107 case ERROR_DISK_WRITE_PROTECTED
:
108 format
= DosGetString(MSG_STRING_DISK_WRITE_PROTECTED
);
112 /* Please (insert|replace) volume FOO: in ... */
113 case ERROR_DEVICE_NOT_MOUNTED
:
114 if (type
== REPORT_INSERT
) {
115 format
= DosGetString(MSG_STRING_DEVICE_NOT_MOUNTED_INSERT
);
118 else if (type
== REPORT_STREAM
) {
119 format
= DosGetString(MSG_STRING_DEVICE_NOT_MOUNTED_REPLACE_TARGET
);
120 want_volume
= want_device
= TRUE
;
123 format
= DosGetString(MSG_STRING_DEVICE_NOT_MOUNTED_REPLACE
);
126 idcmp
= IDCMP_DISKINSERTED
;
129 /* Volume FOO: is full */
130 case ERROR_DISK_FULL
:
131 format
= DosGetString(MSG_STRING_DISK_FULL
);
135 /* Not a DOS disk in ...*/
136 case ERROR_NOT_A_DOS_DISK
:
137 format
= DosGetString(MSG_STRING_NOT_A_DOS_DISK
);
141 /* No disk present in ...*/
143 format
= DosGetString(MSG_STRING_NO_DISK
);
147 /* You MUST replace volume FOO: in ... */
149 format
= DosGetString(MSG_STRING_ABORT_BUSY
);
150 want_volume
= want_device
= TRUE
;
151 idcmp
= IDCMP_DISKINSERTED
;
154 /* Volume FOO: has a read/write error */
155 case ABORT_DISK_ERROR
:
156 format
= DosGetString(MSG_STRING_ABORT_DISK_ERROR
);
160 /* do nothing with other errors */
165 /* now we need to determine the volume name. if they gave it to use
166 * (REPORT_INSERT), we just use it. otherwise, we get it from the device
167 * list (REPORT_VOLUME). if we don't have one, we use the handler/unit
172 if (arg1
== (IPTR
)NULL
)
174 msgport
= ((struct FileHandle
*) BADDR(arg1
))->fh_Type
;
175 dl
= (struct DeviceList
*)BADDR(dopacket1(DOSBase
, NULL
, msgport
, ACTION_CURRENT_VOLUME
, ((struct FileHandle
*) BADDR(arg1
))->fh_Arg1
));
177 volname
= (char*)BADDR(dl
->dl_Name
) + 1;
181 /* XXX what is this? */
187 struct FileInfoBlock
*fib
= AllocDosObject(DOS_FIB
, 0);
190 /* if they provided a lock, just use it */
191 if (arg1
!= (IPTR
)NULL
) {
192 msgport
= ((struct FileLock
*) BADDR(arg1
))->fl_Task
;
196 if (dopacket2(DOSBase
, NULL
, msgport
, ACTION_EXAMINE_OBJECT
, arg1
, (SIPTR
)MKBADDR(fib
))) {
198 strncpy(buf
, fib
->fib_FileName
, sizeof (buf
) - 1);
199 buf
[sizeof(buf
) - 1] = 0;
201 FreeDosObject(DOS_FIB
, fib
);
208 /* a volume, ie a DeviceList */
210 if (arg1
== (IPTR
)NULL
)
213 dl
= (struct DeviceList
*) arg1
;
214 volname
= (char*)BADDR(dl
->dl_Name
) + 1;
215 msgport
= dl
->dl_Task
;
218 /* raw volume name */
220 if (arg1
== (IPTR
)NULL
)
222 if (!getpacketinfo(DOSBase
, (STRPTR
)arg1
, &phs
))
225 volname
= (STRPTR
) arg1
;
226 /* rip off any trailing stuff, if its there */
227 if (SplitName(volname
, ':', buf
, 0, sizeof(buf
)-1) == -1)
229 freepacketinfo(DOSBase
, &phs
);
232 /* do nothing with other types */
237 /* for the device name we need the doslist entry */
239 /* XXX for packets we just search the doslist for a DLT_DEVICE with
240 * the same task pointer. no need to worry about multiple units */
242 /* remember the current error in case we have to bail out */
245 /* get the entry for the volume */
246 if ((dvp
= GetDeviceProc(volname
, NULL
)) == NULL
) {
251 /* search the list for a device node with the same port as the volume */
252 dol
= LockDosList(LDF_READ
| LDF_ALL
);
253 while (dol
!= NULL
&& (dol
->dol_Type
!= DLT_DEVICE
|| dol
->dol_Task
!= msgport
))
254 dol
= BADDR(dol
->dol_Next
);
258 devname
= (char*)dol
->dol_Name
+ 1;
260 /* XXX can this happen? */
264 UnLockDosList(LDF_READ
| LDF_ALL
);
269 /* have all we need, now to build the arg array */
275 else if (want_device
)
278 /* display it. idcmp is set further up to catch "disk insert" events if
279 * we're waiting for them to insert something */
281 res
= DisplayError(format
, idcmp
, &args
);
285 return res
== 0 ? DOSFALSE
: DOSTRUE
;