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.1.1.1 2012/02/21 16:32:16 misho 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
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>