Workbook: Clean up icon layout and drawing
[AROS.git] / rom / dos / exit.c
blob69e97bb877cb8c584756bab89f4324eacf35ee15
1 /*
2 Copyright © 1995-2011, The AROS Development Team. All rights reserved.
3 $Id$
5 Desc:
6 Lang: English
7 */
9 #include <setjmp.h>
11 #include "dos_intern.h"
14 * On m68k exiting a program can be performed by setting SP
15 * to (FindTask(NULL)->pr_ReturnAddr - 4), and performing an rts.
17 * For the complete code, see arch/m68k-amiga/dos/exit.c and
18 * arch/m68k-amiga/dos/bcpl.S, "BCPL Exit"
20 * pr_ReturnAddr points to the actual stack size.
22 * Similar construction should work on all CPUs. I guess this is what
23 * is used by Exit() routine.
25 * For other CPUs we don't keep exact stack layout and consider it
26 * private. Only Exit() knows what to do with it. However we keep stack
27 * size value where it was, some code relies on it.
29 struct StackState
31 IPTR stackSize;
32 APTR stackLower;
33 APTR stackUpper;
34 ULONG retval;
35 jmp_buf state;
38 /*****************************************************************************
40 NAME */
41 #include <proto/dos.h>
43 AROS_LH1(void, Exit,
45 /* SYNOPSIS */
46 AROS_LHA(LONG, returnCode, D1),
48 /* LOCATION */
49 struct DosLibrary *, DOSBase, 24, Dos)
51 /* FUNCTION
52 Instantly terminate the program.
54 INPUTS
55 returnCode - Process' return code.
57 RESULT
58 None.
60 NOTES
61 Calling this function bypasses normal termination sequence of your program.
62 Automatically opened libraries will not be closed, destructors will not be
63 called, etc. Do this only if you really know what are you doing. It's not
64 adviced to use this function at all.
66 EXAMPLE
68 BUGS
70 SEE ALSO
72 INTERNALS
74 *****************************************************************************/
76 AROS_LIBFUNC_INIT
78 struct Process *me = (struct Process *)FindTask(NULL);
79 struct StackState *ss = me->pr_ReturnAddr;
81 /* Return code can be zero, so we can't pass it via longjmp() */
82 ss->retval = returnCode;
84 /* Close dos.library because the program has opened it in order to obtain DOSBase */
85 CloseLibrary(&DOSBase->dl_lib);
87 /* Disable() because we may have to swap stack limits */
88 Disable();
89 longjmp(ss->state, 1);
91 AROS_LIBFUNC_EXIT
92 } /* Exit */
95 * CallEntry() is also defined here because it is closely associated with
96 * Exit() implementation.
97 * For different CPUs we may have optimized versions of these two functions in asm.
99 ULONG CallEntry(STRPTR argptr, ULONG argsize, LONG_FUNC entry, struct Process *me)
101 struct StackState ss;
103 /* Set the first IPTR to something like on AmigaOS(tm) */
104 ss.stackSize = (APTR)&ss - me->pr_Task.tc_SPLower;
105 /* Remember stack limits for Exit() */
106 ss.stackLower = me->pr_Task.tc_SPLower;
107 ss.stackUpper = me->pr_Task.tc_SPUpper;
108 me->pr_ReturnAddr = &ss;
110 if (setjmp(ss.state))
113 * We came here from Exit().
114 * Restore stack limits because the program might have swapped stack.
115 * We are clever enough to recover from this.
117 me->pr_Task.tc_SPLower = ss.stackLower;
118 me->pr_Task.tc_SPUpper = ss.stackUpper;
120 Enable(); /* We Disable()d in Exit() */
122 return ss.retval;
124 else
125 return AROS_UFC3(ULONG, entry,
126 AROS_UFCA(STRPTR, argptr, A0),
127 AROS_UFCA(ULONG, argsize, D0),
128 AROS_UFCA(struct ExecBase *, SysBase, A6));