Authors: David Hammerton <david@transgaming.com>, Peter Hunnisett <peter@transgaming...
[wine.git] / dlls / netapi32 / netapi32.c
blob3b91f736e71327067cf1fdba941298ecac2887da
1 /*
2 * Copyright 2001 Mike McCormack
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2.1 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library; if not, write to the Free Software
16 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 #include "config.h"
21 #include <string.h>
22 #include <stdio.h>
23 #include <fcntl.h>
24 #include <unistd.h>
26 #include "winbase.h"
27 #include "winreg.h"
28 #include "wingdi.h"
29 #include "winuser.h"
30 #include "wine/debug.h"
31 #include "winerror.h"
32 #include "nb30.h"
34 #ifdef HAVE_SYS_FILE_H
35 # include <sys/file.h>
36 #endif
37 #ifdef HAVE_SYS_IOCTL_H
38 # include <sys/ioctl.h>
39 #endif
40 #ifdef HAVE_SYS_SOCKET_H
41 # include <sys/socket.h>
42 #endif
43 #ifdef HAVE_SYS_SOCKIO_H
44 # include <sys/sockio.h>
45 #endif
46 #ifdef HAVE_NET_IF_H
47 # include <net/if.h>
48 #endif
49 #ifdef HAVE_NETINET_IN_H
50 # include <netinet/in.h>
51 #endif
53 #ifdef HAVE_SOCKADDR_SA_LEN
54 # ifndef max
55 # define max(a,b) ((a) > (b) ? (a) : (b))
56 # endif
57 # define ifreq_size(i) max(sizeof(struct ifreq),\
58 sizeof((i).ifr_name)+(i).ifr_addr.sa_len)
59 # else
60 # define ifreq_size(i) sizeof(struct ifreq)
61 # endif /* defined(HAVE_SOCKADDR_SA_LEN) */
63 WINE_DEFAULT_DEBUG_CHANNEL(netbios);
65 HMODULE NETAPI32_hModule = 0;
67 struct NetBiosAdapter
69 int valid;
70 unsigned char address[6];
73 static struct NetBiosAdapter NETBIOS_Adapter[MAX_LANA];
75 # ifdef SIOCGIFHWADDR
76 int get_hw_address(int sd, struct ifreq *ifr, unsigned char *address)
78 if (ioctl(sd, SIOCGIFHWADDR, ifr) < 0)
79 return -1;
80 memcpy(address, (unsigned char *)&ifr->ifr_hwaddr.sa_data, 6);
81 return 0;
83 # else
84 # ifdef SIOCGENADDR
85 int get_hw_address(int sd, struct ifreq *ifr, unsigned char *address)
87 if (ioctl(sd, SIOCGENADDR, ifr) < 0)
88 return -1;
89 memcpy(address, (unsigned char *) ifr->ifr_enaddr, 6);
90 return 0;
92 # else
93 int get_hw_address(int sd, struct ifreq *ifr, unsigned char *address)
95 return -1;
97 # endif /* SIOCGENADDR */
98 # endif /* SIOCGIFHWADDR */
100 static UCHAR NETBIOS_Enum(PNCB ncb)
102 #ifdef HAVE_NET_IF_H
103 int sd;
104 struct ifreq ifr, *ifrp;
105 struct ifconf ifc;
106 unsigned char buf[1024];
107 int i, ofs;
108 #endif
109 LANA_ENUM *lanas = (PLANA_ENUM) ncb->ncb_buffer;
111 TRACE("NCBENUM\n");
113 lanas->length = 0;
115 #ifdef HAVE_NET_IF_H
116 /* BSD 4.4 defines the size of an ifreq to be
117 * max(sizeof(ifreq), sizeof(ifreq.ifr_name)+ifreq.ifr_addr.sa_len
118 * However, under earlier systems, sa_len isn't present, so
119 * the size is just sizeof(struct ifreq)
122 sd = socket(AF_INET, SOCK_DGRAM, IPPROTO_IP);
123 if (sd < 0)
124 return NRC_OPENERROR;
126 memset(buf, 0, sizeof(buf));
127 ifc.ifc_len = sizeof(buf);
128 ifc.ifc_buf = buf;
129 /* get the ifconf interface */
130 if (ioctl (sd, SIOCGIFCONF, (char *)&ifc) < 0)
132 close(sd);
133 return NRC_OPENERROR;
136 /* loop through the interfaces, looking for a valid one */
137 /* n = ifc.ifc_len; */
138 ofs = 0;
139 for (i = 0; i < ifc.ifc_len; i++)
141 unsigned char *a = NETBIOS_Adapter[i].address;
143 ifrp = (struct ifreq *)((char *)ifc.ifc_buf+ofs);
144 strncpy(ifr.ifr_name, ifrp->ifr_name, IFNAMSIZ);
146 /* try to get the address for this interface */
147 if(get_hw_address(sd, &ifr, a)==0)
149 /* make sure it's not blank */
150 /* if (!a[0] && !a[1] && !a[2] && !a[3] && !a[4] && !a[5])
151 continue; */
153 TRACE("Found valid adapter %d at %02x:%02x:%02x:%02x:%02x:%02x\n", i,
154 a[0],a[1],a[2],a[3],a[4],a[5]);
156 NETBIOS_Adapter[i].valid = TRUE;
157 lanas->lana[lanas->length] = i;
158 lanas->length++;
160 ofs += ifreq_size(ifr);
162 close(sd);
163 #endif /* HAVE_NET_IF_H */
164 return NRC_GOODRET;
168 static UCHAR NETBIOS_Astat(PNCB ncb)
170 struct NetBiosAdapter *nad = &NETBIOS_Adapter[ncb->ncb_lana_num];
171 PADAPTER_STATUS astat = (PADAPTER_STATUS) ncb->ncb_buffer;
173 TRACE("NCBASTAT (Adapter %d)\n", ncb->ncb_lana_num);
175 if(!nad->valid)
176 return NRC_INVADDRESS;
178 memset(astat, 0, sizeof astat);
179 memcpy(astat->adapter_address, nad->address, sizeof astat->adapter_address);
181 return NRC_GOODRET;
184 BOOL WINAPI
185 NETAPI32_LibMain (HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
187 TRACE("%x,%lx,%p\n", hinstDLL, fdwReason, lpvReserved);
189 switch (fdwReason) {
190 case DLL_PROCESS_ATTACH:
191 NETAPI32_hModule = hinstDLL;
192 break;
193 case DLL_PROCESS_DETACH:
194 break;
197 return TRUE;
200 BOOL WINAPI Netbios(PNCB pncb)
202 UCHAR ret = NRC_ILLCMD;
204 TRACE("ncb = %p\n",pncb);
206 if(!pncb)
207 return NRC_INVADDRESS;
209 switch(pncb->ncb_command&0x7f)
211 case NCBRESET:
212 FIXME("NCBRESET adapter %d\n",pncb->ncb_lana_num);
213 if( (pncb->ncb_lana_num < MAX_LANA ) &&
214 NETBIOS_Adapter[pncb->ncb_lana_num].valid)
215 ret = NRC_GOODRET;
216 else
217 ret = NRC_ILLCMD; /* NetBIOS emulator not found */
218 break;
220 case NCBADDNAME:
221 FIXME("NCBADDNAME\n");
222 break;
224 case NCBADDGRNAME:
225 FIXME("NCBADDGRNAME\n");
226 break;
228 case NCBDELNAME:
229 FIXME("NCBDELNAME\n");
230 break;
232 case NCBSEND:
233 FIXME("NCBSEND\n");
234 break;
236 case NCBRECV:
237 FIXME("NCBRECV\n");
238 break;
240 case NCBHANGUP:
241 FIXME("NCBHANGUP\n");
242 break;
244 case NCBCANCEL:
245 FIXME("NCBCANCEL\n");
246 break;
248 case NCBLISTEN:
249 FIXME("NCBLISTEN\n");
250 break;
252 case NCBASTAT:
253 ret = NETBIOS_Astat(pncb);
254 break;
256 case NCBENUM:
257 ret = NETBIOS_Enum(pncb);
258 break;
260 default:
261 FIXME("(%p): command code %02x\n", pncb, pncb->ncb_command);
263 ret = NRC_ILLCMD; /* NetBIOS emulator not found */
265 pncb->ncb_retcode = ret;
266 return ret;