13dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin/* -*- Mode: C; tab-width: 4 -*- 23dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * 33dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * Copyright (c) 2002-2004 Apple Computer, Inc. All rights reserved. 43dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * 53dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * Licensed under the Apache License, Version 2.0 (the "License"); 63dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * you may not use this file except in compliance with the License. 73dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * You may obtain a copy of the License at 83dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * 93dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * http://www.apache.org/licenses/LICENSE-2.0 103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * 113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * Unless required by applicable law or agreed to in writing, software 123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * distributed under the License is distributed on an "AS IS" BASIS, 133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * See the License for the specific language governing permissions and 153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin * limitations under the License. 163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin To Do: 183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin - Get unicode name of machine for nice name instead of just the host name. 203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin - Use the IPv6 Internet Connection Firewall API to allow IPv6 mDNS without manually changing the firewall. 213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin - Get DNS server address(es) from Windows and provide them to the uDNS layer. 223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin - Implement TCP support for truncated packets (only stubs now). 233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin*/ 253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <stdarg.h> 273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <stddef.h> 283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <stdio.h> 293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <stdlib.h> 303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <crtdbg.h> 313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <string.h> 323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include "CommonServices.h" 343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include "DebugServices.h" 353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include "Firewall.h" 363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include "RegNames.h" 373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include "Secret.h" 383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <dns_sd.h> 393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <Iphlpapi.h> 413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <mswsock.h> 423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <process.h> 433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <ntsecapi.h> 443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <lm.h> 453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <winioctl.h> 463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include <ntddndis.h> // This defines the IOCTL constants. 473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include "mDNSEmbeddedAPI.h" 493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include "GenLinkedList.h" 503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include "DNSCommon.h" 513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#include "mDNSWin32.h" 523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if 0 543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#pragma mark == Constants == 553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// Constants 593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define DEBUG_NAME "[mDNSWin32] " 623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define MDNS_WINDOWS_USE_IPV6_IF_ADDRS 1 643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define MDNS_WINDOWS_ENABLE_IPV4 1 653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define MDNS_WINDOWS_ENABLE_IPV6 1 663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define MDNS_FIX_IPHLPAPI_PREFIX_BUG 1 673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define MDNS_SET_HINFO_STRINGS 0 683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define kMDNSDefaultName "My Computer" 703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define kWinSockMajorMin 2 723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define kWinSockMinorMin 2 733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define kRegistryMaxKeyLength 255 753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define kRegistryMaxValueName 16383 763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinstatic GUID kWSARecvMsgGUID = WSAID_WSARECVMSG; 783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define kIPv6IfIndexBase (10000000L) 803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define SMBPortAsNumber 445 813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define DEVICE_PREFIX "\\\\.\\" 823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if 0 843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#pragma mark == Prototypes == 853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// Prototypes 893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SetupNiceName( mDNS * const inMDNS ); 923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SetupHostName( mDNS * const inMDNS ); 933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SetupName( mDNS * const inMDNS ); 943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SetupInterface( mDNS * const inMDNS, const struct ifaddrs *inIFA, mDNSInterfaceData **outIFD ); 953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus TearDownInterface( mDNS * const inMDNS, mDNSInterfaceData *inIFD ); 963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void CALLBACK FreeInterface( mDNSInterfaceData *inIFD ); 973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SetupSocket( mDNS * const inMDNS, const struct sockaddr *inAddr, mDNSIPPort port, SocketRef *outSocketRef ); 983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SockAddrToMDNSAddr( const struct sockaddr * const inSA, mDNSAddr *outIP, mDNSIPPort *outPort ); 993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal OSStatus GetWindowsVersionString( char *inBuffer, size_t inBufferSize ); 1003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal int getifaddrs( struct ifaddrs **outAddrs ); 1013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void freeifaddrs( struct ifaddrs *inAddrs ); 1023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// Platform Accessors 1063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#ifdef __cplusplus 1083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin extern "C" { 1093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 1103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlintypedef struct mDNSPlatformInterfaceInfo mDNSPlatformInterfaceInfo; 1123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinstruct mDNSPlatformInterfaceInfo 1133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 1143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const char * name; 1153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSAddr ip; 1163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin}; 1173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mStatus mDNSPlatformInterfaceNameToID( mDNS * const inMDNS, const char *inName, mDNSInterfaceID *outID ); 1203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mStatus mDNSPlatformInterfaceIDToInfo( mDNS * const inMDNS, mDNSInterfaceID inID, mDNSPlatformInterfaceInfo *outInfo ); 1213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// Utilities 1233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( MDNS_WINDOWS_USE_IPV6_IF_ADDRS ) 1253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSlocal int getifaddrs_ipv6( struct ifaddrs **outAddrs ); 1263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 1273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal int getifaddrs_ipv4( struct ifaddrs **outAddrs ); 1293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal DWORD GetPrimaryInterface(); 1323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus AddressToIndexAndMask( struct sockaddr * address, uint32_t * index, struct sockaddr * mask ); 1333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mDNSBool CanReceiveUnicast( void ); 1343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mDNSBool IsPointToPoint( IP_ADAPTER_UNICAST_ADDRESS * addr ); 1353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus StringToAddress( mDNSAddr * ip, LPSTR string ); 1373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus RegQueryString( HKEY key, LPCSTR param, LPSTR * string, DWORD * stringLen, DWORD * enabled ); 1383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal struct ifaddrs* myGetIfAddrs(int refresh); 1393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal OSStatus TCHARtoUTF8( const TCHAR *inString, char *inBuffer, size_t inBufferSize ); 1403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal OSStatus WindowsLatin1toUTF8( const char *inString, char *inBuffer, size_t inBufferSize ); 1413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void TCPDidConnect( mDNS * const inMDNS, HANDLE event, void * context ); 1423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void TCPCanRead( TCPSocket * sock ); 1433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus TCPBeginRecv( TCPSocket * sock ); 1443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void CALLBACK TCPEndRecv( DWORD error, DWORD bytesTransferred, LPWSAOVERLAPPED overlapped, DWORD flags ); 1453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void TCPCloseSocket( TCPSocket * socket ); 1463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void CALLBACK TCPFreeSocket( TCPSocket *sock ); 1473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal OSStatus UDPBeginRecv( UDPSocket * socket ); 1483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void CALLBACK UDPEndRecv( DWORD err, DWORD bytesTransferred, LPWSAOVERLAPPED overlapped, DWORD flags ); 1493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void UDPCloseSocket( UDPSocket * sock ); 1503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void CALLBACK UDPFreeSocket( UDPSocket * sock ); 1513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SetupAddr(mDNSAddr *ip, const struct sockaddr *const sa); 1523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void GetDDNSFQDN( domainname *const fqdn ); 1533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#ifdef UNICODE 1543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void GetDDNSDomains( DNameListElem ** domains, LPCWSTR lpSubKey ); 1553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#else 1563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void GetDDNSDomains( DNameListElem ** domains, LPCSTR lpSubKey ); 1573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 1583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void SetDomainSecrets( mDNS * const inMDNS ); 1593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void SetDomainSecret( mDNS * const m, const domainname * inDomain ); 1603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal VOID CALLBACK CheckFileSharesProc( LPVOID arg, DWORD dwTimerLowValue, DWORD dwTimerHighValue ); 1613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void CheckFileShares( mDNS * const inMDNS ); 1623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void SMBCallback(mDNS *const m, ServiceRecordSet *const srs, mStatus result); 1633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mDNSu8 IsWOMPEnabledForAdapter( const char * adapterName ); 1643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void DispatchUDPEvent( mDNS * const m, UDPSocket * sock ); 1653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void DispatchTCPEvent( mDNS * const m, TCPSocket * sock ); 1663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#ifdef __cplusplus 1683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 1693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 1703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if 0 1723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#pragma mark == Globals == 1733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 1743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 1763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// Globals 1773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 1783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mDNS_PlatformSupport gMDNSPlatformSupport; 1803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSs32 mDNSPlatformOneSecond = 0; 1813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal UDPSocket * gUDPSockets = NULL; 1823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal int gUDPNumSockets = 0; 1833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal GenLinkedList gUDPDispatchableSockets; 1843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal GenLinkedList gTCPDispatchableSockets; 1853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( MDNS_WINDOWS_USE_IPV6_IF_ADDRS ) 1873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin typedef DWORD 1893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( WINAPI * GetAdaptersAddressesFunctionPtr )( 1903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ULONG inFamily, 1913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD inFlags, 1923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin PVOID inReserved, 1933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin PIP_ADAPTER_ADDRESSES inAdapter, 1943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin PULONG outBufferSize ); 1953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSlocal HMODULE gIPHelperLibraryInstance = NULL; 1973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSlocal GetAdaptersAddressesFunctionPtr gGetAdaptersAddressesFunctionPtr = NULL; 1983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 1993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 2003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#ifndef HCRYPTPROV 2033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin typedef ULONG_PTR HCRYPTPROV; // WinCrypt.h, line 249 2043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 2053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#ifndef CRYPT_MACHINE_KEYSET 2083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin# define CRYPT_MACHINE_KEYSET 0x00000020 2093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 2103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#ifndef CRYPT_NEWKEYSET 2123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin# define CRYPT_NEWKEYSET 0x00000008 2133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 2143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#ifndef PROV_RSA_FULL 2163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin# define PROV_RSA_FULL 1 2173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 2183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlintypedef BOOL (__stdcall *fnCryptGenRandom)( HCRYPTPROV, DWORD, BYTE* ); 2203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlintypedef BOOL (__stdcall *fnCryptAcquireContext)( HCRYPTPROV*, LPCTSTR, LPCTSTR, DWORD, DWORD); 2213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlintypedef BOOL (__stdcall *fnCryptReleaseContext)(HCRYPTPROV, DWORD); 2223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinstatic fnCryptAcquireContext g_lpCryptAcquireContext = NULL; 2243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinstatic fnCryptReleaseContext g_lpCryptReleaseContext = NULL; 2253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinstatic fnCryptGenRandom g_lpCryptGenRandom = NULL; 2263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinstatic HINSTANCE g_hAAPI32 = NULL; 2273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinstatic HCRYPTPROV g_hProvider = ( ULONG_PTR ) NULL; 2283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlintypedef DNSServiceErrorType ( DNSSD_API *DNSServiceRegisterFunc ) 2313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( 2323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DNSServiceRef *sdRef, 2333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DNSServiceFlags flags, 2343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin uint32_t interfaceIndex, 2353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const char *name, /* may be NULL */ 2363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const char *regtype, 2373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const char *domain, /* may be NULL */ 2383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const char *host, /* may be NULL */ 2393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin uint16_t port, 2403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin uint16_t txtLen, 2413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const void *txtRecord, /* may be NULL */ 2423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DNSServiceRegisterReply callBack, /* may be NULL */ 2433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin void *context /* may be NULL */ 2443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ); 2453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlintypedef void ( DNSSD_API *DNSServiceRefDeallocateFunc )( DNSServiceRef sdRef ); 2483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal HMODULE gDNSSDLibrary = NULL; 2503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal DNSServiceRegisterFunc gDNSServiceRegister = NULL; 2513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal DNSServiceRefDeallocateFunc gDNSServiceRefDeallocate = NULL; 2523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal HANDLE gSMBThread = NULL; 2533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal HANDLE gSMBThreadRegisterEvent = NULL; 2543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal HANDLE gSMBThreadDeregisterEvent = NULL; 2553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal HANDLE gSMBThreadStopEvent = NULL; 2563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal HANDLE gSMBThreadQuitEvent = NULL; 2573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define kSMBStopEvent ( WAIT_OBJECT_0 + 0 ) 2593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define kSMBRegisterEvent ( WAIT_OBJECT_0 + 1 ) 2603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#define kSMBDeregisterEvent ( WAIT_OBJECT_0 + 2 ) 2613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if 0 2643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#pragma mark - 2653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#pragma mark == Platform Support == 2663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 2673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 2693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformInit 2703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 2713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mStatus mDNSPlatformInit( mDNS * const inMDNS ) 2733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 2743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 2753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin WSADATA wsaData; 2763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int supported; 2773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in sa4; 2783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in6 sa6; 2793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int sa4len; 2803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int sa6len; 2813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD size; 2823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD val; 2833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "platform init\n" ); 2853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Initialize variables. If the PlatformSupport pointer is not null then just assume that a non-Apple client is 2873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // calling mDNS_Init and wants to provide its own storage for the platform-specific data so do not overwrite it. 2883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 2893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSPlatformMemZero( &gMDNSPlatformSupport, sizeof( gMDNSPlatformSupport ) ); 2903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( !inMDNS->p ) inMDNS->p = &gMDNSPlatformSupport; 2913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->mainThread = OpenThread( THREAD_ALL_ACCESS, FALSE, GetCurrentThreadId() ); 2923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( inMDNS->p->mainThread, exit, err = mStatus_UnknownErr ); 2933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->checkFileSharesTimer = CreateWaitableTimer( NULL, FALSE, NULL ); 2943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( inMDNS->p->checkFileSharesTimer, exit, err = mStatus_UnknownErr ); 2953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->checkFileSharesTimeout = 10; // Retry time for CheckFileShares() in seconds 2963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSPlatformOneSecond = 1000; // Use milliseconds as the quantum of time 2973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin InitLinkedList( &gTCPDispatchableSockets, offsetof( TCPSocket, nextDispatchable ) ); 2983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin InitLinkedList( &gUDPDispatchableSockets, offsetof( UDPSocket, nextDispatchable ) ); 2993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Startup WinSock 2.2 or later. 3013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = WSAStartup( MAKEWORD( kWinSockMajorMin, kWinSockMinorMin ), &wsaData ); 3033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 3043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin supported = ( ( LOBYTE( wsaData.wVersion ) == kWinSockMajorMin ) && ( HIBYTE( wsaData.wVersion ) == kWinSockMinorMin ) ); 3063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( supported, exit, err = mStatus_UnsupportedErr ); 3073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->CanReceiveUnicastOn5353 = CanReceiveUnicast(); 3093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Setup the HINFO HW strings. 3113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin //<rdar://problem/7245119> device-info should have model=Windows 3123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin strcpy_s( ( char* ) &inMDNS->HIHardware.c[ 1 ], sizeof( inMDNS->HIHardware.c ) - 2, "Windows" ); 3143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->HIHardware.c[ 0 ] = ( mDNSu8 ) mDNSPlatformStrLen( &inMDNS->HIHardware.c[ 1 ] ); 3153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "HIHardware: %#s\n", inMDNS->HIHardware.c ); 3163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Setup the HINFO SW strings. 3183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if ( MDNS_SET_HINFO_STRINGS ) 3193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNS_snprintf( (char *) &inMDNS->HISoftware.c[ 1 ], sizeof( inMDNS->HISoftware.c ) - 2, 3203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin "mDNSResponder (%s %s)", __DATE__, __TIME__ ); 3213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->HISoftware.c[ 0 ] = (mDNSu8) mDNSPlatformStrLen( &inMDNS->HISoftware.c[ 1 ] ); 3223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "HISoftware: %#s\n", inMDNS->HISoftware.c ); 3233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 3243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set the thread global overlapped flag 3263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin val = 0; 3283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( INVALID_SOCKET, SOL_SOCKET, SO_OPENTYPE, ( char* ) &val, sizeof( val ) ); 3293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( err != SOCKET_ERROR, WSAGetLastError(), kUnknownErr ); 3303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 3313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set up the IPv4 unicast socket 3333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock4.fd = INVALID_SOCKET; 3353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock4.recvMsgPtr = NULL; 3363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock4.ifd = NULL; 3373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock4.overlapped.pending = FALSE; 3383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock4.next = NULL; 3393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock4.m = inMDNS; 3403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if ( MDNS_WINDOWS_ENABLE_IPV4 ) 3423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4.sin_family = AF_INET; 3443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4.sin_addr.s_addr = INADDR_ANY; 3453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupSocket( inMDNS, (const struct sockaddr*) &sa4, zeroIPPort, &inMDNS->p->unicastSock4.fd ); 3463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 3473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4len = sizeof( sa4 ); 3483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = getsockname( inMDNS->p->unicastSock4.fd, (struct sockaddr*) &sa4, &sa4len ); 3493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 3503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock4.port.NotAnInteger = sa4.sin_port; 3513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->UnicastPort4 = inMDNS->p->unicastSock4.port; 3523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = WSAIoctl( inMDNS->p->unicastSock4.fd, SIO_GET_EXTENSION_FUNCTION_POINTER, &kWSARecvMsgGUID, sizeof( kWSARecvMsgGUID ), &inMDNS->p->unicastSock4.recvMsgPtr, sizeof( inMDNS->p->unicastSock4.recvMsgPtr ), &size, NULL, NULL ); 3533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err ) 3553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 3563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock4.recvMsgPtr = NULL; 3573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 3583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = UDPBeginRecv( &inMDNS->p->unicastSock4 ); 3603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 3613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 3633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set up the IPv6 unicast socket 3653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock6.fd = INVALID_SOCKET; 3673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock6.recvMsgPtr = NULL; 3683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock6.ifd = NULL; 3693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock6.overlapped.pending = FALSE; 3703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock6.next = NULL; 3713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock6.m = inMDNS; 3723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if ( MDNS_WINDOWS_ENABLE_IPV6 ) 3743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6.sin6_family = AF_INET6; 3763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6.sin6_addr = in6addr_any; 3773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6.sin6_scope_id = 0; 3783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // This call will fail if the machine hasn't installed IPv6. In that case, 3803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // the error will be WSAEAFNOSUPPORT. 3813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupSocket( inMDNS, (const struct sockaddr*) &sa6, zeroIPPort, &inMDNS->p->unicastSock6.fd ); 3833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( !err || ( err == WSAEAFNOSUPPORT ), exit, err = (mStatus) WSAGetLastError() ); 3843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = kNoErr; 3853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If we weren't able to create the socket (because IPv6 hasn't been installed) don't do this 3873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( inMDNS->p->unicastSock6.fd != INVALID_SOCKET ) 3893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 3903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6len = sizeof( sa6 ); 3913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = getsockname( inMDNS->p->unicastSock6.fd, (struct sockaddr*) &sa6, &sa6len ); 3923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 3933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock6.port.NotAnInteger = sa6.sin6_port; 3943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->UnicastPort6 = inMDNS->p->unicastSock6.port; 3953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = WSAIoctl( inMDNS->p->unicastSock6.fd, SIO_GET_EXTENSION_FUNCTION_POINTER, &kWSARecvMsgGUID, sizeof( kWSARecvMsgGUID ), &inMDNS->p->unicastSock6.recvMsgPtr, sizeof( inMDNS->p->unicastSock6.recvMsgPtr ), &size, NULL, NULL ); 3973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 3983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err != 0 ) 3993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 4003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock6.recvMsgPtr = NULL; 4013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 4023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = UDPBeginRecv( &inMDNS->p->unicastSock6 ); 4043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 4053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 4063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 4083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Notify core of domain secret keys 4103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SetDomainSecrets( inMDNS ); 4123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Success! 4143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSCoreInitComplete( inMDNS, err ); 4163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 4193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err ) 4213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 4223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSPlatformClose( inMDNS ); 4233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 4243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "platform init done (err=%d %m)\n", err, err ); 4263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 4273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 4283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 4303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformClose 4313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 4323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformClose( mDNS * const inMDNS ) 4343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 4353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 4363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "platform close\n" ); 4383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 4393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( gSMBThread != NULL ) 4413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 4423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "tearing down smb registration thread\n" ); 4433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SetEvent( gSMBThreadStopEvent ); 4443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( WaitForSingleObject( gSMBThreadQuitEvent, 5 * 1000 ) == WAIT_OBJECT_0 ) 4463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 4473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( gSMBThreadQuitEvent ) 4483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 4493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin CloseHandle( gSMBThreadQuitEvent ); 4503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gSMBThreadQuitEvent = NULL; 4513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 4523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( gSMBThreadStopEvent ) 4543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 4553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin CloseHandle( gSMBThreadStopEvent ); 4563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gSMBThreadStopEvent = NULL; 4573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 4583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( gSMBThreadDeregisterEvent ) 4603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 4613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin CloseHandle( gSMBThreadDeregisterEvent ); 4623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gSMBThreadDeregisterEvent = NULL; 4633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 4643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( gSMBThreadRegisterEvent ) 4663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 4673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin CloseHandle( gSMBThreadRegisterEvent ); 4683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gSMBThreadRegisterEvent = NULL; 4693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 4703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( gDNSSDLibrary ) 4723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 4733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin FreeLibrary( gDNSSDLibrary ); 4743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gDNSSDLibrary = NULL; 4753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 4763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 4773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 4783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 4793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LogMsg( "Unable to stop SMBThread" ); 4803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 4813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->smbFileSharing = mDNSfalse; 4833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->smbPrintSharing = mDNSfalse; 4843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 4853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Tear everything down in reverse order to how it was set up. 4873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = TearDownInterfaceList( inMDNS ); 4893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 4903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( !inMDNS->p->inactiveInterfaceList ); 4913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if ( MDNS_WINDOWS_ENABLE_IPV4 ) 4933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin UDPCloseSocket( &inMDNS->p->unicastSock4 ); 4953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 4973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 4983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if ( MDNS_WINDOWS_ENABLE_IPV6 ) 4993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin UDPCloseSocket( &inMDNS->p->unicastSock6 ); 5013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 5033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Free the DLL needed for IPv6 support. 5053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( MDNS_WINDOWS_USE_IPV6_IF_ADDRS ) 5073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( gIPHelperLibraryInstance ) 5083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 5093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gGetAdaptersAddressesFunctionPtr = NULL; 5103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin FreeLibrary( gIPHelperLibraryInstance ); 5123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gIPHelperLibraryInstance = NULL; 5133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 5143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 5153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( g_hAAPI32 ) 5173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 5183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Release any resources 5193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( g_hProvider && g_lpCryptReleaseContext ) 5213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 5223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( g_lpCryptReleaseContext )( g_hProvider, 0 ); 5233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 5243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Free the AdvApi32.dll 5263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin FreeLibrary( g_hAAPI32 ); 5283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // And reset all the data 5303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin g_lpCryptAcquireContext = NULL; 5323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin g_lpCryptReleaseContext = NULL; 5333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin g_lpCryptGenRandom = NULL; 5343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin g_hProvider = ( ULONG_PTR ) NULL; 5353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin g_hAAPI32 = NULL; 5363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 5373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Clear out the APC queue 5393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while ( SleepEx( 0, TRUE ) == WAIT_IO_COMPLETION ) 5413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 5423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DispatchSocketEvents( inMDNS ); 5433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 5443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin WSACleanup(); 5463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "platform close done\n" ); 5483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 5493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 5523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformLock 5533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 5543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformLock( const mDNS * const inMDNS ) 5563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 5573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( void ) inMDNS; 5583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 5593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 5613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformUnlock 5623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 5633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformUnlock( const mDNS * const inMDNS ) 5653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 5663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( void ) inMDNS; 5673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 5683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 5703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformStrCopy 5713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 5723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformStrCopy( void *inDst, const void *inSrc ) 5743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 5753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inSrc ); 5763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inDst ); 5773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin strcpy( (char *) inDst, (const char*) inSrc ); 5793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 5803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 5823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformStrLCopy 5833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 5843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mDNSu32 mDNSPlatformStrLCopy(void *inDst, const void *inSrc, mDNSu32 inSize) 5863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 5873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const char * src = (const char *) inSrc; 5883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( inSize > 0 ) 5903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 5913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin size_t n; 5923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char * dst = (char *) inDst; 5933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 5943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( n = inSize - 1; n > 0; --n ) 5953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 5963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ( *dst++ = *src++ ) == '\0' ) 5973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 5983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Null terminator encountered, so exit. 5993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin goto exit; 6003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 6013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 6023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *dst = '\0'; 6033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 6043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while( *src++ != '\0' ) 6063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 6073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Stop at null terminator. 6083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 6093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 6113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( (mDNSu32)( src - (const char *) inSrc ) - 1 ); 6123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 6133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformStrLen 6163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mDNSu32 mDNSPlatformStrLen( const void *inSrc ) 6193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 6203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inSrc ); 6213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( (mDNSu32) strlen( (const char *) inSrc ) ); 6233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 6243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformMemCopy 6273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformMemCopy( void *inDst, const void *inSrc, mDNSu32 inSize ) 6303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 6313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inSrc ); 6323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inDst ); 6333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy( inDst, inSrc, inSize ); 6353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 6363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformMemSame 6393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mDNSBool mDNSPlatformMemSame( const void *inDst, const void *inSrc, mDNSu32 inSize ) 6423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 6433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inSrc ); 6443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inDst ); 6453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( (mDNSBool)( memcmp( inSrc, inDst, inSize ) == 0 ) ); 6473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 6483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformMemZero 6513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformMemZero( void *inDst, mDNSu32 inSize ) 6543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 6553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inDst ); 6563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memset( inDst, 0, inSize ); 6583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 6593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformMemAllocate 6623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void * mDNSPlatformMemAllocate( mDNSu32 inSize ) 6653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 6663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin void * mem; 6673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inSize > 0 ); 6693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mem = malloc( inSize ); 6713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( mem ); 6723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( mem ); 6743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 6753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformMemFree 6783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformMemFree( void *inMem ) 6813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 6823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMem ); 6833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( inMem ); 6853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 6863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformRandomNumber 6893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 6903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mDNSu32 mDNSPlatformRandomNumber(void) 6923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 6933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSu32 randomNumber = 0; 6943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin BOOL bResult; 6953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin OSStatus err = 0; 6963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 6973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !g_hAAPI32 ) 6983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 6993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin g_hAAPI32 = LoadLibrary( TEXT("AdvAPI32.dll") ); 7003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( g_hAAPI32 != NULL, GetLastError(), mStatus_UnknownErr ); 7013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 7023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 7033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Function Pointer: CryptAcquireContext 7053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !g_lpCryptAcquireContext ) 7073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 7083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin g_lpCryptAcquireContext = ( fnCryptAcquireContext ) 7093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#ifdef UNICODE 7103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( GetProcAddress( g_hAAPI32, "CryptAcquireContextW" ) ); 7113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#else 7123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( GetProcAddress( g_hAAPI32, "CryptAcquireContextA" ) ); 7133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 7143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( g_lpCryptAcquireContext != NULL, GetLastError(), mStatus_UnknownErr ); 7153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 7163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 7173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Function Pointer: CryptReleaseContext 7193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !g_lpCryptReleaseContext ) 7213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 7223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin g_lpCryptReleaseContext = ( fnCryptReleaseContext ) 7233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( GetProcAddress( g_hAAPI32, "CryptReleaseContext" ) ); 7243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( g_lpCryptReleaseContext != NULL, GetLastError(), mStatus_UnknownErr ); 7253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 7263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 7273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Function Pointer: CryptGenRandom 7293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !g_lpCryptGenRandom ) 7313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 7323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin g_lpCryptGenRandom = ( fnCryptGenRandom ) 7333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( GetProcAddress( g_hAAPI32, "CryptGenRandom" ) ); 7343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( g_lpCryptGenRandom != NULL, GetLastError(), mStatus_UnknownErr ); 7353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 7363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 7373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Setup 7393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !g_hProvider ) 7413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 7423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin bResult = (*g_lpCryptAcquireContext)( &g_hProvider, NULL, NULL, PROV_RSA_FULL, CRYPT_MACHINE_KEYSET ); 7433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !bResult ) 7453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 7463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin bResult = ( *g_lpCryptAcquireContext)( &g_hProvider, NULL, NULL, PROV_RSA_FULL, CRYPT_MACHINE_KEYSET | CRYPT_NEWKEYSET ); 7473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( bResult, GetLastError(), mStatus_UnknownErr ); 7483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 7493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 7503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 7513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin bResult = (*g_lpCryptGenRandom)( g_hProvider, sizeof( randomNumber ), ( BYTE* ) &randomNumber ); 7533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( bResult, GetLastError(), mStatus_UnknownErr ); 7543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 7553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 7573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err ) 7593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 7603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin randomNumber = rand(); 7613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 7623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return randomNumber; 7643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 7653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 7673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformTimeInit 7683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 7693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mStatus mDNSPlatformTimeInit( void ) 7713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 7723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // No special setup is required on Windows -- we just use GetTickCount(). 7733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( mStatus_NoError ); 7743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 7753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 7773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformRawTime 7783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 7793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mDNSs32 mDNSPlatformRawTime( void ) 7813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 7823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( (mDNSs32) GetTickCount() ); 7833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 7843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 7863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformUTC 7873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 7883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mDNSs32 mDNSPlatformUTC( void ) 7903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 7913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return ( mDNSs32 ) time( NULL ); 7923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 7933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 7953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformInterfaceNameToID 7963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 7973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 7983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mStatus mDNSPlatformInterfaceNameToID( mDNS * const inMDNS, const char *inName, mDNSInterfaceID *outID ) 7993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 8003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 8013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceData * ifd; 8023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 8043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS->p ); 8053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inName ); 8063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Search for an interface with the specified name, 8083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( ifd = inMDNS->p->interfaceList; ifd; ifd = ifd->next ) 8103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 8113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( strcmp( ifd->name, inName ) == 0 ) 8123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 8133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 8143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 8153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 8163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action_quiet( ifd, exit, err = mStatus_NoSuchNameErr ); 8173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Success! 8193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( outID ) 8213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 8223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *outID = (mDNSInterfaceID) ifd; 8233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 8243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = mStatus_NoError; 8253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 8273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 8283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 8293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 8313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformInterfaceIDToInfo 8323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 8333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mStatus mDNSPlatformInterfaceIDToInfo( mDNS * const inMDNS, mDNSInterfaceID inID, mDNSPlatformInterfaceInfo *outInfo ) 8353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 8363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 8373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceData * ifd; 8383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 8403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inID ); 8413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( outInfo ); 8423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Search for an interface with the specified ID, 8443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( ifd = inMDNS->p->interfaceList; ifd; ifd = ifd->next ) 8463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 8473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ifd == (mDNSInterfaceData *) inID ) 8483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 8493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 8503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 8513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 8523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action_quiet( ifd, exit, err = mStatus_NoSuchNameErr ); 8533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Success! 8553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin outInfo->name = ifd->name; 8573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin outInfo->ip = ifd->interfaceInfo.ip; 8583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = mStatus_NoError; 8593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 8613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 8623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 8633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 8653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformInterfaceIDfromInterfaceIndex 8663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 8673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mDNSInterfaceID mDNSPlatformInterfaceIDfromInterfaceIndex( mDNS * const inMDNS, mDNSu32 inIndex ) 8693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 8703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceID id; 8713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin id = mDNSNULL; 8733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( inIndex == kDNSServiceInterfaceIndexLocalOnly ) 8743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 8753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin id = mDNSInterface_LocalOnly; 8763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 8773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin /* uncomment if Windows ever supports P2P 8783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( inIndex == kDNSServiceInterfaceIndexP2P ) 8793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 8803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin id = mDNSInterface_P2P; 8813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 8823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin */ 8833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( inIndex != 0 ) 8843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 8853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceData * ifd; 8863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 8873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( ifd = inMDNS->p->interfaceList; ifd; ifd = ifd->next ) 8883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 8893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ( ifd->scopeID == inIndex ) && ifd->interfaceInfo.InterfaceActive ) 8903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 8913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin id = ifd->interfaceInfo.InterfaceID; 8923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 8933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 8943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 8953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( ifd ); 8963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 8973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( id ); 8983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 8993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 9013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformInterfaceIndexfromInterfaceID 9023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 9033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mDNSu32 mDNSPlatformInterfaceIndexfromInterfaceID( mDNS * const inMDNS, mDNSInterfaceID inID, mDNSBool suppressNetworkChange ) 9053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 9063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSu32 index; 9073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin (void) suppressNetworkChange; // Unused 9083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin index = 0; 9103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( inID == mDNSInterface_LocalOnly ) 9113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 9123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin index = (mDNSu32) kDNSServiceInterfaceIndexLocalOnly; 9133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 9143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin /* uncomment if Windows ever supports P2P 9153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( inID == mDNSInterface_P2P ) 9163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 9173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin index = (mDNSu32) kDNSServiceInterfaceIndexP2P; 9183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 9193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin */ 9203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( inID ) 9213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 9223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceData * ifd; 9233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Search active interfaces. 9253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( ifd = inMDNS->p->interfaceList; ifd; ifd = ifd->next ) 9263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 9273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( (mDNSInterfaceID) ifd == inID ) 9283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 9293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin index = ifd->scopeID; 9303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 9313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 9323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 9333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Search inactive interfaces too so remove events for inactive interfaces report the old interface index. 9353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( !ifd ) 9373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 9383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( ifd = inMDNS->p->inactiveInterfaceList; ifd; ifd = ifd->next ) 9393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 9403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( (mDNSInterfaceID) ifd == inID ) 9413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 9423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin index = ifd->scopeID; 9433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 9443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 9453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 9463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 9473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( ifd ); 9483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 9493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( index ); 9503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 9513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 9543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformTCPSocket 9553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 9563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinTCPSocket * 9583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSPlatformTCPSocket 9593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( 9603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNS * const m, 9613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCPSocketFlags flags, 9623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSIPPort * port 9633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ) 9643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 9653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCPSocket * sock = NULL; 9663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin u_long on = 1; // "on" for setsockopt 9673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in saddr; 9683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int len; 9693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err = mStatus_NoError; 9703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( m ); 9723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( flags == 0, exit, err = mStatus_UnsupportedErr ); 9743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Setup connection data object 9763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = (TCPSocket *) malloc( sizeof( TCPSocket ) ); 9783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( sock, exit, err = mStatus_NoMemoryErr ); 9793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSPlatformMemZero( sock, sizeof( TCPSocket ) ); 9803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->fd = INVALID_SOCKET; 9813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->flags = flags; 9823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->m = m; 9833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSPlatformMemZero(&saddr, sizeof(saddr)); 9853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin saddr.sin_family = AF_INET; 9863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin saddr.sin_addr.s_addr = htonl( INADDR_ANY ); 9873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin saddr.sin_port = port->NotAnInteger; 9883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Create the socket 9903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->fd = socket(AF_INET, SOCK_STREAM, 0); 9923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( sock->fd != INVALID_SOCKET, WSAGetLastError(), mStatus_UnknownErr ); 9933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 9943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // bind 9963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 9973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = bind( sock->fd, ( struct sockaddr* ) &saddr, sizeof( saddr ) ); 9983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( err == 0, WSAGetLastError(), mStatus_UnknownErr ); 9993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 10003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set it to be non-blocking 10023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = ioctlsocket( sock->fd, FIONBIO, &on ); 10043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( err == 0, WSAGetLastError(), mStatus_UnknownErr ); 10053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 10063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get port number 10083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSPlatformMemZero( &saddr, sizeof( saddr ) ); 10103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin len = sizeof( saddr ); 10113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = getsockname( sock->fd, ( struct sockaddr* ) &saddr, &len ); 10133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( err == 0, WSAGetLastError(), mStatus_UnknownErr ); 10143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 10153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin port->NotAnInteger = saddr.sin_port; 10173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 10193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err && sock ) 10213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 10223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCPFreeSocket( sock ); 10233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = mDNSNULL; 10243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 10253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return sock; 10273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 10283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 10303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformTCPConnect 10313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 10323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmStatus 10343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSPlatformTCPConnect 10353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( 10363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCPSocket * sock, 10373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const mDNSAddr * inDstIP, 10383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSOpaque16 inDstPort, 10393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin domainname * hostname, 10403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceID inInterfaceID, 10413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCPConnectionCallback inCallback, 10423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin void * inContext 10433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ) 10443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 10453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in saddr; 10463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err = mStatus_NoError; 10473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( inInterfaceID ); 10493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( void ) hostname; 10503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( inDstIP->type != mDNSAddrType_IPv4 ) 10523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 10533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LogMsg("ERROR: mDNSPlatformTCPConnect - attempt to connect to an IPv6 address: operation not supported"); 10543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return mStatus_UnknownErr; 10553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 10563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Setup connection data object 10583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->readEventHandler = TCPCanRead; 10603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->userCallback = inCallback; 10613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->userContext = inContext; 10623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSPlatformMemZero(&saddr, sizeof(saddr)); 10643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin saddr.sin_family = AF_INET; 10653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin saddr.sin_port = inDstPort.NotAnInteger; 10663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy(&saddr.sin_addr, &inDstIP->ip.v4.NotAnInteger, sizeof(saddr.sin_addr)); 10673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Try and do connect 10693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = connect( sock->fd, ( struct sockaddr* ) &saddr, sizeof( saddr ) ); 10713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( !err || ( WSAGetLastError() == WSAEWOULDBLOCK ), exit, err = mStatus_ConnFailed ); 10723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->connected = !err ? TRUE : FALSE; 10733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->connected ) 10753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 10763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = TCPAddSocket( sock->m, sock ); 10773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 10783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 10793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 10803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 10813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( sock->m->p->registerWaitableEventFunc != NULL, exit, err = mStatus_ConnFailed ); 10823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->connectEvent = CreateEvent( NULL, FALSE, FALSE, NULL ); 10843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( sock->connectEvent, GetLastError(), mStatus_UnknownErr ); 10853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 10863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = WSAEventSelect( sock->fd, sock->connectEvent, FD_CONNECT ); 10883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 10893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = sock->m->p->registerWaitableEventFunc( sock->m, sock->connectEvent, sock, TCPDidConnect ); 10913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 10923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 10933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 10953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 10963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !err ) 10973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 10983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = sock->connected ? mStatus_ConnEstablished : mStatus_ConnPending; 10993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 11003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return err; 11023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 11033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 11053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformTCPAccept 11063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 11073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport 11093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport TCPSocket *mDNSPlatformTCPAccept( TCPSocketFlags flags, int fd ) 11103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 11113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCPSocket * sock = NULL; 11123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err = mStatus_NoError; 11133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( !flags, exit, err = mStatus_UnsupportedErr ); 11153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = malloc( sizeof( TCPSocket ) ); 11173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( sock, exit, err = mStatus_NoMemoryErr ); 11183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSPlatformMemZero( sock, sizeof( *sock ) ); 11203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->fd = fd; 11223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->flags = flags; 11233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 11253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err && sock ) 11273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 11283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( sock ); 11293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = NULL; 11303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 11313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return sock; 11333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 11343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 11373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformTCPCloseConnection 11383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 11393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformTCPCloseConnection( TCPSocket *sock ) 11413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 11423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( sock ); 11433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->connectEvent && sock->m->p->unregisterWaitableEventFunc ) 11453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 11463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->m->p->unregisterWaitableEventFunc( sock->m, sock->connectEvent ); 11473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 11483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->fd != INVALID_SOCKET ) 11503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 11513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCPCloseSocket( sock ); 11523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin QueueUserAPC( ( PAPCFUNC ) TCPFreeSocket, sock->m->p->mainThread, ( ULONG_PTR ) sock ); 11543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 11553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 11563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 11593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformReadTCP 11603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 11613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport long mDNSPlatformReadTCP( TCPSocket *sock, void *inBuffer, unsigned long inBufferSize, mDNSBool * closed ) 11633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 11643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin unsigned long bytesLeft; 11653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int wsaError; 11663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin long ret; 11673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *closed = sock->closed; 11693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin wsaError = sock->lastError; 11703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ret = -1; 11713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( *closed ) 11733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 11743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ret = 0; 11753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 11763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if ( sock->lastError == 0 ) 11773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 11783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // First check to see if we have any data left in our buffer 11793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin bytesLeft = ( DWORD ) ( sock->eptr - sock->bptr ); 11813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( bytesLeft ) 11833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 11843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin unsigned long bytesToCopy = ( bytesLeft < inBufferSize ) ? bytesLeft : inBufferSize; 11853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy( inBuffer, sock->bptr, bytesToCopy ); 11873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->bptr += bytesToCopy; 11883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !sock->overlapped.pending && ( sock->bptr == sock->eptr ) ) 11903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 11913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->bptr = sock->bbuf; 11923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->eptr = sock->bbuf; 11933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 11943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 11953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ret = bytesToCopy; 11963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 11973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 11983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 11993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin wsaError = WSAEWOULDBLOCK; 12003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 12013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 12023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Always set the last winsock error, so that we don't inadvertently use a previous one 12043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin WSASetLastError( wsaError ); 12063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return ret; 12083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 12093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 12123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformWriteTCP 12133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 12143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport long mDNSPlatformWriteTCP( TCPSocket *sock, const char *inMsg, unsigned long inMsgSize ) 12163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 12173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int nsent; 12183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin OSStatus err; 12193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin nsent = send( sock->fd, inMsg, inMsgSize, 0 ); 12213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( ( nsent >= 0 ) || ( WSAGetLastError() == WSAEWOULDBLOCK ), WSAGetLastError(), mStatus_UnknownErr ); 12233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 12243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( nsent < 0) 12263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 12273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin nsent = 0; 12283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 12293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 12313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return nsent; 12333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 12343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 12363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformTCPGetFD 12373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 12383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport int mDNSPlatformTCPGetFD(TCPSocket *sock ) 12403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 12413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return ( int ) sock->fd; 12423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 12433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 12463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// TCPAddConnection 12473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 12483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmStatus TCPAddSocket( mDNS * const inMDNS, TCPSocket *sock ) 12503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 12513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 12523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( void ) inMDNS; 12543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->bptr = sock->bbuf; 12563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->eptr = sock->bbuf; 12573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->ebuf = sock->bbuf + sizeof( sock->bbuf ); 12583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "adding TCPSocket 0x%x:%d\n", sock, sock->fd ); 12603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = TCPBeginRecv( sock ); 12613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 12623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 12643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return err; 12663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 12673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 12703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// TCPDidConnect 12713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 12723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void TCPDidConnect( mDNS * const inMDNS, HANDLE event, void * context ) 12743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 12753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCPSocket * sock = ( TCPSocket* ) context; 12763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCPConnectionCallback callback = NULL; 12773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin WSANETWORKEVENTS sockEvent; 12783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int err = kNoErr; 12793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( inMDNS->p->unregisterWaitableEventFunc ) 12813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 12823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unregisterWaitableEventFunc( inMDNS, event ); 12833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 12843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock ) 12863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 12873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin callback = ( TCPConnectionCallback ) sock->userCallback; 12883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = WSAEnumNetworkEvents( sock->fd, sock->connectEvent, &sockEvent ); 12893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 12903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( sockEvent.lNetworkEvents & FD_CONNECT, exit, err = mStatus_UnknownErr ); 12913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( sockEvent.iErrorCode[ FD_CONNECT_BIT ] == 0, exit, err = sockEvent.iErrorCode[ FD_CONNECT_BIT ] ); 12923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->connected = mDNStrue; 12943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 12953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->fd != INVALID_SOCKET ) 12963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 12973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = TCPAddSocket( sock->m, sock ); 12983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 12993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 13003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( callback ) 13023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 13033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin callback( sock, sock->userContext, TRUE, 0 ); 13043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 13053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 13063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 13083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err && callback ) 13103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 13113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin callback( sock, sock->userContext, TRUE, err ); 13123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 13133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 13143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 13183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// TCPCanRead 13193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 13203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void TCPCanRead( TCPSocket * sock ) 13223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 13233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCPConnectionCallback callback = ( TCPConnectionCallback ) sock->userCallback; 13243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( callback ) 13263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 13273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin callback( sock, sock->userContext, mDNSfalse, sock->lastError ); 13283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 13293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 13303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 13333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// TCPBeginRecv 13343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 13353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus TCPBeginRecv( TCPSocket * sock ) 13373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 13383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD bytesReceived = 0; 13393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD flags = 0; 13403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 13413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "%s: sock = %d\n", __ROUTINE__, sock->fd ); 13433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( !sock->overlapped.pending ); 13453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ZeroMemory( &sock->overlapped.data, sizeof( sock->overlapped.data ) ); 13473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.data.hEvent = sock; 13483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.wbuf.buf = ( char* ) sock->eptr; 13503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.wbuf.len = ( ULONG) ( sock->ebuf - sock->eptr ); 13513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = WSARecv( sock->fd, &sock->overlapped.wbuf, 1, &bytesReceived, &flags, &sock->overlapped.data, ( LPWSAOVERLAPPED_COMPLETION_ROUTINE ) TCPEndRecv ); 13533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( ( err == 0 ) || ( WSAGetLastError() == WSA_IO_PENDING ), WSAGetLastError(), kUnknownErr ); 13543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 13553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.pending = TRUE; 13573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 13593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return err; 13613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 13623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 13653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// TCPEndRecv 13663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 13673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void CALLBACK TCPEndRecv( DWORD error, DWORD bytesTransferred, LPWSAOVERLAPPED overlapped, DWORD flags ) 13693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 13703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCPSocket * sock; 13713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( void ) flags; 13733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "%s: error = %d, bytesTransferred = %d\n", __ROUTINE__, error, bytesTransferred ); 13753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = ( overlapped != NULL ) ? overlapped->hEvent : NULL; 13763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( sock, exit, error = ( DWORD ) mStatus_BadStateErr ); 13773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "%s: sock = %d\n", __ROUTINE__, sock->fd ); 13783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.error = error; 13793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.bytesTransferred = bytesTransferred; 13803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( sock->overlapped.pending ); 13813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.pending = FALSE; 13823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Queue this socket 13843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin AddToTail( &gTCPDispatchableSockets, sock ); 13863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 13883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return; 13903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 13913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 13953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformUDPSocket 13963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 13973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 13983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport UDPSocket* mDNSPlatformUDPSocket(mDNS *const m, const mDNSIPPort requestedport) 13993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 14003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin UDPSocket* sock = NULL; 14013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSIPPort port = requestedport; 14023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err = mStatus_NoError; 14033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin unsigned i; 14043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Setup connection data object 14063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = ( UDPSocket* ) malloc(sizeof( UDPSocket ) ); 14083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( sock, exit, err = mStatus_NoMemoryErr ); 14093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memset( sock, 0, sizeof( UDPSocket ) ); 14103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Create the socket 14123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->fd = INVALID_SOCKET; 14143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->recvMsgPtr = m->p->unicastSock4.recvMsgPtr; 14153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->addr = m->p->unicastSock4.addr; 14163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->ifd = NULL; 14173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.pending = FALSE; 14183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->m = m; 14193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Try at most 10000 times to get a unique random port 14213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for (i=0; i<10000; i++) 14233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 14243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in saddr; 14253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin saddr.sin_family = AF_INET; 14273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin saddr.sin_addr.s_addr = 0; 14283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // The kernel doesn't do cryptographically strong random port 14303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // allocation, so we do it ourselves here 14313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (mDNSIPPortIsZero(requestedport)) 14333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 14343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin port = mDNSOpaque16fromIntVal( ( mDNSu16 ) ( 0xC000 + mDNSRandom(0x3FFF) ) ); 14353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 14363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin saddr.sin_port = port.NotAnInteger; 14383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupSocket(m, ( struct sockaddr* ) &saddr, port, &sock->fd ); 14403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (!err) break; 14413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 14423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 14443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set the port 14463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->port = port; 14483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Arm the completion routine 14503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = UDPBeginRecv( sock ); 14523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 14533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Bookkeeping 14553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->next = gUDPSockets; 14573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gUDPSockets = sock; 14583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gUDPNumSockets++; 14593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 14613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err && sock ) 14633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 14643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin UDPFreeSocket( sock ); 14653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = NULL; 14663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 14673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return sock; 14693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 14703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 14723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformUDPClose 14733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 14743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformUDPClose( UDPSocket *sock ) 14763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 14773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin UDPSocket * current = gUDPSockets; 14783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin UDPSocket * last = NULL; 14793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while ( current ) 14813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 14823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( current == sock ) 14833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 14843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( last == NULL ) 14853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 14863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gUDPSockets = sock->next; 14873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 14883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 14893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 14903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin last->next = sock->next; 14913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 14923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 14933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Alertable I/O is great, except not so much when it comes to closing 14943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // the socket. Anything that has been previously queued for this socket 14953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // will stay in the queue after you close the socket. This is problematic 14963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // for obvious reasons. So we'll attempt to workaround this by closing 14973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // the socket which will prevent any further queued packets and then not calling 14983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // UDPFreeSocket directly, but by queueing it using QueueUserAPC. The queues 14993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // are FIFO, so that will execute *after* any other previous items in the queue 15003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // 15013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // UDPEndRecv will check if the socket is valid, and if not, it will ignore 15023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // the packet 15033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin UDPCloseSocket( sock ); 15053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin QueueUserAPC( ( PAPCFUNC ) UDPFreeSocket, sock->m->p->mainThread, ( ULONG_PTR ) sock ); 15073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gUDPNumSockets--; 15093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 15113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 15123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin last = current; 15143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin current = current->next; 15153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 15163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 15173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 15203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformSendUDP 15213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 15223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mStatus 15243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSPlatformSendUDP( 15253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const mDNS * const inMDNS, 15263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const void * const inMsg, 15273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const mDNSu8 * const inMsgEnd, 15283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceID inInterfaceID, 15293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin UDPSocket * inSrcSocket, 15303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const mDNSAddr * inDstIP, 15313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSIPPort inDstPort ) 15323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 15333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SOCKET sendingsocket = INVALID_SOCKET; 15343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err = mStatus_NoError; 15353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceData * ifd = (mDNSInterfaceData*) inInterfaceID; 15363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_storage addr; 15373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int n; 15383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_USE_ONLY( inMDNS ); 15403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin n = (int)( inMsgEnd - ( (const mDNSu8 * const) inMsg ) ); 15423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 15433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMsg ); 15443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMsgEnd ); 15453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inDstIP ); 15463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "platform send %d bytes to %#a:%u\n", n, inDstIP, ntohs( inDstPort.NotAnInteger ) ); 15483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( inDstIP->type == mDNSAddrType_IPv4 ) 15503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 15513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in * sa4; 15523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4 = (struct sockaddr_in *) &addr; 15543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4->sin_family = AF_INET; 15553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4->sin_port = inDstPort.NotAnInteger; 15563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4->sin_addr.s_addr = inDstIP->ip.v4.NotAnInteger; 15573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sendingsocket = ifd ? ifd->sock.fd : inMDNS->p->unicastSock4.fd; 15583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (inSrcSocket) { sendingsocket = inSrcSocket->fd; debugf("mDNSPlatformSendUDP using port %d, static port %d, sock %d", mDNSVal16(inSrcSocket->port), inMDNS->p->unicastSock4.fd, sendingsocket); } 15603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 15613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( inDstIP->type == mDNSAddrType_IPv6 ) 15623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 15633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in6 * sa6; 15643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6 = (struct sockaddr_in6 *) &addr; 15663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6->sin6_family = AF_INET6; 15673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6->sin6_port = inDstPort.NotAnInteger; 15683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6->sin6_flowinfo = 0; 15693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6->sin6_addr = *( (struct in6_addr *) &inDstIP->ip.v6 ); 15703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6->sin6_scope_id = 0; // Windows requires the scope ID to be zero. IPV6_MULTICAST_IF specifies interface. 15713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sendingsocket = ifd ? ifd->sock.fd : inMDNS->p->unicastSock6.fd; 15723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 15733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 15743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 15753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelError, DEBUG_NAME "%s: dst is not an IPv4 or IPv6 address (type=%d)\n", __ROUTINE__, inDstIP->type ); 15763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = mStatus_BadParamErr; 15773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin goto exit; 15783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 15793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (IsValidSocket(sendingsocket)) 15813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 15823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin n = sendto( sendingsocket, (char *) inMsg, n, 0, (struct sockaddr *) &addr, sizeof( addr ) ); 15833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( n > 0, errno_compat(), kWriteErr ); 15843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err ) 15863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 15873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Don't report EHOSTDOWN (i.e. ARP failure), ENETDOWN, or no route to host for unicast destinations 15883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 15893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !mDNSAddressIsAllDNSLinkGroup( inDstIP ) && ( WSAGetLastError() == WSAEHOSTDOWN || WSAGetLastError() == WSAENETDOWN || WSAGetLastError() == WSAEHOSTUNREACH || WSAGetLastError() == WSAENETUNREACH ) ) 15903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 15913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = mStatus_TransientErr; 15923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 15933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 15943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 15953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 15963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 15973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 15983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 15993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 16013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 16023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 16033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformUpdateProxyList(mDNS *const m, const mDNSInterfaceID InterfaceID) 16063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 16073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( m ); 16083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( InterfaceID ); 16093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 16103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 16123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformSendRawPacket 16133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 16143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformSetAllowSleep(mDNS *const m, mDNSBool allowSleep, const char *reason) 16163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 16173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( m ); 16183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( allowSleep ); 16193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( reason ); 16203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 16213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformSendRawPacket(const void *const msg, const mDNSu8 *const end, mDNSInterfaceID InterfaceID) 16233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 16243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( msg ); 16253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( end ); 16263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( InterfaceID ); 16273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 16283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformReceiveRawPacket(const void *const msg, const mDNSu8 *const end, mDNSInterfaceID InterfaceID) 16303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 16313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( msg ); 16323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( end ); 16333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( InterfaceID ); 16343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 16353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformSetLocalAddressCacheEntry(mDNS *const m, const mDNSAddr *const tpa, const mDNSEthAddr *const tha, mDNSInterfaceID InterfaceID) 16373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 16383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( m ); 16393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( tpa ); 16403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( tha ); 16413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( InterfaceID ); 16423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 16433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformWriteDebugMsg(const char *msg) 16453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 16463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, "%s\n", msg ); 16473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 16483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformWriteLogMsg( const char * ident, const char * msg, mDNSLogLevel_t loglevel ) 16503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 16513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin extern mDNS mDNSStorage; 16523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int type; 16533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( ident ); 16553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin type = EVENTLOG_ERROR_TYPE; 16573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin switch (loglevel) 16593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 16603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin case MDNS_LOG_MSG: type = EVENTLOG_ERROR_TYPE; break; 16613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin case MDNS_LOG_OPERATION: type = EVENTLOG_WARNING_TYPE; break; 16623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin case MDNS_LOG_SPS: type = EVENTLOG_INFORMATION_TYPE; break; 16633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin case MDNS_LOG_INFO: type = EVENTLOG_INFORMATION_TYPE; break; 16643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin case MDNS_LOG_DEBUG: type = EVENTLOG_INFORMATION_TYPE; break; 16653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin default: 16663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin fprintf(stderr, "Unknown loglevel %d, assuming LOG_ERR\n", loglevel); 16673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin fflush(stderr); 16683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 16693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSStorage.p->reportStatusFunc( type, msg ); 16713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, "%s\n", msg ); 16723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 16733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformSourceAddrForDest( mDNSAddr * const src, const mDNSAddr * const dst ) 16753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 16763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( src ); 16773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( dst ); 16783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 16793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 16813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformTLSSetupCerts 16823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 16833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mStatus 16853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSPlatformTLSSetupCerts(void) 16863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 16873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return mStatus_UnsupportedErr; 16883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 16893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 16913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformTLSTearDownCerts 16923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 16933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void 16953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSPlatformTLSTearDownCerts(void) 16963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 16973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 16983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 16993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 17003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformSetDNSConfig 17013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 17023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void SetDNSServers( mDNS *const m ); 17043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void SetSearchDomainList( void ); 17053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformSetDNSConfig(mDNS *const m, mDNSBool setservers, mDNSBool setsearch, domainname *const fqdn, DNameListElem **regDomains, DNameListElem **browseDomains) 17073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 17083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (setservers) SetDNSServers(m); 17093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (setsearch) SetSearchDomainList(); 17103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( fqdn ) 17123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 17133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin GetDDNSFQDN( fqdn ); 17143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 17153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( browseDomains ) 17173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 17183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin GetDDNSDomains( browseDomains, kServiceParametersNode TEXT("\\DynDNS\\Setup\\") kServiceDynDNSBrowseDomains ); 17193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 17203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( regDomains ) 17223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 17233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin GetDDNSDomains( regDomains, kServiceParametersNode TEXT("\\DynDNS\\Setup\\") kServiceDynDNSRegistrationDomains ); 17243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 17253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 17263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 17293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformDynDNSHostNameStatusChanged 17303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 17313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void 17333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSPlatformDynDNSHostNameStatusChanged(const domainname *const dname, const mStatus status) 17343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 17353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char uname[MAX_ESCAPED_DOMAIN_NAME]; 17363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin BYTE bStatus; 17373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LPCTSTR name; 17383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin HKEY key = NULL; 17393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 17403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char * p; 17413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ConvertDomainNameToCString(dname, uname); 17433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p = uname; 17453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while (*p) 17473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 17483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *p = (char) tolower(*p); 17493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (!(*(p+1)) && *p == '.') *p = 0; // if last character, strip trailing dot 17503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p++; 17513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 17523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( strlen( p ) <= MAX_ESCAPED_DOMAIN_NAME ); 17543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin name = kServiceParametersNode TEXT("\\DynDNS\\State\\HostNames"); 17553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegCreateKey( HKEY_LOCAL_MACHINE, name, &key ); 17563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 17573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin bStatus = ( status ) ? 0 : 1; 17593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegSetValueEx( key, kServiceDynDNSStatus, 0, REG_DWORD, (const LPBYTE) &bStatus, sizeof(DWORD) ); 17603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 17613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 17633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( key ) 17653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 17663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RegCloseKey( key ); 17673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 17683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return; 17703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 17713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void FreeEtcHosts(mDNS *const m, AuthRecord *const rr, mStatus result) 17743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 17753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin (void)m; // unused 17763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin (void)rr; 17773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin (void)result; 17783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 17793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 17833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetDomainSecrets 17843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 17853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// This routine needs to be called whenever the system secrets database changes. 17873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// We call it from DynDNSConfigDidChange and mDNSPlatformInit 17883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinvoid 17903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinSetDomainSecrets( mDNS * const m ) 17913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 17923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DomainAuthInfo *ptr; 17933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin domainname fqdn; 17943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DNameListElem * regDomains = NULL; 17953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 17963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Rather than immediately deleting all keys now, we mark them for deletion in ten seconds. 17973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // In the case where the user simultaneously removes their DDNS host name and the key 17983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // for it, this gives mDNSResponder ten seconds to gracefully delete the name from the 17993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // server before it loses access to the necessary key. Otherwise, we'd leave orphaned 18003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // address records behind that we no longer have permission to delete. 18013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for (ptr = m->AuthInfoList; ptr; ptr = ptr->next) 18033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ptr->deltime = NonZeroTime(m->timenow + mDNSPlatformOneSecond*10); 18043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin GetDDNSFQDN( &fqdn ); 18063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( fqdn.c[ 0 ] ) 18083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 18093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SetDomainSecret( m, &fqdn ); 18103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 18113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin GetDDNSDomains( ®Domains, kServiceParametersNode TEXT("\\DynDNS\\Setup\\") kServiceDynDNSRegistrationDomains ); 18133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while ( regDomains ) 18153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 18163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DNameListElem * current = regDomains; 18173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SetDomainSecret( m, ¤t->name ); 18183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin regDomains = regDomains->next; 18193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( current ); 18203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 18213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 18223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 18253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetSearchDomainList 18263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 18273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void SetDomainFromDHCP( void ); 18293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void SetReverseMapSearchDomainList( void ); 18303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void 18323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinSetSearchDomainList( void ) 18333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 18343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char * searchList = NULL; 18353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD searchListLen; 18363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin //DNameListElem * head = NULL; 18373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin //DNameListElem * current = NULL; 18383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char * tok; 18393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin HKEY key; 18403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 18413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegCreateKey( HKEY_LOCAL_MACHINE, TEXT("SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters"), &key ); 18433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 18443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegQueryString( key, "SearchList", &searchList, &searchListLen, NULL ); 18463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 18473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Windows separates the search domains with ',' 18493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin tok = strtok( searchList, "," ); 18513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while ( tok ) 18523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 18533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ( strcmp( tok, "" ) != 0 ) && ( strcmp( tok, "." ) != 0 ) ) 18543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNS_AddSearchDomain_CString(tok, mDNSNULL); 18553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin tok = strtok( NULL, "," ); 18563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 18573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 18593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( searchList ) 18613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 18623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( searchList ); 18633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 18643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( key ) 18663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 18673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RegCloseKey( key ); 18683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 18693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SetDomainFromDHCP(); 18713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SetReverseMapSearchDomainList(); 18723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 18733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 18763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetReverseMapSearchDomainList 18773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 18783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void 18803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinSetReverseMapSearchDomainList( void ) 18813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 18823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * ifa; 18833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa = myGetIfAddrs( 1 ); 18853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while (ifa) 18863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 18873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSAddr addr; 18883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (ifa->ifa_addr->sa_family == AF_INET && !SetupAddr(&addr, ifa->ifa_addr) && !(ifa->ifa_flags & IFF_LOOPBACK) && ifa->ifa_netmask) 18903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 18913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSAddr netmask; 18923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char buffer[256]; 18933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 18943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (!SetupAddr(&netmask, ifa->ifa_netmask)) 18953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 18963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sprintf(buffer, "%d.%d.%d.%d.in-addr.arpa.", addr.ip.v4.b[3] & netmask.ip.v4.b[3], 18973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin addr.ip.v4.b[2] & netmask.ip.v4.b[2], 18983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin addr.ip.v4.b[1] & netmask.ip.v4.b[1], 18993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin addr.ip.v4.b[0] & netmask.ip.v4.b[0]); 19003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNS_AddSearchDomain_CString(buffer, mDNSNULL); 19013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 19023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 19033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa = ifa->ifa_next; 19053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 19063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return; 19083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 19093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 19123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetDNSServers 19133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 19143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void 19163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinSetDNSServers( mDNS *const m ) 19173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 19183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin PIP_PER_ADAPTER_INFO pAdapterInfo = NULL; 19193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin FIXED_INFO * fixedInfo = NULL; 19203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ULONG bufLen = 0; 19213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IP_ADDR_STRING * dnsServerList; 19223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IP_ADDR_STRING * ipAddr; 19233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD index; 19243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int i = 0; 19253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err = kUnknownErr; 19263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get the primary interface. 19283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin index = GetPrimaryInterface(); 19303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // This should have the interface index of the primary index. Fall back in cases where 19323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // it can't be determined. 19333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( index ) 19353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 19363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin bufLen = 0; 19373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( i = 0; i < 100; i++ ) 19393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 19403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = GetPerAdapterInfo( index, pAdapterInfo, &bufLen ); 19413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err != ERROR_BUFFER_OVERFLOW ) 19433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 19443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 19453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 19463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pAdapterInfo = (PIP_PER_ADAPTER_INFO) realloc( pAdapterInfo, bufLen ); 19483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( pAdapterInfo, exit, err = mStatus_NoMemoryErr ); 19493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 19503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 19523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dnsServerList = &pAdapterInfo->DnsServerList; 19543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 19553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 19563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 19573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin bufLen = sizeof( FIXED_INFO ); 19583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( i = 0; i < 100; i++ ) 19603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 19613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( fixedInfo ) 19623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 19633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin GlobalFree( fixedInfo ); 19643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin fixedInfo = NULL; 19653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 19663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin fixedInfo = (FIXED_INFO*) GlobalAlloc( GPTR, bufLen ); 19683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( fixedInfo, exit, err = mStatus_NoMemoryErr ); 19693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = GetNetworkParams( fixedInfo, &bufLen ); 19713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err != ERROR_BUFFER_OVERFLOW ) 19733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 19743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 19753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 19763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 19773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 19793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dnsServerList = &fixedInfo->DnsServerList; 19813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 19823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( ipAddr = dnsServerList; ipAddr; ipAddr = ipAddr->Next ) 19843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 19853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSAddr addr; 19863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = StringToAddress( &addr, ipAddr->IpAddress.String ); 19873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !err ) mDNS_AddDNSServer(m, mDNSNULL, mDNSInterface_Any, &addr, UnicastDNSPort, mDNSfalse, 0); 19883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 19893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 19913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( pAdapterInfo ) 19933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 19943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( pAdapterInfo ); 19953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 19963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 19973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( fixedInfo ) 19983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 19993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin GlobalFree( fixedInfo ); 20003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 20013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 20023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 20053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetDomainFromDHCP 20063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 20073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void 20093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinSetDomainFromDHCP( void ) 20103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 20113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int i = 0; 20123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IP_ADAPTER_INFO * pAdapterInfo; 20133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IP_ADAPTER_INFO * pAdapter; 20143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD bufLen; 20153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD index; 20163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin HKEY key = NULL; 20173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LPSTR domain = NULL; 20183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD dwSize; 20193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err = mStatus_NoError; 20203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pAdapterInfo = NULL; 20223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( i = 0; i < 100; i++ ) 20243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 20253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = GetAdaptersInfo( pAdapterInfo, &bufLen); 20263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err != ERROR_BUFFER_OVERFLOW ) 20283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 20293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 20303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 20313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pAdapterInfo = (IP_ADAPTER_INFO*) realloc( pAdapterInfo, bufLen ); 20333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( pAdapterInfo, exit, err = kNoMemoryErr ); 20343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 20353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 20373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin index = GetPrimaryInterface(); 20393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( pAdapter = pAdapterInfo; pAdapter; pAdapter = pAdapter->Next ) 20413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 20423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( pAdapter->IpAddressList.IpAddress.String && 20433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pAdapter->IpAddressList.IpAddress.String[0] && 20443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pAdapter->GatewayList.IpAddress.String && 20453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pAdapter->GatewayList.IpAddress.String[0] && 20463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( !index || ( pAdapter->Index == index ) ) ) 20473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 20483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Found one that will work 20493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char keyName[1024]; 20513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin _snprintf( keyName, 1024, "%s%s", "SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters\\Interfaces\\", pAdapter->AdapterName ); 20533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegCreateKeyA( HKEY_LOCAL_MACHINE, keyName, &key ); 20553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 20563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegQueryString( key, "Domain", &domain, &dwSize, NULL ); 20583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 20593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !domain || !domain[0] ) 20613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 20623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( domain ) 20633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 20643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( domain ); 20653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin domain = NULL; 20663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 20673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegQueryString( key, "DhcpDomain", &domain, &dwSize, NULL ); 20693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 20703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 20713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( domain && domain[0] ) mDNS_AddSearchDomain_CString(domain, mDNSNULL); 20733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 20753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 20763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 20773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 20793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( pAdapterInfo ) 20813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 20823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( pAdapterInfo ); 20833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 20843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( domain ) 20863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 20873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( domain ); 20883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 20893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( key ) 20913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 20923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RegCloseKey( key ); 20933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 20943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 20953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 20973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 20983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// mDNSPlatformGetPrimaryInterface 20993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 21003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mStatus 21023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSPlatformGetPrimaryInterface( mDNS * const m, mDNSAddr * v4, mDNSAddr * v6, mDNSAddr * router ) 21033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 21043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IP_ADAPTER_INFO * pAdapterInfo; 21053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IP_ADAPTER_INFO * pAdapter; 21063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD bufLen; 21073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int i; 21083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin BOOL found; 21093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD index; 21103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err = mStatus_NoError; 21113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( m ); 21133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *v6 = zeroAddr; 21153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pAdapterInfo = NULL; 21173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin bufLen = 0; 21183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin found = FALSE; 21193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( i = 0; i < 100; i++ ) 21213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 21223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = GetAdaptersInfo( pAdapterInfo, &bufLen); 21233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err != ERROR_BUFFER_OVERFLOW ) 21253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 21263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 21273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 21283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pAdapterInfo = (IP_ADAPTER_INFO*) realloc( pAdapterInfo, bufLen ); 21303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( pAdapterInfo, exit, err = kNoMemoryErr ); 21313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 21323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 21343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin index = GetPrimaryInterface(); 21363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( pAdapter = pAdapterInfo; pAdapter; pAdapter = pAdapter->Next ) 21383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 21393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( pAdapter->IpAddressList.IpAddress.String && 21403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pAdapter->IpAddressList.IpAddress.String[0] && 21413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pAdapter->GatewayList.IpAddress.String && 21423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pAdapter->GatewayList.IpAddress.String[0] && 21433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( StringToAddress( v4, pAdapter->IpAddressList.IpAddress.String ) == mStatus_NoError ) && 21443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( StringToAddress( router, pAdapter->GatewayList.IpAddress.String ) == mStatus_NoError ) && 21453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( !index || ( pAdapter->Index == index ) ) ) 21463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 21473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Found one that will work 21483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( pAdapter->AddressLength == sizeof( m->PrimaryMAC ) ) 21503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 21513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy( &m->PrimaryMAC, pAdapter->Address, pAdapter->AddressLength ); 21523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 21533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin found = TRUE; 21553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 21563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 21573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 21583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 21603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( pAdapterInfo ) 21623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 21633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( pAdapterInfo ); 21643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 21653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return err; 21673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 21683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void mDNSPlatformSendWakeupPacket(mDNS *const m, mDNSInterfaceID InterfaceID, char *EthAddr, char *IPAddr, int iteration) 21703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 21713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin (void) m; 21723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin (void) InterfaceID; 21733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin (void) EthAddr; 21743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin (void) IPAddr; 21753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin (void) iteration; 21763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 21773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport mDNSBool mDNSPlatformValidRecordForInterface(AuthRecord *rr, const NetworkInterfaceInfo *intf) 21793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 21803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin (void) rr; 21813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin (void) intf; 21823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return 1; 21843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 21853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if 0 21883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#pragma mark - 21893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 21903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 21913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 21923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// debugf_ 21933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 21943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( MDNS_DEBUGMSGS ) 21953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void debugf_( const char *inFormat, ... ) 21963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 21973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char buffer[ 512 ]; 21983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin va_list args; 21993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSu32 length; 22003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin va_start( args, inFormat ); 22023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin length = mDNS_vsnprintf( buffer, sizeof( buffer ), inFormat, args ); 22033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin va_end( args ); 22043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, "%s\n", buffer ); 22063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 22073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 22083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 22103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// verbosedebugf_ 22113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 22123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( MDNS_DEBUGMSGS > 1 ) 22143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSexport void verbosedebugf_( const char *inFormat, ... ) 22153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 22163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char buffer[ 512 ]; 22173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin va_list args; 22183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSu32 length; 22193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin va_start( args, inFormat ); 22213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin length = mDNS_vsnprintf( buffer, sizeof( buffer ), inFormat, args ); 22223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin va_end( args ); 22233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelVerbose, "%s\n", buffer ); 22253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 22263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 22273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if 0 22303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#pragma mark - 22313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#pragma mark == Platform Internals == 22323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 22333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 22363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetupNiceName 22373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 22383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmStatus SetupNiceName( mDNS * const inMDNS ) 22403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 22413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin HKEY descKey = NULL; 22423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char utf8[ 256 ]; 22433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LPCTSTR s; 22443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LPWSTR joinName; 22453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin NETSETUP_JOIN_STATUS joinStatus; 22463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err = 0; 22473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD namelen; 22483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin BOOL ok; 22493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 22513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set up the nice name. 22533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin utf8[0] = '\0'; 22543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // First try and open the registry key that contains the computer description value 22563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin s = TEXT("SYSTEM\\CurrentControlSet\\Services\\lanmanserver\\parameters"); 22573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegOpenKeyEx( HKEY_LOCAL_MACHINE, s, 0, KEY_READ, &descKey); 22583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kNameErr ); 22593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !err ) 22613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 22623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCHAR desc[256]; 22633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD descSize = sizeof( desc ); 22643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // look for the computer description 22663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegQueryValueEx( descKey, TEXT("srvcomment"), 0, NULL, (LPBYTE) &desc, &descSize); 22673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !err ) 22693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 22703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = TCHARtoUTF8( desc, utf8, sizeof( utf8 ) ); 22713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 22723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err ) 22743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 22753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin utf8[ 0 ] = '\0'; 22763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 22773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 22783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // if we can't find it in the registry, then use the hostname of the machine 22803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err || ( utf8[ 0 ] == '\0' ) ) 22813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 22823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCHAR hostname[256]; 22833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin namelen = sizeof( hostname ) / sizeof( TCHAR ); 22853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ok = GetComputerNameExW( ComputerNamePhysicalDnsHostname, hostname, &namelen ); 22873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( ok, (mStatus) GetLastError(), kNameErr ); 22883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 22893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( !err ) 22913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 22923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = TCHARtoUTF8( hostname, utf8, sizeof( utf8 ) ); 22933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 22943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 22953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err ) 22963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 22973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin utf8[ 0 ] = '\0'; 22983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 22993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 23003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // if we can't get the hostname 23023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err || ( utf8[ 0 ] == '\0' ) ) 23033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 23043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Invalidate name so fall back to a default name. 23053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin strcpy( utf8, kMDNSDefaultName ); 23073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 23083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin utf8[ sizeof( utf8 ) - 1 ] = '\0'; 23103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->nicelabel.c[ 0 ] = (mDNSu8) (strlen( utf8 ) < MAX_DOMAIN_LABEL ? strlen( utf8 ) : MAX_DOMAIN_LABEL); 23113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy( &inMDNS->nicelabel.c[ 1 ], utf8, inMDNS->nicelabel.c[ 0 ] ); 23123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "nice name \"%.*s\"\n", inMDNS->nicelabel.c[ 0 ], &inMDNS->nicelabel.c[ 1 ] ); 23143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( descKey ) 23163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 23173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RegCloseKey( descKey ); 23183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 23193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ZeroMemory( inMDNS->p->nbname, sizeof( inMDNS->p->nbname ) ); 23213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ZeroMemory( inMDNS->p->nbdomain, sizeof( inMDNS->p->nbdomain ) ); 23223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin namelen = sizeof( inMDNS->p->nbname ); 23243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ok = GetComputerNameExA( ComputerNamePhysicalNetBIOS, inMDNS->p->nbname, &namelen ); 23253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( ok ); 23263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ok ) dlog( kDebugLevelInfo, DEBUG_NAME "netbios name \"%s\"\n", inMDNS->p->nbname ); 23273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = NetGetJoinInformation( NULL, &joinName, &joinStatus ); 23293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check ( err == NERR_Success ); 23303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err == NERR_Success ) 23313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 23323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ( joinStatus == NetSetupWorkgroupName ) || ( joinStatus == NetSetupDomainName ) ) 23333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 23343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = TCHARtoUTF8( joinName, inMDNS->p->nbdomain, sizeof( inMDNS->p->nbdomain ) ); 23353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( !err ); 23363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !err ) dlog( kDebugLevelInfo, DEBUG_NAME "netbios domain/workgroup \"%s\"\n", inMDNS->p->nbdomain ); 23373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 23383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin NetApiBufferFree( joinName ); 23403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin joinName = NULL; 23413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 23423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = 0; 23443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 23463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 23473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 23493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetupHostName 23503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 23513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SetupHostName( mDNS * const inMDNS ) 23533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 23543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err = 0; 23553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char tempString[ 256 ]; 23563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD tempStringLen; 23573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin domainlabel tempLabel; 23583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin BOOL ok; 23593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 23613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set up the nice name. 23633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin tempString[ 0 ] = '\0'; 23643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // use the hostname of the machine 23663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin tempStringLen = sizeof( tempString ); 23673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ok = GetComputerNameExA( ComputerNamePhysicalDnsHostname, tempString, &tempStringLen ); 23683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( ok, (mStatus) GetLastError(), kNameErr ); 23693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 23703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // if we can't get the hostname 23723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( err || ( tempString[ 0 ] == '\0' ) ) 23733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 23743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Invalidate name so fall back to a default name. 23753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin strcpy( tempString, kMDNSDefaultName ); 23773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 23783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin tempString[ sizeof( tempString ) - 1 ] = '\0'; 23803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin tempLabel.c[ 0 ] = (mDNSu8) (strlen( tempString ) < MAX_DOMAIN_LABEL ? strlen( tempString ) : MAX_DOMAIN_LABEL ); 23813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy( &tempLabel.c[ 1 ], tempString, tempLabel.c[ 0 ] ); 23823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set up the host name. 23843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ConvertUTF8PstringToRFC1034HostLabel( tempLabel.c, &inMDNS->hostlabel ); 23863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( inMDNS->hostlabel.c[ 0 ] == 0 ) 23873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 23883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Nice name has no characters that are representable as an RFC1034 name (e.g. Japanese) so use the default. 23893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin MakeDomainLabelFromLiteralString( &inMDNS->hostlabel, kMDNSDefaultName ); 23913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 23923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS->hostlabel.c[ 0 ] != 0 ); 23943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNS_SetFQDN( inMDNS ); 23963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "host name \"%.*s\"\n", inMDNS->hostlabel.c[ 0 ], &inMDNS->hostlabel.c[ 1 ] ); 23983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 23993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 24003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 24013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 24033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetupName 24043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 24053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SetupName( mDNS * const inMDNS ) 24073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 24083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err = 0; 24093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 24113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupNiceName( inMDNS ); 24133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 24143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupHostName( inMDNS ); 24163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 24173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return err; 24193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 24203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 24233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetupInterfaceList 24243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 24253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmStatus SetupInterfaceList( mDNS * const inMDNS ) 24273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 24283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 24293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceData ** next; 24303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceData * ifd; 24313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * addrs; 24323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * p; 24333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * loopbackv4; 24343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * loopbackv6; 24353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin u_int flagMask; 24363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin u_int flagTest; 24373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSBool foundv4; 24383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSBool foundv6; 24393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSBool foundUnicastSock4DestAddr; 24403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSBool foundUnicastSock6DestAddr; 24413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "setting up interface list\n" ); 24433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 24443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS->p ); 24453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->registeredLoopback4 = mDNSfalse; 24473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->nextDHCPLeaseExpires = 0x7FFFFFFF; 24483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin addrs = NULL; 24493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin foundv4 = mDNSfalse; 24503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin foundv6 = mDNSfalse; 24513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin foundUnicastSock4DestAddr = mDNSfalse; 24523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin foundUnicastSock6DestAddr = mDNSfalse; 24533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Tear down any existing interfaces that may be set up. 24553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TearDownInterfaceList( inMDNS ); 24573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set up the name of this machine. 24593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupName( inMDNS ); 24613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 24623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set up IPv4 interface(s). We have to set up IPv4 first so any IPv6 interface with an IPv4-routable address 24643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // can refer to the IPv4 interface when it registers to allow DNS AAAA records over the IPv4 interface. 24653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = getifaddrs( &addrs ); 24673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 24683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin loopbackv4 = NULL; 24703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin loopbackv6 = NULL; 24713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin next = &inMDNS->p->interfaceList; 24723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin flagMask = IFF_UP | IFF_MULTICAST; 24743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin flagTest = IFF_UP | IFF_MULTICAST; 24753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( MDNS_WINDOWS_ENABLE_IPV4 ) 24773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( p = addrs; p; p = p->ifa_next ) 24783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 24793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( !p->ifa_addr || ( p->ifa_addr->sa_family != AF_INET ) || ( ( p->ifa_flags & flagMask ) != flagTest ) ) 24803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 24813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin continue; 24823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 24833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( p->ifa_flags & IFF_LOOPBACK ) 24843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 24853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( !loopbackv4 ) 24863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 24873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin loopbackv4 = p; 24883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 24893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin continue; 24903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 24913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelVerbose, DEBUG_NAME "Interface %40s (0x%08X) %##a\n", 24923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p->ifa_name ? p->ifa_name : "<null>", p->ifa_extra.index, p->ifa_addr ); 24933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupInterface( inMDNS, p, &ifd ); 24953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 24963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 24973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If this guy is point-to-point (ifd->interfaceInfo.McastTxRx == 0 ) we still want to 24983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // register him, but we also want to note that we haven't found a v4 interface 24993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // so that we register loopback so same host operations work 25003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ifd->interfaceInfo.McastTxRx == mDNStrue ) 25023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 25033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin foundv4 = mDNStrue; 25043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 25053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( p->ifa_dhcpEnabled && ( p->ifa_dhcpLeaseExpires < inMDNS->p->nextDHCPLeaseExpires ) ) 25073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 25083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->nextDHCPLeaseExpires = p->ifa_dhcpLeaseExpires; 25093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 25103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If we're on a platform that doesn't have WSARecvMsg(), there's no way 25123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // of determing the destination address of a packet that is sent to us. 25133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // For multicast packets, that's easy to determine. But for the unicast 25143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // sockets, we'll fake it by taking the address of the first interface 25153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // that is successfully setup. 25163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !foundUnicastSock4DestAddr ) 25183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 25193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock4.addr = ifd->interfaceInfo.ip; 25203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin foundUnicastSock4DestAddr = TRUE; 25213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 25223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *next = ifd; 25243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin next = &ifd->next; 25253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ++inMDNS->p->interfaceCount; 25263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 25273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 25283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set up IPv6 interface(s) after IPv4 is set up (see IPv4 notes above for reasoning). 25303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( MDNS_WINDOWS_ENABLE_IPV6 ) 25323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( p = addrs; p; p = p->ifa_next ) 25333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 25343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( !p->ifa_addr || ( p->ifa_addr->sa_family != AF_INET6 ) || ( ( p->ifa_flags & flagMask ) != flagTest ) ) 25353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 25363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin continue; 25373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 25383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( p->ifa_flags & IFF_LOOPBACK ) 25393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 25403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( !loopbackv6 ) 25413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 25423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin loopbackv6 = p; 25433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 25443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin continue; 25453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 25463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelVerbose, DEBUG_NAME "Interface %40s (0x%08X) %##a\n", 25473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p->ifa_name ? p->ifa_name : "<null>", p->ifa_extra.index, p->ifa_addr ); 25483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupInterface( inMDNS, p, &ifd ); 25503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 25513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If this guy is point-to-point (ifd->interfaceInfo.McastTxRx == 0 ) we still want to 25533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // register him, but we also want to note that we haven't found a v4 interface 25543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // so that we register loopback so same host operations work 25553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ifd->interfaceInfo.McastTxRx == mDNStrue ) 25573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 25583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin foundv6 = mDNStrue; 25593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 25603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If we're on a platform that doesn't have WSARecvMsg(), there's no way 25623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // of determing the destination address of a packet that is sent to us. 25633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // For multicast packets, that's easy to determine. But for the unicast 25643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // sockets, we'll fake it by taking the address of the first interface 25653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // that is successfully setup. 25663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !foundUnicastSock6DestAddr ) 25683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 25693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock6.addr = ifd->interfaceInfo.ip; 25703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin foundUnicastSock6DestAddr = TRUE; 25713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 25723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *next = ifd; 25743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin next = &ifd->next; 25753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ++inMDNS->p->interfaceCount; 25763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 25773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 25783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If there are no real interfaces, but there is a loopback interface, use that so same-machine operations work. 25803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( !MDNS_WINDOWS_ENABLE_IPV4 && !MDNS_WINDOWS_ENABLE_IPV6 ) 25823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin flagMask |= IFF_LOOPBACK; 25843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin flagTest |= IFF_LOOPBACK; 25853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( p = addrs; p; p = p->ifa_next ) 25873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 25883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( !p->ifa_addr || ( ( p->ifa_flags & flagMask ) != flagTest ) ) 25893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 25903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin continue; 25913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 25923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ( p->ifa_addr->sa_family != AF_INET ) && ( p->ifa_addr->sa_family != AF_INET6 ) ) 25933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 25943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin continue; 25953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 25963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 25973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin v4loopback = p; 25983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 25993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 26003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 26023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !foundv4 && loopbackv4 ) 26043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 26053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "Interface %40s (0x%08X) %##a\n", 26063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin loopbackv4->ifa_name ? loopbackv4->ifa_name : "<null>", loopbackv4->ifa_extra.index, loopbackv4->ifa_addr ); 26073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupInterface( inMDNS, loopbackv4, &ifd ); 26093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 26103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->registeredLoopback4 = mDNStrue; 26123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( MDNS_WINDOWS_ENABLE_IPV4 ) 26143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If we're on a platform that doesn't have WSARecvMsg(), there's no way 26163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // of determing the destination address of a packet that is sent to us. 26173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // For multicast packets, that's easy to determine. But for the unicast 26183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // sockets, we'll fake it by taking the address of the first interface 26193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // that is successfully setup. 26203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !foundUnicastSock4DestAddr ) 26223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 26233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock4.addr = ifd->sock.addr; 26243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin foundUnicastSock4DestAddr = TRUE; 26253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 26263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 26273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *next = ifd; 26293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin next = &ifd->next; 26303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ++inMDNS->p->interfaceCount; 26313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 26323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !foundv6 && loopbackv6 ) 26343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 26353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "Interface %40s (0x%08X) %##a\n", 26363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin loopbackv6->ifa_name ? loopbackv6->ifa_name : "<null>", loopbackv6->ifa_extra.index, loopbackv6->ifa_addr ); 26373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupInterface( inMDNS, loopbackv6, &ifd ); 26393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 26403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( MDNS_WINDOWS_ENABLE_IPV6 ) 26423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If we're on a platform that doesn't have WSARecvMsg(), there's no way 26443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // of determing the destination address of a packet that is sent to us. 26453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // For multicast packets, that's easy to determine. But for the unicast 26463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // sockets, we'll fake it by taking the address of the first interface 26473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // that is successfully setup. 26483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !foundUnicastSock6DestAddr ) 26503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 26513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->unicastSock6.addr = ifd->sock.addr; 26523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin foundUnicastSock6DestAddr = TRUE; 26533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 26543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 26553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *next = ifd; 26573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin next = &ifd->next; 26583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ++inMDNS->p->interfaceCount; 26593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 26603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin CheckFileShares( inMDNS ); 26623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 26643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( err ) 26653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 26663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TearDownInterfaceList( inMDNS ); 26673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 26683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( addrs ) 26693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 26703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin freeifaddrs( addrs ); 26713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 26723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "setting up interface list done (err=%d %m)\n", err, err ); 26733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 26743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 26753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 26773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// TearDownInterfaceList 26783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 26793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmStatus TearDownInterfaceList( mDNS * const inMDNS ) 26813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 26823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceData ** p; 26833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceData * ifd; 26843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "tearing down interface list\n" ); 26863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 26873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS->p ); 26883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Free any interfaces that were previously marked inactive and are no longer referenced by the mDNS cache. 26903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Interfaces are marked inactive, but not deleted immediately if they were still referenced by the mDNS cache 26913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // so that remove events that occur after an interface goes away can still report the correct interface. 26923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 26933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p = &inMDNS->p->inactiveInterfaceList; 26943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while( *p ) 26953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 26963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd = *p; 26973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( NumCacheRecordsForInterfaceID( inMDNS, (mDNSInterfaceID) ifd ) > 0 ) 26983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 26993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p = &ifd->next; 27003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin continue; 27013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 27023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "freeing unreferenced, inactive interface %#p %#a\n", ifd, &ifd->interfaceInfo.ip ); 27043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *p = ifd->next; 27053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin QueueUserAPC( ( PAPCFUNC ) FreeInterface, inMDNS->p->mainThread, ( ULONG_PTR ) ifd ); 27073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 27083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Tear down all the interfaces. 27103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while( inMDNS->p->interfaceList ) 27123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 27133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd = inMDNS->p->interfaceList; 27143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->interfaceList = ifd->next; 27153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TearDownInterface( inMDNS, ifd ); 27173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 27183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->interfaceCount = 0; 27193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "tearing down interface list done\n" ); 27213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( mStatus_NoError ); 27223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 27233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 27253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetupInterface 27263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 27273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SetupInterface( mDNS * const inMDNS, const struct ifaddrs *inIFA, mDNSInterfaceData **outIFD ) 27293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 27303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceData * ifd; 27313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceData * p; 27323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 27333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd = NULL; 27353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "setting up interface\n" ); 27363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 27373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS->p ); 27383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inIFA ); 27393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inIFA->ifa_addr ); 27403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( outIFD ); 27413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Allocate memory for the interface and initialize it. 27433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd = (mDNSInterfaceData *) calloc( 1, sizeof( *ifd ) ); 27453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( ifd, exit, err = mStatus_NoMemoryErr ); 27463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->sock.fd = kInvalidSocketRef; 27473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->sock.overlapped.pending = FALSE; 27483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->sock.ifd = ifd; 27493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->sock.next = NULL; 27503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->sock.m = inMDNS; 27513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->index = inIFA->ifa_extra.index; 27523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->scopeID = inIFA->ifa_extra.index; 27533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( strlen( inIFA->ifa_name ) < sizeof( ifd->name ) ); 27543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin strncpy( ifd->name, inIFA->ifa_name, sizeof( ifd->name ) - 1 ); 27553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->name[ sizeof( ifd->name ) - 1 ] = '\0'; 27563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin strncpy(ifd->interfaceInfo.ifname, inIFA->ifa_name, sizeof(ifd->interfaceInfo.ifname)); 27583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->interfaceInfo.ifname[sizeof(ifd->interfaceInfo.ifname)-1] = 0; 27593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // We always send and receive using IPv4, but to reduce traffic, we send and receive using IPv6 only on interfaces 27613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // that have no routable IPv4 address. Having a routable IPv4 address assigned is a reasonable indicator of being 27623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // on a large configured network, which means there's a good chance that most or all the other devices on that 27633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // network should also have v4. By doing this we lose the ability to talk to true v6-only devices on that link, 27643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // but we cut the packet rate in half. At this time, reducing the packet rate is more important than v6-only 27653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // devices on a large configured network, so we are willing to make that sacrifice. 27663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->interfaceInfo.McastTxRx = ( ( inIFA->ifa_flags & IFF_MULTICAST ) && !( inIFA->ifa_flags & IFF_POINTTOPOINT ) ) ? mDNStrue : mDNSfalse; 27683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->interfaceInfo.InterfaceID = NULL; 27693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( p = inMDNS->p->interfaceList; p; p = p->next ) 27713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 27723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( strcmp( p->name, ifd->name ) == 0 ) 27733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 27743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (!ifd->interfaceInfo.InterfaceID) 27753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 27763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->interfaceInfo.InterfaceID = (mDNSInterfaceID) p; 27773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 27783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ( inIFA->ifa_addr->sa_family != AF_INET ) && 27803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( p->interfaceInfo.ip.type == mDNSAddrType_IPv4 ) && 27813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( p->interfaceInfo.ip.ip.v4.b[ 0 ] != 169 || p->interfaceInfo.ip.ip.v4.b[ 1 ] != 254 ) ) 27823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 27833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->interfaceInfo.McastTxRx = mDNSfalse; 27843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 27853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 27873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 27883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 27893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !ifd->interfaceInfo.InterfaceID ) 27913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 27923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->interfaceInfo.InterfaceID = (mDNSInterfaceID) ifd; 27933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 27943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set up a socket for this interface (if needed). 27963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 27973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ifd->interfaceInfo.McastTxRx ) 27983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 27993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD size; 28003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupSocket( inMDNS, inIFA->ifa_addr, MulticastDNSPort, &ifd->sock.fd ); 28023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 28033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->sock.addr = ( inIFA->ifa_addr->sa_family == AF_INET6 ) ? AllDNSLinkGroup_v6 : AllDNSLinkGroup_v4; 28043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->sock.port = MulticastDNSPort; 28053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get a ptr to the WSARecvMsg function, if supported. Otherwise, we'll fallback to recvfrom. 28073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = WSAIoctl( ifd->sock.fd, SIO_GET_EXTENSION_FUNCTION_POINTER, &kWSARecvMsgGUID, sizeof( kWSARecvMsgGUID ), &ifd->sock.recvMsgPtr, sizeof( ifd->sock.recvMsgPtr ), &size, NULL, NULL ); 28093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err ) 28113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 28123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->sock.recvMsgPtr = NULL; 28133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 28143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 28153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( inIFA->ifa_dhcpEnabled && ( inIFA->ifa_dhcpLeaseExpires < inMDNS->p->nextDHCPLeaseExpires ) ) 28173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 28183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->nextDHCPLeaseExpires = inIFA->ifa_dhcpLeaseExpires; 28193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 28203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->interfaceInfo.NetWake = inIFA->ifa_womp; 28223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Register this interface with mDNS. 28243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SockAddrToMDNSAddr( inIFA->ifa_addr, &ifd->interfaceInfo.ip, NULL ); 28263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 28273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SockAddrToMDNSAddr( inIFA->ifa_netmask, &ifd->interfaceInfo.mask, NULL ); 28293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 28303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy( ifd->interfaceInfo.MAC.b, inIFA->ifa_physaddr, sizeof( ifd->interfaceInfo.MAC.b ) ); 28323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->interfaceInfo.Advertise = ( mDNSu8 ) inMDNS->AdvertiseLocalAddresses; 28343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ifd->sock.fd != kInvalidSocketRef ) 28363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 28373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = UDPBeginRecv( &ifd->sock ); 28383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 28393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 28403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = mDNS_RegisterInterface( inMDNS, &ifd->interfaceInfo, mDNSfalse ); 28423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 28433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd->hostRegistered = mDNStrue; 28443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "Registered interface %##a with mDNS\n", inIFA->ifa_addr ); 28463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Success! 28483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *outIFD = ifd; 28503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifd = NULL; 28513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 28533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ifd ) 28553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 28563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TearDownInterface( inMDNS, ifd ); 28573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 28583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "setting up interface done (err=%d %m)\n", err, err ); 28593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 28603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 28613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 28633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// TearDownInterface 28643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 28653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus TearDownInterface( mDNS * const inMDNS, mDNSInterfaceData *inIFD ) 28673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 28683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 28693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inIFD ); 28703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Deregister this interface with mDNS. 28723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "Deregistering interface %#a with mDNS\n", &inIFD->interfaceInfo.ip ); 28743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( inIFD->hostRegistered ) 28763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 28773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inIFD->hostRegistered = mDNSfalse; 28783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNS_DeregisterInterface( inMDNS, &inIFD->interfaceInfo, mDNSfalse ); 28793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 28803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Tear down the multicast socket. 28823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin UDPCloseSocket( &inIFD->sock ); 28843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If the interface is still referenced by items in the mDNS cache then put it on the inactive list. This keeps 28863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // the InterfaceID valid so remove events report the correct interface. If it is no longer referenced, free it. 28873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 28883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( NumCacheRecordsForInterfaceID( inMDNS, (mDNSInterfaceID) inIFD ) > 0 ) 28893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 28903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inIFD->next = inMDNS->p->inactiveInterfaceList; 28913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inMDNS->p->inactiveInterfaceList = inIFD; 28923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "deferring free of interface %#p %#a\n", inIFD, &inIFD->interfaceInfo.ip ); 28933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 28943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 28953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 28963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "freeing interface %#p %#a immediately\n", inIFD, &inIFD->interfaceInfo.ip ); 28973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin QueueUserAPC( ( PAPCFUNC ) FreeInterface, inMDNS->p->mainThread, ( ULONG_PTR ) inIFD ); 28983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 28993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( mStatus_NoError ); 29013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 29023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void CALLBACK FreeInterface( mDNSInterfaceData *inIFD ) 29043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 29053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( inIFD ); 29063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 29073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 29093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetupSocket 29103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 29113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SetupSocket( mDNS * const inMDNS, const struct sockaddr *inAddr, mDNSIPPort port, SocketRef *outSocketRef ) 29133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 29143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 29153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SocketRef sock; 29163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int option; 29173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD bytesReturned = 0; 29183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin BOOL behavior = FALSE; 29193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( inMDNS ); 29213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "setting up socket %##a\n", inAddr ); 29233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 29243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( outSocketRef ); 29253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set up an IPv4 or IPv6 UDP socket. 29273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = socket( inAddr->sa_family, SOCK_DGRAM, IPPROTO_UDP ); 29293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( IsValidSocket( sock ), errno_compat(), kUnknownErr ); 29303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 29313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Turn on reuse address option so multiple servers can listen for Multicast DNS packets, 29333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // if we're creating a multicast socket 29343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( port.NotAnInteger ) 29363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 29373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin option = 1; 29383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, SOL_SOCKET, SO_REUSEADDR, (char *) &option, sizeof( option ) ); 29393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 29403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 29413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // <rdar://problem/7894393> Bonjour for Windows broken on Windows XP 29433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // 29443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Not sure why, but the default behavior for sockets is to behave incorrectly 29453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // when using them in Overlapped I/O mode on XP. According to MSDN: 29463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // 29473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // SIO_UDP_CONNRESET (opcode setting: I, T==3) 29483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Windows XP: Controls whether UDP PORT_UNREACHABLE messages are reported. Set to TRUE to enable reporting. 29493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Set to FALSE to disable reporting. 29503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // 29513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Packet traces from misbehaving Bonjour installations showed that ICMP port unreachable 29523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // messages were being sent to us after we sent out packets to a multicast address. This is clearly 29533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // incorrect behavior, but should be harmless. However, after receiving a port unreachable error, WinSock 29543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // will no longer receive any packets from that socket, which is not harmless. This behavior is only 29553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // seen on XP. 29563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // 29573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // So we turn off port unreachable reporting to make sure our sockets that are reading 29583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // multicast packets function correctly under all circumstances. 29593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = WSAIoctl( sock, SIO_UDP_CONNRESET, &behavior, sizeof(behavior), NULL, 0, &bytesReturned, NULL, NULL ); 29613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 29623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( inAddr->sa_family == AF_INET ) 29643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 29653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSv4Addr ipv4; 29663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in sa4; 29673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ip_mreq mreqv4; 29683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Bind the socket to the desired port 29703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ipv4.NotAnInteger = ( (const struct sockaddr_in *) inAddr )->sin_addr.s_addr; 29723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSPlatformMemZero( &sa4, sizeof( sa4 ) ); 29733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4.sin_family = AF_INET; 29743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4.sin_port = port.NotAnInteger; 29753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4.sin_addr.s_addr = ipv4.NotAnInteger; 29763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = bind( sock, (struct sockaddr *) &sa4, sizeof( sa4 ) ); 29783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kUnknownErr ); 29793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Turn on option to receive destination addresses and receiving interface. 29813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin option = 1; 29833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IP, IP_PKTINFO, (char *) &option, sizeof( option ) ); 29843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 29853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (port.NotAnInteger) 29873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 29883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Join the all-DNS multicast group so we receive Multicast DNS packets 29893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mreqv4.imr_multiaddr.s_addr = AllDNSLinkGroup_v4.ip.v4.NotAnInteger; 29913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mreqv4.imr_interface.s_addr = ipv4.NotAnInteger; 29923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IP, IP_ADD_MEMBERSHIP, (char *) &mreqv4, sizeof( mreqv4 ) ); 29933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 29943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Specify the interface to send multicast packets on this socket. 29963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 29973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4.sin_addr.s_addr = ipv4.NotAnInteger; 29983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IP, IP_MULTICAST_IF, (char *) &sa4.sin_addr, sizeof( sa4.sin_addr ) ); 29993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 30003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Enable multicast loopback so we receive multicast packets we send (for same-machine operations). 30023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin option = 1; 30043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IP, IP_MULTICAST_LOOP, (char *) &option, sizeof( option ) ); 30053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 30063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 30073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Send unicast packets with TTL 255 (helps against spoofing). 30093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin option = 255; 30113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IP, IP_TTL, (char *) &option, sizeof( option ) ); 30123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 30133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Send multicast packets with TTL 255 (helps against spoofing). 30153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin option = 255; 30173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IP, IP_MULTICAST_TTL, (char *) &option, sizeof( option ) ); 30183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 30193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 30213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( inAddr->sa_family == AF_INET6 ) 30223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 30233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in6 * sa6p; 30243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in6 sa6; 30253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ipv6_mreq mreqv6; 30263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6p = (struct sockaddr_in6 *) inAddr; 30283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Bind the socket to the desired port 30303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSPlatformMemZero( &sa6, sizeof( sa6 ) ); 30323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6.sin6_family = AF_INET6; 30333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6.sin6_port = port.NotAnInteger; 30343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6.sin6_flowinfo = 0; 30353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6.sin6_addr = sa6p->sin6_addr; 30363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6.sin6_scope_id = sa6p->sin6_scope_id; 30373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = bind( sock, (struct sockaddr *) &sa6, sizeof( sa6 ) ); 30393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kUnknownErr ); 30403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Turn on option to receive destination addresses and receiving interface. 30423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin option = 1; 30443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IPV6, IPV6_PKTINFO, (char *) &option, sizeof( option ) ); 30453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 30463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // We only want to receive IPv6 packets (not IPv4-mapped IPv6 addresses) because we have a separate socket 30483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // for IPv4, but the IPv6 stack in Windows currently doesn't support IPv4-mapped IPv6 addresses and doesn't 30493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // support the IPV6_V6ONLY socket option so the following code would typically not be executed (or needed). 30503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin #if( defined( IPV6_V6ONLY ) ) 30523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin option = 1; 30533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IPV6, IPV6_V6ONLY, (char *) &option, sizeof( option ) ); 30543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 30553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin #endif 30563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( port.NotAnInteger ) 30583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 30593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Join the all-DNS multicast group so we receive Multicast DNS packets. 30603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mreqv6.ipv6mr_multiaddr = *( (struct in6_addr *) &AllDNSLinkGroup_v6.ip.v6 ); 30623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mreqv6.ipv6mr_interface = sa6p->sin6_scope_id; 30633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IPV6, IPV6_JOIN_GROUP, (char *) &mreqv6, sizeof( mreqv6 ) ); 30643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 30653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Specify the interface to send multicast packets on this socket. 30673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin option = (int) sa6p->sin6_scope_id; 30693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IPV6, IPV6_MULTICAST_IF, (char *) &option, sizeof( option ) ); 30703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 30713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Enable multicast loopback so we receive multicast packets we send (for same-machine operations). 30733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin option = 1; 30753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IPV6, IPV6_MULTICAST_LOOP, (char *) &option, sizeof( option ) ); 30763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 30773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 30783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Send unicast packets with TTL 255 (helps against spoofing). 30803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin option = 255; 30823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IPV6, IPV6_UNICAST_HOPS, (char *) &option, sizeof( option ) ); 30833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 30843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Send multicast packets with TTL 255 (helps against spoofing). 30863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin option = 255; 30883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = setsockopt( sock, IPPROTO_IPV6, IPV6_MULTICAST_HOPS, (char *) &option, sizeof( option ) ); 30893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( err == 0, errno_compat(), kOptionErr ); 30903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 30913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 30923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 30933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelError, DEBUG_NAME "%s: unsupport socket family (%d)\n", __ROUTINE__, inAddr->sa_family ); 30943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = kUnsupportedErr; 30953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin goto exit; 30963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 30973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 30983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Success! 30993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *outSocketRef = sock; 31013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = kInvalidSocketRef; 31023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = mStatus_NoError; 31033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 31053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( IsValidSocket( sock ) ) 31063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 31073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin close_compat( sock ); 31083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 31093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 31103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 31113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 31133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetupSocket 31143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 31153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SockAddrToMDNSAddr( const struct sockaddr * const inSA, mDNSAddr *outIP, mDNSIPPort *outPort ) 31173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 31183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 31193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inSA ); 31213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( outIP ); 31223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( inSA->sa_family == AF_INET ) 31243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 31253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in * sa4; 31263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4 = (struct sockaddr_in *) inSA; 31283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin outIP->type = mDNSAddrType_IPv4; 31293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin outIP->ip.v4.NotAnInteger = sa4->sin_addr.s_addr; 31303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( outPort ) 31313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 31323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin outPort->NotAnInteger = sa4->sin_port; 31333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 31343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = mStatus_NoError; 31353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 31363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( inSA->sa_family == AF_INET6 ) 31373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 31383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in6 * sa6; 31393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6 = (struct sockaddr_in6 *) inSA; 31413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin outIP->type = mDNSAddrType_IPv6; 31423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin outIP->ip.v6 = *( (mDNSv6Addr *) &sa6->sin6_addr ); 31433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( IN6_IS_ADDR_LINKLOCAL( &sa6->sin6_addr ) ) 31443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 31453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin outIP->ip.v6.w[ 1 ] = 0; 31463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 31473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( outPort ) 31483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 31493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin outPort->NotAnInteger = sa6->sin6_port; 31503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 31513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = mStatus_NoError; 31523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 31533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 31543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 31553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelError, DEBUG_NAME "%s: invalid sa_family %d", __ROUTINE__, inSA->sa_family ); 31563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = mStatus_BadParamErr; 31573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 31583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 31593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 31603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if 0 31633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#pragma mark - 31643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 31653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 31673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// UDPBeginRecv 31683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 31693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal OSStatus UDPBeginRecv( UDPSocket * sock ) 31713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 31723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD size; 31733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD numTries; 31743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 31753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "%s: sock = %d\n", __ROUTINE__, sock->fd ); 31773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( sock != NULL, exit, err = mStatus_BadStateErr ); 31793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( !sock->overlapped.pending ); 31803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Initialize the buffer structure 31823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.wbuf.buf = (char *) &sock->packet; 31843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.wbuf.len = (u_long) sizeof( sock->packet ); 31853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->srcAddrLen = sizeof( sock->srcAddr ); 31863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Initialize the overlapped structure 31883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ZeroMemory( &sock->overlapped.data, sizeof( OVERLAPPED ) ); 31903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.data.hEvent = sock; 31913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin numTries = 0; 31933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 31943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin do 31953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 31963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->recvMsgPtr ) 31973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 31983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->wmsg.name = ( LPSOCKADDR ) &sock->srcAddr; 31993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->wmsg.namelen = sock->srcAddrLen; 32003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->wmsg.lpBuffers = &sock->overlapped.wbuf; 32013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->wmsg.dwBufferCount = 1; 32023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->wmsg.Control.buf = ( CHAR* ) sock->controlBuffer; 32033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->wmsg.Control.len = sizeof( sock->controlBuffer ); 32043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->wmsg.dwFlags = 0; 32053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = sock->recvMsgPtr( sock->fd, &sock->wmsg, &size, &sock->overlapped.data, ( LPWSAOVERLAPPED_COMPLETION_ROUTINE ) UDPEndRecv ); 32073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( ( err == 0 ) || ( WSAGetLastError() == WSA_IO_PENDING ), (OSStatus) WSAGetLastError(), kUnknownErr ); 32083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // <rdar://problem/7824093> iTunes 9.1 fails to install with Bonjour service on Windows 7 Ultimate 32103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // 32113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // There seems to be a bug in some network device drivers that involves calling WSARecvMsg() in 32123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // overlapped i/o mode. Although all the parameters to WSARecvMsg() are correct, it returns a 32133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // WSAEFAULT error code when there is no actual error. We have found experientially that falling 32143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // back to using WSARecvFrom() when this happens will work correctly. 32153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err == WSAEFAULT ) sock->recvMsgPtr = NULL; 32173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 32183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 32193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 32203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD flags = 0; 32213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = WSARecvFrom( sock->fd, &sock->overlapped.wbuf, 1, NULL, &flags, ( LPSOCKADDR ) &sock->srcAddr, &sock->srcAddrLen, &sock->overlapped.data, ( LPWSAOVERLAPPED_COMPLETION_ROUTINE ) UDPEndRecv ); 32233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( ( err == 0 ) || ( WSAGetLastError() == WSA_IO_PENDING ), ( OSStatus ) WSAGetLastError(), kUnknownErr ); 32243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 32253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // According to MSDN <http://msdn.microsoft.com/en-us/library/ms741687(VS.85).aspx>: 32273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // 32283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // "WSAECONNRESET: For a UDP datagram socket, this error would indicate that a previous 32293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // send operation resulted in an ICMP "Port Unreachable" message." 32303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // 32313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Because this is the case, we want to ignore this error and try again. Just in case 32323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // this is some kind of pathological condition, we'll break out of the retry loop 32333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // after 100 iterations 32343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( !err || ( err == WSAECONNRESET ) || ( err == WSAEFAULT ), exit, err = WSAGetLastError() ); 32363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 32373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while ( ( ( err == WSAECONNRESET ) || ( err == WSAEFAULT ) ) && ( numTries++ < 100 ) ); 32383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.pending = TRUE; 32403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 32423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err ) 32443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 32453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LogMsg( "WSARecvMsg failed (%d)\n", err ); 32463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 32473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return err; 32493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 32503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 32533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// UDPEndRecv 32543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 32553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void CALLBACK UDPEndRecv( DWORD err, DWORD bytesTransferred, LPWSAOVERLAPPED overlapped, DWORD flags ) 32573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 32583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin UDPSocket * sock = NULL; 32593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( void ) flags; 32613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "%s: err = %d, bytesTransferred = %d\n", __ROUTINE__, err, bytesTransferred ); 32633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action_quiet( err != WSA_OPERATION_ABORTED, exit, err = ( DWORD ) kUnknownErr ); 32643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 32653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = ( overlapped != NULL ) ? overlapped->hEvent : NULL; 32663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( sock != NULL, exit, err = ( DWORD ) kUnknownErr ); 32673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "%s: sock = %d\n", __ROUTINE__, sock->fd ); 32683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.error = err; 32693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.bytesTransferred = bytesTransferred; 32703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( sock->overlapped.pending ); 32713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.pending = FALSE; 32723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Translate the source of this packet into mDNS data types 32743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SockAddrToMDNSAddr( (struct sockaddr *) &sock->srcAddr, &sock->overlapped.srcAddr, &sock->overlapped.srcPort ); 32763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Initialize the destination of this packet. Just in case 32783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // we can't determine this info because we couldn't call 32793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // WSARecvMsg (recvMsgPtr) 32803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.dstAddr = sock->addr; 32823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.dstPort = sock->port; 32833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->recvMsgPtr ) 32853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 32863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LPWSACMSGHDR header; 32873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LPWSACMSGHDR last = NULL; 32883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int count = 0; 32893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Parse the control information. Reject packets received on the wrong interface. 32913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 32923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // <rdar://problem/7832196> INSTALL: Bonjour 2.0 on Windows can not start / stop 32933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // 32943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // There seems to be an interaction between Bullguard and this next bit of code. 32953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // When a user's machine is running Bullguard, the control information that is 32963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // returned is corrupted, and the code would go into an infinite loop. We'll add 32973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // two bits of defensive coding here. The first will check that each pointer to 32983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // the LPWSACMSGHDR that is returned in the for loop is different than the last. 32993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // This fixes the problem with Bullguard. The second will break out of this loop 33003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // after 100 iterations, just in case the corruption isn't caught by the first 33013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // check. 33023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( header = WSA_CMSG_FIRSTHDR( &sock->wmsg ); header; header = WSA_CMSG_NXTHDR( &sock->wmsg, header ) ) 33043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 33053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ( header != last ) && ( ++count < 100 ) ) 33063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 33073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin last = header; 33083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ( header->cmsg_level == IPPROTO_IP ) && ( header->cmsg_type == IP_PKTINFO ) ) 33103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 33113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IN_PKTINFO * ipv4PacketInfo; 33123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ipv4PacketInfo = (IN_PKTINFO *) WSA_CMSG_DATA( header ); 33143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->ifd != NULL ) 33163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 33173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( ipv4PacketInfo->ipi_ifindex == sock->ifd->index, exit, err = ( DWORD ) kMismatchErr ); 33183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 33193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.dstAddr.type = mDNSAddrType_IPv4; 33213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.dstAddr.ip.v4.NotAnInteger = ipv4PacketInfo->ipi_addr.s_addr; 33223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 33233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( ( header->cmsg_level == IPPROTO_IPV6 ) && ( header->cmsg_type == IPV6_PKTINFO ) ) 33243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 33253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IN6_PKTINFO * ipv6PacketInfo; 33263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ipv6PacketInfo = (IN6_PKTINFO *) WSA_CMSG_DATA( header ); 33283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->ifd != NULL ) 33303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 33313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( ipv6PacketInfo->ipi6_ifindex == ( sock->ifd->index - kIPv6IfIndexBase ), exit, err = ( DWORD ) kMismatchErr ); 33323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 33333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.dstAddr.type = mDNSAddrType_IPv6; 33353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->overlapped.dstAddr.ip.v6 = *( (mDNSv6Addr *) &ipv6PacketInfo->ipi6_addr ); 33363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 33373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 33383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 33393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 33403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin static BOOL loggedMessage = FALSE; 33413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !loggedMessage ) 33433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 33443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LogMsg( "UDPEndRecv: WSARecvMsg control information error." ); 33453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin loggedMessage = TRUE; 33463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 33473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 33493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 33503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 33513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 33523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "packet received\n" ); 33543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME " size = %d\n", bytesTransferred ); 33553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME " src = %#a:%u\n", &sock->overlapped.srcAddr, ntohs( sock->overlapped.srcPort.NotAnInteger ) ); 33563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME " dst = %#a:%u\n", &sock->overlapped.dstAddr, ntohs( sock->overlapped.dstPort.NotAnInteger ) ); 33573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->ifd != NULL ) 33593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 33603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME " interface = %#a (index=0x%08X)\n", &sock->ifd->interfaceInfo.ip, sock->ifd->index ); 33613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 33623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "\n" ); 33643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Queue this socket 33663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin AddToTail( &gUDPDispatchableSockets, sock ); 33683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 33703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return; 33723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 33733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 33763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// InterfaceListDidChange 33773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 33783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinvoid InterfaceListDidChange( mDNS * const inMDNS ) 33793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 33803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 33813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "interface list changed\n" ); 33833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 33843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Tear down the existing interfaces and set up new ones using the new IP info. 33863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = TearDownInterfaceList( inMDNS ); 33883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 33893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupInterfaceList( inMDNS ); 33913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 33923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = uDNS_SetupDNSConfig( inMDNS ); 33943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 33953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Inform clients of the change. 33973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 33983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNS_ConfigChanged(inMDNS); 33993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Force mDNS to update. 34013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSCoreMachineSleep( inMDNS, mDNSfalse ); // What is this for? Mac OS X does not do this 34033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 34043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 34073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// ComputerDescriptionDidChange 34083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 34093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinvoid ComputerDescriptionDidChange( mDNS * const inMDNS ) 34103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 34113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "computer description has changed\n" ); 34123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 34133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // redo the names 34153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SetupNiceName( inMDNS ); 34163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 34173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 34203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// TCPIPConfigDidChange 34213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 34223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinvoid TCPIPConfigDidChange( mDNS * const inMDNS ) 34233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 34243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 34253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "TCP/IP config has changed\n" ); 34273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 34283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = uDNS_SetupDNSConfig( inMDNS ); 34303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 34313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 34323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 34353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// DynDNSConfigDidChange 34363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 34373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinvoid DynDNSConfigDidChange( mDNS * const inMDNS ) 34383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 34393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 34403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "DynDNS config has changed\n" ); 34423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 34433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SetDomainSecrets( inMDNS ); 34453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = uDNS_SetupDNSConfig( inMDNS ); 34473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 34483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 34493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 34523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// FileSharingDidChange 34533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 34543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinvoid FileSharingDidChange( mDNS * const inMDNS ) 34553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 34563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "File shares has changed\n" ); 34573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 34583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin CheckFileShares( inMDNS ); 34603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 34613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 34643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// FilewallDidChange 34653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 34663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinvoid FirewallDidChange( mDNS * const inMDNS ) 34673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 34683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "Firewall has changed\n" ); 34693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( inMDNS ); 34703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin CheckFileShares( inMDNS ); 34723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 34733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if 0 34763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#pragma mark - 34773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#pragma mark == Utilities == 34783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 34793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 34813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// getifaddrs 34823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 34833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal int getifaddrs( struct ifaddrs **outAddrs ) 34853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 34863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int err; 34873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( MDNS_WINDOWS_USE_IPV6_IF_ADDRS ) 34893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Try to the load the GetAdaptersAddresses function from the IP Helpers DLL. This API is only available on Windows 34913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // XP or later. Looking up the symbol at runtime allows the code to still work on older systems without that API. 34923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 34933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( !gIPHelperLibraryInstance ) 34943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 34953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gIPHelperLibraryInstance = LoadLibrary( TEXT( "Iphlpapi" ) ); 34963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( gIPHelperLibraryInstance ) 34973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 34983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gGetAdaptersAddressesFunctionPtr = 34993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin (GetAdaptersAddressesFunctionPtr) GetProcAddress( gIPHelperLibraryInstance, "GetAdaptersAddresses" ); 35003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( !gGetAdaptersAddressesFunctionPtr ) 35013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 35023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin BOOL ok; 35033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ok = FreeLibrary( gIPHelperLibraryInstance ); 35053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( ok, GetLastError(), kUnknownErr ); 35063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gIPHelperLibraryInstance = NULL; 35073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 35083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 35093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 35103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Use the new IPv6-capable routine if supported. Otherwise, fall back to the old and compatible IPv4-only code. 35123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // <rdar://problem/4278934> Fall back to using getifaddrs_ipv4 if getifaddrs_ipv6 fails 35133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // <rdar://problem/6145913> Fall back to using getifaddrs_ipv4 if getifaddrs_ipv6 returns no addrs 35143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( !gGetAdaptersAddressesFunctionPtr || ( ( ( err = getifaddrs_ipv6( outAddrs ) ) != mStatus_NoError ) || ( ( outAddrs != NULL ) && ( *outAddrs == NULL ) ) ) ) 35163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 35173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = getifaddrs_ipv4( outAddrs ); 35183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 35193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 35203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#else 35223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = getifaddrs_ipv4( outAddrs ); 35243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 35253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 35273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 35293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 35303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 35313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( MDNS_WINDOWS_USE_IPV6_IF_ADDRS ) 35333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 35343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// getifaddrs_ipv6 35353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 35363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal int getifaddrs_ipv6( struct ifaddrs **outAddrs ) 35383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 35393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD err; 35403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int i; 35413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD flags; 35423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * head; 35433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs ** next; 35443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IP_ADAPTER_ADDRESSES * iaaList; 35453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ULONG iaaListSize; 35463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IP_ADAPTER_ADDRESSES * iaa; 35473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin size_t size; 35483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * ifa; 35493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( gGetAdaptersAddressesFunctionPtr ); 35513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin head = NULL; 35533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin next = &head; 35543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin iaaList = NULL; 35553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get the list of interfaces. The first call gets the size and the second call gets the actual data. 35573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // This loops to handle the case where the interface changes in the window after getting the size, but before the 35583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // second call completes. A limit of 100 retries is enforced to prevent infinite loops if something else is wrong. 35593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin flags = GAA_FLAG_INCLUDE_PREFIX | GAA_FLAG_SKIP_ANYCAST | GAA_FLAG_SKIP_MULTICAST | GAA_FLAG_SKIP_DNS_SERVER | GAA_FLAG_SKIP_FRIENDLY_NAME; 35613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin i = 0; 35623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( ;; ) 35633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 35643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin iaaListSize = 0; 35653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = gGetAdaptersAddressesFunctionPtr( AF_UNSPEC, flags, NULL, NULL, &iaaListSize ); 35663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( err == ERROR_BUFFER_OVERFLOW ); 35673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( iaaListSize >= sizeof( IP_ADAPTER_ADDRESSES ) ); 35683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin iaaList = (IP_ADAPTER_ADDRESSES *) malloc( iaaListSize ); 35703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( iaaList, exit, err = ERROR_NOT_ENOUGH_MEMORY ); 35713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = gGetAdaptersAddressesFunctionPtr( AF_UNSPEC, flags, NULL, iaaList, &iaaListSize ); 35733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( err == ERROR_SUCCESS ) break; 35743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( iaaList ); 35763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin iaaList = NULL; 35773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ++i; 35783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require( i < 100, exit ); 35793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelWarning, "%s: retrying GetAdaptersAddresses after %d failure(s) (%d %m)\n", __ROUTINE__, i, err, err ); 35803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 35813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( iaa = iaaList; iaa; iaa = iaa->Next ) 35833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 35843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int addrIndex; 35853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IP_ADAPTER_UNICAST_ADDRESS * addr; 35863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD ipv6IfIndex; 35873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IP_ADAPTER_PREFIX * firstPrefix; 35883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( iaa->IfIndex > 0xFFFFFF ) 35903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 35913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelAlert, DEBUG_NAME "%s: IPv4 ifindex out-of-range (0x%08X)\n", __ROUTINE__, iaa->IfIndex ); 35923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 35933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( iaa->Ipv6IfIndex > 0xFF ) 35943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 35953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelAlert, DEBUG_NAME "%s: IPv6 ifindex out-of-range (0x%08X)\n", __ROUTINE__, iaa->Ipv6IfIndex ); 35963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 35973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 35983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // For IPv4 interfaces, there seems to be a bug in iphlpapi.dll that causes the 35993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // following code to crash when iterating through the prefix list. This seems 36003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // to occur when iaa->Ipv6IfIndex != 0 when IPv6 is not installed on the host. 36013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // This shouldn't happen according to Microsoft docs which states: 36023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // 36033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // "Ipv6IfIndex contains 0 if IPv6 is not available on the interface." 36043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // 36053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // So the data structure seems to be corrupted when we return from 36063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // GetAdaptersAddresses(). The bug seems to occur when iaa->Length < 36073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // sizeof(IP_ADAPTER_ADDRESSES), so when that happens, we'll manually 36083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // modify iaa to have the correct values. 36093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( iaa->Length >= sizeof( IP_ADAPTER_ADDRESSES ) ) 36113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 36123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ipv6IfIndex = iaa->Ipv6IfIndex; 36133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin firstPrefix = iaa->FirstPrefix; 36143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 36153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 36163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 36173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ipv6IfIndex = 0; 36183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin firstPrefix = NULL; 36193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 36203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Skip pseudo and tunnel interfaces. 36223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ( ( ipv6IfIndex == 1 ) && ( iaa->IfType != IF_TYPE_SOFTWARE_LOOPBACK ) ) || ( iaa->IfType == IF_TYPE_TUNNEL ) ) 36243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 36253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin continue; 36263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 36273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Add each address as a separate interface to emulate the way getifaddrs works. 36293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( addrIndex = 0, addr = iaa->FirstUnicastAddress; addr; ++addrIndex, addr = addr->Next ) 36313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 36323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int family; 36333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int prefixIndex; 36343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin IP_ADAPTER_PREFIX * prefix; 36353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ULONG prefixLength; 36363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin uint32_t ipv4Index; 36373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in ipv4Netmask; 36383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin family = addr->Address.lpSockaddr->sa_family; 36403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ( family != AF_INET ) && ( family != AF_INET6 ) ) continue; 36413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // <rdar://problem/6220642> iTunes 8: Bonjour doesn't work after upgrading iTunes 8 36433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Seems as if the problem here is a buggy implementation of some network interface 36443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // driver. It is reporting that is has a link-local address when it is actually 36453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // disconnected. This was causing a problem in AddressToIndexAndMask. 36463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // The solution is to call AddressToIndexAndMask first, and if unable to lookup 36473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // the address, to ignore that address. 36483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ipv4Index = 0; 36503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memset( &ipv4Netmask, 0, sizeof( ipv4Netmask ) ); 36513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( family == AF_INET ) 36533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 36543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = AddressToIndexAndMask( addr->Address.lpSockaddr, &ipv4Index, ( struct sockaddr* ) &ipv4Netmask ); 36553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err ) 36573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 36583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = 0; 36593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin continue; 36603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 36613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 36623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa = (struct ifaddrs *) calloc( 1, sizeof( struct ifaddrs ) ); 36643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( ifa, exit, err = WSAENOBUFS ); 36653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *next = ifa; 36673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin next = &ifa->ifa_next; 36683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get the name. 36703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin size = strlen( iaa->AdapterName ) + 1; 36723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_name = (char *) malloc( size ); 36733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( ifa->ifa_name, exit, err = WSAENOBUFS ); 36743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy( ifa->ifa_name, iaa->AdapterName, size ); 36753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get interface flags. 36773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_flags = 0; 36793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( iaa->OperStatus == IfOperStatusUp ) ifa->ifa_flags |= IFF_UP; 36803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( iaa->IfType == IF_TYPE_SOFTWARE_LOOPBACK ) ifa->ifa_flags |= IFF_LOOPBACK; 36813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if ( IsPointToPoint( addr ) ) ifa->ifa_flags |= IFF_POINTTOPOINT; 36823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( !( iaa->Flags & IP_ADAPTER_NO_MULTICAST ) ) ifa->ifa_flags |= IFF_MULTICAST; 36833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // <rdar://problem/4045657> Interface index being returned is 512 36863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // 36873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Windows does not have a uniform scheme for IPv4 and IPv6 interface indexes. 36883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // This code used to shift the IPv4 index up to ensure uniqueness between 36893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // it and IPv6 indexes. Although this worked, it was somewhat confusing to developers, who 36903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // then see interface indexes passed back that don't correspond to anything 36913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // that is seen in Win32 APIs or command line tools like "route". As a relatively 36923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // small percentage of developers are actively using IPv6, it seems to 36933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // make sense to make our use of IPv4 as confusion free as possible. 36943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // So now, IPv6 interface indexes will be shifted up by a 36953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // constant value which will serve to uniquely identify them, and we will 36963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // leave IPv4 interface indexes unmodified. 36973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 36983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin switch( family ) 36993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 37003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin case AF_INET: ifa->ifa_extra.index = iaa->IfIndex; break; 37013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin case AF_INET6: ifa->ifa_extra.index = ipv6IfIndex + kIPv6IfIndexBase; break; 37023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin default: break; 37033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 37043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get lease lifetime 37063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ( iaa->IfType != IF_TYPE_SOFTWARE_LOOPBACK ) && ( addr->LeaseLifetime != 0 ) && ( addr->ValidLifetime != 0xFFFFFFFF ) ) 37083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 37093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_dhcpEnabled = TRUE; 37103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_dhcpLeaseExpires = time( NULL ) + addr->ValidLifetime; 37113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 37123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 37133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 37143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_dhcpEnabled = FALSE; 37153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_dhcpLeaseExpires = 0; 37163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 37173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( iaa->PhysicalAddressLength == sizeof( ifa->ifa_physaddr ) ) 37193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 37203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy( ifa->ifa_physaddr, iaa->PhysicalAddress, iaa->PhysicalAddressLength ); 37213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 37223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Because we don't get notified of womp changes, we're going to just assume 37243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // that all wired interfaces have it enabled. Before we go to sleep, we'll check 37253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // if the interface actually supports it, and update mDNS->SystemWakeOnLANEnabled 37263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // accordingly 37273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_womp = ( iaa->IfType == IF_TYPE_ETHERNET_CSMACD ) ? mDNStrue : mDNSfalse; 37293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get address. 37313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin switch( family ) 37333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 37343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin case AF_INET: 37353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin case AF_INET6: 37363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_addr = (struct sockaddr *) calloc( 1, (size_t) addr->Address.iSockaddrLength ); 37373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( ifa->ifa_addr, exit, err = WSAENOBUFS ); 37383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy( ifa->ifa_addr, addr->Address.lpSockaddr, (size_t) addr->Address.iSockaddrLength ); 37393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 37403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin default: 37423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 37433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 37443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( ifa->ifa_addr ); 37453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get subnet mask (IPv4)/link prefix (IPv6). It is specified as a bit length (e.g. 24 for 255.255.255.0). 37473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin prefixLength = 0; 37493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( prefixIndex = 0, prefix = firstPrefix; prefix; ++prefixIndex, prefix = prefix->Next ) 37503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 37513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ( prefix->Address.lpSockaddr->sa_family == family ) && ( prefixIndex == addrIndex ) ) 37523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 37533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_string( prefix->Address.lpSockaddr->sa_family == family, "addr family != netmask family" ); 37543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin prefixLength = prefix->PrefixLength; 37553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 37563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 37573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 37583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin switch( family ) 37593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 37603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin case AF_INET: 37613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 37623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in * sa4; 37633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4 = (struct sockaddr_in *) calloc( 1, sizeof( *sa4 ) ); 37653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( sa4, exit, err = WSAENOBUFS ); 37663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4->sin_family = AF_INET; 37673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4->sin_addr.s_addr = ipv4Netmask.sin_addr.s_addr; 37683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "%s: IPv4 mask = %s\n", __ROUTINE__, inet_ntoa( sa4->sin_addr ) ); 37703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_netmask = (struct sockaddr *) sa4; 37713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 37723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 37733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin case AF_INET6: 37753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 37763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in6 * sa6; 37773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int len; 37783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int maskIndex; 37793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin uint8_t maskByte; 37803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( prefixLength <= 128, exit, err = ERROR_INVALID_DATA ); 37823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6 = (struct sockaddr_in6 *) calloc( 1, sizeof( *sa6 ) ); 37843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( sa6, exit, err = WSAENOBUFS ); 37853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6->sin6_family = AF_INET6; 37863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 37873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( prefixLength == 0 ) 37883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 37893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelWarning, DEBUG_NAME "%s: IPv6 link prefix 0, defaulting to /128\n", __ROUTINE__ ); 37903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin prefixLength = 128; 37913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 37923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin maskIndex = 0; 37933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( len = (int) prefixLength; len > 0; len -= 8 ) 37943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 37953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( len >= 8 ) maskByte = 0xFF; 37963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else maskByte = (uint8_t)( ( 0xFFU << ( 8 - len ) ) & 0xFFU ); 37973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6->sin6_addr.s6_addr[ maskIndex++ ] = maskByte; 37983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 37993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_netmask = (struct sockaddr *) sa6; 38003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 38013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 38023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin default: 38043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 38053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 38063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 38073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 38083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Success! 38103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( outAddrs ) 38123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 38133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *outAddrs = head; 38143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin head = NULL; 38153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 38163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = ERROR_SUCCESS; 38173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 38193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( head ) 38203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 38213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin freeifaddrs( head ); 38223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 38233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( iaaList ) 38243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 38253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( iaaList ); 38263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 38273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( (int) err ); 38283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 38293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif // MDNS_WINDOWS_USE_IPV6_IF_ADDRS 38313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 38333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// getifaddrs_ipv4 38343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 38353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal int getifaddrs_ipv4( struct ifaddrs **outAddrs ) 38373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 38383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int err; 38393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SOCKET sock; 38403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD size; 38413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD actualSize; 38423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin INTERFACE_INFO * buffer; 38433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin INTERFACE_INFO * tempBuffer; 38443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin INTERFACE_INFO * ifInfo; 38453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int n; 38463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int i; 38473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * head; 38483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs ** next; 38493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * ifa; 38503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = INVALID_SOCKET; 38523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin buffer = NULL; 38533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin head = NULL; 38543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin next = &head; 38553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get the interface list. WSAIoctl is called with SIO_GET_INTERFACE_LIST, but since this does not provide a 38573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // way to determine the size of the interface list beforehand, we have to start with an initial size guess and 38583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // call WSAIoctl repeatedly with increasing buffer sizes until it succeeds. Limit this to 100 tries for safety. 38593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = socket( AF_INET, SOCK_DGRAM, IPPROTO_UDP ); 38613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( IsValidSocket( sock ), errno_compat(), kUnknownErr ); 38623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 38633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin n = 0; 38653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin size = 16 * sizeof( INTERFACE_INFO ); 38663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( ;; ) 38673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 38683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin tempBuffer = (INTERFACE_INFO *) realloc( buffer, size ); 38693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( tempBuffer, exit, err = WSAENOBUFS ); 38703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin buffer = tempBuffer; 38713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = WSAIoctl( sock, SIO_GET_INTERFACE_LIST, NULL, 0, buffer, size, &actualSize, NULL, NULL ); 38733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( err == 0 ) 38743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 38753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 38763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 38773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ++n; 38793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( n < 100, exit, err = WSAEADDRNOTAVAIL ); 38803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin size += ( 16 * sizeof( INTERFACE_INFO ) ); 38823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 38833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( actualSize <= size ); 38843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( ( actualSize % sizeof( INTERFACE_INFO ) ) == 0 ); 38853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin n = (int)( actualSize / sizeof( INTERFACE_INFO ) ); 38863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Process the raw interface list and build a linked list of IPv4 interfaces. 38883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( i = 0; i < n; ++i ) 38903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 38913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin uint32_t ifIndex; 38923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in netmask; 38933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 38943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifInfo = &buffer[ i ]; 38953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ifInfo->iiAddress.Address.sa_family != AF_INET ) 38963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 38973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin continue; 38983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 38993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // <rdar://problem/6220642> iTunes 8: Bonjour doesn't work after upgrading iTunes 8 39013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // See comment in getifaddrs_ipv6 39023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifIndex = 0; 39043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memset( &netmask, 0, sizeof( netmask ) ); 39053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = AddressToIndexAndMask( ( struct sockaddr* ) &ifInfo->iiAddress.AddressIn, &ifIndex, ( struct sockaddr* ) &netmask ); 39063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err ) 39083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 39093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin continue; 39103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 39113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa = (struct ifaddrs *) calloc( 1, sizeof( struct ifaddrs ) ); 39133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( ifa, exit, err = WSAENOBUFS ); 39143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *next = ifa; 39163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin next = &ifa->ifa_next; 39173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get the name. 39193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_name = (char *) malloc( 16 ); 39213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( ifa->ifa_name, exit, err = WSAENOBUFS ); 39223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sprintf( ifa->ifa_name, "%d", i + 1 ); 39233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get interface flags. 39253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_flags = (u_int) ifInfo->iiFlags; 39273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get addresses. 39293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ifInfo->iiAddress.Address.sa_family == AF_INET ) 39313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 39323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in * sa4; 39333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4 = &ifInfo->iiAddress.AddressIn; 39353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_addr = (struct sockaddr *) calloc( 1, sizeof( *sa4 ) ); 39363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( ifa->ifa_addr, exit, err = WSAENOBUFS ); 39373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy( ifa->ifa_addr, sa4, sizeof( *sa4 ) ); 39383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_netmask = (struct sockaddr*) calloc(1, sizeof( *sa4 ) ); 39403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( ifa->ifa_netmask, exit, err = WSAENOBUFS ); 39413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // <rdar://problem/4076478> Service won't start on Win2K. The address 39433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // family field was not being initialized. 39443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_netmask->sa_family = AF_INET; 39463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( ( struct sockaddr_in* ) ifa->ifa_netmask )->sin_addr = netmask.sin_addr; 39473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_extra.index = ifIndex; 39483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 39493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 39503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 39513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Emulate an interface index. 39523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa->ifa_extra.index = (uint32_t)( i + 1 ); 39543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 39553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 39563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Success! 39583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( outAddrs ) 39603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 39613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *outAddrs = head; 39623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin head = NULL; 39633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 39643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = 0; 39653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 39673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( head ) 39693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 39703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin freeifaddrs( head ); 39713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 39723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( buffer ) 39733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 39743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( buffer ); 39753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 39763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( sock != INVALID_SOCKET ) 39773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 39783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin closesocket( sock ); 39793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 39803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 39813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 39823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 39843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// freeifaddrs 39853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 39863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void freeifaddrs( struct ifaddrs *inIFAs ) 39883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 39893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * p; 39903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * q; 39913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Free each piece of the structure. Set to null after freeing to handle macro-aliased fields. 39933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( p = inIFAs; p; p = q ) 39953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 39963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin q = p->ifa_next; 39973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 39983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( p->ifa_name ) 39993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 40003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( p->ifa_name ); 40013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p->ifa_name = NULL; 40023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 40033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( p->ifa_addr ) 40043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 40053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( p->ifa_addr ); 40063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p->ifa_addr = NULL; 40073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 40083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( p->ifa_netmask ) 40093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 40103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( p->ifa_netmask ); 40113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p->ifa_netmask = NULL; 40123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 40133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( p->ifa_broadaddr ) 40143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 40153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( p->ifa_broadaddr ); 40163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p->ifa_broadaddr = NULL; 40173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 40183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( p->ifa_dstaddr ) 40193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 40203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( p->ifa_dstaddr ); 40213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p->ifa_dstaddr = NULL; 40223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 40233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( p->ifa_data ) 40243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 40253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( p->ifa_data ); 40263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p->ifa_data = NULL; 40273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 40283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( p ); 40293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 40303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 40313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 40343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// GetPrimaryInterface 40353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 40363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal DWORD 40383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinGetPrimaryInterface() 40393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 40403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin PMIB_IPFORWARDTABLE pIpForwardTable = NULL; 40413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD dwSize = 0; 40423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin BOOL bOrder = FALSE; 40433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin OSStatus err; 40443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD index = 0; 40453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD metric = 0; 40463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin unsigned long int i; 40473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Find out how big our buffer needs to be. 40493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = GetIpForwardTable(NULL, &dwSize, bOrder); 40513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( err == ERROR_INSUFFICIENT_BUFFER, exit, err = kUnknownErr ); 40523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Allocate the memory for the table 40543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pIpForwardTable = (PMIB_IPFORWARDTABLE) malloc( dwSize ); 40563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( pIpForwardTable, exit, err = kNoMemoryErr ); 40573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Now get the table. 40593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = GetIpForwardTable(pIpForwardTable, &dwSize, bOrder); 40613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 40623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Search for the row in the table we want. 40653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( i = 0; i < pIpForwardTable->dwNumEntries; i++) 40673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 40683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Look for a default route 40693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( pIpForwardTable->table[i].dwForwardDest == 0 ) 40713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 40723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( index && ( pIpForwardTable->table[i].dwForwardMetric1 >= metric ) ) 40733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 40743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin continue; 40753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 40763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin index = pIpForwardTable->table[i].dwForwardIfIndex; 40783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin metric = pIpForwardTable->table[i].dwForwardMetric1; 40793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 40803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 40813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 40833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( pIpForwardTable != NULL ) 40853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 40863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( pIpForwardTable ); 40873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 40883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return index; 40903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 40913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 40943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// AddressToIndexAndMask 40953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 40963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 40973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus 40983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinAddressToIndexAndMask( struct sockaddr * addr, uint32_t * ifIndex, struct sockaddr * mask ) 40993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 41003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Before calling AddIPAddress we use GetIpAddrTable to get 41013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // an adapter to which we can add the IP. 41023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin PMIB_IPADDRTABLE pIPAddrTable = NULL; 41043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD dwSize = 0; 41053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err = mStatus_UnknownErr; 41063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD i; 41073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // For now, this is only for IPv4 addresses. That is why we can safely cast 41093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // addr's to sockaddr_in. 41103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( addr->sa_family == AF_INET, exit, err = mStatus_UnknownErr ); 41123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Make an initial call to GetIpAddrTable to get the 41143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // necessary size into the dwSize variable 41153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( i = 0; i < 100; i++ ) 41173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 41183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = GetIpAddrTable( pIPAddrTable, &dwSize, 0 ); 41193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err != ERROR_INSUFFICIENT_BUFFER ) 41213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 41223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 41233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 41243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pIPAddrTable = (MIB_IPADDRTABLE *) realloc( pIPAddrTable, dwSize ); 41263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( pIPAddrTable, exit, err = WSAENOBUFS ); 41273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 41283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 41303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = mStatus_UnknownErr; 41313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( i = 0; i < pIPAddrTable->dwNumEntries; i++ ) 41333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 41343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ( ( struct sockaddr_in* ) addr )->sin_addr.s_addr == pIPAddrTable->table[i].dwAddr ) 41353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 41363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *ifIndex = pIPAddrTable->table[i].dwIndex; 41373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( ( struct sockaddr_in*) mask )->sin_addr.s_addr = pIPAddrTable->table[i].dwMask; 41383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = mStatus_NoError; 41393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 41403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 41413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 41423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 41443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( pIPAddrTable ) 41463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 41473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( pIPAddrTable ); 41483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 41493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return err; 41513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 41523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 41553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// CanReceiveUnicast 41563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 41573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mDNSBool CanReceiveUnicast( void ) 41593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 41603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSBool ok; 41613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SocketRef sock; 41623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in addr; 41633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Try to bind to the port without the SO_REUSEADDR option to test if someone else has already bound to it. 41653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock = socket( AF_INET, SOCK_DGRAM, IPPROTO_UDP ); 41673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_translated_errno( IsValidSocket( sock ), errno_compat(), kUnknownErr ); 41683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ok = IsValidSocket( sock ); 41693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ok ) 41703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 41713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSPlatformMemZero( &addr, sizeof( addr ) ); 41723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin addr.sin_family = AF_INET; 41733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin addr.sin_port = MulticastDNSPort.NotAnInteger; 41743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin addr.sin_addr.s_addr = htonl( INADDR_ANY ); 41753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ok = ( bind( sock, (struct sockaddr *) &addr, sizeof( addr ) ) == 0 ); 41773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin close_compat( sock ); 41783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 41793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelInfo, DEBUG_NAME "Unicast UDP responses %s\n", ok ? "okay" : "*not allowed*" ); 41813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( ok ); 41823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 41833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 41863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// IsPointToPoint 41873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 41883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mDNSBool IsPointToPoint( IP_ADAPTER_UNICAST_ADDRESS * addr ) 41903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 41913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * addrs = NULL; 41923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct ifaddrs * p = NULL; 41933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin OSStatus err; 41943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSBool ret = mDNSfalse; 41953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // For now, only works for IPv4 interfaces 41973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 41983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( addr->Address.lpSockaddr->sa_family == AF_INET ) 41993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // The getifaddrs_ipv4 call will give us correct information regarding IFF_POINTTOPOINT flags. 42013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = getifaddrs_ipv4( &addrs ); 42033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 42043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( p = addrs; p; p = p->ifa_next ) 42063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ( addr->Address.lpSockaddr->sa_family == p->ifa_addr->sa_family ) && 42083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( ( ( struct sockaddr_in* ) addr->Address.lpSockaddr )->sin_addr.s_addr == ( ( struct sockaddr_in* ) p->ifa_addr )->sin_addr.s_addr ) ) 42093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ret = ( p->ifa_flags & IFF_POINTTOPOINT ) ? mDNStrue : mDNSfalse; 42113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 42123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 42173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( addrs ) 42193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin freeifaddrs( addrs ); 42213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return ret; 42243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 42253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 42283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// GetWindowsVersionString 42293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 42303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal OSStatus GetWindowsVersionString( char *inBuffer, size_t inBufferSize ) 42323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 42333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( !defined( VER_PLATFORM_WIN32_CE ) ) 42343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin #define VER_PLATFORM_WIN32_CE 3 42353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 42363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin OSStatus err; 42383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin OSVERSIONINFO osInfo; 42393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin BOOL ok; 42403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const char * versionString; 42413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD platformID; 42423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD majorVersion; 42433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD minorVersion; 42443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD buildNumber; 42453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "unknown Windows version"; 42473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin osInfo.dwOSVersionInfoSize = sizeof( OSVERSIONINFO ); 42493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ok = GetVersionEx( &osInfo ); 42503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( ok, (OSStatus) GetLastError(), kUnknownErr ); 42513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 42523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin platformID = osInfo.dwPlatformId; 42543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin majorVersion = osInfo.dwMajorVersion; 42553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin minorVersion = osInfo.dwMinorVersion; 42563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin buildNumber = osInfo.dwBuildNumber & 0xFFFF; 42573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 42583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ( platformID == VER_PLATFORM_WIN32_WINDOWS ) && ( majorVersion == 4 ) ) 42593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ( minorVersion < 10 ) && ( buildNumber == 950 ) ) 42613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows 95"; 42633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( ( minorVersion < 10 ) && ( ( buildNumber > 950 ) && ( buildNumber <= 1080 ) ) ) 42653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows 95 SP1"; 42673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( ( minorVersion < 10 ) && ( buildNumber > 1080 ) ) 42693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows 95 OSR2"; 42713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( ( minorVersion == 10 ) && ( buildNumber == 1998 ) ) 42733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows 98"; 42753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( ( minorVersion == 10 ) && ( ( buildNumber > 1998 ) && ( buildNumber < 2183 ) ) ) 42773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows 98 SP1"; 42793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( ( minorVersion == 10 ) && ( buildNumber >= 2183 ) ) 42813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows 98 SE"; 42833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( minorVersion == 90 ) 42853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows ME"; 42873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( platformID == VER_PLATFORM_WIN32_NT ) 42903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( ( majorVersion == 3 ) && ( minorVersion == 51 ) ) 42923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows NT 3.51"; 42943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( ( majorVersion == 4 ) && ( minorVersion == 0 ) ) 42963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 42973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows NT 4"; 42983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 42993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( ( majorVersion == 5 ) && ( minorVersion == 0 ) ) 43003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 43013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows 2000"; 43023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 43033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( ( majorVersion == 5 ) && ( minorVersion == 1 ) ) 43043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 43053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows XP"; 43063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 43073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( ( majorVersion == 5 ) && ( minorVersion == 2 ) ) 43083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 43093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows Server 2003"; 43103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 43113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 43123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if( platformID == VER_PLATFORM_WIN32_CE ) 43133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 43143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin versionString = "Windows CE"; 43153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 43163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 43183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( inBuffer && ( inBufferSize > 0 ) ) 43193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 43203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inBufferSize -= 1; 43213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin strncpy( inBuffer, versionString, inBufferSize ); 43223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin inBuffer[ inBufferSize ] = '\0'; 43233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 43243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 43253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 43263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 43293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// RegQueryString 43303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 43313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus 43333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinRegQueryString( HKEY key, LPCSTR valueName, LPSTR * string, DWORD * stringLen, DWORD * enabled ) 43343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 43353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD type; 43363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int i; 43373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 43383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *stringLen = MAX_ESCAPED_DOMAIN_NAME; 43403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *string = NULL; 43413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin i = 0; 43423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin do 43443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 43453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( *string ) 43463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 43473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( *string ); 43483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 43493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *string = (char*) malloc( *stringLen ); 43513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( *string, exit, err = mStatus_NoMemoryErr ); 43523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegQueryValueExA( key, valueName, 0, &type, (LPBYTE) *string, stringLen ); 43543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin i++; 43563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 43573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while ( ( err == ERROR_MORE_DATA ) && ( i < 100 ) ); 43583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr_quiet( err, exit ); 43603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( enabled ) 43623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 43633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD dwSize = sizeof( DWORD ); 43643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegQueryValueEx( key, TEXT("Enabled"), NULL, NULL, (LPBYTE) enabled, &dwSize ); 43663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 43673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = kNoErr; 43693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 43703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 43723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return err; 43743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 43753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 43783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// StringToAddress 43793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 43803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus StringToAddress( mDNSAddr * ip, LPSTR string ) 43823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 43833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in6 sa6; 43843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in sa4; 43853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin INT dwSize; 43863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 43873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa6.sin6_family = AF_INET6; 43893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dwSize = sizeof( sa6 ); 43903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = WSAStringToAddressA( string, AF_INET6, NULL, (struct sockaddr*) &sa6, &dwSize ); 43923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 43933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err == mStatus_NoError ) 43943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 43953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupAddr( ip, (struct sockaddr*) &sa6 ); 43963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 43973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 43983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 43993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 44003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sa4.sin_family = AF_INET; 44013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dwSize = sizeof( sa4 ); 44023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = WSAStringToAddressA( string, AF_INET, NULL, (struct sockaddr*) &sa4, &dwSize ); 44043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( err == 0, WSAGetLastError(), kUnknownErr ); 44053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 44063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = SetupAddr( ip, (struct sockaddr*) &sa4 ); 44083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 44093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 44103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 44123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return err; 44143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 44153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 44183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// myGetIfAddrs 44193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 44203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal struct ifaddrs* 44223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmyGetIfAddrs(int refresh) 44233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 44243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin static struct ifaddrs *ifa = NULL; 44253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (refresh && ifa) 44273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 44283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin freeifaddrs(ifa); 44293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ifa = NULL; 44303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 44313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (ifa == NULL) 44333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 44343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin getifaddrs(&ifa); 44353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 44363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return ifa; 44383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 44393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 44423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// TCHARtoUTF8 44433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 44443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal OSStatus 44463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinTCHARtoUTF8( const TCHAR *inString, char *inBuffer, size_t inBufferSize ) 44473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 44483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#if( defined( UNICODE ) || defined( _UNICODE ) ) 44493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin OSStatus err; 44503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int len; 44513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin len = WideCharToMultiByte( CP_UTF8, 0, inString, -1, inBuffer, (int) inBufferSize, NULL, NULL ); 44533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( len > 0, errno_compat(), kUnknownErr ); 44543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 44553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 44573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 44583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#else 44593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( WindowsLatin1toUTF8( inString, inBuffer, inBufferSize ) ); 44603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 44613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 44623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 44653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// WindowsLatin1toUTF8 44663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 44673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal OSStatus 44693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinWindowsLatin1toUTF8( const char *inString, char *inBuffer, size_t inBufferSize ) 44703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 44713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin OSStatus err; 44723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin WCHAR * utf16; 44733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int len; 44743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin utf16 = NULL; 44763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Windows doesn't support going directly from Latin-1 to UTF-8 so we have to go from Latin-1 to UTF-16 first. 44783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin len = MultiByteToWideChar( CP_ACP, 0, inString, -1, NULL, 0 ); 44803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( len > 0, errno_compat(), kUnknownErr ); 44813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 44823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin utf16 = (WCHAR *) malloc( len * sizeof( *utf16 ) ); 44843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( utf16, exit, err = kNoMemoryErr ); 44853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin len = MultiByteToWideChar( CP_ACP, 0, inString, -1, utf16, len ); 44873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( len > 0, errno_compat(), kUnknownErr ); 44883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 44893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Now convert the temporary UTF-16 to UTF-8. 44913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin len = WideCharToMultiByte( CP_UTF8, 0, utf16, -1, inBuffer, (int) inBufferSize, NULL, NULL ); 44933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( len > 0, errno_compat(), kUnknownErr ); 44943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 44953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 44963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 44973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if( utf16 ) free( utf16 ); 44983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return( err ); 44993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 45003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 45033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// TCPCloseSocket 45043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 45053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void 45073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinTCPCloseSocket( TCPSocket * sock ) 45083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 45093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "closing TCPSocket 0x%x:%d\n", sock, sock->fd ); 45103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RemoveFromList( &gTCPDispatchableSockets, sock ); 45123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->fd != INVALID_SOCKET ) 45143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 45153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin closesocket( sock->fd ); 45163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->fd = INVALID_SOCKET; 45173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 45183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 45193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 45223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// TCPFreeSocket 45233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 45243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void CALLBACK 45263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinTCPFreeSocket( TCPSocket *sock ) 45273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 45283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( sock ); 45293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "freeing TCPSocket 0x%x:%d\n", sock, sock->fd ); 45313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->connectEvent ) 45333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 45343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin CloseHandle( sock->connectEvent ); 45353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->connectEvent = NULL; 45363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 45373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->fd != INVALID_SOCKET ) 45393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 45403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin closesocket( sock->fd ); 45413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->fd = INVALID_SOCKET; 45423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 45433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( sock ); 45453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 45463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 45493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// UDPCloseSocket 45503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 45513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void 45533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinUDPCloseSocket( UDPSocket * sock ) 45543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 45553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "closing UDPSocket %d\n", sock->fd ); 45563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RemoveFromList( &gUDPDispatchableSockets, sock ); 45583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->fd != INVALID_SOCKET ) 45603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 45613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin closesocket( sock->fd ); 45623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->fd = INVALID_SOCKET; 45633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 45643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 45653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 45683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// UDPFreeSocket 45693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 45703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void CALLBACK 45723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinUDPFreeSocket( UDPSocket * sock ) 45733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 45743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( sock ); 45753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "freeing UDPSocket %d\n", sock->fd ); 45773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->fd != INVALID_SOCKET ) 45793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 45803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin closesocket( sock->fd ); 45813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->fd = INVALID_SOCKET; 45823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 45833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( sock ); 45853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 45863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 45883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin// SetupAddr 45893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin//=========================================================================================================================== 45903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mStatus SetupAddr(mDNSAddr *ip, const struct sockaddr *const sa) 45923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 45933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (!sa) { LogMsg("SetupAddr ERROR: NULL sockaddr"); return(mStatus_Invalid); } 45943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 45953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (sa->sa_family == AF_INET) 45963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 45973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in *ifa_addr = (struct sockaddr_in *)sa; 45983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ip->type = mDNSAddrType_IPv4; 45993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ip->ip.v4.NotAnInteger = ifa_addr->sin_addr.s_addr; 46003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return(mStatus_NoError); 46013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 46023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (sa->sa_family == AF_INET6) 46043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 46053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin struct sockaddr_in6 *ifa_addr = (struct sockaddr_in6 *)sa; 46063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ip->type = mDNSAddrType_IPv6; 46073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (IN6_IS_ADDR_LINKLOCAL(&ifa_addr->sin6_addr)) ifa_addr->sin6_addr.u.Word[1] = 0; 46083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ip->ip.v6 = *(mDNSv6Addr*)&ifa_addr->sin6_addr; 46093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return(mStatus_NoError); 46103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 46113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LogMsg("SetupAddr invalid sa_family %d", sa->sa_family); 46133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return(mStatus_Invalid); 46143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 46153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void GetDDNSFQDN( domainname *const fqdn ) 46183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 46193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LPSTR name = NULL; 46203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD dwSize; 46213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD enabled; 46223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin HKEY key = NULL; 46233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin OSStatus err; 46243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( fqdn ); 46263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Initialize 46283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin fqdn->c[0] = '\0'; 46303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get info from Bonjour registry key 46323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegCreateKey( HKEY_LOCAL_MACHINE, kServiceParametersNode TEXT("\\DynDNS\\Setup\\") kServiceDynDNSHostNames, &key ); 46343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 46353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegQueryString( key, "", &name, &dwSize, &enabled ); 46373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !err && ( name[0] != '\0' ) && enabled ) 46383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 46393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !MakeDomainNameFromDNSNameString( fqdn, name ) || !fqdn->c[0] ) 46403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 46413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelError, "bad DDNS host name in registry: %s", name[0] ? name : "(unknown)"); 46423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 46433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 46443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 46463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( key ) 46483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 46493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RegCloseKey( key ); 46503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin key = NULL; 46513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 46523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( name ) 46543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 46553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( name ); 46563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin name = NULL; 46573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 46583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 46593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#ifdef UNICODE 46623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void GetDDNSDomains( DNameListElem ** domains, LPCWSTR lpSubKey ) 46633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#else 46643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void GetDDNSConfig( DNameListElem ** domains, LPCSTR lpSubKey ) 46653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin#endif 46663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 46673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char subKeyName[kRegistryMaxKeyLength + 1]; 46683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD cSubKeys = 0; 46693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD cbMaxSubKey; 46703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD cchMaxClass; 46713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD dwSize; 46723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin HKEY key = NULL; 46733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin HKEY subKey = NULL; 46743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin domainname dname; 46753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD i; 46763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin OSStatus err; 46773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( domains ); 46793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Initialize 46813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *domains = NULL; 46833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegCreateKey( HKEY_LOCAL_MACHINE, lpSubKey, &key ); 46853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 46863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Get information about this node 46883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegQueryInfoKey( key, NULL, NULL, NULL, &cSubKeys, &cbMaxSubKey, &cchMaxClass, NULL, NULL, NULL, NULL, NULL ); 46903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 46913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( i = 0; i < cSubKeys; i++) 46933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 46943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD enabled; 46953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dwSize = kRegistryMaxKeyLength; 46973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 46983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegEnumKeyExA( key, i, subKeyName, &dwSize, NULL, NULL, NULL, NULL ); 46993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !err ) 47013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 47023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegOpenKeyExA( key, subKeyName, 0, KEY_READ, &subKey ); 47033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_noerr( err, exit ); 47043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dwSize = sizeof( DWORD ); 47063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegQueryValueExA( subKey, "Enabled", NULL, NULL, (LPBYTE) &enabled, &dwSize ); 47073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !err && ( subKeyName[0] != '\0' ) && enabled ) 47093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 47103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !MakeDomainNameFromDNSNameString( &dname, subKeyName ) || !dname.c[0] ) 47113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 47123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelError, "bad DDNS domain in registry: %s", subKeyName[0] ? subKeyName : "(unknown)"); 47133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 47143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 47153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 47163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DNameListElem * domain = (DNameListElem*) malloc( sizeof( DNameListElem ) ); 47173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( domain, exit, err = mStatus_NoMemoryErr ); 47183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin AssignDomainName(&domain->name, &dname); 47203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin domain->next = *domains; 47213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *domains = domain; 47233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 47243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 47253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RegCloseKey( subKey ); 47273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin subKey = NULL; 47283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 47293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 47303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 47323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( subKey ) 47343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 47353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RegCloseKey( subKey ); 47363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 47373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( key ) 47393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 47403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RegCloseKey( key ); 47413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 47423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 47433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void SetDomainSecret( mDNS * const m, const domainname * inDomain ) 47463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 47473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char domainUTF8[ 256 ]; 47483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DomainAuthInfo *foundInList; 47493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DomainAuthInfo *ptr; 47503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char outDomain[ 256 ]; 47513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char outKey[ 256 ]; 47523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char outSecret[ 256 ]; 47533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin OSStatus err; 47543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ConvertDomainNameToCString( inDomain, domainUTF8 ); 47563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If we're able to find a secret for this domain 47583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( LsaGetSecret( domainUTF8, outDomain, sizeof( outDomain ), outKey, sizeof( outKey ), outSecret, sizeof( outSecret ) ) ) 47603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 47613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin domainname domain; 47623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin domainname key; 47633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Tell the core about this secret 47653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin MakeDomainNameFromDNSNameString( &domain, outDomain ); 47673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin MakeDomainNameFromDNSNameString( &key, outKey ); 47683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for (foundInList = m->AuthInfoList; foundInList; foundInList = foundInList->next) 47703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (SameDomainName(&foundInList->domain, &domain ) ) break; 47713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ptr = foundInList; 47733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if (!ptr) 47753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 47763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ptr = (DomainAuthInfo*)malloc(sizeof(DomainAuthInfo)); 47773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( ptr, exit, err = mStatus_NoMemoryErr ); 47783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 47793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = mDNS_SetSecretForDomain(m, ptr, &domain, &key, outSecret, NULL, 0, NULL ); 47813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( err != mStatus_BadParamErr, exit, if (!foundInList ) mDNSPlatformMemFree( ptr ) ); 47823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin debugf("Setting shared secret for zone %s with key %##s", outDomain, key.c); 47843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 47853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 47873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return; 47893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 47903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal VOID CALLBACK 47933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinCheckFileSharesProc( LPVOID arg, DWORD dwTimerLowValue, DWORD dwTimerHighValue ) 47943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 47953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNS * const m = ( mDNS * const ) arg; 47963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 47973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( void ) dwTimerLowValue; 47983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( void ) dwTimerHighValue; 47993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin CheckFileShares( m ); 48013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 48023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal unsigned __stdcall 48053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinSMBRegistrationThread( void * arg ) 48063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 48073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNS * const m = ( mDNS * const ) arg; 48083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DNSServiceRef sref = NULL; 48093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin HANDLE handles[ 3 ]; 48103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSu8 txtBuf[ 256 ]; 48113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSu8 * txtPtr; 48123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin size_t keyLen; 48133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin size_t valLen; 48143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSIPPort port = { { SMBPortAsNumber >> 8, SMBPortAsNumber & 0xFF } }; 48153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DNSServiceErrorType err; 48163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DEBUG_UNUSED( arg ); 48183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin handles[ 0 ] = gSMBThreadStopEvent; 48203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin handles[ 1 ] = gSMBThreadRegisterEvent; 48213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin handles[ 2 ] = gSMBThreadDeregisterEvent; 48223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memset( txtBuf, 0, sizeof( txtBuf ) ); 48243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin txtPtr = txtBuf; 48253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin keyLen = strlen( "netbios=" ); 48263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin valLen = strlen( m->p->nbname ); 48273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( valLen < 32, exit, err = kUnknownErr ); // This should never happen, but check to avoid further memory corruption 48283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *txtPtr++ = ( mDNSu8 ) ( keyLen + valLen ); 48293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy( txtPtr, "netbios=", keyLen ); 48303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin txtPtr += keyLen; 48313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( valLen ) { memcpy( txtPtr, m->p->nbname, valLen ); txtPtr += ( mDNSu8 ) valLen; } 48323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin keyLen = strlen( "domain=" ); 48333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin valLen = strlen( m->p->nbdomain ); 48343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( valLen < 32, exit, err = kUnknownErr ); // This should never happen, but check to avoid further memory corruption 48353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin *txtPtr++ = ( mDNSu8 )( keyLen + valLen ); 48363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin memcpy( txtPtr, "domain=", keyLen ); 48373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin txtPtr += keyLen; 48383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( valLen ) { memcpy( txtPtr, m->p->nbdomain, valLen ); txtPtr += valLen; } 48393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for ( ;; ) 48413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 48423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD ret; 48433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ret = WaitForMultipleObjects( 3, handles, FALSE, INFINITE ); 48453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ret != WAIT_FAILED ) 48473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 48483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ret == kSMBStopEvent ) 48493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 48503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 48513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 48523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if ( ret == kSMBRegisterEvent ) 48533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 48543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = gDNSServiceRegister( &sref, 0, 0, NULL, "_smb._tcp,_file", NULL, NULL, ( uint16_t ) port.NotAnInteger, ( mDNSu16 )( txtPtr - txtBuf ), txtBuf, NULL, NULL ); 48553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( err ) 48573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 48583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LogMsg( "SMBRegistrationThread: DNSServiceRegister returned %d\n", err ); 48593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sref = NULL; 48603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 48613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 48623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 48633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if ( ret == kSMBDeregisterEvent ) 48643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 48653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sref ) 48663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 48673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gDNSServiceRefDeallocate( sref ); 48683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sref = NULL; 48693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 48703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 48713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 48723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else 48733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 48743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LogMsg( "SMBRegistrationThread: WaitForMultipleObjects returned %d\n", GetLastError() ); 48753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 48763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 48773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 48783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 48803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sref != NULL ) 48823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 48833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gDNSServiceRefDeallocate( sref ); 48843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sref = NULL; 48853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 48863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SetEvent( gSMBThreadQuitEvent ); 48883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin _endthreadex( 0 ); 48893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return 0; 48903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 48913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 48933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void 48943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinCheckFileShares( mDNS * const m ) 48953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 48963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin PSHARE_INFO_1 bufPtr = ( PSHARE_INFO_1 ) NULL; 48973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD entriesRead = 0; 48983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD totalEntries = 0; 48993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD resume = 0; 49003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSBool advertise = mDNSfalse; 49013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSBool fileSharing = mDNSfalse; 49023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSBool printSharing = mDNSfalse; 49033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin HKEY key = NULL; 49043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin BOOL retry = FALSE; 49053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin NET_API_STATUS res; 49063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mStatus err; 49073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check( m ); 49093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Only do this if we're not shutting down 49113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action_quiet( m->AdvertiseLocalAddresses && !m->ShutdownTime, exit, err = kNoErr ); 49133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = RegCreateKey( HKEY_LOCAL_MACHINE, kServiceParametersNode L"\\Services\\SMB", &key ); 49153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !err ) 49173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD dwSize = sizeof( DWORD ); 49193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RegQueryValueEx( key, L"Advertise", NULL, NULL, (LPBYTE) &advertise, &dwSize ); 49203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 49213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( advertise && mDNSIsFileAndPrintSharingEnabled( &retry ) ) 49233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "Sharing is enabled\n" ); 49253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin res = NetShareEnum( NULL, 1, ( LPBYTE* )&bufPtr, MAX_PREFERRED_LENGTH, &entriesRead, &totalEntries, &resume ); 49273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ( res == ERROR_SUCCESS ) || ( res == ERROR_MORE_DATA ) ) 49293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin PSHARE_INFO_1 p = bufPtr; 49313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD i; 49323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( i = 0; i < entriesRead; i++ ) 49343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // We are only interested if the user is sharing anything other 49363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // than the built-in "print$" source 49373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( ( p->shi1_type == STYPE_DISKTREE ) && ( wcscmp( p->shi1_netname, TEXT( "print$" ) ) != 0 ) ) 49393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin fileSharing = mDNStrue; 49413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 49423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if ( p->shi1_type == STYPE_PRINTQ ) 49433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin printSharing = mDNStrue; 49453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 49463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin p++; 49483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 49493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin NetApiBufferFree( bufPtr ); 49513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin bufPtr = NULL; 49523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin retry = FALSE; 49533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 49543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if ( res == NERR_ServerNotStarted ) 49553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin retry = TRUE; 49573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 49583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 49593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( retry ) 49613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin __int64 qwTimeout; 49633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin LARGE_INTEGER liTimeout; 49643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin qwTimeout = -m->p->checkFileSharesTimeout * 10000000; 49663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin liTimeout.LowPart = ( DWORD )( qwTimeout & 0xFFFFFFFF ); 49673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin liTimeout.HighPart = ( LONG )( qwTimeout >> 32 ); 49683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SetWaitableTimer( m->p->checkFileSharesTimer, &liTimeout, 0, CheckFileSharesProc, m, FALSE ); 49703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 49713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !m->p->smbFileSharing && fileSharing ) 49733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !gSMBThread ) 49753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !gDNSSDLibrary ) 49773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gDNSSDLibrary = LoadLibrary( TEXT( "dnssd.dll" ) ); 49793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( gDNSSDLibrary, exit, err = GetLastError() ); 49803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 49813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !gDNSServiceRegister ) 49833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gDNSServiceRegister = ( DNSServiceRegisterFunc ) GetProcAddress( gDNSSDLibrary, "DNSServiceRegister" ); 49853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( gDNSServiceRegister, exit, err = GetLastError() ); 49863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 49873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !gDNSServiceRefDeallocate ) 49893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gDNSServiceRefDeallocate = ( DNSServiceRefDeallocateFunc ) GetProcAddress( gDNSSDLibrary, "DNSServiceRefDeallocate" ); 49913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( gDNSServiceRefDeallocate, exit, err = GetLastError() ); 49923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 49933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 49943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !gSMBThreadRegisterEvent ) 49953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 49963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gSMBThreadRegisterEvent = CreateEvent( NULL, FALSE, FALSE, NULL ); 49973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( gSMBThreadRegisterEvent != NULL, exit, err = GetLastError() ); 49983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 49993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !gSMBThreadDeregisterEvent ) 50013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 50023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gSMBThreadDeregisterEvent = CreateEvent( NULL, FALSE, FALSE, NULL ); 50033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( gSMBThreadDeregisterEvent != NULL, exit, err = GetLastError() ); 50043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 50053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !gSMBThreadStopEvent ) 50073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 50083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gSMBThreadStopEvent = CreateEvent( NULL, FALSE, FALSE, NULL ); 50093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( gSMBThreadStopEvent != NULL, exit, err = GetLastError() ); 50103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 50113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !gSMBThreadQuitEvent ) 50133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 50143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gSMBThreadQuitEvent = CreateEvent( NULL, FALSE, FALSE, NULL ); 50153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( gSMBThreadQuitEvent != NULL, exit, err = GetLastError() ); 50163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 50173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin gSMBThread = ( HANDLE ) _beginthreadex( NULL, 0, SMBRegistrationThread, m, 0, NULL ); 50193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( gSMBThread != NULL, exit, err = GetLastError() ); 50203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 50213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SetEvent( gSMBThreadRegisterEvent ); 50233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin m->p->smbFileSharing = mDNStrue; 50253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 50263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin else if ( m->p->smbFileSharing && !fileSharing ) 50273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 50283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "deregistering smb type\n" ); 50293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( gSMBThreadDeregisterEvent != NULL ) 50313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 50323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin SetEvent( gSMBThreadDeregisterEvent ); 50333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 50343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin m->p->smbFileSharing = mDNSfalse; 50363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 50373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 50393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( key ) 50413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 50423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RegCloseKey( key ); 50433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 50443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 50453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinBOOL 50483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinIsWOMPEnabled( mDNS * const m ) 50493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 50503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin BOOL enabled; 50513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSInterfaceData * ifd; 50533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin enabled = FALSE; 50553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin for( ifd = m->p->interfaceList; ifd; ifd = ifd->next ) 50573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 50583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( IsWOMPEnabledForAdapter( ifd->name ) ) 50593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 50603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin enabled = TRUE; 50613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin break; 50623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 50633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 50643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return enabled; 50663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 50673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal mDNSu8 50703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinIsWOMPEnabledForAdapter( const char * adapterName ) 50713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 50723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin char fileName[80]; 50733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin NDIS_OID oid; 50743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DWORD count; 50753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin HANDLE handle = INVALID_HANDLE_VALUE; 50763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin NDIS_PNP_CAPABILITIES * pNPC = NULL; 50773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int err; 50783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSu8 ok = TRUE; 50793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( adapterName != NULL, exit, ok = FALSE ); 50813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "IsWOMPEnabledForAdapter: %s\n", adapterName ); 50833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // Construct a device name to pass to CreateFile 50853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin strncpy_s( fileName, sizeof( fileName ), DEVICE_PREFIX, strlen( DEVICE_PREFIX ) ); 50873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin strcat_s( fileName, sizeof( fileName ), adapterName ); 50883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin handle = CreateFileA( fileName, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, OPEN_EXISTING, 0, INVALID_HANDLE_VALUE ); 50893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action ( handle != INVALID_HANDLE_VALUE, exit, ok = FALSE ); 50903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // We successfully opened the driver, format the IOCTL to pass the driver. 50923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 50933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin oid = OID_PNP_CAPABILITIES; 50943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin pNPC = ( NDIS_PNP_CAPABILITIES * ) malloc( sizeof( NDIS_PNP_CAPABILITIES ) ); 50953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( pNPC != NULL, exit, ok = FALSE ); 50963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ok = ( mDNSu8 ) DeviceIoControl( handle, IOCTL_NDIS_QUERY_GLOBAL_STATS, &oid, sizeof( oid ), pNPC, sizeof( NDIS_PNP_CAPABILITIES ), &count, NULL ); 50973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin err = translate_errno( ok, GetLastError(), kUnknownErr ); 50983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin require_action( !err, exit, ok = FALSE ); 50993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ok = ( mDNSu8 ) ( ( count == sizeof( NDIS_PNP_CAPABILITIES ) ) && ( pNPC->Flags & NDIS_DEVICE_WAKE_ON_MAGIC_PACKET_ENABLE ) ); 51003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51013dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinexit: 51023dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51033dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( pNPC != NULL ) 51043dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 51053dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin free( pNPC ); 51063dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 51073dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51083dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( handle != INVALID_HANDLE_VALUE ) 51093dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 51103dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin CloseHandle( handle ); 51113dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 51123dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51133dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelTrace, DEBUG_NAME "IsWOMPEnabledForAdapter returns %s\n", ok ? "true" : "false" ); 51143dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51153dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin return ( mDNSu8 ) ok; 51163dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 51173dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51183dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51193dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlinvoid 51203dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinDispatchSocketEvents( mDNS * const inMDNS ) 51213dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 51223dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin UDPSocket * udpSock; 51233dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin TCPSocket * tcpSock; 51243dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51253dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while ( ( udpSock = ( UDPSocket* ) gUDPDispatchableSockets.Head ) != NULL ) 51263dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 51273dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "%s: calling DispatchUDPEvent on socket %d, error = %d, bytesTransferred = %d\n", 51283dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin __ROUTINE__, udpSock->fd, udpSock->overlapped.error, udpSock->overlapped.bytesTransferred ); 51293dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RemoveFromList( &gUDPDispatchableSockets, udpSock ); 51303dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DispatchUDPEvent( inMDNS, udpSock ); 51313dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 51323dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51333dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin while ( ( tcpSock = ( TCPSocket* ) gTCPDispatchableSockets.Head ) != NULL ) 51343dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 51353dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "%s: calling DispatchTCPEvent on socket %d, error = %d, bytesTransferred = %d\n", 51363dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin __ROUTINE__, tcpSock->fd, tcpSock->overlapped.error, tcpSock->overlapped.bytesTransferred ); 51373dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin RemoveFromList( &gTCPDispatchableSockets, tcpSock ); 51383dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin DispatchTCPEvent( inMDNS, tcpSock ); 51393dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 51403dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 51413dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51423dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51433dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void 51443dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinDispatchUDPEvent( mDNS * const inMDNS, UDPSocket * sock ) 51453dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 51463dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( void ) inMDNS; 51473dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51483dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If we've closed the socket, then we want to ignore 51493dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // this read. The packet might have been queued before 51503dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // the socket was closed. 51513dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51523dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->fd != INVALID_SOCKET ) 51533dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 51543dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin const mDNSInterfaceID iid = sock->ifd ? sock->ifd->interfaceInfo.InterfaceID : NULL; 51553dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSu8 * end = ( (mDNSu8 *) &sock->packet ) + sock->overlapped.bytesTransferred; 51563dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51573dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "calling mDNSCoreReceive on socket: %d\n", sock->fd ); 51583dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin mDNSCoreReceive( sock->m, &sock->packet, end, &sock->overlapped.srcAddr, sock->overlapped.srcPort, &sock->overlapped.dstAddr, sock->overlapped.dstPort, iid ); 51593dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 51603dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51613dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If the socket is still good, then start up another asynchronous read 51623dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51633dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->fd != INVALID_SOCKET ) 51643dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 51653dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int err = UDPBeginRecv( sock ); 51663dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 51673dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 51683dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 51693dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51703dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51713dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinmDNSlocal void 51723dfdc952a3e125868a0a4123e40e1f7fd868af21Casey DahlinDispatchTCPEvent( mDNS * const inMDNS, TCPSocket * sock ) 51733dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin{ 51743dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin ( void ) inMDNS; 51753dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51763dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->fd != INVALID_SOCKET ) 51773dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 51783dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->eptr += sock->overlapped.bytesTransferred; 51793dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->lastError = sock->overlapped.error; 51803dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51813dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !sock->overlapped.error && !sock->overlapped.bytesTransferred ) 51823dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 51833dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->closed = TRUE; 51843dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 51853dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51863dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( sock->readEventHandler != NULL ) 51873dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 51883dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin dlog( kDebugLevelChatty, DEBUG_NAME "calling TCP read handler on socket: %d\n", sock->fd ); 51893dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin sock->readEventHandler( sock ); 51903dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 51913dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 51923dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51933dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin // If the socket is still good, then start up another asynchronous read 51943dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin 51953dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin if ( !sock->closed && ( sock->fd != INVALID_SOCKET ) ) 51963dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin { 51973dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin int err = TCPBeginRecv( sock ); 51983dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin check_noerr( err ); 51993dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin } 52003dfdc952a3e125868a0a4123e40e1f7fd868af21Casey Dahlin} 5201