1 /* Loglan82 Compiler&Interpreter
2 Copyright (C) 1981-1993 Institute of Informatics, University of Warsaw
3 Copyright (C) 1993, 1994 LITA, Pau
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
19 contacts: Andrzej.Salwicki@univ-pau.fr
22 LITA Departement d'Informatique
24 Avenue de l'Universite
26 tel. ++33 59923154 fax. ++33 59841696
28 =======================================================================
47 struct sockaddr_in addr;
52 static int node2book[ MAX_NODES ]; /* only 256 nodes - can be changed */
55 static void sock_recv_from( void *, int, struct sockaddr_in * );
56 static void sock_recv_from( buf, buflen, from_addr )
59 struct sockaddr_in *from_addr;
61 struct sockaddr_in addr;
64 if( ( retval = sock_recv( sock, buf, buflen, &addr ) ) < 0 )
65 perror("receive"),abend("no answer from master");
67 from_addr->sin_port != addr.sin_port
69 from_addr->sin_addr.s_addr != addr.sin_addr.s_addr
73 fprintf( stderr, "unexpected message from %s:%d length %d\n",
74 inet_ntoa( from_addr->sin_addr ),
75 (int)ntohs( from_addr->sin_port ),
83 /* nn.nn.nn.nn:port address */
84 void tcpip_connect_to_master( addr ) char *addr; {
89 struct sockaddr_in m_address;
91 for( aux = 0; aux < MAX_NODES; aux++ )
92 node2book[ aux ] = -1;
94 if( host_addr( host, &m_address ) < 0 ){
95 perror("invalid host name:");
99 sock = sock_open( SOCK_DGRAM, "udp", NULL, 0 ); /* any port */
100 if( sock < 0 ) perror("can't open any socket"),exit(10);
103 struct sockaddr_in addr;
104 int namelen = sizeof(struct sockaddr_in);
105 getsockname( sock, &addr, &namelen );
106 fprintf( stderr, "socket opened on %s:%d\n",
107 inet_ntoa(addr.sin_addr),
108 (int)ntohs(addr.sin_port)
112 aux = htonl( console );
113 sock_send( sock, &aux, sizeof(aux), &m_address );
115 stderr, "waiting for acknowledge from %s:%d\n",
116 host, (int)ntohs( m_address.sin_port )
119 sock_recv_from( &aux, sizeof(aux), &m_address );
120 slaves = ntohl( aux );
121 fprintf( stderr, "answer from master: %d interpreters\n", slaves );
123 phone_book = (struct addr *)calloc( slaves, sizeof( struct addr ) );
124 if( phone_book==NULL ) abend("can't allocate table of addresses");
126 sock_recv_from( &aux, sizeof(aux), &m_address );
127 phone_book[0].console = ntohl( aux );
128 phone_book[0].addr = m_address;
130 fprintf( stderr, "master console %d at %s:%d\n",
131 phone_book[0].console,
132 inet_ntoa(phone_book[0].addr.sin_addr),
133 (int)ntohs(phone_book[0].addr.sin_port)
136 node2book[ phone_book[ 0 ].console ] = 0;
140 for( i=1; i<slaves; i++ ){ /* on 0 will be master */
142 sock_recv_from( &aux, sizeof(aux), &m_address );
143 phone_book[i].console = ntohl( aux );
145 &(phone_book[i].addr),
146 sizeof(struct sockaddr_in),
149 fprintf( stderr, "interpreter %d connected at %s:%d\n",
150 phone_book[i].console,
151 inet_ntoa(phone_book[i].addr.sin_addr),
152 (int)ntohs(phone_book[i].addr.sin_port)
154 node2book[ phone_book[ i ].console ] = i;
158 fprintf( stderr, "\nprogram started\n\n" );
164 void tcpip_wait_for_slaves( _slaves ) int _slaves; {
168 struct sockaddr_in slave_address;
169 int namelen = sizeof(struct sockaddr_in);
171 for( aux = 0; aux < MAX_NODES; aux++ )
172 node2book[ aux ] = -1;
176 phone_book = (struct addr *)calloc( slaves, sizeof( struct addr ) );
177 if( phone_book==NULL ) abend("can't allocate table of addresses");
179 sock = sock_open( SOCK_DGRAM, "udp", NULL, PORT );
180 if( sock < 0 ) perror("master socket"),abend("can't install master");
182 phone_book[0].console = console;
183 getsockname( sock, &(phone_book[0].addr), &namelen );
184 assert( namelen == sizeof( struct sockaddr_in ) );
186 fprintf( stderr, "waiting for %d slaves on console %d at %s:%d\n",
188 phone_book[0].console,
189 inet_ntoa(phone_book[0].addr.sin_addr),
190 (int)ntohs(phone_book[0].addr.sin_port)
193 node2book[ console ] = 0;
195 while( _slaves > 0 ){
197 if( sock_recv( sock , &slave_console, sizeof(slave_console), &slave_address ) < 0 )
198 perror("server receive"),abend("can't connect slave");
200 fprintf( stderr, "slave %d connected at %s:%d\n",
201 ntohl(slave_console),
202 inet_ntoa(slave_address.sin_addr),
203 (int)ntohs(slave_address.sin_port)
206 slave_console = ntohl( slave_console );
208 phone_book[_slaves].console = slave_console;
209 phone_book[_slaves].addr = slave_address;
211 if( node2book[ slave_console ] != -1 ){
212 fprintf( stderr, "node %d already bound\n", slave_console );
215 node2book[ slave_console ] = _slaves;
221 fprintf( stderr, "all slaves notified - sending acknowledges\n" );
225 for( i=1; i<slaves; i++ ){
228 sock_send( sock, &aux, sizeof(aux), &(phone_book[i].addr) );
230 aux = htonl(console);
231 sock_send( sock, &aux, sizeof(aux), &(phone_book[i].addr) );
233 for( j=1; j<slaves; j++ ){
234 aux = htonl(phone_book[j].console);
235 sock_send( sock, &aux, sizeof(aux), &(phone_book[i].addr) );
238 &(phone_book[j].addr),
239 sizeof(struct sockaddr_in),
240 &(phone_book[i].addr)
246 fprintf( stderr, "\nprogram started\n\n" );
250 void tcpip_send( msg ) message *msg; {
251 int node = msg->control.receiver.node;
252 int ix = node2book[ node ];
254 fprintf( stderr, "tcpip send message to not existing node %d\n", node );
258 fprintf( stderr, "tcpip send message to node %d indx %d\n", node, ix );
264 &( phone_book[ ix ].addr )
268 bool tcpip_poll( ms ) int ms; {
269 return sock_poll( sock, ms );
272 bool tcpip_recv( msg ) message *msg; {
274 struct sockaddr_in addr;
275 if( ( retval = sock_recv( sock, msg, sizeof( message ), &addr ) ) < 0 ){
280 if( retval == sizeof( message ) )
282 fprintf(stderr,"tcpip recv message from node %d\n",msg->control.sender.node);
284 fprintf(stderr,"tcpip recv incorrect message from node %d\n",msg->control.sender.node);
286 return ( retval == sizeof( message ) );