|
|
1.1 root 1: /* ro2ps.c - ROPM: PSAP interface */
2:
3: #ifndef lint
4: static char *rcsid = "$Header: /f/osi/rosap/RCS/ro2ps.c,v 7.1 90/07/01 21:05:43 mrose Exp $";
5: #endif
6:
7: /*
8: * $Header: /f/osi/rosap/RCS/ro2ps.c,v 7.1 90/07/01 21:05:43 mrose Exp $
9: *
10: * Based on an TCP-based implementation by George Michaelson of University
11: * College London.
12: *
13: *
14: * $Log: ro2ps.c,v $
15: * Revision 7.1 90/07/01 21:05:43 mrose
16: * pepsy
17: *
18: * Revision 6.0 89/03/18 23:42:08 mrose
19: * Release 5.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 "ROS-types.h"
38: #include "ropkt.h"
39: #include "tailor.h"
40:
41: /* DATA */
42:
43: int acslose ();
44:
45: int pslose ();
46: int psDATAser (), psTOKENser (), psSYNCser (), psACTIVITYser (),
47: psREPORTser (), psFINISHser (), psABORTser ();
48:
49: /* bind underlying service */
50:
51: int RoPService (acb, roi)
52: register struct assocblk *acb;
53: struct RoSAPindication *roi;
54: {
55: if (!(acb -> acb_flags & ACB_ACS) || (acb -> acb_flags & ACB_RTS))
56: return rosaplose (roi, ROS_OPERATION, NULLCP,
57: "not an association descriptor for ROS on presentation");
58:
59: acb -> acb_putosdu = ro2pswrite;
60: acb -> acb_rowaitrequest = ro2pswait;
61: acb -> acb_ready = NULLIFP;
62: acb -> acb_rosetindications = ro2psasync;
63: acb -> acb_roselectmask = ro2psmask;
64: acb -> acb_ropktlose = NULLIFP;
65:
66: return OK;
67: }
68:
69: /* define vectors for INDICATION events */
70:
71: #define e(i) (indication ? (i) : NULLIFP)
72:
73:
74: /* ARGSUSED */
75:
76: int ro2psasync (acb, indication, roi)
77: register struct assocblk *acb;
78: IFP indication;
79: struct RoSAPindication *roi;
80: {
81: struct PSAPindication pis;
82: register struct PSAPabort *pa = &pis.pi_abort;
83:
84: if (PSetIndications (acb -> acb_fd, e (psDATAser), e (psTOKENser),
85: e (psSYNCser), e (psACTIVITYser), e (psREPORTser),
86: e (psFINISHser), e (psABORTser), &pis) == NOTOK)
87: switch (pa -> pa_reason) {
88: case PC_WAITING:
89: return rosaplose (roi, ROS_WAITING, NULLCP, NULLCP);
90:
91: default:
92: (void) pslose (acb, roi, "PSetIndications", pa);
93: freeacblk (acb);
94: return NOTOK;
95: }
96:
97: if (acb -> acb_rosindication = indication)
98: acb -> acb_flags |= ACB_ASYN;
99: else
100: acb -> acb_flags &= ~ACB_ASYN;
101:
102: return OK;
103: }
104:
105: #undef e
106:
107: /* map association descriptors for select() */
108:
109: /* ARGSUSED */
110:
111: int ro2psmask (acb, mask, nfds, roi)
112: register struct assocblk *acb;
113: fd_set *mask;
114: int *nfds;
115: struct RoSAPindication *roi;
116: {
117: struct PSAPindication pis;
118: struct PSAPabort *pa = &pis.pi_abort;
119:
120: if (PSelectMask (acb -> acb_fd, mask, nfds, &pis) == NOTOK)
121: switch (pa -> pa_reason) {
122: case PC_WAITING:
123: return rosaplose (roi, ROS_WAITING, NULLCP, NULLCP);
124:
125: default:
126: (void) pslose (acb, roi, "PSelectMask", pa);
127: freeacblk (acb);
128: return NOTOK;
129: }
130:
131: return OK;
132: }
133:
134: /* AcSAP interface */
135:
136: static int acslose (acb, roi, event, aca)
137: register struct assocblk *acb;
138: register struct RoSAPindication *roi;
139: char *event;
140: register struct AcSAPabort *aca;
141: {
142: int reason;
143: char *cp,
144: buffer[BUFSIZ];
145:
146: if (event)
147: SLOG (rosap_log, LLOG_EXCEPTIONS, NULLCP,
148: (aca -> aca_cc > 0 ? "%s: %s [%*.*s]": "%s: %s", event,
149: AcErrString (aca -> aca_reason), aca -> aca_cc, aca -> aca_cc,
150: aca -> aca_data));
151:
152: cp = "";
153: switch (aca -> aca_reason) {
154: case ACS_ADDRESS:
155: reason = ROS_ADDRESS;
156: break;
157:
158: case ACS_REFUSED:
159: reason = ROS_REFUSED;
160: break;
161:
162: case ACS_CONGEST:
163: reason = ROS_CONGEST;
164: break;
165:
166: default:
167: (void) sprintf (cp = buffer, " (%s at association control)",
168: AcErrString (aca -> aca_reason));
169: case ACS_PRESENTATION:
170: reason = ROS_ACS;
171: break;
172: }
173:
174: if (aca -> aca_cc > 0)
175: return ropktlose (acb, roi, reason, NULLCP, "%*.*s%s",
176: aca -> aca_cc, aca -> aca_cc, aca -> aca_data, cp);
177: else
178: return ropktlose (acb, roi, reason, NULLCP, "%s", cp);
179: }
180:
181: /* PSAP interface */
182:
183: int ro2pswait (acb, invokeID, secs, roi)
184: register struct assocblk *acb;
185: int *invokeID,
186: secs;
187: register struct RoSAPindication *roi;
188: {
189: int result;
190: struct PSAPdata pxs;
191: register struct PSAPdata *px = &pxs;
192: struct PSAPindication pis;
193: register struct PSAPindication *pi = &pis;
194:
195: for (;;) {
196: switch (result = PReadRequest (acb -> acb_fd, px, secs, pi)) {
197: case NOTOK:
198: return doPSabort (acb, &pi -> pi_abort, roi);
199:
200: case OK:
201: if ((result = doPSdata (acb, invokeID, px, roi)) != OK)
202: return (result != DONE ? result : OK);
203: continue;
204:
205: case DONE:
206: switch (pi -> pi_type) {
207: case PI_TOKEN:
208: if (doPStokens (acb, &pi -> pi_token, roi) == NOTOK)
209: return NOTOK;
210: continue;
211:
212: case PI_SYNC:
213: if (doPSsync (acb, &pi -> pi_sync, roi) == NOTOK)
214: return NOTOK;
215: continue;
216:
217: case PI_ACTIVITY:
218: if (doPSactivity (acb, &pi -> pi_activity, roi) == NOTOK)
219: return NOTOK;
220: continue;
221:
222: case PI_REPORT:
223: if (doPSreport (acb, &pi -> pi_report, roi) == NOTOK)
224: return NOTOK;
225: continue;
226:
227: case PI_FINISH:
228: if (doPSfinish (acb, &pi -> pi_finish, roi) == NOTOK)
229: return NOTOK;
230: return DONE;
231:
232: default:
233: (void) ropktlose (acb, roi, ROS_PROTOCOL, NULLCP,
234: "unknown indication (0x%x) from presentation",
235: pi -> pi_type);
236: break;
237: }
238: break;
239:
240: default:
241: (void) ropktlose (acb, roi, ROS_PROTOCOL, NULLCP,
242: "unexpected return from PReadRequest=%d", result);
243: break;
244: }
245: break;
246: }
247:
248: freeacblk (acb);
249:
250: return NOTOK;
251: }
252:
253: /* */
254:
255: /* ARGSUSED */
256:
257: int ro2pswrite (acb, pe, fe, priority, roi)
258: register struct assocblk *acb;
259: PE pe,
260: fe;
261: int priority;
262: struct RoSAPindication *roi;
263: {
264: int result;
265: struct PSAPindication pis;
266: register struct PSAPabort *pa = &pis.pi_abort;
267:
268: pe -> pe_context = acb -> acb_rosid;
269:
270: PLOGP (rosap_log,ROS_ROSEapdus, pe, "ROSEapdus", 0);
271:
272: if ((result = PDataRequest (acb -> acb_fd, &pe, 1, &pis)) == NOTOK) {
273: (void) pslose (acb, roi, "PDataRequest", pa);
274: freeacblk (acb);
275: }
276:
277: if (fe)
278: (void) pe_extract (pe, fe);
279: pe_free (pe);
280:
281: return result;
282: }
283:
284: /* */
285:
286: static int doPSdata (acb, invokeID, px, roi)
287: register struct assocblk *acb;
288: int *invokeID;
289: register struct PSAPdata *px;
290: struct RoSAPindication *roi;
291: {
292: register PE pe;
293:
294: if (px -> px_type != SX_NORMAL) {
295: (void) ropktlose (acb, roi, ROS_PROTOCOL, NULLCP,
296: "unexpected data indication (0x%x)", px -> px_type);
297: PXFREE (px);
298:
299: freeacblk (acb);
300: return NOTOK;
301: }
302:
303: pe = px -> px_info[0], px -> px_info[0] = NULLPE;
304: PXFREE (px);
305:
306: return acb2osdu (acb, invokeID, pe, roi);
307: }
308:
309: /* */
310:
311: static int doPStokens (acb, pt, roi)
312: register struct assocblk *acb;
313: register struct PSAPtoken *pt;
314: struct RoSAPindication *roi;
315: {
316: (void) ropktlose (acb, roi, ROS_PROTOCOL, NULLCP,
317: "unexpected token indication (0x%x)", pt -> pt_type);
318: PTFREE (pt);
319:
320: freeacblk (acb);
321: return NOTOK;
322: }
323:
324: /* */
325:
326: static int doPSsync (acb, pn, roi)
327: register struct assocblk *acb;
328: register struct PSAPsync *pn;
329: struct RoSAPindication *roi;
330: {
331: (void) ropktlose (acb, roi, ROS_PROTOCOL, NULLCP,
332: "unexpected sync indication (0x%x)", pn -> pn_type);
333: PNFREE (pn);
334:
335: freeacblk (acb);
336: return NOTOK;
337: }
338:
339: /* */
340:
341: static int doPSactivity (acb, pv, roi)
342: register struct assocblk *acb;
343: register struct PSAPactivity *pv;
344: struct RoSAPindication *roi;
345: {
346: (void) ropktlose (acb, roi, ROS_PROTOCOL, NULLCP,
347: "unexpected activity indication (0x%x)", pv -> pv_type);
348: PVFREE (pv);
349:
350: freeacblk (acb);
351: return NOTOK;
352: }
353:
354: /* */
355:
356: static int doPSreport (acb, pp, roi)
357: register struct assocblk *acb;
358: register struct PSAPreport *pp;
359: struct RoSAPindication *roi;
360: {
361: (void) ropktlose (acb, roi, ROS_PROTOCOL, NULLCP,
362: "unexpected exception report indication (0x%x)", pp -> pp_peer);
363: PPFREE (pp);
364:
365: freeacblk (acb);
366: return NOTOK;
367: }
368:
369: /* */
370:
371: /* ARGSUSED */
372:
373: static int doPSfinish (acb, pf, roi)
374: register struct assocblk *acb;
375: struct PSAPfinish *pf;
376: struct RoSAPindication *roi;
377: {
378: struct AcSAPindication acis;
379: register struct AcSAPabort *aca = &acis.aci_abort;
380:
381: if (acb -> acb_flags & ACB_INIT) {
382: (void) ropktlose (acb, roi, ROS_PROTOCOL, NULLCP,
383: "association management botched");
384: PFFREE (pf);
385: freeacblk (acb);
386: return NOTOK;
387: }
388:
389: roi -> roi_type = ROI_FINISH;
390: {
391: register struct AcSAPfinish *acf = &roi -> roi_finish;
392:
393: if (AcFINISHser (acb -> acb_fd, pf, &acis) == NOTOK)
394: return acslose (acb, roi, "AcFINISHser", aca);
395:
396: *acf = acis.aci_finish; /* struct copy */
397: }
398:
399: return DONE;
400: }
401:
402: /* */
403:
404: static int doPSabort (acb, pa, roi)
405: register struct assocblk *acb;
406: register struct PSAPabort *pa;
407: struct RoSAPindication *roi;
408: {
409: struct AcSAPindication acis;
410: register struct AcSAPabort *aca = &acis.aci_abort;
411:
412: if (!pa -> pa_peer && pa -> pa_reason == PC_TIMER)
413: return rosaplose (roi, ROS_TIMER, NULLCP, NULLCP);
414:
415: if (AcABORTser (acb -> acb_fd, pa, &acis) == NOTOK) {
416: (void) acslose (acb, roi, "AcABORTser", aca);
417: goto out;
418: }
419:
420: if (aca -> aca_source != ACA_USER)
421: (void) acslose (acb, roi, NULLCP, aca);
422: else
423: (void) rosaplose (roi, ROS_ABORTED, NULLCP, NULLCP);
424:
425: /* XXX: perhaps should pass data up? */
426: ACAFREE (aca);
427:
428: out: ;
429: acb -> acb_fd = NOTOK;
430: freeacblk (acb);
431:
432: return NOTOK;
433: }
434:
435: /* */
436:
437: static int psDATAser (sd, px)
438: int sd;
439: register struct PSAPdata *px;
440: {
441: IFP handler;
442: register struct assocblk *acb;
443: struct RoSAPindication rois;
444: register struct RoSAPindication *roi = &rois;
445:
446: if ((acb = findacblk (sd)) == NULL)
447: return;
448: handler = acb -> acb_rosindication;
449:
450: if (doPSdata (acb, NULLIP, px, roi) != OK)
451: (*handler) (sd, roi);
452: }
453:
454: /* */
455:
456: static int psTOKENser (sd, pt)
457: int sd;
458: register struct PSAPtoken *pt;
459: {
460: IFP handler;
461: register struct assocblk *acb;
462: struct RoSAPindication rois;
463: register struct RoSAPindication *roi = &rois;
464:
465: if ((acb = findacblk (sd)) == NULL)
466: return;
467: handler = acb -> acb_rosindication;
468:
469: if (doPStokens (acb, pt, roi) != OK)
470: (*handler) (sd, roi);
471: }
472:
473: /* */
474:
475: static int psSYNCser (sd, pn)
476: int sd;
477: register struct PSAPsync *pn;
478: {
479: IFP handler;
480: register struct assocblk *acb;
481: struct RoSAPindication rois;
482: register struct RoSAPindication *roi = &rois;
483:
484: if ((acb = findacblk (sd)) == NULL)
485: return;
486: handler = acb -> acb_rosindication;
487:
488: if (doPSsync (acb, pn, roi) != OK)
489: (*handler) (sd, roi);
490: }
491:
492: /* */
493:
494: static int psACTIVITYser (sd, pv)
495: int sd;
496: register struct PSAPactivity *pv;
497: {
498: IFP handler;
499: register struct assocblk *acb;
500: struct RoSAPindication rois;
501: register struct RoSAPindication *roi = &rois;
502:
503: if ((acb = findacblk (sd)) == NULL)
504: return;
505: handler = acb -> acb_rosindication;
506:
507: if (doPSactivity (acb, pv, roi) != OK)
508: (*handler) (sd, roi);
509: }
510:
511: /* */
512:
513: static int psREPORTser (sd, pp)
514: int sd;
515: register struct PSAPreport *pp;
516: {
517: IFP handler;
518: register struct assocblk *acb;
519: struct RoSAPindication rois;
520: register struct RoSAPindication *roi = &rois;
521:
522: if ((acb = findacblk (sd)) == NULL)
523: return;
524: handler = acb -> acb_rosindication;
525:
526: if (doPSreport (acb, pp, roi) != OK)
527: (*handler) (sd, roi);
528: }
529:
530: /* */
531:
532: static int psFINISHser (sd, pf)
533: int sd;
534: struct PSAPfinish *pf;
535: {
536: IFP handler;
537: register struct assocblk *acb;
538: struct RoSAPindication rois;
539: register struct RoSAPindication *roi = &rois;
540:
541: if ((acb = findacblk (sd)) == NULL)
542: return;
543: handler = acb -> acb_rosindication;
544:
545: (void) doPSfinish (acb, pf, roi);
546:
547: (*handler) (sd, roi);
548: }
549:
550: /* */
551:
552: static int psABORTser (sd, pa)
553: int sd;
554: register struct PSAPabort *pa;
555: {
556: IFP handler;
557: register struct assocblk *acb;
558: struct RoSAPindication rois;
559: register struct RoSAPindication *roi = &rois;
560:
561: if ((acb = findacblk (sd)) == NULL)
562: return;
563: handler = acb -> acb_rosindication;
564:
565: (void) doPSabort (acb, pa, roi);
566:
567: (*handler) (sd, roi);
568: }
569:
570: /* */
571:
572: static int pslose (acb, roi, event, pa)
573: register struct assocblk *acb;
574: register struct RoSAPindication *roi;
575: char *event;
576: register struct PSAPabort *pa;
577: {
578: int reason;
579: char *cp,
580: buffer[BUFSIZ];
581:
582: if (event)
583: SLOG (rosap_log, LLOG_EXCEPTIONS, NULLCP,
584: (pa -> pa_cc > 0 ? "%s: %s [%*.*s]": "%s: %s", event,
585: PErrString (pa -> pa_reason), pa -> pa_cc, pa -> pa_cc,
586: pa -> pa_data));
587:
588: cp = "";
589: switch (pa -> pa_reason) {
590: case PC_ADDRESS:
591: reason = ROS_ADDRESS;
592: break;
593:
594: case PC_REFUSED:
595: reason = ROS_REFUSED;
596: break;
597:
598: case PC_CONGEST:
599: reason = ROS_CONGEST;
600: break;
601:
602: default:
603: (void) sprintf (cp = buffer, " (%s at presentation)",
604: PErrString (pa -> pa_reason));
605: case PC_SESSION:
606: reason = ROS_PRESENTATION;
607: break;
608: }
609:
610: if (pa -> pa_cc > 0)
611: return ropktlose (acb, roi, reason, NULLCP, "%*.*s%s",
612: pa -> pa_cc, pa -> pa_cc, pa -> pa_data, cp);
613: else
614: return ropktlose (acb, roi, reason, NULLCP, "%s", *cp ? cp + 1 : cp);
615: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.