|
|
DataMuseum.dkPresents historical artifacts from the history of: DKUUG/EUUG Conference tapes |
This is an automatic "excavation" of a thematic subset of
See our Wiki for more about DKUUG/EUUG Conference tapes Excavated with: AutoArchaeologist - Free & Open Source Software. |
top - metrics - downloadIndex: T i
Length: 13212 (0x339c)
Types: TextFile
Names: »ipc.c«
└─⟦2d1937cfd⟧ Bits:30007241 EUUGD22: P.P 5.0
└─⟦e83f91978⟧ »EurOpenD22/isode/osimis-2.0.tar.Z«
└─⟦d846658bd⟧
└─⟦this⟧ »osimis/sma/ipc.c«
/*
* Copyright (c) 1988 University College London
* All rights reserved.
*
* Redistribution and use in source and binary forms are permitted
* provided that the above copyright notice and this paragraph are
* duplicated in all such forms and that any documentation,
* advertising materials, and other materials related to such
* distribution and use acknowledge that the software was developed
* by the Department of Computer Science, University College London.
* The name of the University may not be used to
* endorse or promote products derived from this software without
* specific prior written permission.
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
* IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
* WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
/* ipc.c - handle the local communication side of the SMA */
/*
* By Simon Walton, October 1988
* Modified by George Pavlou, April 1990
*/
#include <stdio.h>
#include <sys/errno.h>
#include <signal.h>
#include "isode/rosap.h"
#include "isode/mpkt.h"
#include "msap.h"
#include "objects.h"
extern struct ManagedObject * MIBroot, * findcomp(), * forccomp();
extern void deletecomp();
extern MO_ID * moid_alloc();
static struct ManagedObject * IsodeEntity;
MIB_update(M)
struct MReport * M;
{
static int inited = 0;
static MO_ID invoc, cept;
static MO_ID * id1, * id2, * id3;
struct ManagedObject * mo1, * mo2;
static T_LayerEntity * entityatts;
T_EntityInvocation * invocatts;
T_ConnectionEndpoint * ceptatts;
struct TSAPaddr * taddr;
int t, prev_val;
if (inited == 0)
{
oid_copy(str2oid("2.37.1.4.1"), &invoc.rdntype);
invoc.rdnlen = sizeof (int) + 1;
oid_copy(str2oid("2.37.1.5.1"), &cept.rdntype);
cept.rdnlen = sizeof (int) + 1;
if ((id1 = moid_alloc("2.37.1.3.1", "isode")) == NULL)
ohshit("moid_alloc out of mem");
if ((id2 = moid_alloc("2.37.1.2.1", NULLCP, -1)) == NULL)
ohshit("moid_alloc out of mem");
id2 -> Next = id1;
if ((id3 = moid_alloc("2.37.1.1.1", NULLCP, -1)) == NULL)
ohshit("moid_alloc out of mem");
id3 -> Next = id2;
if ( (IsodeEntity = forccomp(MIBroot, id3)) == NULL)
ohshit("Can't create isode");
entityatts = (T_LayerEntity*) IsodeEntity -> attributes;
id1 -> Next = &invoc;
inited = 1;
}
switch (M -> type)
{
case OPREQIN:
#ifdef DEBUG
fprintf(stderr, "CR_TPDU Successful In, pid %d, cid %d\n",
M -> id, M -> cid);
#endif
bcopy((char*) &M -> id, &invoc.rdnval[1], sizeof (int));
if ( (mo1 = forccomp(IsodeEntity, &invoc)) == NULL)
return (-1);
entityatts -> activeConnections.Value++;
entityatts -> crTPDUSuccessfulIn.Value++;
invocatts = (T_EntityInvocation*) mo1 -> attributes;
invocatts -> crTPDUSuccessfulIn.Value++;
invocatts -> activeConnections.Value++;
{
int q;
q = M -> cid;
bcopy((char*) &q, &cept.rdnval[1], sizeof (int));
if ( (mo2 = forccomp(mo1, &cept)) == NULL)
return (-1);
ceptatts = (T_ConnectionEndpoint*) mo2 -> attributes;
if (ceptatts -> destinationAddress != NULL)
{
#ifdef DEBUG
fprintf(stderr, "IPC Error: Cept already exists\n");
#endif
return (-1);
}
if ( (taddr = (struct TSAPaddr*)calloc(1, sizeof (*taddr))) == NULL)
return (-1);
taddr -> ta_selectlen = M -> u.taddr.tsel_len;
bcopy(M -> u.taddr.tsel, taddr -> ta_selector, taddr -> ta_selectlen);
taddr -> ta_addrs[0] = M -> u.taddr.nsap;
ceptatts -> destinationAddress = taddr;
ceptatts -> tProtocol = tp0;
}
invoc.Next = NULL;
if (invocatts -> crTPDUSuccessfulIn.Value == 1) /* new entity */
{
entityatts -> activeEntityInvocations.Value++;
cause_DefinedEvent(mo1, id3, &invocatts -> tEntinvCreationEvent);
}
break;
case OPREQOUT:
#ifdef DEBUG
fprintf(stderr, "CR_TPDU Successful Out, pid %d, cid %d\n",
M -> id, M -> cid);
#endif
bcopy((char*) &M -> id, &invoc.rdnval[1], sizeof (int));
if ( (mo1 = forccomp(IsodeEntity, &invoc)) == NULL)
return (-1);
entityatts -> activeConnections.Value++;
entityatts -> crTPDUSuccessfulOut.Value++;
invocatts = (T_EntityInvocation*) mo1 -> attributes;
invocatts -> crTPDUSuccessfulOut.Value++;
invocatts -> activeConnections.Value++;
{
int q;
q = M -> cid;
bcopy((char*) &q, &cept.rdnval[1], sizeof (int));
if ( (mo2 = forccomp(mo1, &cept)) == NULL)
return (-1);
ceptatts = (T_ConnectionEndpoint*) mo2 -> attributes;
if (ceptatts -> destinationAddress != NULL)
{
#ifdef DEBUG
fprintf(stderr, "IPC Error: Cept already exists\n");
#endif
return (-1);
}
if ( (taddr = (struct TSAPaddr*)calloc(1, sizeof (*taddr))) == NULL)
return (-1);
taddr -> ta_selectlen = M -> u.taddr.tsel_len;
bcopy(M -> u.taddr.tsel, taddr -> ta_selector, taddr -> ta_selectlen);
taddr -> ta_addrs[0] = M -> u.taddr.nsap;
ceptatts -> destinationAddress = taddr;
ceptatts -> tProtocol = tp0;
}
invoc.Next = NULL;
if (invocatts -> crTPDUSuccessfulOut.Value == 1) /* new entity */
{
entityatts -> activeEntityInvocations.Value++;
cause_DefinedEvent(mo1, id3, &invocatts -> tEntinvCreationEvent);
}
break;
case SOURCEADDR:
#ifdef DEBUG
fprintf(stderr, "Source T-Addr notification, pid %d, cid %d\n",
M -> id, M -> cid);
#endif
bcopy((char*) &M -> id, &invoc.rdnval[1], sizeof (int));
t = M -> cid;
invoc.Next = &cept;
bcopy((char*) &t, &cept.rdnval[1], sizeof (int));
if ( (mo2 = findcomp(IsodeEntity, &invoc)) == NULL)
{
#ifdef DEBUG
fprintf(stderr, "Can't find C.Endpoint\n");
#endif
invoc.Next = NULL;
return (-1);
}
ceptatts = (T_ConnectionEndpoint*) mo2 -> attributes;
if ( (taddr = (struct TSAPaddr*)calloc(1, sizeof (*taddr))) == NULL)
return (-1);
taddr -> ta_selectlen = M -> u.taddr.tsel_len;
bcopy(M -> u.taddr.tsel, taddr -> ta_selector, taddr -> ta_selectlen);
taddr -> ta_addrs[0] = M -> u.taddr.nsap;
ceptatts -> sourceAddress = taddr;
invoc.Next = &cept;
cause_DefinedEvent(mo2, id3, &ceptatts -> tCeptCreationEvent);
invoc.Next = NULL;
break;
case USERDT:
if (M -> u.gp.a == 0)
M -> u.gp.b = 0; /* hack */
#ifdef DEBUG
fprintf(stderr, "Data Sent, pid %d, fd %d, %d bytes, %d pdus\n",
M ->id, M -> cid, M -> u.gp.a, M -> u.gp.b);
#endif
bcopy((char*) &M -> id, &invoc.rdnval[1], sizeof (int));
t = M -> cid;
bcopy((char*) &t, &cept.rdnval[1], sizeof (int));
invoc.Next = &cept;
if ( (mo2 = findcomp(IsodeEntity, &invoc)) == NULL)
{
#ifdef DEBUG
fprintf(stderr, "Can't find C.Endpoint\n");
#endif
invoc.Next = NULL;
return (-1);
}
ceptatts = (T_ConnectionEndpoint*) mo2 -> attributes;
prev_val = ceptatts -> numberTPDUSent.Value;
ceptatts -> numberTPDUSent.Value = M -> u.gp.b;
ceptatts -> numberBytesSent.Value += M -> u.gp.a;
entityatts -> numberTPDUSent.Value += M -> u.gp.b - prev_val;
check_Counter(mo2, id3, &ceptatts -> numberTPDUSent, prev_val);
invoc.Next = NULL;
break;
case USERDR:
if (M -> u.gp.a == 0)
M -> u.gp.b = 0; /* hack */
#ifdef DEBUG
fprintf(stderr, "Data Received, pid %d, fd %d, %d bytes, %d pdus\n",
M ->id, M -> cid, M -> u.gp.a, M -> u.gp.b);
#endif
bcopy((char*) &M -> id, &invoc.rdnval[1], sizeof (int));
t = M -> cid;
bcopy((char*) &t, &cept.rdnval[1], sizeof (int));
invoc.Next = &cept;
if ( (mo2 = findcomp(IsodeEntity, &invoc)) == NULL)
{
#ifdef DEBUG
fprintf(stderr, "Can't find C.Endpoint\n");
#endif
invoc.Next = NULL;
return (-1);
}
ceptatts = (T_ConnectionEndpoint*) mo2 -> attributes;
prev_val = ceptatts -> numberTPDUReceived.Value;
ceptatts -> numberTPDUReceived.Value = M -> u.gp.b;
ceptatts -> numberBytesReceived.Value += M -> u.gp.a;
entityatts -> numberTPDUReceived.Value += M -> u.gp.b - prev_val;
check_Counter(mo2, id3, &ceptatts -> numberTPDUReceived, prev_val);
invoc.Next = NULL;
break;
case OPREQINBAD:
case OPREQOUTBAD:
case CONGEST:
case CONFIGBAD:
#ifdef DEBUG
fprintf(stderr, "OPREQ Err, pid %d\n", M ->id);
#endif
bcopy((char*) &M -> id, &invoc.rdnval[1], sizeof (int));
if ( (mo1 = findcomp(IsodeEntity, &invoc)) == NULL)
{
#ifdef DEBUG
fprintf(stderr, "Can't find Entity Invocation\n");
#endif
return (-1);
}
invocatts = (T_EntityInvocation*) mo1 -> attributes;
switch (M -> type)
{
case OPREQINBAD:
entityatts -> crTPDUUnsuccessfulIn.Value++;
entityatts -> numberTPDUReceived.Value++;
check_Counter(mo1, id3, &invocatts -> crTPDUUnsuccessfulIn,
invocatts -> crTPDUUnsuccessfulIn.Value++);
break;
case OPREQOUTBAD:
entityatts -> crTPDUUnsuccessfulOut.Value++;
entityatts -> numberTPDUSent.Value++;
check_Counter(mo1, id3, &invocatts -> crTPDUUnsuccessfulOut,
invocatts -> crTPDUUnsuccessfulOut.Value++);
break;
case CONGEST:
case PROTERR:
entityatts -> crTPDUUnsuccessfulIn.Value++;
entityatts -> crTPDUCongestion.Value++;
entityatts -> numberTPDUReceived.Value++;
check_Counter(mo1, id3, &invocatts -> crTPDUUnsuccessfulIn,
invocatts -> crTPDUUnsuccessfulIn.Value++);
check_Counter(mo1, id3, &invocatts -> crTPDUCongestion,
invocatts -> crTPDUCongestion.Value++);
break;
case CONFIGBAD:
entityatts -> crTPDUUnsuccessfulIn.Value++;
entityatts -> crTPDUConfigurationError.Value++;
entityatts -> numberTPDUReceived.Value++;
check_Counter(mo1, id3, &invocatts -> crTPDUUnsuccessfulIn,
invocatts -> crTPDUUnsuccessfulIn.Value++);
check_Counter(mo1, id3, &invocatts -> crTPDUConfigurationError,
invocatts -> crTPDUConfigurationError.Value++);
break;
} /* close switch */
break;
case DISCREQ:
#ifdef DEBUG
fprintf(stderr, "Disconnect received, pid %d, fd %d\n",
M -> id, M -> cid);
#endif
bcopy((char*) &M -> id, &invoc.rdnval[1], sizeof (int));
t = M -> cid;
bcopy((char*) &t, &cept.rdnval[1], sizeof (int));
invoc.Next = &cept;
if ( (mo2 = findcomp(IsodeEntity, &invoc)) == NULL)
{
#ifdef DEBUG
fprintf(stderr, "Can't find C.Endpoint\n");
#endif
invoc.Next = NULL;
return (-1);
}
ceptatts = (T_ConnectionEndpoint*) mo2 -> attributes;
mo1 = mo2 -> parent;
invocatts = (T_EntityInvocation*) mo1 -> attributes;
invocatts -> activeConnections.Value--;
entityatts -> activeConnections.Value--;
entityatts ->previousConnections.Value++;
prev_val = ceptatts -> numberTPDUReceived.Value;
ceptatts -> numberTPDUReceived.Value = M -> u.gp.d;
ceptatts -> numberBytesReceived.Value += M -> u.gp.b;
entityatts -> numberTPDUReceived.Value += M -> u.gp.d - prev_val;
check_Counter(mo2, id3, &ceptatts -> numberTPDUReceived, prev_val);
prev_val = ceptatts -> numberTPDUSent.Value;
ceptatts -> numberTPDUSent.Value = M -> u.gp.c;
ceptatts -> numberBytesSent.Value += M -> u.gp.a;
entityatts -> numberTPDUSent.Value += M -> u.gp.c - prev_val;
check_Counter(mo2, id3, &ceptatts -> numberTPDUSent, prev_val);
cause_DefinedEvent(mo2, id3, &ceptatts ->tCeptShutdownEvent);
deletecomp(IsodeEntity, &invoc);
invoc.Next = NULL;
break;
case STARTLISTEN:
#ifdef DEBUG
fprintf(stderr, "Process %d at port %s starts listening\n",
M -> id, M -> u.taddr.tsel);
#endif
break;
case ENDLISTEN:
#ifdef DEBUG
fprintf(stderr, "Process %d at port %s stops listening\n",
M -> id, M -> u.taddr.tsel);
#endif
break;
default:
#ifdef DEBUG
fprintf(stderr, "Unknown MReport type %d\n", M -> type);
#endif
break;
} /* close switch */
return (0);
}
/* ARGSUSED */
EntInv_check(sig, sigparam, sigcontext)
int sig, sigparam;
struct sigcontext * sigcontext;
{
static MO_ID invoc, * id1, * id2, * id3;
struct ManagedObject * mo, * next;
static OID TEntClass;
T_EntityInvocation * invocatts;
static T_LayerEntity * entityatts;
extern errno;
if (IsodeEntity == NULL) return (0);
if (invoc.rdntype.oid_nelem == 0)
{
oid_copy(str2oid("2.37.1.4.1"), &invoc.rdntype);
TEntClass = oid_cpy(str2oid("2.37.1.4"));
invoc.rdnlen = sizeof (int) + 1;
if ((id1 = moid_alloc("2.37.1.3.1", "isode")) == NULL)
ohshit("moid_alloc out of mem");
id1 -> Next = &invoc;
if ((id2 = moid_alloc("2.37.1.2.1", NULLCP, -1)) == NULL)
ohshit("moid_alloc out of mem");
id2 -> Next = id1;
if ((id3 = moid_alloc("2.37.1.1.1", NULLCP, -1)) == NULL)
ohshit("moid_alloc out of mem");
id3 -> Next = id2;
entityatts = (T_LayerEntity*) IsodeEntity -> attributes;
}
for(mo = IsodeEntity -> subordinate; mo; mo = next)
{
next = mo -> sibling;
if (oid_cmp(&mo -> Class, TEntClass) == 0)
{
int pid;
bcopy(&mo -> rdnval[1], (char*) &pid, sizeof (int));
if ( kill(pid, 0) == -1 && errno == ESRCH)
{ /* entity has died */
#ifdef DEBUG
fprintf(stderr, "Entity Invocation %d has exited\n", pid);
#endif
bcopy((char*) &pid, &invoc.rdnval[1], sizeof (int));
invocatts = (T_EntityInvocation*)mo -> attributes;
if (--entityatts -> activeEntityInvocations.Value < 0)
entityatts -> activeEntityInvocations.Value = 0; /* whoops */
cause_DefinedEvent(mo, id3, &invocatts -> tEntinvShutdownEvent);
deletecomp(IsodeEntity, &invoc);
}
}
}
return (0);
}
static ohshit(s)
char * s;
{
fprintf(stderr, "Fatal: %s\n", s);
exit(1);
}