DataMuseum.dkPresents historical artifacts from the history of: Rational R1000/400 Tapes |
This is an automatic "excavation" of a thematic subset of
See our Wiki for more about Rational R1000/400 Tapes Excavated with: AutoArchaeologist - Free & Open Source Software. |
top - downloadIndex: ┃ T ┃
Length: 45502 (0xb1be) Types: TextFile Names: »TCPLIB_C«
└─⟦afbc8121e⟧ Bits:30000532 8mm tape, Rational 1000, MC68020_OS2000 7_2_2 └─ ⟦77aa8350c⟧ »DATA« └─⟦f794ecd1d⟧ └─⟦this⟧
/*****************************************************************************/ /* */ /* TCP/IP interface between application and driver. */ /* */ /* All calls to the TCP/IP driver are made trough routines in this file. */ /* This file shall be linked with the application programs. */ /* */ /* If switch ERR_REPORT is active the file TCPERR.C also must be linked with */ /* the application programs. */ /* */ /* Application programs may also have to include MSOCKET.H */ /* */ /* The function of each routine is described elsewhere in this file. */ /* */ /* Notes: */ /* 'Port' in OS9 corresponds to 'Socket' in ADA.C */ /* */ /* The parameter iocpara.timeout is passed to the driver. It specifies how */ /* long the program shall wait for an interrupt response from the board. */ /* */ /*---------------------------------------------------------------------------*/ /* Programmer: Lars Engdahl Mikrotell. 87.06.30 */ /* --------------------------------------------------------------------------*/ /* Entries: */ /* -------- */ /* nopen */ /* nsocket */ /* nconnect */ /* naccept */ /* nread */ /* nreread */ /* nwrite */ /* nioctl */ /* nsocketaddr */ /*****************************************************************************/ /*\f */ #include "../INCL/msocket.h" /* get the structs shown below */ #define ERR_REPORT /* to get error report */ #define ERR_PRINT /* to get error printout */ int tcp_errno; /* Error code, returned from libcalls below is placed here */ /*----------------------------------------------------------------------------*/ /* The FUNC_xxxxx defines below are also defined in TCPDRIVER.A */ /* These codes are used as parameters to TCPDRIVER.A */ #asm FUNC_READ equ 140 FUNC_WRITE equ 141 FUNC_SOIOCTL equ 142 FUNC_SOCLOSE equ 143 FUNC_CLEANUP equ 160 ERR_DRV equ $EE00 #endasm /*----------------------------------------------------------------------------*/ /*\f */ /*----------------------------------------------------------------------------*/ /* struct sockaddr */ /* { */ /* short sin_family */ /* Ushort sin_port */ /* Ulong sin_addr */ /* char sin_data[8] */ /* } */ /*----------------------------------------------------------------------------*/ /* struct sockproto not used in OS9 */ /* { */ /* short sp_family */ /* short sp_protocoll */ /* } */ /*----------------------------------------------------------------------------*/ /* /* struct ioc_para */ /* Used to pass parameters to driver */ /* { /* short reply ; */ /* must be first */ /* int type; */ /* int cmd; */ /* int sock_id ; */ /* char *bufptr ; */ /* int length ; */ /* short iamroot; */ /* short isaddr; */ /* int options; */ /* struct sockaddr asa; */ /* int timeout; */ /* }; */ /*-------------------------------------------------------------------------*/ int device_id; /*-------------------------------------------------------------------------*/ /*\f */ /*==========================================================================*/ /* NOPEN Open device driver. */ /* */ /* Call: dev_id = nopen() */ /* */ /* Purpose: Open device driver. */ /* */ /* Input: --- */ /* */ /* Output: dev_id = to be used on following calls to nsocket, nsockaddr */ /* naccept, nconnect, nread, nioctl, nwrite, nclose. */ /* */ /* Driver : ---- */ /* */ /* ERROR: dev_id -1 errornumber in tcp_errno. */ /*--------------------------------------------------------------------------*/ /* Corresponding ADA procedure: none */ /*==========================================================================*/ int nopen() { int dev_id ; #ifdef TRACE printf("TCPLIB: nopen()\n"); #endif dev_id = open("/tcpdev",3); #ifdef ERR_PRINT if (dev_id==-1) printf("TCPLIB: nopen() *** ERROR. Can't open TCP device.\n"); #endif #ifdef TRACE printf("TCPLIB: nopen() done. dev_id =x%x\n", dev_id); #endif device_id = dev_id ; /* used by intercept routine */ init_intercept(); return (dev_id) ; } /*--------------------------------------------------------------------------*/ /*\f */ /*===========================================================================*/ /* NSOCKET create an end point for communication. */ /* */ /* If the socket is to be used for acccept the specified portnumber must be */ /* used by the connecting device. ( in struct asa ) */ /* */ /* Call: socket_id = nsocket(dev_id,type,asp,asa,options) */ /* */ /* input: dev_id = process-path id. (returned from nopen) */ /* type = defines sematics for comm. Only SOCK_STREAM is supported. */ /* *asp = protocoll family. Must be a NULL pointer. */ /* *asa = Used to define a specific local port. */ /* This is the port the Remote will make a connect on. */ /* */ /* 1. If *asa is a NULL pointer the EXOS board */ /* will pick an available port. */ /* nsocketaddr() can be used to find out what port */ /* value it picked. */ /* 2. If a specific port is desired: */ /* asa.sin_port := Local_Port_Number; */ /* asa.sin_family := AF_INET; (address family) */ /* */ /* options = SO_ACCEPTCONN must be used with sockets for accept */ /* */ /* output: socket_id to be used on following accept,connect,open,close requ */ /* */ /* Error: sock_id = -1. errornumber in tcp_errno. */ /* */ /* Driver: xsoioctl in MEXSOCKET */ /*---------------------------------------------------------------------------*/ /* Corresponding ADA procedure: */ /* Procedure Open( Connection: out Transport.Connection_Id; */ /* Status: out Transport_Defs.Status_Type; */ /* Network: Transport_Defs.Network_Name; */ /* Local_Socket: Transport_Defs.Socket_Id ); */ /* */ /* INPUT: Network: = "TCP/IP" */ /* Local_Socket: If Null then the system will pick one. */ /* OUTPUT: Connection: To be used in subsequent procedure calls. */ /* Status: Error message. */ /*===========================================================================*/ /*\f */ int nsocket(dev_id,type,asp,asa,options) int dev_id; /* returned from previuos mopen */ int type; /* must be SOCK_STREAM */ struct sockproto *asp; /* must be a NULL pointer. */ struct sockaddr *asa; /* */ int options; { short sock_id; struct ioc_para iocpara ; /* used to pass param to driver */ #ifdef TRACE printf("TCPLIB: nsocket(). dev_id = x%x\n",dev_id); #endif iocpara.cmd = SOSOCKET; iocpara.type = SOCK_STREAM; /* ? or input param 'type' */ iocpara.options = options; iocpara.iamroot = 1; /* always considered privileged */ iocpara.timeout = 2000 ; /* timeout in ticks for board response */ if (asa == (struct sockaddr *) 0 ) iocpara.isaddr = 0 ; else { iocpara.isaddr = 1 ; iocpara.asa.sin_family = asa->sin_family ; iocpara.asa.sin_port = asa->sin_port ; iocpara.asa.sin_addr = asa->sin_addr ; } mso_ioctl(dev_id,&iocpara) ; tcp_errno = iocpara.reply ; #ifdef TRACE printf("TCPLIB: nsocket() done. sock_id =x%x. Reply = x%x \n", iocpara.sock_id,iocpara.reply); #endif if (tcp_errno != 0 ) goto error; return iocpara.sock_id; error: #ifdef ERR_REPORT print_error(tcp_errno,"nsocket()."); #else #ifdef ERR_PRINT printf("TCPLIB: *** ERROR in routine nsocket(): ErrCode = x%x\n",tcp_errno); #endif #endif return -1; } /*--------------------------------------------------------------------------*/ /*\f */ /*===========================================================================*/ /* NSOCKADDR get own address and port. */ /* */ /* If the socket is to be used for acccept the specified portnumber must be */ /* known by the connecting device. */ /* */ /* Call: status = nsockaddr(dev_id,sock_id,asa) */ /* */ /* input: dev_id = process-path id. (returned from nopen) */ /* *asa = ...Used to define a specific local port. */ /* This is the port the Remote will make a connect on. */ /* */ /* output: The result is the same result that a remote host would get from */ /* an naccept call if you connected to him. */ /* asa.sin_port = Local port */ /* asa.sin_addr = Local Host address <<< addr does not work >>> */ /* */ /* Error: sock_id = -1. errornumber in tcp_errno. */ /* */ /* Driver: xsoioctl in MEXSOCKET */ /*---------------------------------------------------------------------------*/ /* Corresponding ADA procedures: Local_Host(...) , Local_Socket(....) */ /*===========================================================================*/ /*\f */ int nsockaddr(dev_id,sock_id,asa) int dev_id; /* returned from previuos mopen */ int sock_id; struct sockaddr *asa; /* */ { struct ioc_para iocpara ; /* used to pass param to driver */ #ifdef TRACE printf("TCPLIB: nsockaddr().\n"); #endif iocpara.cmd = SOSOCKETADDR; iocpara.sock_id = sock_id; iocpara.type = SOCK_STREAM; /* ? or input param 'type' */ iocpara.timeout = 2000 ; /* timeout in ticks for board response */ iocpara.isaddr = 1 ; mso_ioctl(dev_id,&iocpara) ; tcp_errno = iocpara.reply ; if (tcp_errno != 0 ) goto error; asa->sin_port = iocpara.asa.sin_port ; /* driver placed Local port here*/ asa->sin_addr = iocpara.asa.sin_addr ; /* driver placed Local addr here*/ #ifdef TRACE printf("TCPLIB: nsockaddr() done. addr =x%x. Port = x%x \n", asa->sin_addr,asa->sin_port); #endif return 0; error: #ifdef ERR_REPORT print_error(tcp_errno,"nsockaddr()."); #else #ifdef ERR_PRINT printf("TCPLIB: *** ERROR in routine nsockaddr(): ErrCode= x%x\n",tcp_errno); #endif #endif return -1; } /*--------------------------------------------------------------------------*/ /*\f */ /*===========================================================================*/ /* NCONNECT initiates a connection request. */ /* */ /* Call: status = nconnect(dev_id,sock_id,asa) */ /* */ /* input: dev_id: device id, returned from previus mopen() */ /* sock_id: socket_id returned by previus socket() call. */ /* asa: pointer to struct with Remote Host's address and port. */ /* (address the remote is making an accept at() */ /* */ /* asa.sin-family = AF_INET */ /* asa.sin-port = Remote_Port_Number */ /* asa.sin_addr = Remote_Host_addr */ /* */ /* output: 0 is returned when the conection is established. */ /* -1 is returned if error. */ /* */ /* output: rval = -1 -- error. (error number is placed in tcp_errno) */ /* */ /* Driver: xsoioctl in MEXSOCKET */ /*---------------------------------------------------------------------------*/ /* Corresponding ADA procedure: */ /* */ /* Procedure Connect -- active connect */ /* ( */ /* Connection : Transport.connection_Id; -- returned from open */ /* Status : out Transport_Defs.Status_Type; */ /* Remote_Host : Transport_Defs.Host_Id; -- remote Host id. */ /* Remote_Socket: Transport_Defs.Socket_Id; -- remote socket id. */ /* Max_Wait : Duration := Duration'last; */ /* ); */ /* */ /*===========================================================================*/ /*\f */ nconnect(dev_id,sock_id,asa) int dev_id; /* returned from previuos mopen */ short sock_id; struct sockaddr *asa; { struct ioc_para iocpara ; /* used to pass param to driver */ #ifdef TRACE printf("TCPLIB: nconnect()\n"); #endif iocpara.cmd = SOCONNECT ; iocpara.timeout = 4000 ; /* timeout in ticks for board response */ iocpara.type = SOCK_STREAM; iocpara.sock_id = sock_id ; iocpara.isaddr = 1 ; iocpara.isaddr = 1 ; iocpara.asa.sin_family = asa->sin_family ; iocpara.asa.sin_port = asa->sin_port ; iocpara.asa.sin_addr = asa->sin_addr ; mso_ioctl(dev_id,&iocpara) ; tcp_errno = iocpara.reply ; #ifdef TRACE printf("TCPLIB: nconnect() done. Reply = x%x\n",iocpara.reply); #endif if (tcp_errno != 0 ) goto error; return 0; error: #ifdef ERR_REPORT print_error(tcp_errno,"nconnect()."); #else #ifdef ERR_PRINT printf("TCPLIB: *** ERROR in routine nconnect(): ErrCode = x%x\n",tcp_errno); #endif #endif return -1; } /*--------------------------------------------------------------------------*/ /*\f */ /*===========================================================================*/ /* NACCEPT provides the "listen end" of the protocoll handshake. */ /* */ /* Call: status = naccept(dev_id,sock_id,asa) */ /* */ /* input: dev_id: device id, returned from previus mopen() */ /* sock_id: socket_id returned by previus socket() call. */ /* asa: pointer to struct where connecting process' address and */ /* portnumber is returned. */ /* */ /* output: if accept is successful: connecting process' address and portno */ /* asa.sin-port = Remote_Port_Number */ /* asa.sin_addr = Remote_Host_addr */ /* */ /* 0 is returned when the connection is established. */ /* -1 error. (error number is placed in tcp_errno)? */ /* */ /* Driver: xsoioctl in MEXSOCKET */ /*---------------------------------------------------------------------------*/ /* Corresponding ADA procedure: Procedure Connect(....) -- passive connect */ /*===========================================================================*/ /*\f */ naccept(dev_id,sock_id,asa) int dev_id; /* returned from previuos mopen */ short sock_id; struct sockaddr *asa; { struct ioc_para iocpara ; /* used to pass param to driver */ #ifdef TRACE printf("TCPLIB: naccept()\n"); #endif iocpara.cmd = SOACCEPT ; iocpara.timeout = 0000 ; /* no timeout */ iocpara.type = SOCK_STREAM; /* do I need this ??? */ iocpara.isaddr = 1 ; /* do I need this ??? */ iocpara.sock_id = sock_id ; mso_ioctl(dev_id,&iocpara) ; tcp_errno = iocpara.reply; if (tcp_errno != 0 ) goto error; asa->sin_port = iocpara.asa.sin_port ; /* driver placed Remote port here */ asa->sin_addr = iocpara.asa.sin_addr ; /* driver placed Remote addr here */ #ifdef TRACE printf("TCPLIB: naccept() done. addr =x%x. Port = x%x \n", asa->sin_addr,asa->sin_port); #endif return 0; error: #ifdef ERR_REPORT print_error(tcp_errno,"naccept()."); #else #ifdef ERR_PRINT printf("TCPLIB: *** ERROR in routine naccept(). ErrCode = x%x\n",tcp_errno); #endif #endif return -1; } /*--------------------------------------------------------------------------*/ /*\f */ /*===========================================================================*/ /* NIOCTL. */ /* */ /* Call:status = nioctl(dev_id,sock_id,func,para) */ /* */ /* input: dev_id: device id, returned from previus mopen() */ /* sock_id: socket_id returned by previus socket() call. */ /* ioctlcmd: Code for function to perform: */ /* para: pointer to in/out parameter. */ /* */ /* output: Depends on ioctlcmd: see below */ /* ------------------------------------------------------------------------ */ /* FIONREAD: Returns a byte count (in parameter 'para') of data in the */ /* socket's receive buffer. */ /* The user can use this before a nread() to avoid waiting for data.*/ /* ------------------------------------------------------------------------ */ /* FIONBIO: Enable/disable nonblocking IO */ /* input: *para = 1 - enable nonblocking IO */ /* input *para = 0 - disable nonblocking IO */ /* no output in *para. */ /* ------------------------------------------------------------------------ */ /* other functions may work, (if they are made 'not comments'). */ /* belived to be supported in driver ?? but are not tested (yet). */ /* ------------------------------------------------------------------------ */ /* */ /* output = -1 = error. (error number is placed in tcp_errno) */ /* */ /* Driver: xsoioctl - xsocontrol in MEXSOCKET */ /*---------------------------------------------------------------------------*/ /* Corresponding ADA procedure: ????? */ /*===========================================================================*/ /*\f */ nioctl(dev_id,sock_id,func,para) int dev_id; /* returned from previuos mopen */ short sock_id; short func; /* function code */ int *para; { struct ioc_para iocpara ; /* used to pass param to driver */ #ifdef TRACE printf("TCPLIB: nioctl()\n"); #endif iocpara.cmd = func ; /* = FIONREAD or FIONBIO ... ? */ iocpara.timeout = 2000 ; /* timeout in ticks for board response */ iocpara.sock_id = sock_id ; /* check if a valid (implemented) function request */ switch(func) { case FIONREAD : /* ret no of bytes in rec buffer */ /* case SIOCGKEEP: */ /* case SIOCGLINGER: */ /* case SIOCRCVOOB: */ /* case SIOCATMARK: */ /* case SIOCGPGRP: */ break; /* no input parameter tu functions above */ /* case SIOCSENDOOB: */ case FIONBIO: /* enable disable nonblocking IO*/ /* case SIOCDONE: */ /* case SIOCSKEEP: */ /* case SIOCSLINGER: */ /* case SIOCSPGRP: */ iocpara.options = *para ; break; default: tcp_errno = 0x5500 ; goto error; /* err code to be def later???*/ } mso_ioctl(dev_id,&iocpara) ; tcp_errno = iocpara.reply ; #ifdef TRACE printf("TCPLIB: nioctl() done. reply = x%x *para = %x\n", iocpara.reply,iocpara.options ); #endif if (tcp_errno != 0 ) goto error; /* ---- put result (if any) in *para ---- */ switch(func) { case FIONREAD : /* ret no of bytes (int) in rec buf*/ /* case SIOCGKEEP: */ /* these returns a short */ /* case SIOCGLINGER: */ /* case SIOCATMARK: */ /* case SIOCGPGRP: */ /* case SIOCRCVOOB: */ /* this returns a char */ *para = iocpara.options ; break; } return 0; error: #ifdef ERR_REPORT print_error(tcp_errno,"nioctl()."); #else #ifdef ERR_PRINT printf("TCPLIB: *** ERROR in routine nioctl(). ErrCode = x%x\n",tcp_errno); #endif #endif return -1; } /*-------------------------------------------------------------------------*/ /*\f */ /*===========================================================================*/ /* interface for driver call from nsocket,nsockaddr, naccept, nconnect,nioctl*/ /* return 0 if OK, -1 if error. return data in struct ioc_para. */ /*===========================================================================*/ #asm mso_ioctl: MOVEM.L D1/A0,-(A7) MOVE.L D1,A0 /* A0 = pntr to ioc_para structure */ MOVE.W #FUNC_SOIOCTL,D1 /* D1 = funtion code passed to driver */ /* D0 = parameter path to OS-9 call */ OS9 I$GetStt BCS.S err_mso /* error if carry set */ MOVEM.L (A7)+,D1/A0 RTS * err_mso MOVE.W #ERR_DRV,(A0) /* return error code in parptr-reply */ MOVEM.L (A7)+,D1/A0 RTS #endasm /*---------------------------------------------------------------------------*/ /*\f */ /*==========================================================================*/ /* NREAD */ /* */ /* Call: no_of_bytes = nread(id,s_id,bufptr,buflen) */ /* no_of_bytes = nreread(id,s_id,bufptr,buflen) << no timeout >> */ /* */ /* If the connection is still open but no message is in the queue, nread */ /* wait for the message. */ /* If the remote host is disconnected, nread will return zero. */ /* wait for the message. */ /* If bufflen < the maximum packet size (1024) and the message is > than */ /* buflen, buflen bytes will be read and the rest of the packet will be lost.*/ /* Therefore allways use a readbuffer with size >= 1024. */ /* */ /* Input: dev_id = device id. (returned from previus nopen) */ /* sock_id = socket id. (returned from previus nsocket) */ /* r_length = max no of bytes. */ /* r_buff = pointer to read buffer. */ /* */ /* output: no_of_bytes = -1 -- error. (errornumber is placed in tcp_errno)*/ /* no_of_bytes number of bytes read. */ /* */ /* Driver: xsoread in MEXSOCKET */ /*--------------------------------------------------------------------------*/ /* Corresponding ADA procedure: */ /* */ /* Procedure Receive */ /* ( */ /* Connection : Transport.connection_Id; */ /* Status : out Transport_Defs.Status_Code; */ /* Data : out Byte_Defs.Byte_String; */ /* Count : out Natural; */ /* Max_Wait : Duration := Duration'last; */ /* ); */ /*===========================================================================*/ /*\f */ int nread(dev_id,sock_id,r_buff,r_length) int dev_id; int sock_id; int r_length; char *r_buff; { struct ioc_para iocpara; int count; #ifdef TRACE printf("TCPLIB: nread()\n"); #endif iocpara.timeout = 0000 ; /* no timeout for board response */ iocpara.sock_id = sock_id ; iocpara.bufptr = r_buff ; iocpara.length = r_length ; read_call(dev_id,&iocpara) ; tcp_errno = iocpara.reply; if (tcp_errno != 0 ) goto error; #ifdef TRACE printf("TCPLIB: nread() done. reply = x%x count = %x\n", iocpara.reply,iocpara.length ); #endif return (iocpara.length) ; error: #ifdef ERR_REPORT print_error(tcp_errno,"nread()."); #else #ifdef ERR_PRINT printf("TCPLIB: *** ERROR in routine nread(). ErrCode = x%x\n",tcp_errno); #endif #endif return -1; } /*==========================================================================*/ /* <<<<< not tested >>>>>> */ /*--------------------------------------------------------------------------*/ int nreread(dev_id,sock_id,r_buff,r_length) int dev_id,sock_id,r_length; char *r_buff; { struct ioc_para iocpara; int count; #ifdef TRACE printf("TCPLIB: nreread()\n"); #endif iocpara.timeout = 0000 ; /* no timeout for board response */ iocpara.sock_id = sock_id ; iocpara.bufptr = r_buff ; iocpara.length = r_length ; read_call(dev_id,&iocpara) ; tcp_errno = iocpara.reply; if (tcp_errno != 0 ) goto error; #ifdef TRACE printf("TCPLIB: nreread() done. reply = x%x count = %x\n", iocpara.reply,iocpara.length ); #endif return (iocpara.length) ; error: #ifdef ERR_REPORT print_error(tcp_errno,"nreread()."); #else #ifdef ERR_PRINT printf("TCPLIB: *** ERROR in routine nreread(). ErrCode = x%x\n",tcp_errno); #endif #endif return -1; } /*--------------------------------------------------------------------------*/ /* interface for driver call from nread, nreread */ /* return 0 if OK, -1 if error. return data in struct ioc_para. */ /*--------------------------------------------------------------------------*/ #asm read_call: MOVEM.L D1/A0,-(A7) MOVE.L D1,A0 /* A0 = pntr ioc_para structure */ MOVE.W #FUNC_READ,D1 /* D1 = funtion code passed to driver */ /* D0 = parameter path to OS-9 call */ OS9 I$GetStt BCS.S err_rea /* error if carry set */ MOVEM.L (A7)+,D1/A0 RTS err_rea MOVE.W #ERR_DRV,(A0) /* return error code in parptr-reply */ MOVEM.L (A7)+,D1/A0 RTS #endasm /*---------------------------------------------------------------------------*/ /*\f */ /*==========================================================================*/ /* NWRITE */ /* */ /* input: id: returned from previus mopen() */ /* s_id: socket_id returned by previus socket() call. */ /* s_buff: pointer to the message. */ /* s_length: length of the message. */ /* */ /* output: 0 number of written bytes. */ /* -1 -- error. (errornumber is placed in tcp_errno) */ /* */ /* Driver: xsowrite in MEX_SOCKET */ /*--------------------------------------------------------------------------*/ /* Corresponding ADA procedure: */ /* */ /* Procedure Transmit */ /* ( */ /* Connection : Transport.connection_Id; */ /* Status : out Transport_Defs.Status_Type; */ /* Data : out Byte_Defs.Byte_String; */ /* Count : out Natural; */ /* Max_Wait : Duration := Duration'last; */ /* More : Boolean := False */ /* ); */ /*===========================================================================*/ /*\f */ int nwrite(dev_id,sock_id,s_buff,s_length) int dev_id,sock_id,s_length; char *s_buff; { struct ioc_para iocpara; #ifdef TRACE printf("TCPLIB: nwrite()\n"); #endif iocpara.timeout = 8000 ; /* timeout in ticks for board response */ iocpara.sock_id = sock_id ; iocpara.bufptr = s_buff ; iocpara.length = s_length ; write_call(dev_id,&iocpara) ; tcp_errno = iocpara.reply; if (tcp_errno != 0 ) goto error; #ifdef TRACE printf("TCPLIB: nwrite() done. reply = x%x count = %x\n", iocpara.reply,iocpara.length ); #endif return (iocpara.length) ; error: #ifdef ERR_REPORT print_error(tcp_errno,"nwrite()."); #else #ifdef ERR_PRINT printf("TCPLIB: *** ERROR in routine nwrite(). ErrCode = x%x\n",tcp_errno); #endif #endif return -1; } /*--------------------------------------------------------------------------*/ /* interface for driver call from write */ /* return 0 if OK, -1 if error. return data in struct ioc_para. */ /*--------------------------------------------------------------------------*/ #asm write_call: MOVEM.L D1/A0,-(A7) MOVE.L D1,A0 /* A0 = pntr ioc_para structure */ MOVE.W #FUNC_WRITE,D1 /* D1 = funtion code passed to driver */ /* D0 = parameter path to OS-9 call */ OS9 I$GetStt BCS.S err_wri /* error if carry set */ MOVEM.L (A7)+,D1/A0 RTS err_wri MOVE.W #ERR_DRV,(A0) /* return error code in parptr-reply */ MOVEM.L (A7)+,D1/A0 RTS #endasm /*---------------------------------------------------------------------------*/ /*\f */ /*==========================================================================*/ /* MSOCLOSE */ /* dont close driver only socket. */ /* input: dev_id: returned from previus mopen() */ /* sock_id: socket_id returned by previus nsocket() call. */ /* */ /* output: 0 OK */ /* -1 -- error. (errornumber is placed in tcp_errno) */ /* */ /* Driver: xsoclose in MEXSOCKET */ /*--------------------------------------------------------------------------*/ /* Corresponding ADA procedure: */ /* Procedure Disconnect ( Connection: Connection: Transport.Connection_Id );*/ /*===========================================================================*/ /*\f */ int nsoclose(dev_id,sock_id) int dev_id,sock_id; { struct ioc_para iocpara; #ifdef TRACE printf("TCPLIB: nsoclose()\n"); #endif iocpara.timeout = 2000 ; /* timeout in ticks for board response */ iocpara.sock_id = sock_id ; soclose_call(dev_id,&iocpara) ; tcp_errno = iocpara.reply; if (tcp_errno != 0 ) goto error; #ifdef TRACE printf("TCPLIB: nsoclose() done. status = x%x\n",iocpara.reply); #endif return 0 ; error: #ifdef ERR_REPORT print_error(tcp_errno,"nsoclose()."); #else #ifdef ERR_PRINT printf("TCPLIB: *** ERROR in routine nsoclose(). ErrCode = x%x\n",tcp_errno); #endif #endif return(-1); } /*---------------------------------------------------------------------------*/ /* interface for driver call from soclose */ /* return 0 if OK, -1 if error. return data in struct ioc_para. */ /*---------------------------------------------------------------------------*/ #asm soclose_call: MOVEM.L D1/A0,-(A7) MOVE.L D1,A0 /* A0 = pntr ioc_para structure */ MOVE.W #FUNC_SOCLOSE,D1 /* D1 = funtion code passed to driver */ /* D0 = parameter path to OS-9 call */ OS9 I$GetStt BCS.S err_scl /* error if carry set */ MOVEM.L (A7)+,D1/A0 RTS err_scl MOVE.W #ERR_DRV,(A0) /* return error code in parptr-reply */ MOVEM.L (A7)+,D1/A0 RTS #endasm /*---------------------------------------------------------------------------*/ /*\f */ /*==========================================================================*/ /* */ /* rval = nclose(id,s_id) perform an OS-9 close. */ /* if s_id >0 then also the socket is closed. */ /* (see nsoclose) */ /* Call: rval = nclose(dev_id,sock_id) */ /* */ /* input: dev_id: returned from previus mopen() */ /* sock_id: socket_id returned by previus socket() call. */ /* if =0 nsoclose is not called. */ /* if >0 a nsoclose is first performed. */ /* output: >=0 OK . */ /* -1 if error */ /* */ /* Driver: */ /*--------------------------------------------------------------------------*/ /* Corresponding ADA procedure: */ /* Procedure Close ( Connection: Transport.Connection_Id ); */ /*===========================================================================*/ int nclose(dev_id,sock_id) int dev_id; short sock_id; { int status ; #ifdef TRACE printf("TCPLIB: nclose()\n"); #endif if (sock_id >0 ) nsoclose(dev_id,sock_id); /* no error handling ???? */ status = close(dev_id); #ifdef TRACE printf("TCPLIB: nclose() done. status = x%x\n",status); #endif return (status); } /*==========================================================================*/ /*\f */ /*===========================================================================*/ /* Whenever the process receives a signal this routine is executed. */ /* (an exception is the S$Wake signal sent by the interrrupt routine). */ /* control C -> signal code = 3 */ /* control E -> signal code = 2 */ /*===========================================================================*/ /* assembler routine t set up the intercept routine */ #asm init_intercept: MOVEM.L A0,-(sp) LEA call_intercept(pc),A0 OS9 F$Icpt MOVEM.L (sp)+,A0 RTS call_intercept: BSR tcp_intercept /* entry intercept routine sigcode in D1.W */ OS9 F$RTE #endasm /*===========================================================================*/ tcp_intercept(dummy,signalcode) int dummy,signalcode; { switch(signalcode & 0xffff) { case 2: /* control E was pressed. Abort process. (after cleaning)*/ /* first perform some cleaning up, then exit process. */ #ifdef ERR_PRINT printf (">>>>>>>> Control E was pressed. Abort process. (after cleaning up.)\n"); #endif tcp_cleanup( getpid() ); exit(); case 3: /* control C was pressed. */ /* just return. If the driver was waiting for a board */ /* interrupt. Error code ERR_ABORT will be returned to */ /* the caller which must do his own error handling. */ #ifdef ERR_PRINT printf(">>>>>>>> Control C was pressed. Process interrupted.\n"); #endif break; default: #ifdef ERR_PRINT printf("TCPLIB: tcp_intercept() signalcode = %x.\n",signalcode); #endif exit(); } } /*===========================================================================*/ /* This function will free resoures on the EXOS bord owned by the process */ /* specified by the input parameter pid. */ /*===========================================================================*/ tcp_cleanup(pid) int pid ; { struct ioc_para iocpara; iocpara.type = pid; #ifdef ERR_PRINT printf("TCPLIB: tcp_cleanup() calling driver. Process id = x%x\n",pid); #endif cleanup_call(device_id,&iocpara) ; } /*===========================================================================*/ /* interface for driver call from tcp_cleanup to xsocleanup in MEXSOCKET.C */ /* return 0 if OK, -1 if error. return data in struct ioc_para. */ /*===========================================================================*/ #asm cleanup_call: MOVEM.L D1/A0,-(A7) MOVE.L D1,A0 /* A0 = pntr to ioc_para structure */ MOVE.W #FUNC_CLEANUP,D1 /* D1 = funtion code passed to driver */ /* D0 = parameter path to OS-9 call */ OS9 I$GetStt BCS.S err_cln /* error if carry set */ MOVEM.L (A7)+,D1/A0 RTS * err_cln MOVE.W #ERR_DRV,(A0) /* return error code in parptr-reply */ MOVEM.L (A7)+,D1/A0 RTS #endasm /*===========================================================================*/