|
|
BSD 4.3reno
/* ro2ssinitiat.c - initiator */
#ifndef lint
static char *rcsid = "$Header: /var/lib/cvsd/repos/CSRG/43BSDReno/contrib/isode-beta/rosap/ro2ssinitiat.c,v 1.1.1.1 2018/04/24 16:12:56 root Exp $";
#endif
/*
* $Header: /var/lib/cvsd/repos/CSRG/43BSDReno/contrib/isode-beta/rosap/ro2ssinitiat.c,v 1.1.1.1 2018/04/24 16:12:56 root Exp $
*
* Based on an TCP-based implementation by George Michaelson of University
* College London.
*
*
* $Log: ro2ssinitiat.c,v $
* Revision 1.1.1.1 2018/04/24 16:12:56 root
* BSD 4.3reno
*
* Revision 7.1 90/07/01 21:05:52 mrose
* pepsy
*
* Revision 6.1 89/06/24 00:55:54 mrose
* reason
*
* Revision 6.0 89/03/18 23:42:16 mrose
* Release 5.0
*
*/
/*
* NOTICE
*
* Acquisition, use, and distribution of this module and related
* materials are subject to the restrictions of a license agreement.
* Consult the Preface in the User's Manual for the full terms of
* this agreement.
*
*/
/* LINTLIBRARY */
#include <stdio.h>
#include <signal.h>
#include "../acsap/OACS-types.h"
#include "ropkt.h"
#include "isoservent.h"
#include "tailor.h"
/* RO-BEGIN.REQUEST */
int RoBeginRequest (called, data, roc, roi)
struct RoSAPaddr *called;
PE data;
struct RoSAPconnect *roc;
struct RoSAPindication *roi;
{
SBV smask;
int result;
isodetailor (NULLCP, 0);
missingP (called);
missingP (roc);
bzero ((char *) roc, sizeof *roc);
missingP (roi);
smask = sigioblock ();
result = RoBeginRequestAux (called, data, roc, roi);
(void) sigiomask (smask);
return result;
}
/* */
static int RoBeginRequestAux (called, data, roc, roi)
struct RoSAPaddr *called;
PE data;
struct RoSAPconnect *roc;
struct RoSAPindication *roi;
{
int len,
result,
settings;
char *base;
#ifdef notdef
register struct isoservent *is;
#endif
PE pe;
register struct assocblk *acb;
struct SSAPref ref;
struct SSAPconnect scs;
register struct SSAPconnect *sc = &scs;
struct SSAPindication sis;
register struct SSAPindication *si = &sis;
register struct SSAPabort *sa = &si -> si_abort;
struct type_OACS_PConnect pcnnct;
struct type_OACS_DataTransferSyntax dts;
struct member_OACS_1 udata;
struct type_OACS_ConnectionData condata;
struct type_OACS_PAccept *paccpt;
struct type_OACS_PRefuse pref;
if ((acb = newacblk ()) == NULL)
return rosaplose (roi, ROS_CONGEST, NULLCP, "out of memory");
pcnnct.member_OACS_0 = &dts;
dts.parm = int_OACS_DataTransferSyntax_x409;
pcnnct.pUserData = &udata;
udata.optionals = 0;
udata.member_OACS_2 = &condata;
condata.offset = type_OACS_ConnectionData_open;
if (data)
condata.un.open = data;
else
/* Seems to be needed to make the responder happy. */
condata.un.open = pe_alloc (PE_CLASS_UNIV, PE_FORM_PRIM, PE_PRIM_NULL);
udata.applicationProtocol = (int) ntohs (called -> roa_port);
if (encode_OACS_PConnect (&pe, 1, 0, NULLCP, &pcnnct) == NOTOK) {
no_mem: ;
result = rosaplose (roi, ROS_CONGEST, NULLCP, "out of memory");
goto out1;
}
PLOGP (rosap_log,OACS_PConnect, pe, "PConnect", 0);
if (pe2ssdu (pe, &base, &len) == NOTOK)
goto no_mem;
if (data)
(void) pe_extract (pe, data), data = NULLPE;
pe_free (pe);
pe = NULLPE;
#ifdef notdef /* SEK doesn't like this */
if (called -> roa_addr.sa_selectlen == 0) {
if ((is = getisoserventbyname ("ros", "ssap")) == NULL) {
result = rosaplose (roi, ROS_ADDRESS, NULLCP,
"ssap/ros: unknown entity");
goto out2;
}
if (is -> is_selectlen > SSSIZE) { /* XXX */
result = rosaplose (roi, ROS_ADDRESS, NULLCP,
"ssap/ros: selector too long (%d octets)",
is -> is_selectlen);
goto out2;
}
bcopy (is -> is_selector, called -> roa_addr.sa_selector,
called -> roa_addr.sa_selectlen = is -> is_selectlen);
}
#endif
acb -> acb_requirements = SR_BCSUBSET;
settings = 0;
#define dotoken(requires,shift,bit,type) \
{ \
if (acb -> acb_requirements & requires) \
settings |= ST_INIT_VALUE << shift; \
}
dotokens ();
#undef dotoken
bzero ((char *) &ref, sizeof ref); /* ECMA says don't encode this yet */
if (SConnRequest (&ref, NULLSA, &called -> roa_addr,
acb -> acb_requirements, settings, SERIAL_NONE, base, len,
NULLQOS, sc, si) == NOTOK) {
result = ss2roslose (NULLACB, roi, "SConnRequest", sa);
goto out2;
}
free (base);
bzero ((char *) roc, sizeof *roc);
if (sc -> sc_result == SC_ACCEPT) {
acb -> acb_fd = sc -> sc_sd;
acb -> acb_uabort = SUAbortRequest;
}
else
if (sc -> sc_result == SC_ABORT) {
acb -> acb_fd = NOTOK;
(void) ss2rosabort (acb, sa, roi);
roc -> roc_sd = NOTOK;
roc -> roc_result = ROS_ABORTED;
return OK;
}
if ((pe = ssdu2pe (sc -> sc_data, sc -> sc_cc, NULLCP, &result))
== NULLPE) {
if (sc -> sc_result != SC_ACCEPT) {
bzero ((char *) sa, sizeof *sa);
sa -> sa_reason = sc -> sc_result;
acb -> acb_fd = NOTOK;
(void) ss2roslose (acb, roi, "SConnRequest(pseudo)", sa);
roc -> roc_sd = NOTOK;
roc -> roc_result = roi -> roi_preject.rop_reason;
result = OK;
}
else
result = ropktlose (acb, roi, result != PS_ERR_NMEM ? ROS_PROTOCOL
: ROS_CONGEST, NULLCP, "%s", ps_error (result));
goto out1;
}
SCFREE (sc);
if (sc -> sc_result != SC_ACCEPT) {
if (parse_OACS_PRefuse (pe, 1, NULLIP, NULLVP, &pref) == NOTOK) {
result = pylose ();
goto out1;
}
PLOGP (rosap_log,OACS_PRefuse, pe, "PRefuse", 1);
pe_free (pe);
freeacblk (acb);
roc -> roc_sd = NOTOK;
switch (pref.parm) {
case REFUSE_BUSY:
roc -> roc_result = ROS_BUSY;
break;
case REFUSE_VALIDATE:
roc -> roc_result = ROS_VALIDATE;
break;
default:
roc -> roc_result = ROS_PROTOCOL;
break;
}
return OK;
}
acb -> acb_flags = ACB_CONN | ACB_ROS | ACB_INIT;
(void) RoSService (acb, roi);
if (!((acb -> acb_requirements = sc -> sc_requirements) & SR_DUPLEX)
&& !(acb -> acb_requirements & SR_HALFDUPLEX)) {
result = ropktlose (acb, roi, ROS_PROTOCOL, NULLCP,
"desired session requirements denied");
goto out1;
}
if (acb -> acb_requirements & SR_HALFDUPLEX)
acb -> acb_flags |= ACB_TURN; /* it it is there we must have it */
if (parse_OACS_PAccept (pe, 1, NULLIP, NULLVP, &paccpt) == NOTOK) {
result = pylose ();
goto out1;
}
PLOGP (rosap_log,OACS_PAccept, pe, "PAccept", 1);
roc -> roc_sd = acb -> acb_fd;
roc -> roc_result = ROS_ACCEPT;
if (paccpt -> pUserData -> member_OACS_5->offset
== type_OACS_ConnectionData_open) {
roc -> roc_data = pe_expunge (pe, paccpt -> pUserData
-> member_OACS_5 -> un.open);
} else
roc -> roc_data = NULLPE;
free_OACS_PAccept (paccpt);
return OK;
out2: ;
free (base);
out1: ;
SCFREE (sc);
if (pe) {
if (data)
(void) pe_extract (pe, data);
pe_free (pe);
}
freeacblk (acb);
return result;
}
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.