Home My Page Projects Code Snippets Project Openings SML/NJ
Summary Activity Forums Tracker Lists Tasks Docs Surveys News SCM Files

SCM Repository

[smlnj] Annotation of /sml/trunk/src/runtime/mach-dep/signal-util.c
ViewVC logotype

Annotation of /sml/trunk/src/runtime/mach-dep/signal-util.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2 - (view) (download) (as text)

1 : monnier 2 /* signal-util.c
2 :     *
3 :     * COPYRIGHT (c) 1995 by AT&T Bell Laboratories.
4 :     *
5 :     * System independent utility routines for supporting signals and
6 :     * software polling.
7 :     */
8 :    
9 :     #include <stdio.h>
10 :     #include "ml-base.h"
11 :     #include "ml-limits.h"
12 :     #include "ml-state.h"
13 :     #include "vproc-state.h"
14 :     #include "ml-objects.h"
15 :     #include "ml-signals.h"
16 :     #include "system-signals.h"
17 :    
18 :    
19 :     /* ChooseSignal:
20 :     *
21 :     * Choose which signal to pass to the ML handler and setup the ML state
22 :     * vector accordingly.
23 :     * WARNING: This should be called with signals masked to avoid race
24 :     * conditions.
25 :     */
26 :     void ChooseSignal (vproc_state_t *vsp)
27 :     {
28 :     ASSERT(vsp->vp_numInQ > 0);
29 :    
30 :     /* record the signal and count */
31 :     vsp->vp_sigCode = vsp->vp_pendingSigQ[vsp->vp_nextPendingSig].sigNum;
32 :     vsp->vp_sigCount = vsp->vp_pendingSigQ[vsp->vp_nextPendingSig].count;
33 :     if (IS_SYSTEM_SIG(vsp->vp_sigCode))
34 :     vsp->vp_numPendingSigs -= vsp->vp_sigCount;
35 :     else
36 :     vsp->vp_numPendingSysSigs -= vsp->vp_sigCount;
37 :    
38 :     /* advance the pending queue */
39 :     if ((--vsp->vp_numInQ == 0) || (++vsp->vp_nextPendingSig == NUM_SIGS))
40 :     vsp->vp_nextPendingSig = 0;
41 :    
42 :     #ifdef SIGNAL_DEBUG
43 :     SayDebug ("ChooseSignal: sig = %d, count = %d\n",
44 :     vsp->vp_sigCode, vsp->vp_sigCount);
45 :     #endif
46 :    
47 :     } /* end of ChooseSignal */
48 :    
49 :    
50 :     /* EnqueueSignal:
51 :     *
52 :     * Add a signal to the pending queue; if the signal is already present, then
53 :     * bump its count.
54 :     */
55 :     void EnqueueSignal (vproc_state_t *vsp, int sigCode)
56 :     {
57 :     int i, j;
58 :    
59 :     #ifdef SIGNAL_DEBUG
60 :     SayDebug("EnqueueSignal: numInQ = %d, sig = %d\n", vsp->vp_numInQ, sigCode);
61 :     #endif
62 :    
63 :     ASSERT(vsp->vp_numInQ >= 0);
64 :    
65 :     for (i = vsp->vp_nextPendingSig, j = vsp->vp_numInQ; --j >= 0; ) {
66 :     if (vsp->vp_pendingSigQ[i].sigNum == sigCode)
67 :     break;
68 :     if (++i == NUM_SIGS) i = 0;
69 :     }
70 :     if (j < 0) {
71 :     vsp->vp_pendingSigQ[i].sigNum = sigCode;
72 :     vsp->vp_pendingSigQ[i].count = 1;
73 :     vsp->vp_numInQ++;
74 :     }
75 :     else
76 :     vsp->vp_pendingSigQ[i].count++;
77 :    
78 :     } /* end of EnqueueSignal */
79 :    
80 :    
81 :     /* MakeResumeCont:
82 :     *
83 :     * Build the resume continuation for a signal or poll event handler.
84 :     * Layout of the resumption continuation:
85 :     *
86 :     * resumption continuation
87 :     * |
88 :     * v
89 :     * +------------------+----+-+-+-+-+-+~+---------~
90 :     * |STRING| floatregs |DESC|1|2|3|4| |B| live regs
91 :     * +------------------+----+-+-+-+-+|+~+---------~
92 :     * ^ |
93 :     * |________________________|
94 :     *
95 :     * At least 4K avail. heap assumed.
96 :     */
97 :     ml_val_t MakeResumeCont (ml_state_t *msp, ml_val_t resume[])
98 :     {
99 :     ml_val_t fpRegs;
100 :     int i, n, mask;
101 :    
102 :     #if (FLOAT_CALLEESAVE > 0)
103 :     # ifdef ALIGN_REALDS
104 :     /* Force REALD_SZB alignment */
105 :     msp->ml_allocPtr =
106 :     (ml_val_t *)(((Addr_t)(msp->ml_allocPtr) & ~(REALD_SZB-1))+WORD_SZB);
107 :     # endif
108 :     # if defined(TARGET_X86)
109 :     n = FP_STATE_SIZE;
110 :     # else
111 :     n = (REALD_SZB*FLOAT_CALLEESAVE)/WORD_SZB;
112 :     ML_AllocWrite(msp, 0, MAKE_DESC(n, DTAG_string));
113 :     SaveFPRegs ((Addr_t)(msp->ml_allocPtr) + WORD_SZB);
114 :     fpRegs = ML_Alloc(msp, n);
115 :     # endif /* TARGET_X86 */
116 :     #else
117 :     fpRegs = ML_unit;
118 :     #endif
119 :    
120 :     /* allocate the resumption closure */
121 :     ML_AllocWrite(msp, 1, PTR_CtoML(resume));
122 :     ML_AllocWrite(msp, 2, INT_CtoML(msp->ml_liveRegMask));
123 :     ML_AllocWrite(msp, 3, msp->ml_pc);
124 :     ML_AllocWrite(msp, 4, msp->ml_exnCont);
125 :     ML_AllocWrite(msp, 5, fpRegs);
126 :     n = 6;
127 :    
128 :     #if defined(BASE_INDX)
129 :     ML_AllocWrite(msp, n, msp->ml_baseReg);
130 :     n++;
131 :     #endif
132 :    
133 :     /* save the live registers */
134 :     mask = msp->ml_liveRegMask;
135 :     for (i = 0; mask != 0; i++, mask >>= 1) {
136 :     if (mask & 0x1) {
137 :     ML_AllocWrite(msp, n, msp->ml_roots[ArgRegMap[i]]);
138 :     n++;
139 :     }
140 :     }
141 :    
142 :     /* write the object descriptor */
143 :     ML_AllocWrite(msp, 0, MAKE_DESC(n-1, DTAG_record));
144 :    
145 :     return ML_Alloc(msp, n-1);
146 :    
147 :     } /* end of MakeResumeCont */
148 :    
149 :    
150 :     /* MakeHandlerArg:
151 :     *
152 :     * Build the argument record for the ML signal handler. It has the type
153 :     *
154 :     * val sigHandler : (int * int * unit cont) -> 'a
155 :     *
156 :     * The first argument is the signal code, the second is the signal count and the
157 :     * third is the resumption continuation. The ML signal handler should never
158 :     * return.
159 :     * NOTE: maybe this should be combined with ChooseSignal???
160 :     */
161 :     ml_val_t MakeHandlerArg (ml_state_t *msp, ml_val_t resume[])
162 :     {
163 :     ml_val_t resumeCont, arg;
164 :     vproc_state_t *vsp = msp->ml_vproc;
165 :    
166 :     resumeCont = MakeResumeCont(msp, resume);
167 :    
168 :     /* allocate the ML signal handler's argument record */
169 :     REC_ALLOC3(msp, arg,
170 :     INT_CtoML(vsp->vp_sigCode), INT_CtoML(vsp->vp_sigCount),
171 :     resumeCont);
172 :    
173 :     #ifdef SIGNAL_DEBUG
174 :     SayDebug ("MakeHandlerArg: resumeC = %#x, arg = %#x\n", resumeCont, arg);
175 :     #endif
176 :     return arg;
177 :    
178 :     } /* end of MakeHandlerArg */
179 :    
180 :    
181 :     /* LoadResumeState:
182 :     *
183 :     * Load the ML state with the state preserved in resumption continuation
184 :     * made by MakeResumeCont.
185 :     */
186 :     void LoadResumeState (ml_state_t *msp)
187 :     {
188 :     ml_val_t *contClosure;
189 :     int i, n, mask;
190 :     #ifdef SIGNAL_DEBUG
191 :     SayDebug ("LoadResumeState:\n");
192 :     #endif
193 :    
194 :     contClosure = PTR_MLtoC(ml_val_t, msp->ml_closure);
195 :    
196 :     mask =
197 :     msp->ml_liveRegMask = INT_MLtoC(contClosure[1]);
198 :     msp->ml_pc = contClosure[2];
199 :     msp->ml_exnCont = contClosure[3];
200 :     #if (FLOAT_CALLEESAVE > 0)
201 :     RestoreFPRegs(PTR_MLtoC(Word_t, contClosure[4]));
202 :     #endif
203 :     n = 5;
204 :     #ifdef BASE_INDX
205 :     msp->ml_baseReg = contClosure[n];
206 :     n++;
207 :     #endif
208 :     for (i = 0; mask != 0; i++, mask >>= 1) {
209 :     if (mask & 0x1) {
210 :     msp->ml_roots[ArgRegMap[i]] = contClosure[n];
211 :     n++;
212 :     }
213 :     }
214 :    
215 :     } /* end of LoadResumeState */
216 :    
217 :    
218 :     /* GCSignal:
219 :     *
220 :     * Record a garbage collection signal (if enabled). Return true, if a signal
221 :     * was recorded.
222 :     */
223 :     bool_t GCSignal (vproc_state_t *vsp)
224 :     {
225 :     if (vsp->vp_gcSigState == ML_SIG_ENABLED) {
226 :     vsp->vp_numPendingSigs++;
227 :     EnqueueSignal (vsp, RUNSIG_GC);
228 :     return TRUE;
229 :     }
230 :     else
231 :     return FALSE;
232 :    
233 :     } /* end of GCSignal */
234 :    

root@smlnj-gforge.cs.uchicago.edu
ViewVC Help
Powered by ViewVC 1.0.0