|
|
1.1 root 1: /* rywait.c - ROSY: wait */
2:
3: #ifndef lint
4: static char *rcsid = "$Header: /f/osi/rosy/RCS/rywait.c,v 7.2 90/07/09 14:48:09 mrose Exp $";
5: #endif
6:
7: /*
8: * $Header: /f/osi/rosy/RCS/rywait.c,v 7.2 90/07/09 14:48:09 mrose Exp $
9: *
10: *
11: * $Log: rywait.c,v $
12: * Revision 7.2 90/07/09 14:48:09 mrose
13: * sync
14: *
15: * Revision 7.1 90/07/01 21:06:41 mrose
16: * pepsy
17: *
18: * Revision 7.0 89/11/23 22:22:05 mrose
19: * Release 6.0
20: *
21: */
22:
23: /*
24: * NOTICE
25: *
26: * Acquisition, use, and distribution of this module and related
27: * materials are subject to the restrictions of a license agreement.
28: * Consult the Preface in the User's Manual for the full terms of
29: * this agreement.
30: *
31: */
32:
33:
34: /* LINTLIBRARY */
35:
36: #include <stdio.h>
37: #include "rosy.h"
38:
39:
40: #define missingP(p) \
41: { \
42: if (p == NULL) \
43: return rosaplose (roi, ROS_PARAMETER, NULLCP, \
44: "mandatory parameter \"%s\" missing", "p"); \
45: }
46:
47: /* WAIT */
48:
49: int RyWait (sd, id, out, secs, roi)
50: int sd,
51: *id,
52: secs;
53: caddr_t *out;
54: struct RoSAPindication *roi;
55: {
56: int reason,
57: result;
58: register struct opsblk *opb;
59:
60: #ifdef notdef
61: missingP (out);
62: #endif
63: missingP (roi);
64:
65: if (id) {
66: if ((opb = findopblk (sd, *id, OPB_INITIATOR)) == NULLOPB)
67: return rosaplose (roi, ROS_PARAMETER, NULLCP,
68: "invocation %d not in progress on association %d",
69: *id, sd);
70: }
71: else
72: opb = firstopblk (sd);
73:
74: if (out && opb && (opb -> opb_flags & OPB_EVENT)) {
75: *out = opb -> opb_out;
76: *roi = opb -> opb_event; /* struct copy */
77: opb -> opb_out = NULL;
78: freeopblk (opb);
79:
80: return OK;
81: }
82:
83: if (!id)
84: opb = NULLOPB;
85:
86: switch (result = RoWaitRequest (sd, secs, roi)) {
87: case NOTOK:
88: reason = roi -> roi_preject.rop_reason;
89: if (ROS_FATAL (reason))
90: loseopblk (sd, reason);
91: break;
92:
93: case DONE:
94: loseopblk (sd, ROS_IP_RELEASE);
95: break;
96:
97: case OK:
98: result = RyWaitAux (sd, opb, out, secs, roi);
99: break;
100:
101: default:
102: result = rosaplose (roi, ROS_PROTOCOL, NULLCP,
103: "unknown return from RoWaitRequest=%d", result);
104: break;
105: }
106:
107: return result;
108: }
109:
110: /* */
111:
112: int RyWaitAux (sd, opb, out, secs, roi)
113: int sd;
114: register struct opsblk *opb;
115: int secs;
116: caddr_t *out;
117: struct RoSAPindication *roi;
118: {
119: int id,
120: reason,
121: result;
122: char *cp;
123: caddr_t in;
124: register struct dspblk *dsb;
125: register struct opsblk *op2;
126: register struct RyError **rye;
127: register struct RyOperation *ryo;
128:
129: missingP (roi);
130:
131: if (out)
132: *out = NULL;
133:
134: for (;;) {
135: switch (roi -> roi_type) {
136: case ROI_INVOKE: {
137: struct RoSAPinvoke roxs;
138: register struct RoSAPinvoke *rox = &roxs;
139:
140: *rox = roi -> roi_invoke; /* struct copy */
141:
142: if (op2 = findopblk (sd, rox -> rox_id, OPB_RESPONDER)) {
143: (void) rosaplose (roi, result = ROS_IP_DUP, NULLCP,
144: "duplicate invocation %d", rox -> rox_id);
145:
146: bad_request: ;
147: (void) RoURejectRequest (sd, &rox -> rox_id, result,
148: ROS_NOPRIO, roi);
149: ROXFREE (rox);
150:
151: if (opb == NULLOPB)
152: return NOTOK;
153: goto next;
154: }
155:
156: if ((dsb = finddsblk (sd, rox -> rox_op)) == NULLDSB
157: && (dsb = finddsblk (NOTOK, rox -> rox_op))
158: == NULLDSB) {
159: (void) rosaplose (roi, result = ROS_IP_UNRECOG, NULLCP,
160: "unexpected invocation %d of operation %d",
161: rox -> rox_id, rox -> rox_op);
162: goto bad_request;
163: }
164:
165: ryo = dsb -> dsb_ryo;
166: in = NULL;
167: if (rox -> rox_args) {
168: #ifdef PEPSY_DEFINITIONS
169: if (!ryo -> ryo_arg_mod) { /* XXX: MISTYPED? */
170: #else
171: if (!ryo -> ryo_arg_decode) { /* XXX: MISTYPED? */
172: #endif
173: (void) rosaplose (roi, result = ROS_IP_MISTYPED,
174: NULLCP,
175: "unexpected argument for invocation %d of operation %s/%d",
176: rox -> rox_id, ryo -> ryo_name, ryo -> ryo_op);
177: goto bad_request;
178: }
179:
180: PY_pepy[0] = 0;
181: #ifdef PEPSY_DEFINITIONS
182: if (dec_f (ryo -> ryo_arg_index, ryo -> ryo_arg_mod,
183: rox -> rox_args, 1, NULLIP, NULLVP, &in)
184: == NOTOK) {
185: #else
186: if ((*ryo -> ryo_arg_decode) (rox -> rox_args, 1, NULLIP,
187: NULLVP, &in) == NOTOK) {
188: #endif
189: (void) rosaplose (roi, result = ROS_IP_MISTYPED,
190: NULLCP,
191: "mistyped argument for invocation %d of operation %s/%d [%s]",
192: rox -> rox_id, ryo -> ryo_name, ryo -> ryo_op,
193: PY_pepy);
194: goto bad_request;
195: }
196: }
197:
198: if (ryo -> ryo_result || ryo -> ryo_errors) {
199: if ((op2 = newopblk (sd, rox -> rox_id)) == NULLOPB) {
200: (void) rosaplose (roi, result = ROS_IP_LIMIT, NULLCP,
201: "unable to allocate opblock for invocation %d of operation %s/%d",
202: rox -> rox_id, ryo -> ryo_name, ryo -> ryo_op);
203: goto bad_request;
204: }
205: op2 -> opb_flags &= ~OPB_INITIATOR;
206: op2 -> opb_flags |= OPB_RESPONDER;
207: op2 -> opb_ryo = ryo;
208: }
209:
210: result = (*dsb -> dsb_vector) (sd, ryo, rox, in, roi);
211: #ifdef PEPSY_DEFINITIONS
212: if (in && ryo -> ryo_arg_mod)
213: fre_obj (in,
214: ryo -> ryo_arg_mod
215: -> md_dtab[ryo -> ryo_arg_index],
216: ryo -> ryo_arg_mod);
217: #else
218: if (in && ryo -> ryo_arg_free)
219: (void) (*ryo -> ryo_arg_free) (in);
220: #endif
221: ROXFREE (rox);
222:
223: switch (result) {
224: default:
225: result = rosaplose (roi, ROS_PROTOCOL, NULLCP,
226: "%s invoke dispatch for invoke id %d returns %d",
227: ryo -> ryo_name, rox -> rox_id, result);
228: /* and fall */
229: case NOTOK:
230: if (opb != NULLOPB)
231: break;
232: case DONE:
233: return result;
234:
235: case OK:
236: break;
237: }
238: goto next;
239: }
240:
241: case ROI_RESULT: {
242: register struct RoSAPresult *ror = &roi -> roi_result;
243:
244: if ((op2 = findopblk (sd, ror -> ror_id, OPB_INITIATOR))
245: == NULLOPB
246: || (op2 -> opb_flags & OPB_EVENT)) {
247: (void) RoURejectRequest (sd, &ror -> ror_id,
248: ROS_RRP_UNRECOG, ROS_NOPRIO, roi);
249: RORFREE (ror);
250: goto next;
251: }
252:
253: ryo = op2 -> opb_ryo;
254: if (!ryo -> ryo_result) {
255: result = ROS_RRP_UNEXP;
256:
257: bad_result: ;
258: RORFREE (ror);
259: goto bad_response;
260: }
261:
262: #ifdef PEPSY_DEFINITIONS
263: if (ryo -> ryo_res_mod) { /* XXX: MISTYPED? */
264: #else
265: if (ryo -> ryo_res_decode) { /* XXX: MISTYPED? */
266: #endif
267: if (!ror -> ror_result) {
268: result = ROS_RRP_MISTYPED;
269: goto bad_result;
270: }
271: PY_pepy[0] = 0;
272: #ifdef PEPSY_DEFINITIONS
273: if (result = dec_f (ryo -> ryo_res_index,
274: ryo -> ryo_res_mod, ror -> ror_result,
275: 1, NULLIP, NULLVP, &op2 -> opb_out)
276: == NOTOK) {
277: op2 -> opb_free_index = ryo -> ryo_res_index;
278: op2 -> opb_free_mod = ryo -> ryo_res_mod;
279: }
280: #else
281: result = (*ryo -> ryo_res_decode) (ror -> ror_result, 1,
282: NULLIP, NULLVP, &op2 -> opb_out);
283: op2 -> opb_free = ryo -> ryo_res_free;
284: #endif
285: }
286: else {
287: if (ror -> ror_result) {
288: result = ROS_RRP_MISTYPED;
289: goto bad_result;
290: }
291:
292: result = OK;
293: }
294:
295: op2 -> opb_pe = ror -> ror_result, ror -> ror_result = NULLPE;
296: RORFREE (ror);
297:
298: if (result == NOTOK) {
299: result = ROS_RRP_MISTYPED;
300: goto bad_response;
301: }
302:
303: if (op2 -> opb_resfnx) {
304: result = (*op2 -> opb_resfnx) (sd, op2 -> opb_id,
305: RY_RESULT, op2 -> opb_out,
306: roi);
307: freeopblk (op2);
308:
309: id = ror -> ror_id, cp = "result";
310: punch: ;
311: switch (result) {
312: default:
313: result = rosaplose (roi, ROS_PROTOCOL, NULLCP,
314: "%s %s dispatch for invoke id %d returns %d",
315: ryo -> ryo_name, cp, id, result);
316: /* and fall */
317: case NOTOK:
318: if (opb != NULLOPB)
319: break;
320: case DONE:
321: return result;
322:
323: case OK:
324: break;
325: }
326: if (opb == op2)
327: return OK;
328: goto next;
329: }
330:
331: if (opb == NULLOPB || opb == op2) {
332: if (out == NULL) {
333: waiting: ;
334: op2 -> opb_flags |= OPB_EVENT;
335: op2 -> opb_event = *roi; /* struct copy */
336: return rosaplose (roi, ROS_WAITING, NULLCP, NULLCP);
337: }
338:
339: *out = op2 -> opb_out;
340: op2 -> opb_out = NULL;
341: freeopblk (op2);
342:
343: return OK;
344: }
345:
346: op2 -> opb_flags |= OPB_EVENT;
347: op2 -> opb_event = *roi; /* struct copy */
348: goto next;
349: }
350:
351: case ROI_ERROR: {
352: register struct RoSAPerror *roe = &roi -> roi_error;
353:
354: if ((op2 = findopblk (sd, roe -> roe_id, OPB_INITIATOR))
355: == NULLOPB
356: || (op2 -> opb_flags & OPB_EVENT)) {
357: (void) RoURejectRequest (sd, &roe -> roe_id,
358: ROS_REP_UNRECOG, ROS_NOPRIO, roi);
359: ROEFREE (roe);
360: goto next;
361: }
362:
363: ryo = op2 -> opb_ryo;
364: if (!(rye = ryo -> ryo_errors)) {
365: result = ROS_REP_UNEXP;
366:
367: bad_error: ;
368: ROEFREE (roe);
369: goto bad_response;
370: }
371: for (; *rye; rye++)
372: if ((*rye) -> rye_err == roe -> roe_error)
373: break;
374: if (!*rye) {
375: result = ROS_REP_UNEXPERR;
376: goto bad_error;
377: }
378:
379: #ifdef PEPSY_DEFINITIONS
380: if ((*rye) -> rye_param_mod) { /* XXX: MISTYPED? */
381: #else
382: if ((*rye) -> rye_param_decode) { /* XXX: MISTYPED? */
383: #endif
384: if (!roe -> roe_param) {
385: result = ROS_REP_MISTYPED;
386: goto bad_error;
387: }
388:
389: #ifdef PEPSY_DEFINITIONS
390: result = dec_f( (*rye) -> rye_param_index,
391: (*rye) -> rye_param_mod, roe -> roe_param,
392: #else
393: result = (*(*rye) -> rye_param_decode) (roe -> roe_param,
394: #endif
395: 1, NULLIP, NULLVP, &op2 -> opb_out);
396: #ifdef PEPSY_DEFINITIONS
397: op2 -> opb_free_index = (*rye) -> rye_param_index;
398: op2 -> opb_free_mod = (*rye) -> rye_param_mod;
399: #else
400: op2 -> opb_free = (*rye) -> rye_param_free;
401: #endif
402: }
403: else {
404: if (roe -> roe_param) {
405: result = ROS_REP_MISTYPED;
406: goto bad_error;
407: }
408:
409: result = OK;
410: }
411:
412: op2 -> opb_pe = roe -> roe_param, roe -> roe_param = NULLPE;
413: ROEFREE (roe);
414:
415: if (result == NOTOK) {
416: result = ROS_REP_MISTYPED;
417: goto bad_response;
418: }
419:
420: if (op2 -> opb_errfnx) {
421: result = (*op2 -> opb_errfnx) (sd, op2 -> opb_id,
422: roe -> roe_error,
423: op2 -> opb_out, roi);
424: freeopblk (op2);
425:
426: id = roe -> roe_id, cp = "error";
427: goto punch;
428: }
429:
430: if (opb == NULLOPB || opb == op2) {
431: if (out == NULL)
432: goto waiting;
433: *out = op2 -> opb_out;
434: op2 -> opb_out = NULL;
435: freeopblk (op2);
436:
437: return OK;
438: }
439:
440: op2 -> opb_flags |= OPB_EVENT;
441: op2 -> opb_event = *roi; /* struct copy */
442: goto next;
443: }
444:
445: case ROI_UREJECT: {
446: register struct RoSAPureject *rou = &roi -> roi_ureject;
447:
448: if (rou -> rou_noid)
449: op2 = opb;
450: else
451: if ((op2 = findopblk (sd, rou -> rou_id, OPB_INITIATOR))
452: == NULLOPB
453: || (op2 -> opb_flags & OPB_EVENT))
454: goto next;
455:
456: if (op2 -> opb_errfnx) {
457: result = (*op2 -> opb_errfnx) (sd, id = op2 -> opb_id,
458: RY_REJECT,
459: (caddr_t) rou -> rou_reason,
460: roi);
461: freeopblk (op2);
462:
463: cp = "reject";
464: goto punch;
465: }
466:
467: if (opb == NULLOPB || opb == op2) {
468: freeopblk (op2);
469:
470: return OK;
471: }
472:
473: op2 -> opb_flags |= OPB_EVENT;
474: op2 -> opb_event = *roi; /* struct copy */
475: goto next;
476: }
477:
478: default:
479: return rosaplose (roi, ROS_PROTOCOL, NULLCP,
480: "unknown indication type=%d", roi -> roi_type);
481: }
482:
483: bad_response: ;
484: {
485: register struct RoSAPureject *rou = &roi -> roi_ureject;
486:
487: (void) RoURejectRequest (op2 -> opb_fd, &op2 -> opb_id,
488: result, ROS_NOPRIO, roi);
489:
490: roi -> roi_type = ROI_UREJECT;
491: rou -> rou_id = op2 -> opb_id;
492: rou -> rou_noid = 0;
493: rou -> rou_reason = result;
494:
495: if (op2 -> opb_errfnx) {
496: result = (*op2 -> opb_errfnx) (sd, id = op2 -> opb_id, RY_REJECT,
497: (caddr_t) rou ->rou_reason, roi);
498:
499: freeopblk (op2);
500:
501: cp = "reject";
502: goto punch;
503: }
504:
505: if (opb == NULLOPB || opb == op2) {
506: freeopblk (op2);
507:
508: return OK;
509: }
510:
511: op2 -> opb_flags |= OPB_EVENT;
512: op2 -> opb_event = *roi; /* struct copy */
513: }
514: /* and fall... */
515:
516: next: ;
517: if (secs != NOTOK)
518: return rosaplose (roi, ROS_TIMER, NULLCP, NULLCP);
519:
520: switch (result = RoWaitRequest (sd, NOTOK, roi)) {
521: case NOTOK:
522: reason = roi -> roi_preject.rop_reason;
523: if (ROS_FATAL (reason))
524: loseopblk (sd, reason);
525: break;
526:
527: case DONE:
528: loseopblk (sd, ROS_IP_RELEASE);
529: break;
530:
531: case OK:
532: continue;
533:
534: default:
535: result = rosaplose (roi, ROS_PROTOCOL, NULLCP,
536: "unknown return from RoWaitRequest=%d", result);
537: break;
538: }
539:
540: return result;
541: }
542: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.