1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
|
/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License (the "License").
* You may not use this file except in compliance with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* or http://www.opensolaris.org/os/licensing.
* See the License for the specific language governing permissions
* and limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
* If applicable, add the following below this CDDL HEADER, with the
* fields enclosed by brackets "[]" replaced with your own identifying
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
/*
* Copyright 2008 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
#ifndef _SYS_SOFTMAC_IMPL_H
#define _SYS_SOFTMAC_IMPL_H
#pragma ident "%Z%%M% %I% %E% SMI"
#include <sys/types.h>
#include <sys/ethernet.h>
#include <sys/taskq.h>
#include <sys/sunddi.h>
#include <sys/sunldi.h>
#include <sys/strsun.h>
#include <sys/stream.h>
#include <sys/dlpi.h>
#include <sys/mac.h>
#include <sys/mac_ether.h>
#ifdef __cplusplus
extern "C" {
#endif
typedef struct softmac_lower_s {
struct softmac *sl_softmac;
queue_t *sl_wq;
/*
* sl_ctl_inprogress is used to serialize the control path. It will
* be set when either an ioctl or an M_{PC,}PROTO message is received
* from the upper layer, and will be cleared when processing done.
*/
kmutex_t sl_ctl_mutex;
kcondvar_t sl_ctl_cv;
boolean_t sl_ctl_inprogress;
/*
* When a control message is processed, either sl_pending_prim or
* sl_pending_ioctl will be set. They will be cleared when the
* acknowledgement of the specific control message is received
* from the underlying legacy driver.
*/
kmutex_t sl_mutex;
kcondvar_t sl_cv;
t_uscalar_t sl_pending_prim;
boolean_t sl_pending_ioctl;
mblk_t *sl_ack_mp;
mac_resource_handle_t sl_handle;
ldi_handle_t sl_lh;
} softmac_lower_t;
enum softmac_state {
SOFTMAC_INITIALIZED,
SOFTMAC_READY
};
typedef struct softmac_dev_s {
dev_t sd_dev;
} softmac_dev_t;
/*
* smac_flag values.
*/
#define SOFTMAC_GLDV3 0x01
#define SOFTMAC_NOSUPP 0x02
#define SOFTMAC_ATTACH_DONE 0x04
#define SOFTMAC_NEED_RECREATE 0x08
/*
* The softmac structure allows all minor nodes (at most two, style-1 and
* style-2) for the same device to be processed. A softmac_dev_t will be
* created for each minor node.
*
* We try to "register" the mac after all the softmac_dev_t's are processed so
* that even if DLPI operations fail (because of driver bugs) for one minor
* node, the other minor node can still be used to register the mac.
* (Specifically, an incorrect xxx_getinfo() implementation will cause style-2
* minor node mac registration to fail.)
*/
typedef struct softmac {
/*
* The following fields will be set when the softmac is created and
* will not change. No lock is required.
*/
char smac_devname[MAXNAMELEN];
major_t smac_umajor;
int smac_uppa;
uint32_t smac_cnt; /* # of minor nodes for this device */
/*
* The following fields are protected by softmac_hash_lock.
*/
/*
* The smac_hold_cnt field increases when softmac_hold_device() is
* called to force the dls_vlan_t of the device to be created. The
* device pre-detach fails if this counter is not 0.
*/
uint32_t smac_hold_cnt;
/*
* The following fields are protected by smac_lock.
*/
kmutex_t smac_mutex;
kcondvar_t smac_cv;
uint32_t smac_flags;
int smac_attacherr;
mac_handle_t smac_mh;
softmac_dev_t *smac_softmac[2];
taskqid_t smac_taskq;
/*
* Number of minor nodes whose post-attach routine has succeeded.
* This should be the same as the numbers of softmac_dev_t.
* Note that it does not imply SOFTMAC_ATTACH_DONE as the taskq might
* be still ongoing.
*/
uint32_t smac_attachok_cnt;
/*
* Number of softmac_dev_t left when pre-detach fails. This is used
* to indicate whether postattach is called because of a failed
* pre-detach.
*/
uint32_t smac_attached_left;
/*
* The remaining fields are used to register the MAC for a legacy
* device. They are set in softmac_mac_register() and do not change.
* One can access them when mac_register() is done without locks.
*/
/*
* media type is needed for create <link name, linkid> mapping, so
* it is set for GLDv3 device as well
*/
uint_t smac_media;
/* DLPI style of the underlying device */
int smac_style;
dev_t smac_dev;
size_t smac_saplen;
size_t smac_addrlen;
uchar_t smac_unicst_addr[MAXMACADDRLEN];
uint_t smac_min_sdu;
uint_t smac_max_sdu;
uint32_t smac_margin;
/* Notifications the underlying driver can support. */
uint32_t smac_notifications;
/*
* Capabilities of the underlying driver.
*/
uint32_t smac_capab_flags;
uint32_t smac_hcksum_txflags;
boolean_t smac_no_capability_req;
dl_capab_mdt_t smac_mdt_capab;
boolean_t smac_mdt;
/*
* The following fields are protected by smac_lock
*/
krwlock_t smac_lock;
enum softmac_state smac_state;
/* Lower stream structure */
softmac_lower_t *smac_lower;
} softmac_t;
typedef struct smac_ioc_start_s {
softmac_lower_t *si_slp;
} smac_ioc_start_t;
#define SMAC_IOC ('S' << 24 | 'M' << 16 | 'C' << 8)
#define SMAC_IOC_START (SMAC_IOC | 0x01)
#define SOFTMAC_BLANK_TICKS 128
#define SOFTMAC_BLANK_PKT_COUNT 8
extern dev_info_t *softmac_dip;
#define SOFTMAC_DEV_NAME "softmac"
extern int softmac_send_bind_req(softmac_lower_t *, uint_t);
extern int softmac_send_notify_req(softmac_lower_t *, uint32_t);
extern int softmac_send_promisc_req(softmac_lower_t *, t_uscalar_t,
boolean_t);
extern void softmac_init(void);
extern void softmac_fini(void);
extern boolean_t softmac_busy(void);
extern int softmac_fill_capab(ldi_handle_t, softmac_t *);
extern int softmac_capab_enable(softmac_lower_t *);
extern void softmac_rput_process_notdata(queue_t *, mblk_t *);
extern void softmac_rput_process_data(softmac_lower_t *, mblk_t *);
extern int softmac_m_promisc(void *, boolean_t);
extern int softmac_m_multicst(void *, boolean_t, const uint8_t *);
extern int softmac_m_unicst(void *, const uint8_t *);
extern void softmac_m_ioctl(void *, queue_t *, mblk_t *);
extern int softmac_m_stat(void *, uint_t, uint64_t *);
extern mblk_t *softmac_m_tx(void *, mblk_t *);
extern void softmac_m_resources(void *);
extern int softmac_proto_tx(softmac_lower_t *, mblk_t *, mblk_t **);
extern void softmac_ioctl_tx(softmac_lower_t *, mblk_t *, mblk_t **);
#ifdef __cplusplus
}
#endif
#endif /* _SYS_SOFTMAC_IMPL_H */
|