VirtualBox

source: vbox/trunk/src/VBox/HostDrivers/VBoxNetAdp/solaris/VBoxNetAdp-solaris.c@ 18265

Last change on this file since 18265 was 17803, checked in by vboxsync, 16 years ago

Solaris/vboxnetadp: removed unused bits.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id
File size: 15.4 KB
Line 
1/* $Id: VBoxNetAdp-solaris.c 17803 2009-03-13 10:39:08Z vboxsync $ */
2/** @file
3 * VBoxNetAdapter - Network Adapter Driver (Host), Solaris Specific Code.
4 */
5
6/*
7 * Copyright (C) 2009 Sun Microsystems, Inc.
8 *
9 * This file is part of VirtualBox Open Source Edition (OSE), as
10 * available from http://www.virtualbox.org. This file is free software;
11 * you can redistribute it and/or modify it under the terms of the GNU
12 * General Public License (GPL) as published by the Free Software
13 * Foundation, in version 2 as it comes in the "COPYING" file of the
14 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
15 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
16 *
17 * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa
18 * Clara, CA 95054 USA or visit http://www.sun.com if you need
19 * additional information or have any questions.
20 */
21
22/*******************************************************************************
23* Header Files *
24*******************************************************************************/
25#if defined(DEBUG_ramshankar) && !defined(LOG_ENABLED)
26# define LOG_ENABLED
27#endif
28
29#define LOG_GROUP LOG_GROUP_NET_ADP_DRV
30#include <VBox/log.h>
31#include <VBox/err.h>
32#include <VBox/version.h>
33#include <iprt/assert.h>
34#include <iprt/semaphore.h>
35#include <iprt/initterm.h>
36#include <iprt/assert.h>
37#include <iprt/mem.h>
38#include <iprt/rand.h>
39
40#include <sys/types.h>
41#include <sys/dlpi.h>
42#include <sys/types.h>
43#include <sys/param.h>
44#include <sys/stat.h>
45#include <sys/stream.h>
46#include <sys/stropts.h>
47#include <sys/strsun.h>
48#include <sys/modctl.h>
49#include <sys/ddi.h>
50#include <sys/sunddi.h>
51#include <sys/sunldi.h>
52#include <sys/gld.h>
53
54#include "../VBoxNetAdpInternal.h"
55
56/*******************************************************************************
57* Defined Constants And Macros *
58*******************************************************************************/
59#define VBOXSOLQUOTE2(x) #x
60#define VBOXSOLQUOTE(x) VBOXSOLQUOTE2(x)
61#define DEVICE_NAME "vboxnet"
62/** The module descriptions as seen in 'modinfo'. */
63#define DEVICE_DESC_DRV "VirtualBox NetAdp"
64#define VBOXNETADP_MTU 1500
65
66static int VBoxNetAdpSolarisAttach(dev_info_t *pDip, ddi_attach_cmd_t enmCmd);
67static int VBoxNetAdpSolarisDetach(dev_info_t *pDip, ddi_detach_cmd_t enmCmd);
68
69/**
70 * Streams: module info.
71 */
72static struct module_info g_VBoxNetAdpSolarisModInfo =
73{
74 0x0dd, /* module id */
75 DEVICE_NAME,
76 0, /* min. packet size */
77 INFPSZ, /* max. packet size */
78 0, /* hi-water mark */
79 0 /* lo-water mark */
80};
81
82/**
83 * Streams: read queue hooks.
84 */
85static struct qinit g_VBoxNetAdpSolarisReadQ =
86{
87 NULL, /* read */
88 gld_rsrv,
89 gld_open,
90 gld_close,
91 NULL, /* admin (reserved) */
92 &g_VBoxNetAdpSolarisModInfo,
93 NULL /* module stats */
94};
95
96/**
97 * Streams: write queue hooks.
98 */
99static struct qinit g_VBoxNetAdpSolarisWriteQ =
100{
101 gld_wput,
102 gld_wsrv,
103 NULL, /* open */
104 NULL, /* close */
105 NULL, /* admin (reserved) */
106 &g_VBoxNetAdpSolarisModInfo,
107 NULL /* module stats */
108};
109
110/**
111 * Streams: IO stream tab.
112 */
113static struct streamtab g_VBoxNetAdpSolarisStreamTab =
114{
115 &g_VBoxNetAdpSolarisReadQ,
116 &g_VBoxNetAdpSolarisWriteQ,
117 NULL, /* muxread init */
118 NULL /* muxwrite init */
119};
120
121/**
122 * cb_ops: driver char/block entry points
123 */
124static struct cb_ops g_VBoxNetAdpSolarisCbOps =
125{
126 nulldev, /* cb open */
127 nulldev, /* cb close */
128 nodev, /* b strategy */
129 nodev, /* b dump */
130 nodev, /* b print */
131 nodev, /* cb read */
132 nodev, /* cb write */
133 nodev, /* cb ioctl */
134 nodev, /* c devmap */
135 nodev, /* c mmap */
136 nodev, /* c segmap */
137 nochpoll, /* c poll */
138 ddi_prop_op, /* property ops */
139 &g_VBoxNetAdpSolarisStreamTab,
140 D_MP, /* compat. flag */
141 CB_REV /* revision */
142};
143
144/**
145 * dev_ops: driver entry/exit and other ops.
146 */
147static struct dev_ops g_VBoxNetAdpSolarisDevOps =
148{
149 DEVO_REV, /* driver build revision */
150 0, /* ref count */
151 gld_getinfo,
152 nulldev, /* identify */
153 nulldev, /* probe */
154 VBoxNetAdpSolarisAttach,
155 VBoxNetAdpSolarisDetach,
156 nodev, /* reset */
157 &g_VBoxNetAdpSolarisCbOps,
158 (struct bus_ops *)0,
159 nodev /* power */
160};
161
162/**
163 * modldrv: export driver specifics to kernel
164 */
165static struct modldrv g_VBoxNetAdpSolarisDriver =
166{
167 &mod_driverops, /* extern from kernel */
168 DEVICE_DESC_DRV " " VBOX_VERSION_STRING "r" VBOXSOLQUOTE(VBOX_SVN_REV),
169 &g_VBoxNetAdpSolarisDevOps
170};
171
172/**
173 * modlinkage: export install/remove/info to the kernel
174 */
175static struct modlinkage g_VBoxNetAdpSolarisModLinkage =
176{
177 MODREV_1, /* loadable module system revision */
178 &g_VBoxNetAdpSolarisDriver, /* adapter streams driver framework */
179 NULL /* terminate array of linkage structures */
180};
181
182
183/*******************************************************************************
184* Global Variables *
185*******************************************************************************/
186/** The default ethernet broadcast address */
187static uchar_t achBroadcastAddr[] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF };
188
189/**
190 * vboxnetadp_state_t: per-instance data
191 */
192typedef struct vboxnetadp_state_t
193{
194 dev_info_t *pDip; /* device info. */
195 RTMAC FactoryMac; /* default 'factory' MAC address */
196 RTMAC CurrentMac; /* current MAC address */
197} vboxnetadp_state_t;
198
199
200/*******************************************************************************
201* Internal Functions *
202*******************************************************************************/
203static int vboxNetAdpSolarisGenerateMac(PRTMAC pMac);
204static int vboxNetAdpSolarisSetMacAddress(gld_mac_info_t *pMacInfo, unsigned char *pszMacAddr);
205static int vboxNetAdpSolarisSend(gld_mac_info_t *pMacInfo, mblk_t *pMsg);
206static int vboxNetAdpSolarisStub(gld_mac_info_t *pMacInfo);
207static int vboxNetAdpSolarisSetPromisc(gld_mac_info_t *pMacInfo, int fPromisc);
208static int vboxNetAdpSolarisSetMulticast(gld_mac_info_t *pMacInfo, unsigned char *pMulticastAddr, int fMulticast);
209
210
211/**
212 * Kernel entry points
213 */
214int _init(void)
215{
216 LogFlow((DEVICE_NAME ":_init\n"));
217
218 /*
219 * Prevent module autounloading.
220 */
221 modctl_t *pModCtl = mod_getctl(&g_VBoxNetAdpSolarisModLinkage);
222 if (pModCtl)
223 pModCtl->mod_loadflags |= MOD_NOAUTOUNLOAD;
224 else
225 LogRel((DEVICE_NAME ":failed to disable autounloading!\n"));
226
227 /*
228 * Initialize IPRT.
229 */
230 int rc = RTR0Init(0);
231 if (RT_SUCCESS(rc))
232 {
233 rc = mod_install(&g_VBoxNetAdpSolarisModLinkage);
234 if (!rc)
235 return rc;
236
237 LogRel((DEVICE_NAME ":mod_install failed. rc=%d\n", rc));
238 RTR0Term();
239 }
240 else
241 LogRel((DEVICE_NAME ":failed to initialize IPRT (rc=%d)\n", rc));
242
243 return RTErrConvertToErrno(rc);
244}
245
246
247int _fini(void)
248{
249 int rc;
250 LogFlow((DEVICE_NAME ":_fini\n"));
251
252 /*
253 * Undo the work done during start (in reverse order).
254 */
255 RTR0Term();
256
257 return mod_remove(&g_VBoxNetAdpSolarisModLinkage);
258}
259
260
261int _info(struct modinfo *pModInfo)
262{
263 LogFlow((DEVICE_NAME ":_info\n"));
264
265 int rc = mod_info(&g_VBoxNetAdpSolarisModLinkage, pModInfo);
266
267 LogFlow((DEVICE_NAME ":_info returns %d\n", rc));
268 return rc;
269}
270
271
272/**
273 * Attach entry point, to attach a device to the system or resume it.
274 *
275 * @param pDip The module structure instance.
276 * @param enmCmd Operation type (attach/resume).
277 *
278 * @returns corresponding solaris error code.
279 */
280static int VBoxNetAdpSolarisAttach(dev_info_t *pDip, ddi_attach_cmd_t enmCmd)
281{
282 LogFlow((DEVICE_NAME ":VBoxNetAdpSolarisAttach pDip=%p enmCmd=%d\n", pDip, enmCmd));
283
284 int rc = -1;
285 switch (enmCmd)
286 {
287 case DDI_ATTACH:
288 {
289 gld_mac_info_t *pMacInfo = gld_mac_alloc(pDip);
290 if (pMacInfo)
291 {
292 vboxnetadp_state_t *pState = RTMemAllocZ(sizeof(vboxnetadp_state_t));
293 if (pState)
294 {
295 pState->pDip = pDip;
296
297 /*
298 * Setup GLD MAC layer registeration info.
299 */
300 pMacInfo->gldm_reset = vboxNetAdpSolarisStub;
301 pMacInfo->gldm_start = vboxNetAdpSolarisStub;
302 pMacInfo->gldm_stop = vboxNetAdpSolarisStub;
303 pMacInfo->gldm_set_mac_addr = vboxNetAdpSolarisSetMacAddress;
304 pMacInfo->gldm_set_multicast = vboxNetAdpSolarisSetMulticast;
305 pMacInfo->gldm_set_promiscuous = vboxNetAdpSolarisSetPromisc;
306 pMacInfo->gldm_send = vboxNetAdpSolarisSend;
307 pMacInfo->gldm_intr = NULL;
308 pMacInfo->gldm_get_stats = NULL;
309 pMacInfo->gldm_ioctl = NULL;
310 pMacInfo->gldm_ident = DEVICE_NAME;
311 pMacInfo->gldm_type = DL_ETHER;
312 pMacInfo->gldm_minpkt = 0;
313 pMacInfo->gldm_maxpkt = VBOXNETADP_MTU;
314
315 AssertCompile(sizeof(RTMAC) == ETHERADDRL);
316
317 pMacInfo->gldm_addrlen = ETHERADDRL;
318 pMacInfo->gldm_saplen = -2;
319 pMacInfo->gldm_broadcast_addr = achBroadcastAddr;
320 pMacInfo->gldm_ppa = ddi_get_instance(pState->pDip);
321 pMacInfo->gldm_devinfo = pState->pDip;
322 pMacInfo->gldm_private = (caddr_t)pState;
323
324 /*
325 * We use a semi-random MAC addresses similar to a guest NIC's MAC address
326 * as the default factory address of the interface.
327 */
328 rc = vboxNetAdpSolarisGenerateMac(&pState->FactoryMac);
329 if (RT_SUCCESS(rc))
330 {
331 bcopy(&pState->FactoryMac, &pState->CurrentMac, sizeof(RTMAC));
332 pMacInfo->gldm_vendor_addr = (unsigned char *)&pState->FactoryMac;
333
334 /*
335 * Now try registering our GLD with the MAC layer.
336 * Registeration can fail on some S10 versions when the MTU size is more than 1500.
337 * When we implement jumbo frames we should probably retry with MTU 1500 for S10.
338 */
339 rc = gld_register(pDip, (char *)ddi_driver_name(pDip), pMacInfo);
340 if (rc == DDI_SUCCESS)
341 {
342 ddi_report_dev(pDip);
343 return DDI_SUCCESS;
344 }
345 else
346 LogRel((DEVICE_NAME ":VBoxNetAdpSolarisAttach failed to register GLD. rc=%d\n", rc));
347 }
348 else
349 LogRel((DEVICE_NAME ":VBoxNetAdpSolarisAttach failed to generate mac address.rc=%d\n"));
350
351 RTMemFree(pState);
352 }
353 else
354 LogRel((DEVICE_NAME ":VBoxNetAdpSolarisAttach failed to alloc state.\n"));
355
356 gld_mac_free(pMacInfo);
357 }
358 else
359 LogRel((DEVICE_NAME ":VBoxNetAdpSolarisAttach failed to alloc mac structure.\n"));
360 return DDI_FAILURE;
361 }
362
363 case DDI_RESUME:
364 {
365 /* Nothing to do here... */
366 return DDI_SUCCESS;
367 }
368 }
369 return DDI_FAILURE;
370}
371
372
373/**
374 * Detach entry point, to detach a device to the system or suspend it.
375 *
376 * @param pDip The module structure instance.
377 * @param enmCmd Operation type (detach/suspend).
378 *
379 * @returns corresponding solaris error code.
380 */
381static int VBoxNetAdpSolarisDetach(dev_info_t *pDip, ddi_detach_cmd_t enmCmd)
382{
383 LogFlow((DEVICE_NAME ":VBoxNetAdpSolarisDetach pDip=%p enmCmd=%d\n", pDip, enmCmd));
384
385 switch (enmCmd)
386 {
387 case DDI_DETACH:
388 {
389 /*
390 * Unregister and clean up.
391 */
392 gld_mac_info_t *pMacInfo = ddi_get_driver_private(pDip);
393 if (pMacInfo)
394 {
395 vboxnetadp_state_t *pState = (vboxnetadp_state_t *)pMacInfo->gldm_private;
396 if (pState)
397 {
398 int rc = gld_unregister(pMacInfo);
399 if (rc == DDI_SUCCESS)
400 {
401 gld_mac_free(pMacInfo);
402 RTMemFree(pState);
403 return DDI_SUCCESS;
404 }
405 else
406 LogRel((DEVICE_NAME ":VBoxNetAdpSolarisDetach failed to unregister GLD from MAC layer.rc=%d\n", rc));
407 }
408 else
409 LogRel((DEVICE_NAME ":VBoxNetAdpSolarisDetach failed to get internal state.\n"));
410 }
411 else
412 LogRel((DEVICE_NAME ":VBoxNetAdpSolarisDetach failed to get driver private GLD data.\n"));
413
414 return DDI_FAILURE;
415 }
416
417 case DDI_RESUME:
418 {
419 /* Nothing to do here... */
420 return DDI_SUCCESS;
421 }
422 }
423 return DDI_FAILURE;
424}
425
426
427static int vboxNetAdpSolarisGenerateMac(PRTMAC pMac)
428{
429 pMac->au8[0] = 0x00;
430 pMac->au8[1] = 0x08;
431 pMac->au8[2] = 0x27;
432 RTRandBytes(&pMac->au8[3], 3);
433 LogFlow((DEVICE_NAME ":VBoxNetAdpSolarisGenerateMac Generated %.*Rhxs\n", sizeof(RTMAC), &pMac));
434 return VINF_SUCCESS;
435}
436
437
438static int vboxNetAdpSolarisSetMacAddress(gld_mac_info_t *pMacInfo, unsigned char *pszMacAddr)
439{
440 vboxnetadp_state_t *pState = (vboxnetadp_state_t *)pMacInfo->gldm_private;
441 if (pState)
442 {
443 bcopy(pszMacAddr, &pState->CurrentMac, sizeof(RTMAC));
444 LogFlow((DEVICE_NAME ":vboxNetAdpSolarisSetMacAddress updated MAC %.*Rhxs\n", sizeof(RTMAC), &pState->CurrentMac));
445 return GLD_SUCCESS;
446 }
447 else
448 LogRel((DEVICE_NAME ":vboxNetAdpSolarisSetMacAddress failed to get internal state.\n"));
449 return GLD_FAILURE;
450}
451
452
453static int vboxNetAdpSolarisSend(gld_mac_info_t *pMacInfo, mblk_t *pMsg)
454{
455 return GLD_SUCCESS;
456}
457
458
459static int vboxNetAdpSolarisStub(gld_mac_info_t *pMacInfo)
460{
461 return GLD_SUCCESS;
462}
463
464
465static int vboxNetAdpSolarisSetMulticast(gld_mac_info_t *pMacInfo, unsigned char *pMulticastAddr, int fMulticast)
466{
467 return GLD_SUCCESS;
468}
469
470
471static int vboxNetAdpSolarisSetPromisc(gld_mac_info_t *pMacInfo, int fPromisc)
472{
473 /* Host requesting promiscuous intnet connection... */
474 return GLD_SUCCESS;
475}
476
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette