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 /* 23 * Copyright (c) 2006, 2010, Oracle and/or its affiliates. All rights reserved. 24 */ 25 26 #ifndef _SYS_VIO_MAILBOX_H 27 #define _SYS_VIO_MAILBOX_H 28 29 #ifdef __cplusplus 30 extern "C" { 31 #endif 32 33 #include <sys/ldc.h> 34 35 /* Message types */ 36 #define VIO_TYPE_CTRL 0x1 37 #define VIO_TYPE_DATA 0x2 38 #define VIO_TYPE_ERR 0x4 39 40 /* Message sub-types */ 41 #define VIO_SUBTYPE_INFO 0x1 42 #define VIO_SUBTYPE_ACK 0x2 43 #define VIO_SUBTYPE_NACK 0x4 44 45 /* 46 * VIO specific control envelopes: 0x0000 - 0x00FF 47 * VNET specific control envelopes: 0x0100 - 0x01FF 48 * VDSK specific control envelopes: 0x0200 - 0x02FF 49 * UNUSED envelopes: 0x0300 - 0x0FFF 50 */ 51 52 /* 53 * Generic Control Subtype Envelopes: 54 * type == VIO_TYPE_CTRL 55 * subtype == VIO_SUBTYPE_{INFO|ACK|NACK} 56 * 57 * 0x0000 - 0x003F 58 */ 59 #define VIO_VER_INFO 0x0001 60 #define VIO_ATTR_INFO 0x0002 61 #define VIO_DRING_REG 0x0003 62 #define VIO_DRING_UNREG 0x0004 63 #define VIO_RDX 0x0005 64 #define VIO_DDS_INFO 0x0006 65 66 /* 67 * Generic subtype Data envelopes 68 * type == VIO_TYPE_DATA 69 * subtype == VIO_SUBTYPE_{INFO|ACK|NACK} 70 * 71 * 0x0040 - 0x007F 72 */ 73 #define VIO_PKT_DATA 0x0040 74 #define VIO_DESC_DATA 0x0041 75 #define VIO_DRING_DATA 0x0042 76 77 78 /* 79 * Generic subtype Error envelopes 80 * type == VIO_TYPE_ERR 81 * subtype == VIO_SUBTYPE_{INFO|ACK|NACK} 82 * 83 * 0x0080 - 0x00FF 84 * 85 * Currently unused 86 */ 87 88 /* 89 * Supported Device Types 90 */ 91 #define VDEV_NETWORK 0x1 92 #define VDEV_NETWORK_SWITCH 0x2 93 #define VDEV_DISK 0x3 94 #define VDEV_DISK_SERVER 0x4 95 96 /* 97 * VIO data transfer mode 98 */ 99 #define VIO_PKT_MODE 0x1 100 #define VIO_DESC_MODE 0x2 101 #define VIO_DRING_MODE_V1_0 0x3 102 #define VIO_DRING_MODE_V1_2 0x4 103 104 /* 105 * VIO Descriptor Ring registration options 106 * (intended use for Descriptor Ring) 107 */ 108 #define VIO_TX_DRING 0x1 109 #define VIO_RX_DRING 0x2 110 #define VIO_RX_DRING_DATA 0x4 111 112 /* 113 * Size of message payload 114 */ 115 #define VIO_MSGTAG_SZ (sizeof (vio_msg_tag_t)) /* bytes */ 116 #define VIO_PAYLOAD_SZ (LDC_PAYLOAD_SIZE_UNRELIABLE - VIO_MSGTAG_SZ) 117 #define VIO_PAYLOAD_ELEMS (VIO_PAYLOAD_SZ / LDC_ELEM_SIZE) /* num words */ 118 119 /* 120 * Peer dring processing state. Either actively processing dring 121 * or stopped. 122 */ 123 #define VIO_DP_ACTIVE 1 124 #define VIO_DP_STOPPED 2 125 126 /* 127 * VIO device message tag. 128 * 129 * These 64 bits are used as a common header for all VIO message types. 130 */ 131 typedef union vio_msg_tag { 132 struct { 133 uint8_t _msgtype; 134 uint8_t _subtype; 135 uint16_t _subtype_env; 136 uint32_t _sid; /* session id */ 137 } _hdr; 138 uint64_t tagword; 139 } vio_msg_tag_t; 140 141 #define vio_msgtype _hdr._msgtype 142 #define vio_subtype _hdr._subtype 143 #define vio_subtype_env _hdr._subtype_env 144 #define vio_sid _hdr._sid 145 146 /* 147 * VIO version negotation message. 148 * 149 * tag.msgtype == VIO_TYPE_CTRL 150 * tag.submsgtype = VIO_SUBTYPE_{INFO|ACK|NACK} 151 * tag.subtype_env == VIO_VER_INFO 152 */ 153 154 /* Structure to store a version tuple */ 155 typedef struct vio_ver { 156 uint16_t major; /* major version number */ 157 uint16_t minor; /* minor version number */ 158 } vio_ver_t; 159 160 typedef struct vio_ver_msg { 161 /* Common tag */ 162 vio_msg_tag_t tag; 163 164 /* version specific payload */ 165 uint16_t ver_major; /* major version number */ 166 uint16_t ver_minor; /* minor version number */ 167 168 uint8_t dev_class; /* type of device */ 169 170 /* padding */ 171 uint8_t resv1; 172 uint16_t resv2; 173 uint64_t resv3[VIO_PAYLOAD_ELEMS - 1]; 174 } vio_ver_msg_t; 175 176 /* 177 * VIO Descriptor Ring Register message. 178 * 179 * tag.msgtype == VIO_TYPE_CTRL 180 * tag.submsgtype = VIO_SUBTYPE_{INFO|ACK|NACK} 181 * tag.subtype_env == VIO_DRING_REG 182 */ 183 typedef struct vio_dring_reg_msg { 184 /* Common tag */ 185 vio_msg_tag_t tag; 186 187 /* Descriptor ring information */ 188 uint64_t dring_ident; /* =0 for SUBTYPE_INFO msg */ 189 uint32_t num_descriptors; /* # of desc in the ring */ 190 uint32_t descriptor_size; /* size of each entry */ 191 uint16_t options; /* dring mode */ 192 uint16_t resv; /* padding */ 193 uint32_t ncookies; /* # cookies exporting ring */ 194 195 /* 196 * The rest of the structure is variable in size. The first member that 197 * follows is the descriptor ring cookie(s), that is used in all dring 198 * modes. Following that are the members that are needed only in 199 * RxDringData mode. If the dring mode is not RxDringData and the # of 200 * dring cookies is 1, the message can be sent by LDC without 201 * fragmentation. As dring cookie array is variable in size depending 202 * on ncookies, the subsequent members are defined in a separate 203 * structure vio_dring_reg_msg_ext_t as shown below. 204 */ 205 206 ldc_mem_cookie_t cookie[1]; 207 } vio_dring_reg_msg_t; 208 209 /* 210 * VIO Descriptor Ring Register Extended message; used in RxDringData mode. 211 */ 212 typedef struct vio_dring_reg_extended_msg { 213 uint32_t data_ncookies; /* # of data area cookies */ 214 uint32_t data_area_size; /* size of data area */ 215 216 /* 217 * The data_cookie[] array is variable in size based on data_ncookies. 218 */ 219 ldc_mem_cookie_t data_cookie[1]; /* data cookies */ 220 } vio_dring_reg_ext_msg_t; 221 222 /* 223 * VIO Descriptor Ring Unregister message. 224 * 225 * tag.msgtype == VIO_TYPE_CTRL 226 * tag.submsgtype = VIO_SUBTYPE_{INFO|ACK|NACK} 227 * tag.subtype_env == VIO_DRING_UNREG 228 */ 229 typedef struct vio_dring_unreg_msg { 230 /* Common tag */ 231 vio_msg_tag_t tag; 232 233 /* Descriptor ring information */ 234 uint64_t dring_ident; 235 uint64_t resv[VIO_PAYLOAD_ELEMS - 1]; 236 } vio_dring_unreg_msg_t; 237 238 /* 239 * Definition of a generic VIO message (with no payload) which can be cast 240 * to other message types. 241 */ 242 typedef struct vio_msg { 243 /* Common tag */ 244 vio_msg_tag_t tag; 245 246 /* no payload */ 247 uint64_t resv[VIO_PAYLOAD_ELEMS]; 248 } vio_msg_t; 249 250 /* 251 * VIO Ready to Receive message. 252 * 253 * tag.msgtype == VIO_TYPE_CTRL 254 * tag.submsgtype = VIO_SUBTYPE_{INFO|ACK} 255 * tag.subtype_env == VIO_RDX 256 */ 257 typedef vio_msg_t vio_rdx_msg_t; 258 259 /* 260 * VIO error message. 261 * 262 * tag.msgtype == VIO_TYPE_ERR 263 * tag.subtype == VIO_SUBTYPE_{INFO|ACK|NACK} 264 * tag.subtype_env == TBD 265 */ 266 typedef vio_msg_t vio_err_msg_t; 267 268 /* 269 * VIO descriptor ring data message. 270 * 271 * tag.msgtype == VIO_TYPE_DATA 272 * tag.subtype == VIO_SUBTYPE_{INFO|ACK|NACK} 273 * tag.subtype_env == VIO_DRING_DATA 274 */ 275 typedef struct vio_dring_msg { 276 /* Common message tag */ 277 vio_msg_tag_t tag; 278 279 /* Data dring info */ 280 uint64_t seq_num; 281 uint64_t dring_ident; /* ident of modified DRing */ 282 uint32_t start_idx; /* Indx of first updated elem */ 283 int32_t end_idx; /* Indx of last updated elem */ 284 285 uint8_t dring_process_state; /* Processing state */ 286 287 /* 288 * Padding. 289 */ 290 uint8_t resv1; 291 uint16_t resv2; 292 uint32_t resv3; 293 uint64_t resv4[VIO_PAYLOAD_ELEMS - 4]; 294 } vio_dring_msg_t; 295 296 /* 297 * VIO Common header for inband descriptor messages. 298 * 299 * Clients will then combine this header with a device specific payload. 300 */ 301 typedef struct vio_inband_desc_msg_hdr { 302 /* Common message tag */ 303 vio_msg_tag_t tag; 304 305 uint64_t seq_num; /* sequence number */ 306 uint64_t desc_handle; /* opaque descriptor handle */ 307 } vio_inband_desc_msg_hdr_t; 308 309 /* 310 * VIO raw data message. 311 * 312 * tag.msgtype == VIO_TYPE_DATA 313 * tag.subtype == VIO_SUBTYPE_{INFO|ACK|NACK} 314 * tag.subtype_env == VIO_PKT_DATA 315 * 316 * Note the data payload is so small to keep this message 317 * within the size LDC can cope with without fragmentation. 318 * If it turns out in the future that we are not concerned 319 * with fragmentation then we can increase the size of this 320 * field. 321 */ 322 typedef struct vio_raw_data_msg { 323 /* Common message tag */ 324 vio_msg_tag_t tag; 325 326 /* Raw data packet payload */ 327 uint64_t seq_num; /* sequence number */ 328 uint64_t data[VIO_PAYLOAD_ELEMS - 1]; 329 } vio_raw_data_msg_t; 330 331 #define VIO_PKT_DATA_HDRSIZE \ 332 (sizeof (vio_msg_tag_t) + sizeof (uint64_t)) 333 334 /* 335 * Definitions of the valid states a Descriptor can be in. 336 */ 337 #define VIO_DESC_FREE 0x1 338 #define VIO_DESC_READY 0x2 339 #define VIO_DESC_ACCEPTED 0x3 340 #define VIO_DESC_DONE 0x4 341 #define VIO_DESC_INITIALIZING 0x5 342 #define VIO_DESC_MASK 0xf 343 344 /* Macro to populate the generic fields of the DRing data msg */ 345 #define VIO_INIT_DRING_DATA_TAG(dmsg) \ 346 dmsg.tag.vio_msgtype = VIO_TYPE_DATA; \ 347 dmsg.tag.vio_subtype = VIO_SUBTYPE_INFO; \ 348 dmsg.tag.vio_subtype_env = VIO_DRING_DATA; 349 350 351 #ifdef __cplusplus 352 } 353 #endif 354 355 #endif /* _SYS_VIO_MAILBOX_H */ 356