diff options
Diffstat (limited to 'xorg-server/os')
-rw-r--r-- | xorg-server/os/WaitFor.c | 6 | ||||
-rw-r--r-- | xorg-server/os/access.c | 337 | ||||
-rw-r--r-- | xorg-server/os/auth.c | 12 | ||||
-rw-r--r-- | xorg-server/os/connection.c | 89 | ||||
-rw-r--r-- | xorg-server/os/io.c | 1 | ||||
-rw-r--r-- | xorg-server/os/log.c | 20 | ||||
-rw-r--r-- | xorg-server/os/makefile | 55 | ||||
-rw-r--r-- | xorg-server/os/osinit.c | 5 | ||||
-rw-r--r-- | xorg-server/os/strndup.c | 4 | ||||
-rw-r--r-- | xorg-server/os/utils.c | 129 | ||||
-rw-r--r-- | xorg-server/os/xdmcp.c | 142 | ||||
-rw-r--r-- | xorg-server/os/xprintf.c | 7 | ||||
-rw-r--r-- | xorg-server/os/xstrans.c | 12 |
13 files changed, 685 insertions, 134 deletions
diff --git a/xorg-server/os/WaitFor.c b/xorg-server/os/WaitFor.c index 393890f19..95762ef18 100644 --- a/xorg-server/os/WaitFor.c +++ b/xorg-server/os/WaitFor.c @@ -204,6 +204,12 @@ WaitForSomething(int *pClientsReady) wt = &waittime; } } + if (!wt) + { + wt = &waittime; + waittime.tv_sec = 0; + waittime.tv_usec = 100; + } XFD_COPYSET(&AllSockets, &LastSelectMask); } diff --git a/xorg-server/os/access.c b/xorg-server/os/access.c index 550f2ed8c..71af6e7c9 100644 --- a/xorg-server/os/access.c +++ b/xorg-server/os/access.c @@ -220,6 +220,10 @@ static int AccessEnabled = DEFAULT_ACCESS_CONTROL; static int LocalHostEnabled = FALSE; static int LocalHostRequested = FALSE; static int UsingXdmcp = FALSE; +static u_long *pInterfaces = NULL; +static int ActiveInterfaces = 0; + +void match_interface(u_long u_lQuery); /* FamilyServerInterpreted implementation */ static Bool siAddrMatch(int family, pointer addr, int len, HOST * host, @@ -227,6 +231,84 @@ static Bool siAddrMatch(int family, pointer addr, int len, HOST * host, static int siCheckAddr(const char *addrString, int length); static void siTypesInitialize(void); +#if NTDDI_VERSION < NTDDI_VISTA +const char *inet_ntop(int af, const void *src, char *dst, socklen_t cnt) +{ + if (af == AF_INET) + { + struct sockaddr_in in; + memset(&in, 0, sizeof(in)); + in.sin_family = AF_INET; + memcpy(&in.sin_addr, src, sizeof(struct in_addr)); + if (getnameinfo((struct sockaddr *)&in, sizeof(struct sockaddr_in), dst, cnt, NULL, 0, NI_NUMERICHOST) != 0) + { + errno = WSAGetLastError(); + return NULL; + } + else return dst; + } + else if (af == AF_INET6) + { + struct sockaddr_in6 in; + memset(&in, 0, sizeof(in)); + in.sin6_family = AF_INET6; + memcpy(&in.sin6_addr, src, sizeof(struct in_addr6)); + if (getnameinfo((struct sockaddr *)&in, sizeof(struct sockaddr_in6), dst, cnt, NULL, 0, NI_NUMERICHOST) != 0) + { + errno = WSAGetLastError(); + return NULL; + } + else return dst; + } + errno = WSAEAFNOSUPPORT; + return NULL; +} + +int inet_pton(int af, const char *src, void *dst) +{ + struct sockaddr_storage ss; + int sslen = sizeof(ss); + if (af == AF_INET) + { + struct in_addr out; + char buffer[INET_ADDRSTRLEN + 1]; + strncpy (buffer, src, INET_ADDRSTRLEN); + buffer [INET_ADDRSTRLEN] = '\0'; + if (WSAStringToAddressA(buffer, AF_INET, NULL, (struct sockaddr*)&ss, &sslen) == SOCKET_ERROR) + { + errno = WSAGetLastError(); + return 0; + } + else + { + out = ((struct sockaddr_in *)&ss)->sin_addr; + memcpy (dst, &out, sizeof(struct in_addr)); + return 1; + } + } + else if (af == AF_INET6) + { + struct in6_addr out6; + char buffer6[INET6_ADDRSTRLEN + 1]; + strncpy (buffer6, src, INET6_ADDRSTRLEN); + buffer6 [INET6_ADDRSTRLEN] = '\0'; + if (WSAStringToAddressA(buffer6, AF_INET6, NULL, (struct sockaddr*)&ss, &sslen) == SOCKET_ERROR) + { + errno = WSAGetLastError(); + return 0; + } + else + { + out6 = ((struct sockaddr_in6 *)&ss)->sin6_addr; + memcpy (dst, &out6, sizeof(struct in6_addr)); + return 1; + } + } + errno = WSAEAFNOSUPPORT; + return -1; +} +#endif + /* * called when authorization is not enabled to add the * local host to the access list @@ -303,7 +385,7 @@ ifioctl(int fd, int cmd, char *arg) #endif /* - * DefineSelf (fd): + * DefineSelf (fd, protocol): * * Define this host for access control. Find all the hosts the OS knows about * for this fd and add them to the selfhosts list. @@ -311,12 +393,11 @@ ifioctl(int fd, int cmd, char *arg) #if !defined(SIOCGIFCONF) void -DefineSelf(int fd) +DefineSelf(int fd, const int protocol) { #if !defined(TCPCONN) && !defined(STREAMSCONN) && !defined(UNIXCONN) return; #else - register int n; int len; caddr_t addr; int family; @@ -328,6 +409,10 @@ DefineSelf(int fd) struct { char nodename[512]; } name; + HOST ha; + struct addrinfo *addresses; + struct addrinfo *a; + struct addrinfo hints; #endif register struct hostent *hp; @@ -347,7 +432,6 @@ DefineSelf(int fd) #ifdef XTHREADS_NEEDS_BYNAMEPARAMS _Xgethostbynameparams hparams; #endif - /* Why not use gethostname()? Well, at least on my system, I've had to * make an ugly kernel patch to get a name longer than 8 characters, and * uname() lets me access to the whole string (it smashes release, you @@ -359,16 +443,93 @@ DefineSelf(int fd) gethostname(name.nodename, sizeof(name.nodename)); #endif + /* Colin's experiments with using getaddrinfo() instead of the IPv6-useless gethostbyname() */ + memset( &hints, 0, sizeof(hints) ); + if (protocol == 4) hints.ai_family = AF_INET; + else if (protocol == 6) hints.ai_family = AF_INET6; + + if (getaddrinfo(name.nodename, NULL, &hints, &addresses) != 0) goto CarryOnTheOldWay; + + if (protocol == 6) ErrorF ("DefineSelf - %s has IPv%d addresses...\n", + name.nodename, protocol); + + for (a = addresses; a != NULL; a = a->ai_next) { + char ad[INET6_ADDRSTRLEN]; + ha.family = a->ai_family; + if (a->ai_family == AF_INET6) { + ha.addr = (unsigned char *) + &((struct sockaddr_in6 *) a->ai_addr)->sin6_addr; + ha.len = + sizeof (((struct sockaddr_in6 *) a->ai_addr)->sin6_addr); + } else { + ha.addr = (unsigned char *) + &((struct sockaddr_in *) a->ai_addr)->sin_addr; + ha.len = + sizeof (((struct sockaddr_in *) a->ai_addr)->sin_addr); + } + inet_ntop(ha.family, ha.addr, ad, sizeof(ad)); + + if (ha.family == AF_INET6) { + ErrorF(" %s", ad); + saddr.sa.sa_family = AF_INET6; + inet6addr = (struct sockaddr_in6 *) (&(saddr.sa)); + memcpy (&(inet6addr->sin6_addr), ha.addr, ha.len); + len = sizeof(saddr.in6); + family = ConvertAddr (&(saddr.sa), &len, (pointer *)&addr); + if ( family != -1 && family != FamilyLocal ) { + for (host = selfhosts; + host && !addrEqual (family, addr, len, host); + host = host->next) ; + if (!host) { + /* add this host to the host list. */ + MakeHost(host,len) + if (host) { + host->family = family; + host->len = len; + memcpy (host->addr, addr, len); + host->next = selfhosts; + selfhosts = host; + } + if (family == FamilyInternet6 && + !(IN6_IS_ADDR_LOOPBACK((struct in6_addr *)addr))) { + XdmcpRegisterConnection (family, (char *)addr, len); + } + } + } + } + } + if (protocol == 6) ErrorF ("\n"); + freeaddrinfo(addresses); + /* End of Colin's experiments */ + +CarryOnTheOldWay: + hp = _XGethostbyname(name.nodename, hparams); if (hp != NULL) { + int i = 0, j = 0; + IN_ADDR Inter; saddr.sa.sa_family = hp->h_addrtype; switch (hp->h_addrtype) { case AF_INET: + if (protocol == 6) return; /* We should not be here: gethostbyname() is useless with inet6! */ inetaddr = (struct sockaddr_in *) (&(saddr.sa)); - memcpy(&(inetaddr->sin_addr), hp->h_addr, hp->h_length); - len = sizeof(saddr.sa); + if (!pInterfaces) match_interface(0); + if (ActiveInterfaces && pInterfaces && *pInterfaces) + { + ErrorF ("DefineSelf - %s has %d usable IPv%d interface%s...\n address%s", + name.nodename, ActiveInterfaces, protocol, + ActiveInterfaces==1 ? "" : "s", + ActiveInterfaces==1 ? "" : "es"); + for (i = 0; hp->h_addr_list[i]; i++) + { + Inter.S_un.S_addr = *(u_long *)hp->h_addr_list[i]; + ErrorF(" %s", inet_ntoa(Inter)); + if (*pInterfaces == *(u_long *)hp->h_addr_list[i]) j = i; + } + ErrorF ("\n"); + } break; -#if defined(IPv6) && defined(AF_INET6) +#if 0 /* We never used to get here and AF_INET6 is now processed by getaddrinfo() */ case AF_INET6: inet6addr = (struct sockaddr_in6 *) (&(saddr.sa)); memcpy(&(inet6addr->sin6_addr), hp->h_addr, hp->h_length); @@ -378,48 +539,56 @@ DefineSelf(int fd) default: goto DefineLocalHost; } - family = ConvertAddr(&(saddr.sa), &len, (pointer *) &addr); - if (family != -1 && family != FamilyLocal) { - for (host = selfhosts; - host && !addrEqual(family, addr, len, host); - host = host->next); - if (!host) { - /* add this host to the host list. */ - MakeHost(host, len) + + for (i = -1; i < 0 || hp->h_addr_list[i]; i++) + { + if (i < 0) memcpy ( &(inetaddr->sin_addr), hp->h_addr_list[j], hp->h_length); + else if (i == j) continue; + else memcpy ( &(inetaddr->sin_addr), hp->h_addr_list[i], hp->h_length); + len = sizeof(saddr.sa); + family = ConvertAddr(&(saddr.sa), &len, (pointer *) &addr); + if ( family != -1 && family != FamilyLocal ) { + for (host = selfhosts; + host && !addrEqual (family, addr, len, host); + host = host->next) ; + if (!host) { + /* add this host to the host list. */ + MakeHost(host,len) if (host) { - host->family = family; - host->len = len; - memcpy(host->addr, addr, len); - host->next = selfhosts; - selfhosts = host; - } -#ifdef XDMCP - /* - * If this is an Internet Address, but not the localhost - * address (127.0.0.1), nor the bogus address (0.0.0.0), - * register it. - */ - if (family == FamilyInternet && - !(len == 4 && - ((addr[0] == 127) || - (addr[0] == 0 && addr[1] == 0 && - addr[2] == 0 && addr[3] == 0))) - ) { - XdmcpRegisterConnection(family, (char *) addr, len); - broad_addr = *inetaddr; - ((struct sockaddr_in *) &broad_addr)->sin_addr.s_addr = + host->family = family; + host->len = len; + memcpy ( host->addr, addr, len); + host->next = selfhosts; + selfhosts = host; + } + #ifdef XDMCP + /* + * If this is an Internet Address, but not the localhost + * address (127.0.0.1), nor the bogus address (0.0.0.0), + * register it. + */ + if (family == FamilyInternet && + !(len == 4 && + ((addr[0] == 127) || + (addr[0] == 0 && addr[1] == 0 && + addr[2] == 0 && addr[3] == 0))) + ) { + XdmcpRegisterConnection (family, (char *)addr, len); + broad_addr = *inetaddr; + ((struct sockaddr_in *) &broad_addr)->sin_addr.s_addr = htonl(INADDR_BROADCAST); - XdmcpRegisterBroadcastAddress((struct sockaddr_in *) + XdmcpRegisterBroadcastAddress ((struct sockaddr_in *) &broad_addr); + } + #if defined(IPv6) && defined(AF_INET6) + else if (family == FamilyInternet6 && + !(IN6_IS_ADDR_LOOPBACK((struct in6_addr *)addr))) { + XdmcpRegisterConnection (family, (char *)addr, len); + } + #endif + + #endif /* XDMCP */ } -#if defined(IPv6) && defined(AF_INET6) - else if (family == FamilyInternet6 && - !(IN6_IS_ADDR_LOOPBACK((struct in6_addr *) addr))) { - XdmcpRegisterConnection(family, (char *) addr, len); - } -#endif - -#endif /* XDMCP */ } } } @@ -427,6 +596,7 @@ DefineSelf(int fd) * now add a host of family FamilyLocalHost... */ DefineLocalHost: + free(pInterfaces); for (host = selfhosts; host && !addrEqual(FamilyLocalHost, "", 0, host); host = host->next); if (!host) { @@ -846,18 +1016,19 @@ ResetHosts(char *display) FreeHost(host); } -#if defined WIN32 && defined __MINGW32__ -#define ETC_HOST_PREFIX "X" -#else #define ETC_HOST_PREFIX "/etc/X" -#endif #define ETC_HOST_SUFFIX ".hosts" fnamelen = strlen(ETC_HOST_PREFIX) + strlen(ETC_HOST_SUFFIX) + strlen(display) + 1; if (fnamelen > sizeof(fname)) FatalError("Display name `%s' is too long\n", display); +#ifdef __MINGW32__ + snprintf(fname, sizeof(fname), "%s%s" ETC_HOST_SUFFIX, getenv("XHOSTPREFIX"), + display); +#else snprintf(fname, sizeof(fname), ETC_HOST_PREFIX "%s" ETC_HOST_SUFFIX, display); +#endif if ((fd = fopen(fname, "r")) != 0) { while (fgets(ohostname, sizeof(ohostname), fd)) { @@ -921,9 +1092,13 @@ ResetHosts(char *display) (family == FamilyWild)) { struct addrinfo *addresses; struct addrinfo *a; + struct addrinfo hints; int f; - if (getaddrinfo(hostname, NULL, NULL, &addresses) == 0) { + memset( &hints, 0, sizeof(hints) ); + if (family == FamilyInternet) hints.ai_family = AF_INET; + else if (family == FamilyInternet6) hints.ai_family = AF_INET6; + if (getaddrinfo(hostname, NULL, &hints, &addresses) == 0) { for (a = addresses; a != NULL; a = a->ai_next) { len = a->ai_addrlen; f = ConvertAddr(a->ai_addr, &len, @@ -1245,7 +1420,9 @@ NewHost(int family, const void *addr, int len, int addingLocalHosts) { register HOST *host; + if (family == FamilyLocal) return TRUE; /* No FamilyLocal in Vcxsrv */ for (host = validhosts; host; host = host->next) { + if (addrEqual(family, addr, len, host)) return TRUE; } @@ -1682,6 +1859,7 @@ siHostnameAddrMatch(int family, pointer addr, int len, char hostname[SI_HOSTNAME_MAXLEN]; struct addrinfo *addresses; struct addrinfo *a; + struct addrinfo hints; int f, hostaddrlen; pointer hostaddr; @@ -1690,7 +1868,10 @@ siHostnameAddrMatch(int family, pointer addr, int len, strlcpy(hostname, siAddr, siAddrLen + 1); - if (getaddrinfo(hostname, NULL, NULL, &addresses) == 0) { + memset( &hints, 0, sizeof(hints) ); + if (family == FamilyInternet) hints.ai_family = AF_INET; + else if (family == FamilyInternet6) hints.ai_family = AF_INET6; + if (getaddrinfo(hostname, NULL, &hints, &addresses) == 0) { for (a = addresses; a != NULL; a = a->ai_next) { hostaddrlen = a->ai_addrlen; f = ConvertAddr(a->ai_addr, &hostaddrlen, &hostaddr); @@ -1723,7 +1904,7 @@ siHostnameAddrMatch(int family, pointer addr, int len, if ((hp = _XGethostbyname(hostname, hparams)) != NULL) { #ifdef h_addr /* new 4.3bsd version of gethostent */ /* iterate over the addresses */ - for (addrlist = hp->h_addr_list; *addrlist; addrlist++) + for (addrlist = (const char **)hp->h_addr_list; *addrlist; addrlist++) #else addrlist = &hp->h_addr; #endif @@ -2020,3 +2201,55 @@ siTypesInitialize(void) &siLocalGroupPriv); #endif } + +void match_interface(u_long u_lQuery) +{ + WSADATA w; + SOCKET sd; + INTERFACE_INFO InterfaceList[25]; + PSOCKADDR_IN pAddress, pNetmask; + u_long nBytesReturned, tempAddress; + u_long u_lAddress, u_lNetmask, u_lFlags; + int nNumInterfaces, i, j = 0; + + if (WSAStartup(MAKEWORD(2,2), &w) != 0) + return; + + sd = WSASocket(AF_INET, SOCK_DGRAM, 0, 0, 0, 0); + if (sd == INVALID_SOCKET) + { + WSACleanup(); + return; + } + + if (WSAIoctl(sd, SIO_GET_INTERFACE_LIST, 0, 0, &InterfaceList, sizeof(InterfaceList), &nBytesReturned, 0, 0) == SOCKET_ERROR) + { + closesocket(sd); + WSACleanup(); + return; + } + + nNumInterfaces = (int)(nBytesReturned/sizeof(INTERFACE_INFO)); + pInterfaces = malloc(25*sizeof(u_long)); + for (i = 0; i < nNumInterfaces; ++i) + { + pAddress = &InterfaceList[i].iiAddress.AddressIn; + u_lAddress = pAddress->sin_addr.S_un.S_addr; + + pNetmask = &InterfaceList[i].iiNetmask.AddressIn; + u_lNetmask = pNetmask->sin_addr.S_un.S_addr; + + u_lFlags = InterfaceList[i].iiFlags; + if ((u_lFlags & IFF_UP) && !(u_lFlags & IFF_LOOPBACK)) + { + if ((u_lAddress & u_lNetmask) == (u_lQuery & u_lNetmask)) j = i; + *(pInterfaces + ActiveInterfaces) = u_lAddress; + ActiveInterfaces++; + } + } + tempAddress = *pInterfaces; + *pInterfaces = *(pInterfaces + j); + *(pInterfaces + j) = tempAddress; + closesocket(sd); + WSACleanup(); +} diff --git a/xorg-server/os/auth.c b/xorg-server/os/auth.c index ac20de47d..b95786bee 100644 --- a/xorg-server/os/auth.c +++ b/xorg-server/os/auth.c @@ -303,11 +303,23 @@ GenerateAuthorization(unsigned name_length, void GenerateRandomData(int len, char *buf) { +#ifdef _MSC_VER + static HANDLE hAdvApi32; + static BOOLEAN (_stdcall * RtlGenRandom)(void *,unsigned long); + + if (!hAdvApi32) + { + hAdvApi32=LoadLibrary("advapi32.dll"); + RtlGenRandom=(BOOLEAN (_stdcall *)(void*,unsigned long))GetProcAddress(hAdvApi32,"SystemFunction036"); + } + RtlGenRandom(buf, len); +#else int fd; fd = open("/dev/urandom", O_RDONLY); read(fd, buf, len); close(fd); +#endif } #endif /* XCSECURITY */ diff --git a/xorg-server/os/connection.c b/xorg-server/os/connection.c index 344147220..50ed4ae69 100644 --- a/xorg-server/os/connection.c +++ b/xorg-server/os/connection.c @@ -66,6 +66,9 @@ SOFTWARE. #ifdef WIN32 #include <X11/Xwinsock.h> +#ifdef _DEBUG +#define DEBUG +#endif #endif #include <X11/X.h> #include <X11/Xproto.h> @@ -108,6 +111,10 @@ SOFTWARE. #include "dixstruct.h" #include "xace.h" +#ifdef _MSC_VER +typedef int pid_t; +#endif + #define Pid_t pid_t #ifdef HAVE_GETPEERUCRED @@ -139,12 +146,15 @@ int MaxClients = 0; Bool NewOutputPending; /* not yet attempted to write some new output */ Bool AnyClientsWriteBlocked; /* true if some client blocked on write */ +#if !defined(_MSC_VER) static Bool RunFromSmartParent; /* send SIGUSR1 to parent process */ +static Pid_t ParentProcess; +#endif Bool RunFromSigStopParent; /* send SIGSTOP to our own process; Upstart (or equivalent) will send SIGCONT back. */ static char dynamic_display[7]; /* display name */ +static int dynamic_display_id; Bool PartialNetwork; /* continue even if unable to bind all addrs */ -static Pid_t ParentProcess; static Bool debug_conns = FALSE; @@ -166,9 +176,9 @@ int *ConnectionTranslation = NULL; */ #undef MAXSOCKS -#define MAXSOCKS 500 +#define MAXSOCKS FD_SETSIZE #undef MAXSELECT -#define MAXSELECT 500 +#define MAXSELECT FD_SETSIZE struct _ct_node { struct _ct_node *next; @@ -269,6 +279,23 @@ lookup_trans_conn(int fd) return NULL; } +int +TransIsListening(char *protocol) +{ + /* look for this transport in the list of listeners */ + int i; + for (i = 0; i < ListenTransCount; i++) + { + if (!strcmp(protocol, ListenTransConns[i]->transptr->TransName)) + { + return 1; + } + } + + return 0; +} + + /* Set MaxClients and lastfdesc, and allocate ConnectionTranslation */ void @@ -363,6 +390,11 @@ NotifyParentProcess(void) } if (RunFromSigStopParent) raise(SIGSTOP); +#else +/* On windows the displayfd points to shared memory, so write the id to it */ + int *pDisplayfd=(int*)MapViewOfFile((HANDLE)displayfd, FILE_MAP_READ|FILE_MAP_WRITE, 0, 0, 0); + if (pDisplayfd) + *pDisplayfd=dynamic_display_id; #endif } @@ -424,20 +456,25 @@ CreateWellKnownSockets(void) } if (!found) FatalError("Failed to find a socket to listen on"); + dynamic_display_id=i; snprintf(dynamic_display, sizeof(dynamic_display), "%d", i); display = dynamic_display; } ListenTransFds = malloc(ListenTransCount * sizeof (int)); - for (i = 0; i < ListenTransCount; i++) { - int fd = _XSERVTransGetConnectionNumber(ListenTransConns[i]); + for (i = ListenTransCount; i > 0; i--) { + int fd = _XSERVTransGetConnectionNumber (ListenTransConns[i-1]); - ListenTransFds[i] = fd; + ListenTransFds[i-1] = fd; FD_SET(fd, &WellKnownConnections); - if (!_XSERVTransIsLocal(ListenTransConns[i])) - DefineSelf (fd); + if (!_XSERVTransIsLocal (ListenTransConns[i-1])) { + int protocol = 0; + if (!strcmp("inet", ListenTransConns[i-1]->transptr->TransName)) protocol = 4; + else if (!strcmp("inet6", ListenTransConns[i-1]->transptr->TransName)) protocol = 6; + DefineSelf (fd, protocol); + } } if (!XFD_ANYSET(&WellKnownConnections)) @@ -978,15 +1015,17 @@ CheckConnections(void) { #ifndef WIN32 fd_mask mask; + int curoff; #endif fd_set tmask; - int curclient, curoff; + int curclient; int i; struct timeval notime; int r; #ifdef WIN32 - fd_set savedAllClients; + fd_set savedAllSockets; + unsigned j; #endif notime.tv_sec = 0; @@ -1010,17 +1049,21 @@ CheckConnections(void) } } #else - XFD_COPYSET(&AllClients, &savedAllClients); - for (i = 0; i < XFD_SETCOUNT(&savedAllClients); i++) { - curclient = XFD_FD(&savedAllClients, i); - FD_ZERO(&tmask); - FD_SET(curclient, &tmask); - do { - r = Select(curclient + 1, &tmask, NULL, NULL, ¬ime); - } while (r < 0 && (errno == EINTR || errno == EAGAIN)); - if (r < 0) - if (GetConnectionTranslation(curclient) > 0) - CloseDownClient(clients[GetConnectionTranslation(curclient)]); + /* First test AllSockets and then AllClients are valid sockets */ + XFD_COPYSET(&AllSockets, &savedAllSockets); + for (j=0; j<2; j++) { + for (i = 0; i < XFD_SETCOUNT(&savedAllSockets); i++) { + curclient = XFD_FD(&savedAllSockets, i); + FD_ZERO(&tmask); + FD_SET(curclient, &tmask); + do { + r = Select (curclient + 1, &tmask, NULL, NULL, ¬ime); + } while (r == SOCKET_ERROR && (WSAGetLastError() == WSAEINTR || WSAGetLastError() == WSAEWOULDBLOCK)); + if (r < 0) + if (GetConnectionTranslation(curclient) > 0) + CloseDownClient(clients[GetConnectionTranslation(curclient)]); + } + XFD_COPYSET(&AllClients, &savedAllSockets); } #endif } @@ -1038,6 +1081,10 @@ CloseDownConnection(ClientPtr client) if (FlushCallback) CallCallbacks(&FlushCallback, NULL); +#ifdef DEBUG + ErrorF("CloseDownConnection: client index = %d, socket fd = %d\n", + client->index, oc->fd); +#endif if (oc->output && oc->output->count) FlushClient(client, oc, (char *) NULL, 0); #ifdef XDMCP diff --git a/xorg-server/os/io.c b/xorg-server/os/io.c index b67a5f324..84757294b 100644 --- a/xorg-server/os/io.c +++ b/xorg-server/os/io.c @@ -903,6 +903,7 @@ FlushClient(ClientPtr who, OsCommPtr oc, const void *__extraBuf, int extraCount) /* If we've arrived here, then the client is stuffed to the gills and not ready to accept more. Make a note of it and buffer the rest. */ + errno=0; FD_SET(connection, &ClientsWriteBlocked); AnyClientsWriteBlocked = TRUE; diff --git a/xorg-server/os/log.c b/xorg-server/os/log.c index 25da9f63a..2e5b97a60 100644 --- a/xorg-server/os/log.c +++ b/xorg-server/os/log.c @@ -92,8 +92,14 @@ OR PERFORMANCE OF THIS SOFTWARE. #ifdef WIN32 #include <process.h> +#ifndef _MSC_VER #define getpid(x) _getpid(x) #endif +#endif + +#ifdef _MSC_VER +#define S_ISREG(m) (((m)&_S_IFMT) == _S_IFREG) +#endif #ifdef XF86BIGFONT #include "xf86bigfontsrv.h" @@ -400,7 +406,7 @@ LogSWrite(int verb, const char *buf, size_t len, Bool end_line) void LogVWrite(int verb, const char *f, va_list args) { - return LogVMessageVerb(X_NONE, verb, f, args); + LogVMessageVerb(X_NONE, verb, f, args); } void @@ -727,7 +733,7 @@ VAuditF(const char *f, va_list args) if (auditTimer != NULL) TimerForce(auditTimer); ErrorF("%s%s", prefix != NULL ? prefix : "", buf); - strlcpy(oldbuf, buf, sizeof(oldbuf)); + strncpy(oldbuf, buf, sizeof(oldbuf)); oldlen = len; nrepeat = 0; auditTimer = TimerSet(auditTimer, 0, AUDIT_TIMEOUT, AuditFlush, NULL); @@ -735,6 +741,8 @@ VAuditF(const char *f, va_list args) free(prefix); } +extern char g_FatalErrorMessage[1024]; + void FatalError(const char *f, ...) { @@ -749,8 +757,10 @@ FatalError(const char *f, ...) va_start(args, f); +#ifndef _MSC_VER /* Make a copy for OsVendorFatalError */ va_copy(args2, args); +#endif #ifdef __APPLE__ { @@ -762,9 +772,15 @@ FatalError(const char *f, ...) va_end(apple_args); } #endif +#ifdef WIN32 + vsnprintf(g_FatalErrorMessage, 1024, f, args); +#endif VErrorF(f, args); va_end(args); ErrorF("\n"); +#ifdef _MSC_VER + va_start(args2, f); +#endif if (!beenhere) OsVendorFatalError(f, args2); va_end(args2); diff --git a/xorg-server/os/makefile b/xorg-server/os/makefile new file mode 100644 index 000000000..b7fdc12b1 --- /dev/null +++ b/xorg-server/os/makefile @@ -0,0 +1,55 @@ +LIBRARY=libos
+
+ifeq ($(DEBUG),1)
+DEFINES += XSERVER_DTRACE
+endif
+SECURE_RPC=1
+XDMCP=1
+NEED_STRLCAT=1
+NEED_STRNDUP=1
+
+SECURERPC_SRCS = rpcauth.c
+XDMCP_SRCS = xdmcp.c
+STRLCAT_SRCS = strlcat.c strlcpy.c
+XORG_SRCS = log.c
+STRNDUP_SRCS = strndup.c
+
+libos_la_SOURCES = \
+ WaitFor.c \
+ access.c \
+ auth.c \
+ backtrace.c \
+ client.c \
+ connection.c \
+ io.c \
+ mitauth.c \
+ oscolor.c \
+ osdep.h \
+ osinit.c \
+ utils.c \
+ strcasecmp.c \
+ strcasestr.c \
+ xdmauth.c \
+ xsha1.c \
+ xstrans.c \
+ xprintf.c \
+ $(XORG_SRCS)
+
+if SECURE_RPC
+libos_la_SOURCES += $(SECURERPC_SRCS)
+endif
+if XDMCP
+libos_la_SOURCES += $(XDMCP_SRCS)
+endif
+
+if NEED_STRLCAT
+libos_la_SOURCES += $(STRLCAT_SRCS)
+endif
+
+if NEED_STRNDUP
+libos_la_SOURCES += $(STRNDUP_SRCS)
+endif
+
+CSRCS = $(filter %.c,$(libos_la_SOURCES))
+
+
diff --git a/xorg-server/os/osinit.c b/xorg-server/os/osinit.c index 6cc040178..c2cff757b 100644 --- a/xorg-server/os/osinit.c +++ b/xorg-server/os/osinit.c @@ -155,6 +155,7 @@ OsInit(void) char fname[PATH_MAX]; if (!been_here) { +#ifndef _MSC_VER struct sigaction act, oact; int i; @@ -202,7 +203,7 @@ OsInit(void) dlinfo(RTLD_SELF, RTLD_DI_SETSIGNAL, &failure_signal); #endif - +#endif #if !defined(__CYGWIN__) fclose(stdin); fclose(stdout); @@ -241,8 +242,10 @@ OsInit(void) #endif } +#ifndef _MSC_VER if (getpgrp() == 0) setpgid(0, 0); +#endif #ifdef RLIMIT_DATA if (limitDataSpace >= 0) { diff --git a/xorg-server/os/strndup.c b/xorg-server/os/strndup.c index b604b9bac..e0eddf13d 100644 --- a/xorg-server/os/strndup.c +++ b/xorg-server/os/strndup.c @@ -27,6 +27,10 @@ * SUCH DAMAGE. */ +#ifdef HAVE_DIX_CONFIG_H +#include <dix-config.h> +#endif + #include <stddef.h> #include <stdlib.h> #include <string.h> diff --git a/xorg-server/os/utils.c b/xorg-server/os/utils.c index 998c3ed4a..e94179518 100644 --- a/xorg-server/os/utils.c +++ b/xorg-server/os/utils.c @@ -206,6 +206,11 @@ char *SeatId = NULL; sig_atomic_t inSignalContext = FALSE; +#ifdef _MSC_VER +static HANDLE s_hSmartScheduleTimer = NULL; +static HANDLE s_hSmartScheduleTimerQueue = NULL; +#endif + #if defined(SVR4) || defined(__linux__) || defined(CSRG_BASED) #define HAS_SAVED_IDS_AND_SETEUID #endif @@ -213,6 +218,9 @@ sig_atomic_t inSignalContext = FALSE; OsSigHandlerPtr OsSignal(int sig, OsSigHandlerPtr handler) { +#ifdef X_NOT_POSIX + return signal(sig, handler); +#else struct sigaction act, oact; sigemptyset(&act.sa_mask); @@ -223,6 +231,7 @@ OsSignal(int sig, OsSigHandlerPtr handler) if (sigaction(sig, &act, &oact)) perror("sigaction"); return oact.sa_handler; +#endif } /* @@ -236,6 +245,10 @@ OsSignal(int sig, OsSigHandlerPtr handler) #define LOCK_PREFIX "/.X" #define LOCK_SUFFIX "-lock" +#ifdef _MSC_VER +#define LockFile szLockFile +#endif + static Bool StillLocking = FALSE; static char LockFile[PATH_MAX]; static Bool nolock = FALSE; @@ -249,6 +262,14 @@ static Bool nolock = FALSE; void LockServer(void) { +#if defined(WIN32) && !defined(__CYGWIN__) + char MutexName[100]; + sprintf(MutexName, "Global\\VcXsrv_Mutex_%d\n", getpid()); + if (!CreateMutex(NULL,TRUE,MutexName) || GetLastError()== ERROR_ALREADY_EXISTS) + { + FatalError("Server is already active for display %d\n", atoi(display)); + } +#else char tmp[PATH_MAX], pid_str[12]; int lfd, i, haslock, l_pid, t; const char *tmppath = LOCK_DIR; @@ -366,6 +387,7 @@ LockServer(void) if (!haslock) FatalError("Could not create server lock file: %s\n", LockFile); StillLocking = FALSE; +#endif } /* @@ -470,7 +492,10 @@ AdjustWaitForDelay(pointer waitTime, unsigned long newdelay) void UseMsg(void) { - ErrorF("use: X [:<display>] [option]\n"); + ErrorF("Usage...\nVcxsrv [:<display>] [option]\n\n"); + ErrorF(":display-number\n\tVcxsrv runs as the given display-number, which defaults to 0.\n"); + ErrorF("\tTo run multiple instances, use unique display-numbers.\n\n"); + ErrorF("-a # default pointer acceleration (factor)\n"); ErrorF("-ac disable access control restrictions\n"); ErrorF("-audit int set audit trail level\n"); @@ -478,12 +503,14 @@ UseMsg(void) ErrorF("-br create root window with black background\n"); ErrorF("+bs enable any backing store support\n"); ErrorF("-bs disable any backing store support\n"); - ErrorF("-c turns off key-click\n"); - ErrorF("c # key-click volume (0-100)\n"); ErrorF("-cc int default color visual class\n"); ErrorF("-nocursor disable the cursor\n"); ErrorF("-core generate core dump on fatal error\n"); +#ifdef _MSC_VER + ErrorF("-dpi [auto|int] screen resolution set to native or this dpi\n"); +#else ErrorF("-dpi int screen resolution in dots per inch\n"); +#endif #ifdef DPMSExtension ErrorF("-dpms disables VESA DPMS monitor control\n"); #endif @@ -509,25 +536,19 @@ UseMsg(void) ErrorF("-noreset don't reset after last client exists\n"); ErrorF("-background [none] create root window with no background\n"); ErrorF("-reset reset after last client exists\n"); - ErrorF("-p # screen-saver pattern duration (minutes)\n"); ErrorF("-pn accept failure to listen on all ports\n"); ErrorF("-nopn reject failure to listen on all ports\n"); ErrorF("-r turns off auto-repeat\n"); ErrorF("r turns on auto-repeat \n"); ErrorF("-render [default|mono|gray|color] set render color alloc policy\n"); - ErrorF("-retro start with classic stipple and cursor\n"); - ErrorF("-s # screen-saver timeout (minutes)\n"); + ErrorF("-retro start with classic stipple\n"); ErrorF("-seat string seat to run on\n"); ErrorF("-t # default pointer threshold (pixels/t)\n"); ErrorF("-terminate terminate at server reset\n"); ErrorF("-to # connection time out\n"); ErrorF("-tst disable testing extensions\n"); - ErrorF("ttyxx server started from init on /dev/ttyxx\n"); - ErrorF("v video blanking for screen-saver\n"); - ErrorF("-v screen-saver without video blanking\n"); ErrorF("-wm WhenMapped default backing-store\n"); ErrorF("-wr create root window with white background\n"); - ErrorF("-maxbigreqsize set maximal bigrequest size \n"); #ifdef PANORAMIX ErrorF("+xinerama Enable XINERAMA extension\n"); ErrorF("-xinerama Disable XINERAMA extension\n"); @@ -535,7 +556,6 @@ UseMsg(void) ErrorF ("-dumbSched Disable smart scheduling, enable old behavior\n"); ErrorF("-schedInterval int Set scheduler interval in msec\n"); - ErrorF("-sigstop Enable SIGSTOP based startup\n"); ErrorF("+extension name Enable extension\n"); ErrorF("-extension name Disable extension\n"); #ifdef XDMCP @@ -627,15 +647,6 @@ ProcessCommandLine(int argc, char *argv[]) enableBackingStore = TRUE; else if (strcmp(argv[i], "-bs") == 0) disableBackingStore = TRUE; - else if (strcmp(argv[i], "c") == 0) { - if (++i < argc) - defaultKeyboardControl.click = atoi(argv[i]); - else - UseMsg(); - } - else if (strcmp(argv[i], "-c") == 0) { - defaultKeyboardControl.click = 0; - } else if (strcmp(argv[i], "-cc") == 0) { if (++i < argc) defaultColorVisualClass = atoi(argv[i]); @@ -657,7 +668,24 @@ ProcessCommandLine(int argc, char *argv[]) } else if (strcmp(argv[i], "-dpi") == 0) { if (++i < argc) +#ifdef _MSC_VER + { + if (strcmp(argv[i], "auto") == 0) + { + HDC hdc = GetDC(NULL); + if (hdc) + { + int dpiY = GetDeviceCaps(hdc, LOGPIXELSY); + monitorResolution = dpiY; + ReleaseDC(NULL, hdc); + } + } + else if (isdigit(*argv[i])) /* Naively prevent a crash if not numeric */ + monitorResolution = atoi(argv[i]); + } +#else monitorResolution = atoi(argv[i]); +#endif else UseMsg(); } @@ -820,10 +848,6 @@ ProcessCommandLine(int argc, char *argv[]) else if (strcmp(argv[i], "-tst") == 0) { noTestExtensions = TRUE; } - else if (strcmp(argv[i], "v") == 0) - defaultScreenSaverBlanking = PreferBlanking; - else if (strcmp(argv[i], "-v") == 0) - defaultScreenSaverBlanking = DontPreferBlanking; else if (strcmp(argv[i], "-wm") == 0) defaultBackingStore = WhenMapped; else if (strcmp(argv[i], "-wr") == 0) @@ -905,9 +929,6 @@ ProcessCommandLine(int argc, char *argv[]) else UseMsg(); } - else if (strcmp(argv[i], "-sigstop") == 0) { - RunFromSigStopParent = TRUE; - } else if (strcmp(argv[i], "+extension") == 0) { if (++i < argc) { if (!EnableDisableExtension(argv[i], TRUE)) @@ -1104,6 +1125,12 @@ XNFstrdup(const char *s) void SmartScheduleStopTimer(void) { +#ifdef _MSC_VER + if (SmartScheduleDisable) + return; + DeleteTimerQueueTimer(s_hSmartScheduleTimerQueue, s_hSmartScheduleTimer, NULL); + s_hSmartScheduleTimer=NULL; +#else struct itimerval timer; if (SmartScheduleDisable) @@ -1113,11 +1140,36 @@ SmartScheduleStopTimer(void) timer.it_value.tv_sec = 0; timer.it_value.tv_usec = 0; (void) setitimer(ITIMER_REAL, &timer, 0); +#endif } +#ifdef _MSC_VER +static VOID CALLBACK SmartScheduleTimer( PVOID lpParameter, BOOLEAN TimerOrWaitFired) +#else +static void SmartScheduleTimer (int sig) +#endif +{ + SmartScheduleTime += SmartScheduleInterval; +} + + void SmartScheduleStartTimer(void) { +#ifdef _MSC_VER + if (SmartScheduleDisable) + return; + + if (!CreateTimerQueueTimer( &s_hSmartScheduleTimer, s_hSmartScheduleTimerQueue, SmartScheduleTimer, NULL + , SmartScheduleInterval, SmartScheduleInterval, WT_EXECUTEONLYONCE|WT_EXECUTEINPERSISTENTTHREAD)) + { + DWORD Error=GetLastError(); + ErrorF("Error starting timer, smart scheduling disabled: 0x%x (%d)\n",Error,Error); + CloseHandle(s_hSmartScheduleTimer); + SmartScheduleDisable = TRUE; + return; + } +#else struct itimerval timer; if (SmartScheduleDisable) @@ -1127,17 +1179,23 @@ SmartScheduleStartTimer(void) timer.it_value.tv_sec = 0; timer.it_value.tv_usec = SmartScheduleInterval * 1000; setitimer(ITIMER_REAL, &timer, 0); -} - -static void -SmartScheduleTimer(int sig) -{ - SmartScheduleTime += SmartScheduleInterval; +#endif } void SmartScheduleInit(void) { +#ifdef _MSC_VER + if (SmartScheduleDisable) + return; + s_hSmartScheduleTimerQueue = CreateTimerQueue(); + if (!s_hSmartScheduleTimerQueue) + { + DWORD Error=GetLastError(); + ErrorF("Error creating timer, smart scheduling disabled: 0x%x (%d)\n",Error,Error); + SmartScheduleDisable = TRUE; + } +#else struct sigaction act; if (SmartScheduleDisable) @@ -1153,6 +1211,7 @@ SmartScheduleInit(void) perror("sigaction for smart scheduler"); SmartScheduleDisable = TRUE; } +#endif } #ifdef SIG_BLOCK @@ -1509,6 +1568,7 @@ Fclose(pointer iop) */ /* Consider LD* variables insecure? */ +#ifndef _MSC_VER #ifndef REMOVE_ENV_LD #define REMOVE_ENV_LD 1 #endif @@ -1517,6 +1577,7 @@ Fclose(pointer iop) #ifndef REMOVE_LONG_ENV #define REMOVE_LONG_ENV 1 #endif +#endif /* * Disallow stdout or stderr as pipes? It's possible to block the X server @@ -1546,7 +1607,7 @@ Fclose(pointer iop) #endif #define MAX_ARG_LENGTH 128 -#define MAX_ENV_LENGTH 256 +#define MAX_ENV_LENGTH 2048 #define MAX_ENV_PATH_LENGTH 2048 /* Limit for *PATH and TERMCAP */ #if USE_ISPRINT diff --git a/xorg-server/os/xdmcp.c b/xorg-server/os/xdmcp.c index 87f04b455..6c5ebca5c 100644 --- a/xorg-server/os/xdmcp.c +++ b/xorg-server/os/xdmcp.c @@ -62,6 +62,8 @@ static const char *defaultDisplayClass = COMPILEDDISPLAYCLASS; +extern void match_interface(u_long u_lQuery); + static int xdmcpSocket, sessionSocket; static xdmcp_states state; @@ -197,6 +199,11 @@ static void XdmcpWakeupHandler(pointer /*data */ , int /*i */ , pointer /*LastSelectMask */ ); +#define XSERV_t +#define TRANS_SERVER +#define TRANS_REOPEN +#include <X11/Xtrans/Xtrans.h> + /* * Register the Manufacturer display ID */ @@ -581,6 +588,32 @@ XdmcpInit(void) (pointer) 0); timeOutRtx = 0; DisplayNumber = (CARD16) atoi(display); + if (ConnectionTypes.length>1 && xdm_from==NULL) + { + unsigned i=0; + char ErrorMessage[1024]; + sprintf(ErrorMessage,"Multiple ip-addresses detected:\n"); + for (i=0; i<ConnectionTypes.length; i++) + { + int AddrLen=ConnectionAddresses.data[i].length; + if (AddrLen==4) + sprintf(ErrorMessage+strlen(ErrorMessage)," %d.%d.%d.%d\n", + ConnectionAddresses.data[i].data[0], + ConnectionAddresses.data[i].data[1], + ConnectionAddresses.data[i].data[2], + ConnectionAddresses.data[i].data[3]); + else + { + int j; + sprintf(ErrorMessage+strlen(ErrorMessage)," "); + for (j=0; j<AddrLen; j++) + sprintf(ErrorMessage+strlen(ErrorMessage),"%02x",ConnectionAddresses.data[i].data[j]); + sprintf(ErrorMessage+strlen(ErrorMessage),"\n"); + } + } + sprintf(ErrorMessage+strlen(ErrorMessage),"Please specify the ip-address you want to use with -from\n"); + FatalError(ErrorMessage); + } get_xdmcp_sock(); send_packet(); } @@ -651,8 +684,8 @@ XdmcpBlockHandler(pointer data, /* unused */ if (timeOutTime == 0) return; millisToGo = timeOutTime - GetTimeInMillis(); - if ((int) millisToGo < 0) - millisToGo = 0; + if ((int) millisToGo <= 0) + millisToGo = 1; AdjustWaitForDelay(wt, millisToGo); } @@ -689,16 +722,6 @@ XdmcpWakeupHandler(pointer data, /* unused */ else if (state == XDM_RUN_SESSION) keepaliveDormancy = defaultKeepaliveDormancy; } - if (XFD_ANYSET(&AllClients) && state == XDM_RUN_SESSION) - timeOutTime = GetTimeInMillis() + keepaliveDormancy * 1000; - } - else if (timeOutTime && (int) (GetTimeInMillis() - timeOutTime) >= 0) { - if (state == XDM_RUN_SESSION) { - state = XDM_KEEPALIVE; - send_packet(); - } - else - timeout(); } } @@ -724,12 +747,71 @@ XdmcpSelectHost(const struct sockaddr *host_sockaddr, * selects the first host to respond with willing message. */ +#ifdef _MSC_VER +void DisplayXdmcpHostsDialog(void); +int XdmcpHostAddName(const char *HostName, int HostIndex); + +struct hostinfo +{ + struct sockaddr *from; + int fromlen; + ARRAY8 AuthenticationName; +}; +static int g_NrHosts; +static struct hostinfo *g_Hosts; + +void XdmcpHostSelected(int HostIdx) +{ + int i; + + /* Connect to the selected host */ + XdmcpSelectHost(g_Hosts[HostIdx].from, g_Hosts[HostIdx].fromlen, &g_Hosts[HostIdx].AuthenticationName); + + for (i=0; i<g_NrHosts; i++) + { + free(g_Hosts[i].from); + free(g_Hosts[i].AuthenticationName.data); + } + free(g_Hosts); + g_Hosts=NULL; + g_NrHosts=0; +} +#endif + /*ARGSUSED*/ static void XdmcpAddHost(const struct sockaddr *from, int fromlen, ARRAY8Ptr AuthenticationName, ARRAY8Ptr hostname, ARRAY8Ptr status) { - XdmcpSelectHost(from, fromlen, AuthenticationName); +#ifdef _MSC_VER + char szHostName[100]; + int HostIdx; + + memcpy(szHostName,hostname->data,hostname->length); + szHostName[hostname->length]=0; + + DisplayXdmcpHostsDialog(); /* Display the dialog if not already displayed */ + + HostIdx=XdmcpHostAddName(szHostName, g_NrHosts); + if (HostIdx==-1) + { + HostIdx=g_NrHosts; + g_NrHosts++; + g_Hosts=realloc(g_Hosts,g_NrHosts*sizeof(*g_Hosts)); + g_Hosts[HostIdx].AuthenticationName.data=NULL; + g_Hosts[HostIdx].from=NULL; + } + + g_Hosts[HostIdx].fromlen=fromlen; + g_Hosts[HostIdx].from=realloc(g_Hosts[HostIdx].from,g_Hosts[HostIdx].fromlen); + memcpy(g_Hosts[HostIdx].from,from,fromlen); + + g_Hosts[HostIdx].AuthenticationName.length=AuthenticationName->length; + g_Hosts[HostIdx].AuthenticationName.data=realloc(g_Hosts[HostIdx].AuthenticationName.data,AuthenticationName->length); + memcpy(g_Hosts[HostIdx].AuthenticationName.data,AuthenticationName->data,AuthenticationName->length); +#else + XdmcpSelectHost(from, fromlen, AuthenticationName); +#endif } /* @@ -1001,12 +1083,20 @@ get_xdmcp_sock(void) sizeof(soopts)) < 0) XdmcpWarning("UDP set broadcast socket-option failed"); #endif /* SO_BROADCAST */ - if (xdmcpSocket >= 0 && xdm_from != NULL) { + if (xdm_from) + { + if (xdmcpSocket >= 0 && SOCKADDR_FAMILY(FromAddress)==AF_INET) { if (bind(xdmcpSocket, (struct sockaddr *) &FromAddress, FromAddressLen) < 0) { - FatalError("Xserver: failed to bind to -from address: %s\n", - xdm_from); + FatalError("Xserver: failed to bind to -from address: %s error %d\n", xdm_from, WSAGetLastError()); + } + } + else if (xdmcpSocket6 >= 0 && SOCKADDR_FAMILY(FromAddress)==AF_INET6) { + if (bind(xdmcpSocket6, (struct sockaddr *)&FromAddress, + FromAddressLen) < 0) { + FatalError("Xserver: failed to bind to -from address: %s error %d\n", xdm_from, WSAGetLastError()); } + } } #endif /* STREAMSCONN */ } @@ -1070,18 +1160,18 @@ send_query_msg(void) for (mcl = mcastlist; mcl != NULL; mcl = mcl->next) { for (ai = mcl->ai; ai != NULL; ai = ai->ai_next) { if (ai->ai_family == AF_INET) { - unsigned char hopflag = (unsigned char) mcl->hops; + int hopflag = mcl->hops; socketfd = xdmcpSocket; setsockopt(socketfd, IPPROTO_IP, IP_MULTICAST_TTL, - &hopflag, sizeof(hopflag)); + (char*)&hopflag, sizeof(hopflag)); } else if (ai->ai_family == AF_INET6) { int hopflag6 = mcl->hops; socketfd = xdmcpSocket6; setsockopt(socketfd, IPPROTO_IPV6, IPV6_MULTICAST_HOPS, - &hopflag6, sizeof(hopflag6)); + (char*)&hopflag6, sizeof(hopflag6)); } else { continue; @@ -1435,6 +1525,10 @@ get_addr_by_name(const char *argtype, char *pport = portstr; int gaierr; +#if defined(WIN32) && defined(TCPCONN) + _XSERVTransWSAStartup(); +#endif + memset(&hints, 0, sizeof(hints)); hints.ai_socktype = socktype; @@ -1478,9 +1572,6 @@ get_addr_by_name(const char *argtype, #ifdef XTHREADS_NEEDS_BYNAMEPARAMS _Xgethostbynameparams hparams; #endif -#if defined(WIN32) && defined(TCPCONN) - _XSERVTransWSAStartup(); -#endif if (!(hep = _XGethostbyname(namestr, hparams))) { FatalError("Xserver: %s unknown host: %s\n", argtype, namestr); } @@ -1501,7 +1592,11 @@ static void get_manager_by_name(int argc, char **argv, int i) { + PSOCKADDR_IN queryAddr = NULL; + u_long u_lqueryAddr = 0; + if ((i + 1) == argc) { + FatalError("Xserver: missing %s host name in command line\n", argv[i]); } @@ -1511,6 +1606,9 @@ get_manager_by_name(int argc, char **argv, int i) , &mgrAddr, &mgrAddrFirst #endif ); + queryAddr = (PSOCKADDR_IN)&ManagerAddress; + u_lqueryAddr = queryAddr->sin_addr.S_un.S_addr; + match_interface(u_lqueryAddr); } static void diff --git a/xorg-server/os/xprintf.c b/xorg-server/os/xprintf.c index 80caa5790..58aad894b 100644 --- a/xorg-server/os/xprintf.c +++ b/xorg-server/os/xprintf.c @@ -78,9 +78,11 @@ #ifdef __va_copy #define va_copy __va_copy #else +#ifndef _MSC_VER #error "no working va_copy was found" #endif #endif +#endif /** * Varargs sprintf that allocates a string buffer the right size for @@ -99,11 +101,16 @@ Xvasprintf(char **ret, const char *_X_RESTRICT_KYWD format, va_list va) return vasprintf(ret, format, va); #else int size; + +#ifdef _MSC_VER + size = vsnprintf(NULL, 0, format, va); +#else va_list va2; va_copy(va2, va); size = vsnprintf(NULL, 0, format, va2); va_end(va2); +#endif *ret = malloc(size + 1); if (*ret == NULL) diff --git a/xorg-server/os/xstrans.c b/xorg-server/os/xstrans.c index 6348a6511..cdc8f8eec 100644 --- a/xorg-server/os/xstrans.c +++ b/xorg-server/os/xstrans.c @@ -5,11 +5,19 @@ #include <X11/Xfuncproto.h> /* ErrorF is used by xtrans */ -extern _X_EXPORT void +/*extern _X_EXPORT void ErrorF(const char *f, ...) -_X_ATTRIBUTE_PRINTF(1, 2); +_X_ATTRIBUTE_PRINTF(1, 2);*/ #define TRANS_REOPEN #define TRANS_SERVER #define XSERV_t +#ifndef TCPCONN +#define TCPCONN +#endif +#ifdef WIN32 +#undef SO_REUSEADDR +#define SO_BINDRETRYCOUNT 0 // do not try to bind again when it fails, this will speed up searching for a free listening port +#endif + #include <X11/Xtrans/transport.c> |