1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 /* 22 * Copyright 2010 Sun Microsystems, Inc. All rights reserved. 23 * Use is subject to license terms. 24 */ 25 26 #ifndef _SYS_USB_USBETH_H 27 #define _SYS_USB_USBETH_H 28 29 30 #include <sys/types.h> 31 #include <sys/dditypes.h> 32 #include <sys/mac.h> 33 #include <sys/note.h> 34 35 #ifdef __cplusplus 36 extern "C" { 37 #endif 38 39 typedef struct usbecm_state usbecm_state_t; 40 41 42 /* 43 * PM support 44 */ 45 typedef struct usbecm_power { 46 uint8_t pm_wakeup_enabled; /* remote wakeup enabled */ 47 uint8_t pm_pwr_states; /* bit mask of power states */ 48 boolean_t pm_raise_power; /* driver is about to raise power */ 49 uint8_t pm_cur_power; /* current power level */ 50 uint_t pm_busy_cnt; /* number of set_busy requests */ 51 } usbecm_pm_t; 52 53 struct usbecm_statistics { 54 uint32_t es_upspeed; /* Upstream bit rate, bps */ 55 uint32_t es_downspeed; /* Downstream bit rate, bps */ 56 int es_linkstate; /* link state */ 57 uint64_t es_ipackets; 58 uint64_t es_opackets; 59 uint64_t es_ibytes; 60 uint64_t es_obytes; 61 uint64_t es_ierrors; /* received frames with errors */ 62 uint64_t es_oerrors; /* transmitted frames with errors */ 63 uint64_t es_multircv; /* received multicast frames */ 64 uint64_t es_multixmt; /* transmitted multicast frames */ 65 uint64_t es_brdcstrcv; 66 uint64_t es_brdcstxmt; 67 uint64_t es_macxmt_err; 68 }; 69 70 struct usbecm_ds_ops { 71 /* Device specific initialization and deinitialization */ 72 int (*ecm_ds_init)(usbecm_state_t *); 73 int (*ecm_ds_fini)(usbecm_state_t *); 74 75 int (*ecm_ds_start)(usbecm_state_t *); 76 int (*ecm_ds_stop)(usbecm_state_t *); 77 int (*ecm_ds_unicst)(usbecm_state_t *); 78 int (*ecm_ds_promisc)(usbecm_state_t *); 79 int (*ecm_ds_multicst)(usbecm_state_t *); 80 mblk_t *(*ecm_ds_tx)(usbecm_state_t *, mblk_t *); 81 82 int (*ecm_ds_intr_cb)(usbecm_state_t *, mblk_t *); 83 int (*ecm_ds_bulkin_cb)(usbecm_state_t *, mblk_t *); 84 int (*ecm_ds_bulkout_cb)(usbecm_state_t *, mblk_t *); 85 }; 86 87 /* 88 * per bulk in/out structure 89 */ 90 struct usbecm_state { 91 kmutex_t ecm_mutex; /* structure lock */ 92 dev_info_t *ecm_dip; /* device info */ 93 usb_client_dev_data_t *ecm_dev_data; /* registration data */ 94 usb_pipe_handle_t ecm_def_ph; /* default pipe hdl */ 95 usb_log_handle_t ecm_lh; /* USBA log handle */ 96 int ecm_dev_state; /* USB device state */ 97 size_t ecm_xfer_sz; /* bulk xfer size */ 98 size_t ecm_bulkin_sz; 99 usbecm_pm_t *ecm_pm; /* PM support */ 100 mac_handle_t ecm_mh; /* mac handle */ 101 usb_serialization_t ecm_ser_acc; /* serialization object */ 102 103 uint_t ecm_cfg_index; /* config contains ECM ifc */ 104 uint16_t ecm_ctrl_if_no; 105 uint16_t ecm_data_if_no; 106 uint16_t ecm_data_if_alt; /* non-compatible device */ 107 108 usb_ep_data_t *ecm_intr_ep; 109 usb_ep_data_t *ecm_bulk_in_ep; 110 usb_ep_data_t *ecm_bulk_out_ep; 111 112 boolean_t ecm_compatibility; /* if conform to spec */ 113 usb_cdc_ecm_descr_t ecm_desc; /* if conform to spec */ 114 115 uint8_t ecm_srcaddr[6]; /* source MAC addr */ 116 uint16_t ecm_pkt_flt; /* pkt flt bitmap ECM1.2 T.8 */ 117 118 usb_pipe_handle_t ecm_bulkout_ph; 119 int ecm_bulkout_state; 120 usb_pipe_handle_t ecm_bulkin_ph; 121 int ecm_bulkin_state; 122 usb_pipe_handle_t ecm_intr_ph; 123 int ecm_intr_state; 124 struct usbecm_statistics ecm_stat; 125 uint32_t ecm_init_flags; 126 int ecm_mac_state; 127 mblk_t *ecm_rcv_queue; /* receive queue */ 128 int ecm_tx_cnt; 129 130 void *ecm_priv; /* device private data */ 131 struct usbecm_ds_ops *ecm_ds_ops; 132 }; 133 134 135 _NOTE(MUTEX_PROTECTS_DATA(usbecm_state::ecm_mutex, usbecm_state)) 136 _NOTE(MUTEX_PROTECTS_DATA(usbecm_state::ecm_mutex, usbecm_statistics)) 137 138 _NOTE(DATA_READABLE_WITHOUT_LOCK(usbecm_state::{ 139 ecm_dip 140 ecm_dev_data 141 ecm_def_ph 142 ecm_lh 143 ecm_dev_state 144 ecm_xfer_sz 145 ecm_compatibility 146 ecm_pm 147 ecm_mh 148 ecm_bulkin_ph 149 ecm_bulkout_ph 150 ecm_intr_ph 151 ecm_ser_acc 152 ecm_ctrl_if_no 153 ecm_data_if_no 154 ecm_data_if_alt 155 ecm_desc 156 ecm_bulk_in_ep 157 ecm_intr_ep 158 ecm_bulk_out_ep 159 ecm_bulkin_sz 160 ecm_priv 161 ecm_ds_ops 162 })) 163 164 _NOTE(SCHEME_PROTECTS_DATA("unshared data", mblk_t iocblk)) 165 _NOTE(SCHEME_PROTECTS_DATA("unshared data", usb_bulk_req_t usb_intr_req_t)) 166 167 /* pipe state */ 168 enum { 169 USBECM_PIPE_CLOSED, /* pipe is closed */ 170 USBECM_PIPE_IDLE, /* open but no requests */ 171 USBECM_PIPE_BUSY, /* servicing request */ 172 USBECM_PIPE_CLOSING /* pipe is closing */ 173 }; 174 175 enum { 176 USBECM_MAC_STOPPED = 0, 177 USBECM_MAC_STARTED, 178 }; 179 180 /* various tunables */ 181 enum { 182 USBECM_BULKOUT_TIMEOUT = 15, /* bulkout timeout */ 183 USBECM_BULKIN_TIMEOUT = 0 /* bulkin timeout */ 184 }; 185 186 /* hardware definitions */ 187 enum { 188 USBSACM_REQ_OUT = USB_DEV_REQ_TYPE_CLASS| USB_DEV_REQ_HOST_TO_DEV, 189 USBSACM_REQ_IN = USB_DEV_REQ_TYPE_CLASS | USB_DEV_REQ_DEV_TO_HOST, 190 USBSACM_REQ_WRITE_IF = USBSACM_REQ_OUT | USB_DEV_REQ_RCPT_IF, 191 USBSACM_REQ_READ_IF = USBSACM_REQ_IN | USB_DEV_REQ_RCPT_IF 192 }; 193 194 #define USBECM_INIT_EVENTS (0x01 << 0) 195 #define USBECM_INIT_SER (0x01 << 1) 196 #define USBECM_INIT_MAC (0x01 << 2) 197 198 /* Bit offset for ECM statistics capabilities, CDC ECM Rev 1.2, Table 4 */ 199 #define ECM_XMIT_OK 0 200 #define ECM_RCV_OK 1 201 #define ECM_XMIT_ERROR 2 202 #define ECM_RCV_ERROR 3 203 #define ECM_RCV_NO_BUFFER 4 204 #define ECM_DIRECTED_BYTES_XMIT 5 205 #define ECM_DIRECTED_FRAMES_XMIT 6 206 #define ECM_MULTICAST_BYTES_XMIT 7 207 #define ECM_MULTICAST_FRAMES_XMIT 8 208 #define ECM_BROADCAST_BYTES_XMIT 9 209 #define ECM_BROADCAST_FRAMES_XMIT 10 210 #define ECM_DIRECTED_BYTES_RCV 11 211 #define ECM_DIRECTED_FRAMES_RCV 12 212 #define ECM_MULTICAST_BYTES_RCV 13 213 #define ECM_MULTICAST_FRAMES_RCV 14 214 #define ECM_BROADCAST_BYTES_RCV 15 215 #define ECM_BROADCAST_FRAMES_RCV 16 216 #define ECM_RCV_CRC_ERROR 17 217 #define ECM_TRANSMIT_QUEUE_LENGTH 18 218 #define ECM_RCV_ERROR_ALIGNMENT 19 219 #define ECM_XMIT_ONE_COLLISION 20 220 #define ECM_XMIT_MORE_COLLISIONS 21 221 #define ECM_XMIT_DEFERRED 22 222 #define ECM_XMIT_MAX_COLLISIONS 23 223 #define ECM_RCV_OVERRUN 24 224 #define ECM_XMIT_UNDERRUN 25 225 #define ECM_XMIT_HEARTBEAT_FAILURE 26 226 #define ECM_XMIT_TIMES_CRS_LOST 27 227 #define ECM_XMIT_LATE_COLLISIONS 28 228 229 #define ECM_STAT_CAP_MASK(x) (1UL << (x)) /* Table 4 */ 230 #define ECM_STAT_SELECTOR(x) ((x) + 1) /* Table 9 */ 231 232 /* ECM class-specific request codes, Table 6 */ 233 #define CDC_ECM_SET_ETH_MCAST_FLT 0x40 234 #define CDC_ECM_SET_ETH_PM_FLT 0x41 235 #define CDC_ECM_GET_ETH_PM_FLT 0x42 236 #define CDC_ECM_SET_ETH_PKT_FLT 0x43 237 #define CDC_ECM_GET_ETH_STAT 0x44 238 239 /* ECM Ethernet Pakcet Filter Bitmap, Table 8 */ 240 #define CDC_ECM_PKT_TYPE_PROMISC (1<<0) 241 #define CDC_ECM_PKT_TYPE_ALL_MCAST (1<<1) /* all multicast */ 242 #define CDC_ECM_PKT_TYPE_DIRECTED (1<<2) 243 #define CDC_ECM_PKT_TYPE_BCAST (1<<3) /* broadcast */ 244 #define CDC_ECM_PKT_TYPE_MCAST (1<<4) /* multicast */ 245 246 #define PRINT_MASK_ATTA 0x00000001 247 #define PRINT_MASK_CLOSE 0x00000002 248 #define PRINT_MASK_OPEN 0x00000004 249 #define PRINT_MASK_EVENTS 0x00000008 250 #define PRINT_MASK_PM 0x00000010 251 #define PRINT_MASK_CB 0x00000020 252 #define PRINT_MASK_OPS 0x00000040 253 #define PRINT_MASK_ALL 0xFFFFFFFF 254 255 /* Turn a little endian byte array to a uint32_t */ 256 #define LE_TO_UINT32(src, des) { \ 257 uint32_t tmp; \ 258 des = src[3]; \ 259 des = des << 24; \ 260 tmp = src[2]; \ 261 des |= tmp << 16; \ 262 tmp = src[1]; \ 263 des |= tmp << 8; \ 264 des |= src[0]; \ 265 } 266 267 #define isdigit(c) ((c) >= '0' && c <= '9') 268 #define toupper(C) (((C) >= 'a' && (C) <= 'z')? ((C) - 'a' + 'A'): (C)) 269 270 /* #define NELEM(a) (sizeof (a) / sizeof (*(a))) */ 271 272 273 #ifdef __cplusplus 274 } 275 #endif 276 277 #endif /* _SYS_USB_USBETH_H */ 278