]> git.proxmox.com Git - mirror_smartmontools-debian.git/blob - os_win32/hostname_win32.cpp
Imported Upstream version 5.42+svn3561
[mirror_smartmontools-debian.git] / os_win32 / hostname_win32.cpp
1 /*
2 * os_win32/hostname_win32.cpp
3 *
4 * Home page of code is: http://smartmontools.sourceforge.net
5 *
6 * Copyright (C) 2004-8 Christian Franke <smartmontools-support@lists.sourceforge.net>
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2, or (at your option)
11 * any later version.
12 *
13 * You should have received a copy of the GNU General Public License
14 * (for example COPYING); if not, write to the Free
15 * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
16 *
17 */
18
19 #include "hostname_win32.h"
20
21 const char * hostname_win32_c_cvsid = "$Id: hostname_win32.cpp,v 1.6 2008/03/04 22:09:48 ballen4705 Exp $" HOSTNAME_WIN32_H_CVSID;
22
23 #define WIN32_LEAN_AND_MEAN
24 #include <windows.h>
25 #include <string.h>
26
27 #ifndef MAX_HOSTNAME_LEN
28
29 // From IPHlpApi.dll:
30
31 #define MAX_HOSTNAME_LEN 132
32 #define MAX_DOMAIN_NAME_LEN 132
33 #define MAX_SCOPE_ID_LEN 260
34
35 typedef struct {
36 char String[4 * 4];
37 } IP_ADDRESS_STRING,
38 *PIP_ADDRESS_STRING, IP_MASK_STRING, *PIP_MASK_STRING;
39
40 typedef struct _IP_ADDR_STRING {
41 struct _IP_ADDR_STRING* Next;
42 IP_ADDRESS_STRING IpAddress;
43 IP_MASK_STRING IpMask;
44 DWORD Context;
45 } IP_ADDR_STRING,
46 *PIP_ADDR_STRING;
47
48 typedef struct {
49 char HostName[MAX_HOSTNAME_LEN];
50 char DomainName[MAX_DOMAIN_NAME_LEN];
51 PIP_ADDR_STRING CurrentDnsServer;
52 IP_ADDR_STRING DnsServerList;
53 UINT NodeType;
54 char ScopeId[MAX_SCOPE_ID_LEN];
55 UINT EnableRouting;
56 UINT EnableProxy;
57 UINT EnableDns;
58 } FIXED_INFO,
59 *PFIXED_INFO;
60
61 DWORD WINAPI GetNetworkParams(PFIXED_INFO info, PULONG size);
62
63 #endif // MAX_HOSTNAME_LEN
64
65
66 // Call GetComputerNameEx() if available (Win2000/XP)
67
68 static BOOL CallGetComputerNameExA(int type, LPSTR name, LPDWORD size)
69 {
70 HINSTANCE hdll;
71 BOOL (WINAPI * GetComputerNameExA_p)(int/*enum COMPUTER_NAME_FORMAT*/, LPSTR, LPDWORD);
72 BOOL ret;
73 if (!(hdll = LoadLibraryA("KERNEL32.DLL")))
74 return FALSE;
75 if (!(GetComputerNameExA_p = (BOOL (WINAPI *)(int, LPSTR, LPDWORD))GetProcAddress(hdll, "GetComputerNameExA")))
76 ret = FALSE;
77 else
78 ret = GetComputerNameExA_p(type, name, size);
79 FreeLibrary(hdll);
80 return ret;
81 }
82
83
84 // Call GetNetworkParams() if available (Win98/ME/2000/XP)
85
86 static DWORD CallGetNetworkParams(PFIXED_INFO info, PULONG size)
87 {
88 HINSTANCE hdll;
89 DWORD (WINAPI * GetNetworkParams_p)(PFIXED_INFO, PULONG);
90 DWORD ret;
91 if (!(hdll = LoadLibraryA("IPHlpApi.dll")))
92 return ERROR_NOT_SUPPORTED;
93 if (!(GetNetworkParams_p = (DWORD (WINAPI *)(PFIXED_INFO, PULONG))GetProcAddress(hdll, "GetNetworkParams")))
94 ret = ERROR_NOT_SUPPORTED;
95 else
96 ret = GetNetworkParams_p(info, size);
97 FreeLibrary(hdll);
98 return ret;
99 }
100
101
102 // Get host/domainname from registry (Win98/ME/NT4/2000/XP)
103
104 static DWORD GetNamesFromRegistry(BOOL domain, char * name, int len)
105 {
106 HKEY hk; DWORD size, type;
107 if (RegOpenKeyExA(HKEY_LOCAL_MACHINE,
108 (GetVersion() & 0x80000000
109 ? "System\\CurrentControlSet\\Services\\VxD\\MSTCP" //Win9x/ME
110 : "System\\CurrentControlSet\\Services\\Tcpip\\Parameters"),
111 0, KEY_READ, &hk) != ERROR_SUCCESS)
112 return 0;
113 size = len-1;
114 if (!(RegQueryValueExA(hk, (!domain?"HostName":"Domain"), 0, &type, (unsigned char *)name, &size) == ERROR_SUCCESS && type == REG_SZ))
115 size = 0;
116 if (size == 0 && domain) {
117 size = len-1;
118 if (!(RegQueryValueExA(hk, "DhcpDomain", 0, &type, (unsigned char *)name, &size) == ERROR_SUCCESS && type == REG_SZ))
119 size = 0;
120 }
121 RegCloseKey(hk);
122 return size;
123 }
124
125
126 static int gethostdomname(int domain, char * name, int len)
127 {
128 DWORD size; FIXED_INFO info;
129
130 // try KERNEL32.dll::GetComputerNameEx()
131 size = len - 1;
132 if (CallGetComputerNameExA((!domain ? 1:2/*ComputerNameDnsHost:Domain*/), name, &size))
133 return 0;
134
135 // try IPHlpApi.dll::GetNetworkParams()
136 size = sizeof(info);
137 if (CallGetNetworkParams(&info, &size) == ERROR_SUCCESS) {
138 strncpy(name, (!domain?info.HostName:info.DomainName), len-1); name[len-1] = 0;
139 return 0;
140 }
141
142 // try registry
143 if (GetNamesFromRegistry(domain, name, len))
144 return 0;
145
146 if (domain)
147 return -1;
148
149 // last resort: get NETBIOS name
150 size = len - 1;
151 if (GetComputerNameA(name, &size))
152 return 0;
153
154 return -1;
155 }
156
157
158 int gethostname(char * name, int len)
159 {
160 return gethostdomname(0, name, len);
161 }
162
163
164 int getdomainname(char * name, int len)
165 {
166 return gethostdomname(1, name, len);
167 }
168
169
170 #ifdef TEST
171
172 #include <stdio.h>
173
174 main()
175 {
176 char name[256];
177 if (gethostname(name, sizeof(name)))
178 strcpy(name, "Error");
179 printf("hostname=\"%s\"\n", name);
180 if (getdomainname(name, sizeof(name)))
181 strcpy(name, "Error");
182 printf("domainname=\"%s\"\n", name);
183 return 0;
184 }
185
186 #endif