1 /* Implement tasking-related runtime actions for CHILL.
2 Copyright (C) 1992,1993 Free Software Foundation, Inc.
5 This file is part of GNU CC.
7 GNU CC is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
12 GNU CC is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with GNU CC; see the file COPYING. If not, write to
19 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
24 extern void __cause_ex1 (char *ex, char *file, int lineno);
26 EXCEPTION (delayfail);
27 #define CAUSE_DELAYFAIL __cause_ex1 ("delayfail", filename, lineno)
29 EXCEPTION (notyetimplemented);
30 #define CAUSE_NOTIMPLEMENTED __cause_ex1 ("notyetimplemeyed", filename, lineno)
33 * function __delay_event
36 * ev_got pointer to location where to write the event got.
37 * nevents number of events in list
38 * evptrs array of event descriptors
39 * priority specified priority
40 * insloc pointer to resulting instance location
42 * filename filename of caller
43 * lineno linenumber of caller
53 * implement the CHILL DELAY and DELAY CASE actions.
58 __delay_event (ev_got, nevents, evptrs, priority, to, insloc, filename, lineno)
68 int i, already_done = 0;
69 Event_Queue *start_list = 0;
70 Event_Queue **retval = 0;
74 /* check if all specified event queues have enough space left
75 to perform the delay */
76 for (i = 0; i < nevents; i++)
79 unsigned long cnt = 0;
82 if (evptrs[i].maxqueuelength == 0)
84 else if (evptrs[i].maxqueuelength == (unsigned long)-1L)
88 /* check if we already have processed this one, that means, this
89 event is mentioned more then once */
90 for (j = 0; j < i; j++)
92 if (evptrs[i].ev == evptrs[j].ev)
101 memcpy (&e, evptrs[i].ev, sizeof (Event_Queue *));
107 if (cnt >= evptrs[i].maxqueuelength)
111 for (i = 0; i < nevents; i++)
113 /* queue that stuff on each event */
116 Event_Queue *prev_queue_entry = 0;
117 Event_Queue *prev_list_entry;
118 int j, have_done = 0;
120 /* check for this event already processed */
121 for (j = 0; j < i; j++)
123 if (evptrs[i].ev == evptrs[j].ev)
132 memcpy (&ev, &evptrs[i].ev, sizeof (Event_Queue *));
133 MALLOC (wrk, sizeof (Event_Queue));
134 memset (wrk, 0, sizeof (Event_Queue));
136 wrk->priority = priority;
138 wrk->listhead = evptrs[i].ev;
140 /* search for the place to queue this entry in */
141 while (ev->forward != 0 && ev->priority >= priority)
143 prev_queue_entry = ev;
147 /* ready to put entry into queue */
148 if (ev->forward == 0 || prev_queue_entry == 0)
150 /* beginning or end of the list */
151 wrk->forward = ev->forward;
156 /* this is somewhere in the middle */
157 wrk->forward = prev_queue_entry->forward;
158 prev_queue_entry->forward = wrk;
161 /* queue it into list */
162 wrk->startlist = start_list;
165 /* we are the first in the list */
167 prev_list_entry = wrk;
168 wrk->startlist = start_list;
172 prev_list_entry->chain = wrk;
173 prev_list_entry = wrk;
177 /* tell runtime system to delay that process */
178 timed_out = __delay_this (wait_event_delay, to, filename, lineno);
181 /* we have to remove the entries from the queue's */
185 Event_Queue *tmp = (Event_Queue *)wrk->listhead;
187 while (tmp->forward != wrk)
189 tmp->forward = wrk->forward;
199 if (wrk->is_continued && ! already_done)
202 retval = wrk->listhead;
203 if (insloc && !timed_out)
205 insloc->ptype = wrk->who_continued.ptype;
206 insloc->pcopy = wrk->who_continued.pcopy;
213 if (!timed_out && ev_got)
214 *ev_got = (void *)retval;
218 /* force function print_event to be linked */
219 extern void __print_event ();
220 static EntryPoint pev = __print_event;