Various minor windows bugfixes and documentation cleanups.

git-svn-id: svn+ssh://svn.gna.org/svn/gnustep/libs/base/trunk@13167 72102866-910b-0410-8b05-ffd578937521
This commit is contained in:
CaS 2002-03-20 12:03:30 +00:00
parent 2200a7bdc9
commit ebd91ac5c5
6 changed files with 148 additions and 28 deletions

View file

@ -3,6 +3,14 @@
* Source/GSString.m: lossyCString_u() handle case where cString * Source/GSString.m: lossyCString_u() handle case where cString
contains more bytes than unicode string has characters. contains more bytes than unicode string has characters.
* Tools/gdomap.c: Suppress unnecessary warnings except under debug. * Tools/gdomap.c: Suppress unnecessary warnings except under debug.
Implement spawning to run as daemon under windoze.
* Source/GSTcpPort.m: Fix to stop multiple servers trying to use
the same port under windoze.
* Source/WindowsFileHandle.m: Fix to stop multiple servers trying to use
the same port under windoze. Fix to return gdomap port even if
getservbyname() doesn't.
* Source/UnixFileHandle.m: Fix to return gdomap port even if
getservbyname() doesn't.
2002-03-19 Richard Frith-Macdonald <rfm@gnu.org> 2002-03-19 Richard Frith-Macdonald <rfm@gnu.org>

View file

@ -1447,14 +1447,22 @@ static Class tcpPortClass;
NSLog(@"unable to create socket - %s", GSLastErrorStr(errno)); NSLog(@"unable to create socket - %s", GSLastErrorStr(errno));
DESTROY(port); DESTROY(port);
} }
#ifndef __MINGW__
/*
* Under unix, SO_REUSEADDR means that the port can be reused
* immediately that this porcess exits. Under windoze it means
* that multiple processes can serve the same port simultaneously.
* We don't want that windows behavior!
*/
else if (setsockopt(desc, SOL_SOCKET, SO_REUSEADDR, (char*)&reuse, else if (setsockopt(desc, SOL_SOCKET, SO_REUSEADDR, (char*)&reuse,
sizeof(reuse)) < 0) sizeof(reuse)) < 0)
{ {
(void) close(desc); (void) close(desc);
NSLog(@"unable to set reuse on socket - %s", NSLog(@"unable to set reuse on socket - %s",
GSLastErrorStr(errno)); GSLastErrorStr(errno));
DESTROY(port); DESTROY(port);
} }
#endif
else if (bind(desc, (struct sockaddr *)&sockaddr, else if (bind(desc, (struct sockaddr *)&sockaddr,
sizeof(sockaddr)) < 0) sizeof(sockaddr)) < 0)
{ {
@ -1664,12 +1672,20 @@ static Class tcpPortClass;
{ {
NSLog(@"unable to create socket - %s", GSLastErrorStr(errno)); NSLog(@"unable to create socket - %s", GSLastErrorStr(errno));
} }
#ifndef __MINGW__
/*
* Under unix, SO_REUSEADDR means that the port can be reused
* immediately that this porcess exits. Under windoze it means
* that multiple processes can serve the same port simultaneously.
* We don't want that windows behavior!
*/
else if (setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, (char*)&opt, else if (setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, (char*)&opt,
sizeof(opt)) < 0) sizeof(opt)) < 0)
{ {
(void)close(sock); (void)close(sock);
NSLog(@"unable to set reuse on socket - %s", GSLastErrorStr(errno)); NSLog(@"unable to set reuse on socket - %s", GSLastErrorStr(errno));
} }
#endif
else if ((handle = [GSTcpHandle handleWithDescriptor: sock]) == nil) else if ((handle = [GSTcpHandle handleWithDescriptor: sock]) == nil)
{ {
(void)close(sock); (void)close(sock);

View file

@ -38,6 +38,8 @@
#include <Foundation/NSHost.h> #include <Foundation/NSHost.h>
#include <Foundation/NSByteOrder.h> #include <Foundation/NSByteOrder.h>
#include "../Tools/gdomap.h"
#if defined(__MINGW__) #if defined(__MINGW__)
#include <winsock2.h> #include <winsock2.h>
#else #else
@ -104,8 +106,9 @@ getAddr(NSString* name, NSString* svc, NSString* pcl, struct sockaddr_in *sin)
struct servent *sp; struct servent *sp;
if (pcl) if (pcl)
proto = [pcl cString]; {
proto = [pcl lossyCString];
}
memset(sin, '\0', sizeof(*sin)); memset(sin, '\0', sizeof(*sin));
sin->sin_family = AF_INET; sin->sin_family = AF_INET;
@ -122,11 +125,11 @@ getAddr(NSString* name, NSString* svc, NSString* pcl, struct sockaddr_in *sin)
name = [host address]; name = [host address];
#ifndef HAVE_INET_ATON #ifndef HAVE_INET_ATON
sin->sin_addr.s_addr = inet_addr([name cString]); sin->sin_addr.s_addr = inet_addr([name lossyCString]);
if (sin->sin_addr.s_addr == INADDR_NONE) if (sin->sin_addr.s_addr == INADDR_NONE)
return NO; return NO;
#else #else
if (inet_aton([name cString], &sin->sin_addr) == 0) if (inet_aton([name lossyCString], &sin->sin_addr) == 0)
return NO; return NO;
#endif #endif
} }
@ -138,14 +141,15 @@ getAddr(NSString* name, NSString* svc, NSString* pcl, struct sockaddr_in *sin)
sin->sin_port = 0; sin->sin_port = 0;
return YES; return YES;
} }
else if ((sp = getservbyname([svc cString], proto)) == 0) else if ((sp = getservbyname([svc lossyCString], proto)) == 0)
{ {
const char* ptr = [svc cString]; const char* ptr = [svc lossyCString];
int val = atoi(ptr); int val = atoi(ptr);
while (isdigit(*ptr)) while (isdigit(*ptr))
ptr++; {
ptr++;
}
if (*ptr == '\0' && val <= 0xffff) if (*ptr == '\0' && val <= 0xffff)
{ {
gsu16 v = val; gsu16 v = val;
@ -153,8 +157,21 @@ getAddr(NSString* name, NSString* svc, NSString* pcl, struct sockaddr_in *sin)
sin->sin_port = GSSwapHostI16ToBig(v); sin->sin_port = GSSwapHostI16ToBig(v);
return YES; return YES;
} }
else if (strcmp(ptr, "gdomap") == 0)
{
gsu16 v;
#ifdef GDOMAP_PORT_OVERRIDE
v = GDOMAP_PORT_OVERRIDE
#else
v = 538; // IANA allocated port
#endif
sin->sin_port = GSSwapHostI16ToBig(v);
return YES;
}
else else
return NO; {
return NO;
}
} }
else else
{ {

View file

@ -37,6 +37,8 @@
#include <Foundation/NSHost.h> #include <Foundation/NSHost.h>
#include <Foundation/NSByteOrder.h> #include <Foundation/NSByteOrder.h>
#include "../Tools/gdomap.h"
#include <winsock2.h> #include <winsock2.h>
#include <fcntl.h> #include <fcntl.h>
@ -71,7 +73,7 @@ getAddr(NSString* name, NSString* svc, NSString* pcl, struct sockaddr_in *sin)
struct servent *sp; struct servent *sp;
if (pcl) if (pcl)
proto = [pcl cString]; proto = [pcl lossyCString];
memset(sin, '\0', sizeof(*sin)); memset(sin, '\0', sizeof(*sin));
sin->sin_family = AF_INET; sin->sin_family = AF_INET;
@ -89,11 +91,11 @@ getAddr(NSString* name, NSString* svc, NSString* pcl, struct sockaddr_in *sin)
name = [host address]; name = [host address];
#ifndef HAVE_INET_ATON #ifndef HAVE_INET_ATON
sin->sin_addr.s_addr = inet_addr([name cString]); sin->sin_addr.s_addr = inet_addr([name lossyCString]);
if (sin->sin_addr.s_addr == INADDR_NONE) if (sin->sin_addr.s_addr == INADDR_NONE)
return NO; return NO;
#else #else
if (inet_aton([name cString], &sin->sin_addr) == 0) if (inet_aton([name lossyCString], &sin->sin_addr) == 0)
return NO; return NO;
#endif #endif
} }
@ -105,9 +107,9 @@ getAddr(NSString* name, NSString* svc, NSString* pcl, struct sockaddr_in *sin)
sin->sin_port = 0; sin->sin_port = 0;
return YES; return YES;
} }
else if ((sp = getservbyname([svc cString], proto)) == 0) else if ((sp = getservbyname([svc lossyCString], proto)) == 0)
{ {
const char* ptr = [svc cString]; const char* ptr = [svc lossyCString];
int val = atoi(ptr); int val = atoi(ptr);
while (isdigit(*ptr)) while (isdigit(*ptr))
@ -120,8 +122,21 @@ getAddr(NSString* name, NSString* svc, NSString* pcl, struct sockaddr_in *sin)
sin->sin_port = GSSwapHostI16ToBig(v); sin->sin_port = GSSwapHostI16ToBig(v);
return YES; return YES;
} }
else if (strcmp(ptr, "gdomap") == 0)
{
gsu16 v;
#ifdef GDOMAP_PORT_OVERRIDE
v = GDOMAP_PORT_OVERRIDE
#else
v = 538; // IANA allocated port
#endif
sin->sin_port = GSSwapHostI16ToBig(v);
return YES;
}
else else
return NO; {
return NO;
}
} }
else else
{ {
@ -307,8 +322,6 @@ getAddr(NSString* name, NSString* svc, NSString* pcl, struct sockaddr_in *sin)
return nil; return nil;
} }
setsockopt(net, SOL_SOCKET, SO_REUSEADDR, (char *)&status, sizeof(status));
if (bind(net, (struct sockaddr *)&sin, sizeof(sin)) < 0) if (bind(net, (struct sockaddr *)&sin, sizeof(sin)) < 0)
{ {
NSLog(@"unable to bind to port %s:%d - %s", NSLog(@"unable to bind to port %s:%d - %s",

View file

@ -127,7 +127,7 @@
typedef unsigned char *uptr; typedef unsigned char *uptr;
static int is_daemon = 0; /* Currently running as daemon. */ static int is_daemon = 0; /* Currently running as daemon. */
static int debug = 0; /* Extra debug gdomap_logging. */ static int debug = 0; /* Extra debug gdomap_logging. */
static int nobcst = 0; /* turn off broadcast probing. */ static int nobcst = 0; /* turn off broadcast probing. */
static int nofork = 0; /* turn off fork() for debugging. */ static int nofork = 0; /* turn off fork() for debugging. */
static int noprobe = 0; /* disable probe for unknown servers. */ static int noprobe = 0; /* disable probe for unknown servers. */
@ -1646,12 +1646,20 @@ init_ports()
gdomap_log(LOG_CRIT); gdomap_log(LOG_CRIT);
exit(1); exit(1);
} }
#ifndef __MINGW__
/*
* Under windoze, REUSEADDR means something different from under unix.
* It lets multiple processes bind to the same port at once -
* which we don't want. So we only set it under unix (to allow a process to
* bind to the same port immediately after one which was using the port exits.
*/
r = 1; r = 1;
if ((setsockopt(udp_desc,SOL_SOCKET,SO_REUSEADDR,(char*)&r,sizeof(r)))<0) if ((setsockopt(udp_desc,SOL_SOCKET,SO_REUSEADDR,(char*)&r,sizeof(r)))<0)
{ {
sprintf(ebuf, "Unable to set 're-use' on UDP socket"); sprintf(ebuf, "Unable to set 're-use' on UDP socket");
gdomap_log(LOG_WARNING); gdomap_log(LOG_WARNING);
} }
#endif
if (nobcst == 0) if (nobcst == 0)
{ {
r = 1; r = 1;
@ -1698,7 +1706,8 @@ init_ports()
sa.sin_port = my_port; sa.sin_port = my_port;
if (bind(udp_desc, (void*)&sa, sizeof(sa)) < 0) if (bind(udp_desc, (void*)&sa, sizeof(sa)) < 0)
{ {
sprintf(ebuf, "Unable to bind address to UDP socket"); sprintf(ebuf,
"Unable to bind address to UDP socket. Perhaps gdomap is already running");
gdomap_log(LOG_ERR); gdomap_log(LOG_ERR);
if (errno == EACCES) if (errno == EACCES)
{ {
@ -1725,12 +1734,21 @@ init_ports()
gdomap_log(LOG_CRIT); gdomap_log(LOG_CRIT);
exit(1); exit(1);
} }
#ifndef __MINGW__
/*
* Under windoze, REUSEADDR means something different from under unix.
* It lets multiple processes bind to the same port at once -
* which we don't want. So we only set it under unix (to allow a process to
* bind to the same port immediately after one which was using the port exits.
*/
r = 1; r = 1;
if ((setsockopt(tcp_desc,SOL_SOCKET,SO_REUSEADDR,(char*)&r,sizeof(r)))<0) if ((setsockopt(tcp_desc,SOL_SOCKET,SO_REUSEADDR,(char*)&r,sizeof(r)))<0)
{ {
sprintf(ebuf, "Unable to set 're-use' on TCP socket"); sprintf(ebuf, "Unable to set 're-use' on TCP socket");
gdomap_log(LOG_WARNING); gdomap_log(LOG_WARNING);
} }
#endif
#ifdef __MINGW__ #ifdef __MINGW__
dummy = 1; dummy = 1;
if (ioctlsocket(tcp_desc, FIONBIO, &dummy) < 0) if (ioctlsocket(tcp_desc, FIONBIO, &dummy) < 0)
@ -1764,7 +1782,8 @@ init_ports()
sa.sin_port = my_port; sa.sin_port = my_port;
if (bind(tcp_desc, (void*)&sa, sizeof(sa)) < 0) if (bind(tcp_desc, (void*)&sa, sizeof(sa)) < 0)
{ {
sprintf(ebuf, "Unable to bind address to UDP socket"); sprintf(ebuf,
"Unable to bind address to TCP socket. Perhaps gdomap is already running");
gdomap_log(LOG_ERR); gdomap_log(LOG_ERR);
if (errno == EACCES) if (errno == EACCES)
{ {
@ -2616,13 +2635,24 @@ handle_request(int desc)
} }
else else
{ {
#ifndef __MINGW__
int r = 1; int r = 1;
/*
* Under windoze, REUSEADDR means something different from
* under unix.
* It lets multiple processes bind to the same port at once -
* which we don't want. So we only set it under unix (to allow
* a process to bind to the same port immediately after one
* which was using the port exits.
*/
if (setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, if (setsockopt(sock, SOL_SOCKET, SO_REUSEADDR,
(char*)&r, sizeof(r)) < 0) (char*)&r, sizeof(r)) < 0)
{ {
perror("unable to set socket options"); perror("unable to set socket options");
} }
else else
#endif
{ {
struct sockaddr_in sa; struct sockaddr_in sa;
int result; int result;
@ -2707,11 +2737,17 @@ handle_request(int desc)
} }
else else
{ {
/* FIXME: This is weird -- Unix lets you set
SO_REUSEADDR and still returns -1 upon bind() to that
addr? - bjoern */
#ifndef __MINGW__ #ifndef __MINGW__
int r = 1; int r = 1;
/*
* Under windoze, REUSEADDR means something different from
* under unix.
* It lets multiple processes bind to the same port at once -
* which we don't want. So we only set it under unix (to allow
* a process to bind to the same port immediately after one
* which was using the port exits.
*/
if (setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, if (setsockopt(sock, SOL_SOCKET, SO_REUSEADDR,
(char*)&r, sizeof(r)) < 0) (char*)&r, sizeof(r)) < 0)
{ {
@ -4368,7 +4404,27 @@ printf(
} }
} }
#ifndef __MINGW__ /* On Win32, we don't fork */ #ifdef __MINGW__ /* On Win32, we don't fork */
if (nofork == 0)
{
char **a = malloc((argc+2) * sizeof(char*));
memcpy(a, argv, argc*sizeof(char*));
a[argc] = "-f";
a[argc+1] = 0;
if (_spawnv(_P_NOWAIT, argv[0], a) == -1)
{
fprintf(stderr, "gdomap - spawn failed - bye.\n");
exit(1);
}
if (debug)
{
sprintf(ebuf, "initialisation complete.");
gdomap_log(LOG_DEBUG);
}
exit(0);
}
#else
if (nofork == 0) if (nofork == 0)
{ {
is_daemon = 1; is_daemon = 1;
@ -4401,7 +4457,6 @@ printf(
exit(0); exit(0);
} }
} }
#endif /* !__MINGW__ */
if (pidfile) { if (pidfile) {
{ {
@ -4427,12 +4482,18 @@ printf(
for (c = 0; c < FD_SETSIZE; c++) for (c = 0; c < FD_SETSIZE; c++)
{ {
if (c != 2) if (c != 2)
(void)close(c); {
(void)close(c);
}
} }
(void)open("/dev/null", O_RDONLY); /* Stdin. */ (void)open("/dev/null", O_RDONLY); /* Stdin. */
(void)open("/dev/null", O_WRONLY); /* Stdout. */ (void)open("/dev/null", O_WRONLY); /* Stdout. */
#endif /* !__MINGW__ */
init_my_port(); /* Determine port to listen on. */ init_my_port(); /* Determine port to listen on. */
init_ports(); /* Create ports to handle requests. */
if (interfaces == 0) if (interfaces == 0)
{ {
init_iface(); /* Build up list of network interfaces. */ init_iface(); /* Build up list of network interfaces. */
@ -4463,7 +4524,6 @@ printf(
exit(1); exit(1);
} }
} }
init_ports(); /* Create ports to handle requests. */
#ifndef __MINGW__ #ifndef __MINGW__
/* /*

View file

@ -222,10 +222,16 @@ typedef struct {
* as root and will not even let you modify /etc/services to point * as root and will not even let you modify /etc/services to point
* gdomap to another port, you can uncomment the next #define to * 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). * 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 * When you have done this you must recompile gdomap.c and
* NSPortNameServer.m and re-install the base library with * NSPortNameServer.m and re-install the base library with
* the new NSPortNameServer.o * 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 */ /* #define GDOMAP_PORT_OVERRIDE 6006 */