2010-03-08 04:55:21 -06:00
|
|
|
/*****************************************************************************
|
|
|
|
*
|
|
|
|
* NCSA DTM version 2.3
|
|
|
|
* May 1, 1992
|
|
|
|
*
|
|
|
|
* NCSA DTM Version 2.3 source code and documentation are in the public
|
|
|
|
* domain. Specifically, we give to the public domain all rights for future
|
|
|
|
* licensing of the source code, all resale rights, and all publishing rights.
|
|
|
|
*
|
|
|
|
* We ask, but do not require, that the following message be included in all
|
|
|
|
* derived works:
|
|
|
|
*
|
|
|
|
* Portions developed at the National Center for Supercomputing Applications at
|
|
|
|
* the University of Illinois at Urbana-Champaign.
|
|
|
|
*
|
|
|
|
* THE UNIVERSITY OF ILLINOIS GIVES NO WARRANTY, EXPRESSED OR IMPLIED, FOR THE
|
|
|
|
* SOFTWARE AND/OR DOCUMENTATION PROVIDED, INCLUDING, WITHOUT LIMITATION,
|
|
|
|
* WARRANTY OF MERCHANTABILITY AND WARRANTY OF FITNESS FOR A PARTICULAR PURPOSE
|
|
|
|
*
|
|
|
|
*****************************************************************************/
|
|
|
|
|
|
|
|
/*********************************************************************
|
|
|
|
**
|
|
|
|
** $Header: /X11/mosaic/cvsroot/xmosaic3/libdtm/nmsg.c,v 1.3 1996/02/18 23:40:15 spowers Exp $
|
|
|
|
**
|
|
|
|
**********************************************************************/
|
|
|
|
/*
|
|
|
|
#ifdef RCSLOG
|
|
|
|
|
|
|
|
$Log: nmsg.c,v $
|
|
|
|
Revision 1.3 1996/02/18 23:40:15 spowers
|
|
|
|
PROTO -> DTM_PROTO
|
|
|
|
|
|
|
|
Revision 1.2 1995/10/13 06:33:20 spowers
|
|
|
|
Solaris support added.
|
|
|
|
|
|
|
|
Revision 1.1.1.1 1995/01/11 00:03:01 alanb
|
|
|
|
New CVS source tree, Mosaic 2.5 beta 4
|
|
|
|
|
|
|
|
* Revision 2.5 1994/12/29 23:40:08 alanb
|
|
|
|
* I'm committing with a new symbolic revision number.
|
|
|
|
*
|
|
|
|
* Revision 1.1.1.1 1994/12/28 21:37:33 alanb
|
|
|
|
*
|
|
|
|
* Revision 1.2 1993/10/06 06:19:08 ebina
|
|
|
|
* Ditto const shit
|
|
|
|
*
|
|
|
|
* Revision 1.1.1.1 1993/07/04 00:03:13 marca
|
|
|
|
* Mosaic for X version 2 distribution
|
|
|
|
*
|
|
|
|
* Revision 1.1 1993/01/18 21:50:33 marca
|
|
|
|
* I think I got it now.
|
|
|
|
*
|
|
|
|
* Revision 1.15 92/04/30 20:25:27 jplevyak
|
|
|
|
* Changed Version to 2.3.
|
2013-03-09 18:59:42 -06:00
|
|
|
*
|
2010-03-08 04:55:21 -06:00
|
|
|
|
|
|
|
#endif
|
|
|
|
*/
|
|
|
|
/*
|
|
|
|
Purpose : Set of library calls for name server applications to use.
|
|
|
|
Notes :
|
|
|
|
This file contains functions to send and receive
|
|
|
|
DTM control messages such MREG, MROUTE etc.
|
|
|
|
|
|
|
|
The fd parameter should be removed from all calls
|
|
|
|
for portability.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#include <stdlib.h>
|
|
|
|
#include <string.h>
|
|
|
|
#include <sys/types.h>
|
|
|
|
#ifdef _ARCH_MSDOS
|
|
|
|
#include <nmpcip.h>
|
|
|
|
#include <errno.h>
|
|
|
|
#include "uio.h"
|
|
|
|
#else
|
|
|
|
#include <sys/socket.h>
|
|
|
|
#include <netinet/in.h>
|
|
|
|
#include <arpa/inet.h>
|
|
|
|
#include <sys/uio.h>
|
|
|
|
#include <sys/errno.h>
|
|
|
|
#endif
|
|
|
|
#include "dtmint.h"
|
|
|
|
#include "dtmnserv.h"
|
|
|
|
#include <stdio.h>
|
|
|
|
#include "debug.h"
|
|
|
|
|
|
|
|
/*
|
|
|
|
STATIC FUNCTION PROTOTYPES
|
|
|
|
*/
|
|
|
|
static int dtm_send_control DTM_PROTO(( int fd, char *msg, int msize,
|
|
|
|
char *sendto_addr ));
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
Function to send a DTM control message ( messages like MREG, MROUTE etc. )
|
|
|
|
Notes :
|
|
|
|
*/
|
|
|
|
|
|
|
|
#ifdef DTM_PROTOTYPES
|
|
|
|
static int dtm_send_control(int fd,char *msg,int msize,char *sendto_addr )
|
|
|
|
#else
|
|
|
|
static int dtm_send_control( fd, msg, msize, sendto_addr )
|
|
|
|
int fd ;
|
|
|
|
char *msg ;
|
|
|
|
int msize ;
|
|
|
|
char *sendto_addr ; /* read-only */
|
|
|
|
#endif
|
|
|
|
{
|
|
|
|
S_ADDR sockaddr ; /* destination address */
|
|
|
|
struct iovec iov[ 1 ] ; /* message iovec */
|
|
|
|
int status ; /* return value from a call */
|
|
|
|
int32 tmp ; /* temporary */
|
|
|
|
char sendaddr[ MAX132 ] ;
|
|
|
|
int fLogical;
|
|
|
|
|
|
|
|
DBGFLOW( "dtm_send_control called\n" );
|
|
|
|
DBGINT( "dtm_send_control: sendto_addr is '%s'\n", sendto_addr );
|
|
|
|
|
|
|
|
/* Get destination address in sockaddr_in structure */
|
|
|
|
|
|
|
|
strncpy( sendaddr, sendto_addr, (MAX132 - 1)) ;
|
|
|
|
sendaddr[ MAX132 - 1 ] = '\0' ;
|
|
|
|
|
|
|
|
sockaddr.sin_family = AF_INET ;
|
2013-03-09 18:59:42 -06:00
|
|
|
CHECK_ERR( dtm_init_sockaddr( &sockaddr, sendaddr, &fLogical));
|
2010-03-08 04:55:21 -06:00
|
|
|
|
|
|
|
/* Prepare iovec and send message length */
|
|
|
|
|
|
|
|
tmp = msize ;
|
|
|
|
STDINT( tmp );
|
|
|
|
iov[ 0 ].iov_base = (char *)&tmp ;
|
|
|
|
iov[ 0 ].iov_len = 4 ;
|
|
|
|
|
|
|
|
if((status = dtm_writev_buffer( fd, iov, 1, 4, (struct sockaddr *)&sockaddr,
|
|
|
|
sizeof( struct sockaddr_in ))) < 0 )
|
|
|
|
{
|
|
|
|
DBGFLOW( "dtm_send_control: message length send error\n" );
|
|
|
|
return status ;
|
2013-03-09 18:59:42 -06:00
|
|
|
}
|
2010-03-08 04:55:21 -06:00
|
|
|
|
|
|
|
/* Prepare iovec and send message */
|
2013-03-09 18:59:42 -06:00
|
|
|
|
2010-03-08 04:55:21 -06:00
|
|
|
iov[ 0 ].iov_base = msg ;
|
|
|
|
iov[ 0 ].iov_len = msize ;
|
|
|
|
|
|
|
|
return dtm_writev_buffer( fd, iov, 1, msize, (struct sockaddr *)&sockaddr,
|
|
|
|
sizeof( struct sockaddr_in )) ;
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
DTMsendDiscard
|
|
|
|
Function to send a discard message setting the discard state.
|
|
|
|
*/
|
|
|
|
#ifdef DTM_PROTOTYPES
|
|
|
|
int DTMsendDiscard(int fd,char *sendto_addr,int set_or_clear )
|
|
|
|
#else
|
|
|
|
int DTMsendDiscard( fd, sendto_addr, set_or_clear )
|
|
|
|
int fd; /* output socket */
|
|
|
|
char *sendto_addr; /* destination address addr:port number */
|
|
|
|
int set_or_clear;
|
|
|
|
#endif
|
|
|
|
{
|
|
|
|
char mbuf[ MAX132 ]; /* buffer to build messages */
|
|
|
|
|
|
|
|
DBGFLOW( "DTMsendDiscard called\n" );
|
|
|
|
|
|
|
|
sprintf( mbuf, MDISCARD, MROUTEID, set_or_clear );
|
|
|
|
|
2013-03-09 18:59:42 -06:00
|
|
|
DBGFLOW( "DTMsendDiscard: Message:- " );
|
2010-03-08 04:55:21 -06:00
|
|
|
DBGFLOW( mbuf ); DBGFLOW( "\n" );
|
|
|
|
|
2013-03-09 18:59:42 -06:00
|
|
|
return dtm_send_control( fd, mbuf, (strlen( mbuf ) + 1), sendto_addr );
|
2010-03-08 04:55:21 -06:00
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
Function to send a routing message to designated address.
|
|
|
|
Notes : delcount parameter to be added, currently
|
|
|
|
forced to zero.
|
|
|
|
Destination address, and array of addresses are in
|
|
|
|
format IPaddr( dotted decimal ):portid.
|
|
|
|
|
|
|
|
int fd; output socket
|
|
|
|
char *sendto_addr; destination address addr:port number
|
|
|
|
int addcount; number of addresses to connect to
|
|
|
|
char **add_addresses; array of addresses to connect to
|
|
|
|
int delcount; number of addresses to connect to
|
|
|
|
char **del_addresses; array of addresses to connect to
|
|
|
|
*/
|
|
|
|
|
|
|
|
#ifdef DTM_PROTOTYPES
|
|
|
|
int DTMsendRoute(int fd,char *sendto_addr,int addcount,char **add_addresses,
|
|
|
|
int delcount, char **del_addresses )
|
|
|
|
#else
|
2013-03-09 18:59:42 -06:00
|
|
|
int DTMsendRoute( fd, sendto_addr, addcount, add_addresses,
|
|
|
|
delcount, del_addresses )
|
2010-03-08 04:55:21 -06:00
|
|
|
int fd; /* output socket */
|
|
|
|
char *sendto_addr; /* destination address addr:port number */
|
|
|
|
int addcount; /* number of addresses to connect to */
|
|
|
|
char **add_addresses;/* array of addresses to connect to */
|
|
|
|
int delcount; /* number of addresses to connect to */
|
|
|
|
char **del_addresses;/* array of addresses to connect to */
|
|
|
|
#endif
|
|
|
|
{
|
|
|
|
char mbuf[ MAX132 ]; /* buffer to build messages */
|
|
|
|
|
|
|
|
DBGFLOW( "DTMsendRoute called\n" );
|
|
|
|
|
|
|
|
/* Prepare MROUTE message and send it */
|
|
|
|
|
|
|
|
sprintf( mbuf, MROUTE, MROUTEID, delcount, addcount ) ;
|
|
|
|
while( delcount-- ) {
|
|
|
|
strncat( mbuf, " ", (MAX132-1));
|
2013-03-09 18:59:42 -06:00
|
|
|
strncat( mbuf, del_addresses[ delcount ], (MAX132 - 1));
|
2010-03-08 04:55:21 -06:00
|
|
|
}
|
|
|
|
while( addcount-- ) {
|
|
|
|
strncat( mbuf, " ", (MAX132-1));
|
2013-03-09 18:59:42 -06:00
|
|
|
strncat( mbuf, add_addresses[ addcount ], (MAX132 - 1));
|
2010-03-08 04:55:21 -06:00
|
|
|
}
|
2013-03-09 18:59:42 -06:00
|
|
|
mbuf[ MAX132 - 1 ] = '\0' ;
|
2010-03-08 04:55:21 -06:00
|
|
|
|
2013-03-09 18:59:42 -06:00
|
|
|
DBGFLOW( "DTMsendRoute: Message:- " );
|
2010-03-08 04:55:21 -06:00
|
|
|
DBGFLOW( mbuf ); DBGFLOW( "\n" );
|
|
|
|
|
2013-03-09 18:59:42 -06:00
|
|
|
return dtm_send_control( fd, mbuf, (strlen( mbuf ) + 1), sendto_addr );
|
2010-03-08 04:55:21 -06:00
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
Function to send ack to routing message to designated address.
|
|
|
|
NOTE: this function is not used yet as the name server has
|
|
|
|
not implemented the receive portion.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#ifdef DTM_PROTOTYPES
|
|
|
|
int dtm_nsend_ackroute( char *portname )
|
|
|
|
#else
|
|
|
|
int dtm_nsend_ackroute( portname )
|
|
|
|
char *portname ;
|
|
|
|
#endif
|
|
|
|
{
|
|
|
|
int fd ;
|
|
|
|
S_ADDR addr;
|
|
|
|
char *sendto_addr ;
|
|
|
|
char *refname = dtm_get_refname() ;
|
|
|
|
char mbuf[ MAX132 ]; /* buffer to build messages */
|
|
|
|
|
|
|
|
CHECK_ERR( sendto_addr = dtm_get_naddr( &addr, &fd ));
|
|
|
|
|
|
|
|
DBGFLOW( "dtm_nsend_ackroute called\n" );
|
|
|
|
|
|
|
|
/* Prepare Ackroute, send it */
|
|
|
|
|
|
|
|
sprintf( mbuf, MACKROUTE, MACKROUTEID, refname, portname );
|
|
|
|
mbuf[ MAX132 - 1 ] = '\0' ;
|
|
|
|
|
2013-03-09 18:59:42 -06:00
|
|
|
DBGFLOW( "dtm_nsend_ackroute: Message:- " );
|
2010-03-08 04:55:21 -06:00
|
|
|
DBGFLOW( mbuf ); DBGFLOW( "\n" );
|
|
|
|
|
2013-03-09 18:59:42 -06:00
|
|
|
return dtm_send_control( fd, mbuf, (strlen( mbuf ) + 1), sendto_addr );
|
2010-03-08 04:55:21 -06:00
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
Function to send self's socket address to name server process.
|
|
|
|
*/
|
|
|
|
|
|
|
|
#ifdef DTM_PROTOTYPES
|
|
|
|
dtm_nsend_sockaddr(int fd,char *sendto_addr,char *refname,char *portname,
|
|
|
|
S_ADDR *sockaddr )
|
|
|
|
#else
|
|
|
|
dtm_nsend_sockaddr( fd, sendto_addr, refname, portname, sockaddr )
|
|
|
|
int fd ;
|
|
|
|
char *sendto_addr ;
|
|
|
|
char *refname ;
|
|
|
|
char *portname ;
|
|
|
|
S_ADDR *sockaddr ;
|
|
|
|
#endif
|
|
|
|
{
|
|
|
|
struct in_addr inaddr ;
|
|
|
|
char mbuf[ MAX132 ]; /* buffer to build messages */
|
|
|
|
|
|
|
|
DBGFLOW( "dtm_nsend_sockaddr called\n" );
|
|
|
|
|
|
|
|
/* Prepare MREG, send it */
|
|
|
|
|
|
|
|
inaddr.s_addr = sockaddr -> sin_addr.s_addr ;
|
|
|
|
#ifdef _ARCH_MSDOS
|
|
|
|
sprintf( mbuf, MREG, MREGID, refname, portname,
|
|
|
|
inet_ntoa( inaddr.s_addr ), ntohs( sockaddr -> sin_port ) );
|
|
|
|
#else
|
|
|
|
sprintf( mbuf, MREG, MREGID, refname, portname,
|
|
|
|
inet_ntoa( inaddr ), ntohs( sockaddr -> sin_port ) );
|
|
|
|
#endif
|
|
|
|
mbuf[ MAX132 - 1 ] = '\0' ;
|
|
|
|
|
|
|
|
DBGFLOW( "dtm_nsend_sockaddr: Message:- " ); DBGFLOW( mbuf ); DBGFLOW( "\n" );
|
|
|
|
|
|
|
|
return dtm_send_control( fd, mbuf, (strlen( mbuf ) + 1), sendto_addr );
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
Function to recieve registation messages from other processes.
|
|
|
|
Notes : does not block, return length is message
|
|
|
|
received, 0 otherwise
|
|
|
|
|
|
|
|
*/
|
|
|
|
#ifdef DTM_PROTOTYPES
|
|
|
|
int DTMrecvRegistration(int fd,char *buffer,int len)
|
|
|
|
#else
|
|
|
|
int DTMrecvRegistration(fd, buffer, len)
|
|
|
|
int fd, len;
|
|
|
|
char *buffer;
|
|
|
|
#endif
|
|
|
|
{
|
|
|
|
int count;
|
|
|
|
|
|
|
|
if( dtm_quick_select(fd, &count) )
|
|
|
|
return dtm_recv_header(fd, buffer, len);
|
|
|
|
else
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
Function to create a nameserver port for receiving registration
|
|
|
|
messages and sending routing messages.
|
|
|
|
|
|
|
|
*/
|
2013-03-09 18:59:42 -06:00
|
|
|
|
2010-03-08 04:55:21 -06:00
|
|
|
#ifdef DTM_PROTOTYPES
|
|
|
|
int DTMmakeNameServerPort(char *portid)
|
|
|
|
#else
|
|
|
|
int DTMmakeNameServerPort(portid)
|
|
|
|
char *portid;
|
|
|
|
#endif
|
|
|
|
{
|
|
|
|
struct sockaddr_in saddr;
|
2013-03-09 18:59:42 -06:00
|
|
|
|
2010-03-08 04:55:21 -06:00
|
|
|
|
|
|
|
saddr.sin_family = AF_INET;
|
|
|
|
saddr.sin_addr.s_addr = htonl(0);
|
|
|
|
saddr.sin_port = htons(0);
|
|
|
|
|
|
|
|
if (strcmp(portid, ":0") != 0)
|
|
|
|
saddr.sin_port = htons((unsigned short)atoi(strchr(portid, ':')+1));
|
|
|
|
|
|
|
|
return dtm_socket_init( &saddr, OUTPORTTYPE, NOT_LOGICAL_NAME );
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
|
|
|
|
Fucntion to get the port address of the name server port.
|
|
|
|
|
|
|
|
++++ should be a socket.c function that returns bound address of
|
|
|
|
socket file descriptor
|
|
|
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
#ifdef DTM_PROTOTYPES
|
|
|
|
int DTMgetNameServerAddr(int fd,char *name,int len)
|
|
|
|
#else
|
|
|
|
int DTMgetNameServerAddr(fd, name, len)
|
|
|
|
int fd, len;
|
|
|
|
char *name;
|
|
|
|
#endif
|
|
|
|
{
|
|
|
|
char pnum[8];
|
|
|
|
struct sockaddr_in saddr;
|
|
|
|
int saddr_size = sizeof (struct sockaddr_in);
|
|
|
|
|
|
|
|
if (dtm_get_ipaddr(name) == 0) {
|
|
|
|
DTMerrno = DTMHOST;
|
|
|
|
return DTMERROR;
|
|
|
|
}
|
|
|
|
|
|
|
|
if (getsockname( fd, (struct sockaddr *)&saddr, &saddr_size ) < 0 ) {
|
|
|
|
#ifndef _ARCH_MSDOS
|
|
|
|
extern int errno ;
|
|
|
|
#endif
|
|
|
|
DBGINT( "dtm_socket_init: Unable to get sin_port, errno %d\n", errno );
|
|
|
|
DTMerrno = DTMSOCK ;
|
|
|
|
return -1 ;
|
|
|
|
}
|
|
|
|
|
|
|
|
sprintf(pnum, ":%d", (int)ntohs( saddr.sin_port ));
|
|
|
|
strcat(name, pnum);
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|