-
Notifications
You must be signed in to change notification settings - Fork 284
/
Copy pathgdomap.h
234 lines (215 loc) · 9.29 KB
/
gdomap.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
/* Include for communications with GNUstep Distributed Objects name server.
Copyright (C) 1996, 1997 Free Software Foundation, Inc.
Written by: Richard Frith-Macdonald <[email protected]>
Created: October 1996
This file is part of the GNUstep Project.
This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
You should have received a copy of the GNU General Public
License along with this program; see the file COPYING.
If not, write to the Free Software Foundation,
31 Milk Street #960789 Boston, MA 02196 USA.
*/
/*
* About the GNU Distributed Objects name-server
*
* The name server is intended to work with both the UDP and the TCP
* protocols. It is intended that the TCP interface be used by
* GNUstep programs, while the UDP interface is intended primarily
* for communication between name servers on different machines.
*
* The communications protocol is identical for both TCP and UDP and
* consists of a simple request-response sequence.
*
* Each request is a single message consisting of -
* a single byte request type,
* a single byte giving name length,
* a single byte specifying the type of port being registered
* or looked up, or a nul byte for probe operations.
* a single nul byte.
* a four byte port number in network byte order must be
* present for register operations, otherwise this is zero.
* a service name of 0 to GDO_NAME_MAX_LEN bytes (or two IP
* addresses in network byte order and an optional list of
* additional addresseso for probe operations)
* 0 to GDO_NAME_MAX_LEN nul bytes padding the service name to its
* full size.
* a terminating nul byte.
* The total is always sent in a packet with everything after the
* service name (except the final byte) cleared to nul bytes.
*
* Each response consists of at least 4 bytes and depends on the
* corresponding request type and where it came from as follows -
*
* Request type Effect
*
* GDO_LOOKUP Looks up the server name and returns its port number.
* Response is the port number in network byte order,
* or zero if the named server was not registered.
*
* GDO_REGISTER Registers the given server name with a port number.
* This service is only available to processes on the
* same host as the name server.
* Response is the port number in network byte order,
* or zero if the named server was already registered.
*
* GDO_UNREG Un-register the server name and return old port number.
* If the server name is of length zero, and the port is
* non-zero then all names for the port are unregistered.
* This service is only available to a process on the
* same host as this name server.
* Response is the old port number in network byte order,
* or zero if the name could not be un-registered.
* If multiple names were unregistered the response is
* the port for those names.
*
* GDO_SERVERS Return a list of the known servers on the local net.
* Response is an unsigned long (in network byte order)
* saying how many servers the name server knows about,
* followed by a list of their IP addresses in network
* byte order.
* NB. This response may not be possible over UDP as the
* response length may exceed the maximum UDP packet size.
*
* GDO_NAMES Return a list of registered names known to the server.
* Response is an unsigned long (in network byte order)
* saying how many bytes of data are to follow,
* followed by a list of the names each preceded by the
* name length (a single byte) and port type (a byte).
* NB. This response may not be possible over UDP as the
* response length may exceed the maximum UDP packet size.
*
* The following are used for communications between name servers -
*
* GDO_PROBE Requests a response
* Passes two IP addresses in the name field - first the
* address of the sender, next that of the recipient.
* The packet may (optionally) include a variable number
* of addresses (as specified by the name length minus the
* size of the two addresses), each of which is an internet
* address on which the sender is also listening.
* For a request from a name server via UDP there is no
* response, but a GDO_REPLY request is sent.
* For a request from a non-name-server, or a TCP
* connect, the response is the port number of this
* server in network byte order.
*
* GDO_PREPLY Replies to a GDO_PROBE via UDP from a name server.
* The format of the message is as for GDO_PROBE.
* No response is sent.
*
*
* HOW IT WORKS AND WHY (implementation notes)
*
* 1. The fixed size of a request packet was chosen for maximum
* ease and speed of implementation of a non-blocking name server.
* The server knows how much it needs to read and can therefore
* usually do a read as a single operation since it doesn't have
* to read a little, figure out request length, allocate a buffer,
* and read the rest.
*
* The server name length (bytes) is specified - no assumptions
* should be made about whether the name contains nul characters
* or indeed about the name at all. This is future-proofing.
*
* 2. Why UDP as well as TCP?
* The OpenStep specification says that a connection may be
* established to any host on the local network which supplys a
* named service if the host name is specified as '*'
*
* This means that the application must poll to see if it can
* find a server with the name it wants. The polling could take
* a huge amount of time!
*
* To make this all easier - the server is capable of supplying
* a list of those hosts on the local network which it knows to
* have (or have had) a name server running on them.
*
* The application then need only poll those name servers to find
* the service it wants.
*
* However - to give the application a list of hosts, the name
* server must have got the information from somewhere.
* To gather the information the server has to poll the machines
* on the net which would take ages using TCP since attempts to
* talk to machines which are down or do not exist will take a
* while to time out.
*
* To make things speedy, the server sends out GDO_PROBE requests
* on UDP to all the machines on the net when it starts up.
* Each machine which has a name server notes that the new name
* server has started up and sends back a GDOPREPLY packet so
* that the new name server will know about it.
*
* Things are never perfect though - if a name server dies, the
* other name servers won't know, and will continute to tell
* applications that it is there.
*
* 3. Port type codes - these are used to say what the port is for so
* that clients can look up only the names that are relevant to them.
* This is to permit the name server to be used for multiple
* communications protocols (at the moment, tcp or udp) and for
* different systems (distributed objects or others).
* This guarantees that if one app is using DO over UDP, its services
* will not be found by an app which is using DO over TCP.
*/
#define GDOMAP_PORT (538) /* The well-known port for name server. */
/*
* Request type codes
*/
#define GDO_REGISTER 'R'
#define GDO_LOOKUP 'L'
#define GDO_UNREG 'U'
#define GDO_SERVERS 'S'
#define GDO_PROBE 'P'
#define GDO_PREPLY 'p'
#define GDO_NAMES 'N'
/*
* Port type codes
*/
#define GDO_NET_MASK 0x70 /* Network protocol of port. */
#define GDO_NET_TCP 0x10
#define GDO_NET_UDP 0x20
#define GDO_SVC_MASK 0x0f /* High level protocol of port. */
#define GDO_SVC_GDO 0x01
#define GDO_SVC_FOREIGN 0x02
/* tcp/ip distributed object server. */
#define GDO_TCP_GDO (GDO_NET_TCP|GDO_SVC_GDO)
/* udp/ip distributed object server. */
#define GDO_UDP_GDO (GDO_NET_UDP|GDO_SVC_GDO)
/* tcp/ip simple socket connection. */
#define GDO_TCP_FOREIGN (GDO_NET_TCP|GDO_SVC_FOREIGN)
/* udp/ip simple socket connection. */
#define GDO_UDP_FOREIGN (GDO_NET_UDP|GDO_SVC_FOREIGN)
#define GDO_NAME_MAX_LEN 255 /* Max length registered name. */
/*
* Structure to hold a request.
*/
typedef struct {
unsigned char rtype; /* Type of request being made. */
unsigned char nsize; /* Length of the name to use. */
unsigned char ptype; /* Type of port registered. */
unsigned char dummy;
unsigned int port;
unsigned char name[GDO_NAME_MAX_LEN+1];
} gdo_req;
#define GDO_REQ_SIZE sizeof(gdo_req) /* Size of a request packet. */
/*
* If you have a fascist sysadmin who will not let you run gdomap
* as root and will not even let you modify /etc/services to point
* gdomap to another port, you can uncomment the next #define to
* run gdomap on port 6006 (or modify this to a port of your choice).
* Whatever port you choose, you should make sure that no other
* processes running on your network use that number!
*
* When you have done this you must recompile gdomap.c and
* NSPortNameServer.m and re-install the base library with
* the new NSPortNameServer.o
*
* NB. Doing this will render your system unable to communicate with
* other systems which have not performed the same remapping. You
* should not do it unless you have no choice.
*/
/* #define GDOMAP_PORT_OVERRIDE 6006 */