staging: visorchipset driver to provide registration and other services
[deliverable/linux.git] / drivers / staging / unisys / common-spar / include / channels / iochannel.h
1 /* Copyright © 2010 - 2013 UNISYS CORPORATION */
2 /* All rights reserved. */
3 #ifndef __IOCHANNEL_H__
4 #define __IOCHANNEL_H__
5
6 /*
7 * Everything needed for IOPart-GuestPart communication is define in
8 * this file. Note: Everything is OS-independent because this file is
9 * used by Windows, Linux and possible EFI drivers. */
10
11
12 /*
13 * Communication flow between the IOPart and GuestPart uses the channel headers
14 * channel state. The following states are currently being used:
15 * UNINIT(All Zeroes), CHANNEL_ATTACHING, CHANNEL_ATTACHED, CHANNEL_OPENED
16 *
17 * additional states will be used later. No locking is needed to switch between
18 * states due to the following rules:
19 *
20 * 1. IOPart is only the only partition allowed to change from UNIT
21 * 2. IOPart is only the only partition allowed to change from
22 * CHANNEL_ATTACHING
23 * 3. GuestPart is only the only partition allowed to change from
24 * CHANNEL_ATTACHED
25 *
26 * The state changes are the following: IOPart sees the channel is in UNINIT,
27 * UNINIT -> CHANNEL_ATTACHING (performed only by IOPart)
28 * CHANNEL_ATTACHING -> CHANNEL_ATTACHED (performed only by IOPart)
29 * CHANNEL_ATTACHED -> CHANNEL_OPENED (performed only by GuestPart)
30 */
31
32 #include "commontypes.h"
33 #include "vmcallinterface.h"
34
35 #define _ULTRA_CONTROLVM_CHANNEL_INLINE_
36 #include "controlvmchannel.h"
37 #include "vbuschannel.h"
38 #undef _ULTRA_CONTROLVM_CHANNEL_INLINE_
39 #include "channel.h"
40
41 /*
42 * CHANNEL Guids
43 */
44
45 #include "channel_guid.h"
46
47 #define ULTRA_VHBA_CHANNEL_PROTOCOL_SIGNATURE ULTRA_CHANNEL_PROTOCOL_SIGNATURE
48 #define ULTRA_VNIC_CHANNEL_PROTOCOL_SIGNATURE ULTRA_CHANNEL_PROTOCOL_SIGNATURE
49 #define ULTRA_VSWITCH_CHANNEL_PROTOCOL_SIGNATURE \
50 ULTRA_CHANNEL_PROTOCOL_SIGNATURE
51
52 /* Must increment these whenever you insert or delete fields within this channel
53 * struct. Also increment whenever you change the meaning of fields within this
54 * channel struct so as to break pre-existing software. Note that you can
55 * usually add fields to the END of the channel struct withOUT needing to
56 * increment this. */
57 #define ULTRA_VHBA_CHANNEL_PROTOCOL_VERSIONID 2
58 #define ULTRA_VNIC_CHANNEL_PROTOCOL_VERSIONID 2
59 #define ULTRA_VSWITCH_CHANNEL_PROTOCOL_VERSIONID 1
60
61 #define ULTRA_VHBA_CHANNEL_OK_CLIENT(pChannel, logCtx) \
62 (ULTRA_check_channel_client(pChannel, UltraVhbaChannelProtocolGuid, \
63 "vhba", MIN_IO_CHANNEL_SIZE, \
64 ULTRA_VHBA_CHANNEL_PROTOCOL_VERSIONID, \
65 ULTRA_VHBA_CHANNEL_PROTOCOL_SIGNATURE, \
66 __FILE__, __LINE__, logCtx))
67 #define ULTRA_VHBA_CHANNEL_OK_SERVER(actualBytes, logCtx) \
68 (ULTRA_check_channel_server(UltraVhbaChannelProtocolGuid, \
69 "vhba", MIN_IO_CHANNEL_SIZE, actualBytes, \
70 __FILE__, __LINE__, logCtx))
71 #define ULTRA_VNIC_CHANNEL_OK_CLIENT(pChannel, logCtx) \
72 (ULTRA_check_channel_client(pChannel, UltraVnicChannelProtocolGuid, \
73 "vnic", MIN_IO_CHANNEL_SIZE, \
74 ULTRA_VNIC_CHANNEL_PROTOCOL_VERSIONID, \
75 ULTRA_VNIC_CHANNEL_PROTOCOL_SIGNATURE, \
76 __FILE__, __LINE__, logCtx))
77 #define ULTRA_VNIC_CHANNEL_OK_SERVER(actualBytes, logCtx) \
78 (ULTRA_check_channel_server(UltraVnicChannelProtocolGuid, \
79 "vnic", MIN_IO_CHANNEL_SIZE, actualBytes, \
80 __FILE__, __LINE__, logCtx))
81 #define ULTRA_VSWITCH_CHANNEL_OK_CLIENT(pChannel, logCtx) \
82 (ULTRA_check_channel_client(pChannel, UltraVswitchChannelProtocolGuid, \
83 "vswitch", MIN_IO_CHANNEL_SIZE, \
84 ULTRA_VSWITCH_CHANNEL_PROTOCOL_VERSIONID, \
85 ULTRA_VSWITCH_CHANNEL_PROTOCOL_SIGNATURE, \
86 __FILE__, __LINE__, logCtx))
87 #define ULTRA_VSWITCH_CHANNEL_OK_SERVER(actualBytes, logCtx) \
88 (ULTRA_check_channel_server(UltraVswitchChannelProtocolGuid, \
89 "vswitch", MIN_IO_CHANNEL_SIZE, \
90 actualBytes, \
91 __FILE__, __LINE__, logCtx))
92 /*
93 * Everything necessary to handle SCSI & NIC traffic between Guest Partition and
94 * IO Partition is defined below. */
95
96
97 /*
98 * Defines and enums.
99 */
100
101 #define MINNUM(a, b) (((a) < (b)) ? (a) : (b))
102 #define MAXNUM(a, b) (((a) > (b)) ? (a) : (b))
103
104 /* these define the two queues per data channel between iopart and
105 * ioguestparts */
106 #define IOCHAN_TO_IOPART 0 /* used by ioguestpart to 'insert' signals to
107 * iopart */
108 #define IOCHAN_FROM_GUESTPART 0 /* used by iopart to 'remove' signals from
109 * ioguestpart - same queue as previous queue */
110
111 #define IOCHAN_TO_GUESTPART 1 /* used by iopart to 'insert' signals to
112 * ioguestpart */
113 #define IOCHAN_FROM_IOPART 1 /* used by ioguestpart to 'remove' signals from
114 * iopart - same queue as previous queue */
115
116 /* these define the two queues per control channel between controlpart and "its"
117 * guests, which includes the iopart */
118 #define CTRLCHAN_TO_CTRLGUESTPART 0 /* used by ctrlguestpart to 'insert' signals
119 * to ctrlpart */
120 #define CTLRCHAN_FROM_CTRLPART 0 /* used by ctrlpart to 'remove' signals from
121 * ctrlquestpart - same queue as previous
122 * queue */
123
124 #define CTRLCHAN_TO_CTRLPART 1 /* used by ctrlpart to 'insert' signals to
125 * ctrlguestpart */
126 #define CTRLCHAN_FROM_CTRLGUESTPART 1 /* used by ctrguestpart to 'remove'
127 * signals from ctrlpart - same queue as
128 * previous queue */
129
130 /* these define the Event & Ack queues per control channel Events are generated
131 * by CTRLGUESTPART and sent to CTRLPART; Acks are generated by CTRLPART and sent
132 * to CTRLGUESTPART. */
133 #define CTRLCHAN_EVENT_TO_CTRLPART 2 /* used by ctrlguestpart to 'insert' Events
134 * to ctrlpart */
135 #define CTRLCHAN_EVENT_FROM_CTRLGUESTPART 2 /* used by ctrlpart to 'remove'
136 * Events from ctrlguestpart */
137
138 #define CTRLCHAN_ACK_TO_CTRLGUESTPART 3 /* used by ctrlpart to 'insert' Acks to
139 * ctrlguestpart */
140 #define CTRLCHAN_ACK_FROM_CTRLPART 3 /* used by ctrlguestpart to 'remove' Events
141 * from ctrlpart */
142
143 /* size of cdb - i.e., scsi cmnd */
144 #define MAX_CMND_SIZE 16
145 enum dma_data_dir {
146 DMA_DIR_BIDIR = 0,
147 DMA_DIR_TO_DEV,
148 DMA_DIR_FROM_DEV,
149 DMA_DIR_NONE
150 };
151
152 #define MAX_SENSE_SIZE 64
153
154 #define MAX_PHYS_INFO 64
155
156 /* Because GuestToGuestCopy is limited to 4KiB segments, and we have limited the
157 * Emulex Driver to 256 scatter list segments via the lpfc_sg_seg_cnt parameter
158 * to 256, the maximum I/O size is limited to 256 * 4 KiB = 1 MB */
159 #define MAX_IO_SIZE (1024*1024) /* 1 MB */
160
161 /* NOTE 1: lpfc defines its support for segments in
162 * #define LPFC_SG_SEG_CNT 64
163 *
164 * NOTE 2: In Linux, frags array in skb is currently allocated to be
165 * MAX_SKB_FRAGS size, which is 18 which is smaller than MAX_PHYS_INFO for
166 * now. */
167
168 #ifndef MAX_SERIAL_NUM
169 #define MAX_SERIAL_NUM 32
170 #endif /* MAX_SERIAL_NUM */
171
172 #define MAX_SCSI_BUSES 1
173 #define MAX_SCSI_TARGETS 8
174 #define MAX_SCSI_LUNS 16
175 #define MAX_SCSI_FROM_HOST 0xFFFFFFFF /* Indicator to use Physical HBA
176 * SCSI Host value */
177
178 /* various types of network packets that can be sent in cmdrsp */
179 typedef enum { NET_RCV_POST = 0, /* submit buffer to hold receiving
180 * incoming packet */
181 /* virtnic -> uisnic */
182 NET_RCV, /* incoming packet received */
183 /* uisnic -> virtpci */
184 NET_XMIT, /* for outgoing net packets */
185 /* virtnic -> uisnic */
186 NET_XMIT_DONE, /* outgoing packet xmitted */
187 /* uisnic -> virtpci */
188 NET_RCV_ENBDIS, /* enable/disable packet reception */
189 /* virtnic -> uisnic */
190 NET_RCV_ENBDIS_ACK, /* acknowledge enable/disable packet
191 * reception */
192 /* uisnic -> virtnic */
193 NET_RCV_PROMISC, /* enable/disable promiscuous mode */
194 /* virtnic -> uisnic */
195 NET_CONNECT_STATUS, /* indicate the loss or restoration of a network
196 * connection */
197 /* uisnic -> virtnic */
198 NET_MACADDR, /* indicates the client has requested to update
199 * its MAC addr */
200 NET_MACADDR_ACK, /* Mac addres */
201
202 } NET_TYPES;
203
204 #define ETH_HEADER_SIZE 14 /* size of ethernet header */
205
206 #define ETH_MIN_DATA_SIZE 46 /* minimum eth data size */
207 #define ETH_MIN_PACKET_SIZE (ETH_HEADER_SIZE + ETH_MIN_DATA_SIZE)
208
209 #define ETH_DEF_DATA_SIZE 1500 /* default data size */
210 #define ETH_DEF_PACKET_SIZE (ETH_HEADER_SIZE + ETH_DEF_DATA_SIZE)
211
212 #define ETH_MAX_MTU 16384 /* maximum data size */
213
214 #ifndef MAX_MACADDR_LEN
215 #define MAX_MACADDR_LEN 6 /* number of bytes in MAC address */
216 #endif /* MAX_MACADDR_LEN */
217
218 #define ETH_IS_LOCALLY_ADMINISTERED(Address) \
219 (((U8 *) (Address))[0] & ((U8) 0x02))
220 #define NIC_VENDOR_ID 0x0008000B
221
222 /* various types of scsi task mgmt commands */
223 typedef enum { TASK_MGMT_ABORT_TASK =
224 1, TASK_MGMT_BUS_RESET, TASK_MGMT_LUN_RESET,
225 TASK_MGMT_TARGET_RESET,
226 } TASK_MGMT_TYPES;
227
228 /* various types of vdisk mgmt commands */
229 typedef enum { VDISK_MGMT_ACQUIRE = 1, VDISK_MGMT_RELEASE,
230 } VDISK_MGMT_TYPES;
231
232 /* this is used in the vdest field */
233 #define VDEST_ALL 0xFFFF
234
235 #define MIN_NUMSIGNALS 64
236 #define MAX_NUMSIGNALS 4096
237
238 /* MAX_NET_RCV_BUF specifies the number of rcv buffers that are created by each
239 * guest's virtnic and posted to uisnic. Uisnic, for each channel, keeps the rcv
240 * buffers posted and uses them to receive data on behalf of the guest's virtnic.
241 * NOTE: the num_rcv_bufs is configurable for each VNIC. So the following is
242 * simply an upperlimit on what each VNIC can provide. Setting it to half of the
243 * NUMSIGNALS to prevent queue full deadlocks */
244 #define MAX_NET_RCV_BUFS (MIN_NUMSIGNALS / 2)
245
246 /*
247 * structs with pragma pack */
248
249
250 /* ///////////// BEGIN PRAGMA PACK PUSH 1 ///////////////////////// */
251 /* ///////////// ONLY STRUCT TYPE SHOULD BE BELOW */
252
253 #pragma pack(push, 1)
254
255 struct guest_phys_info {
256 U64 address;
257 U64 length;
258 };
259
260 #define GPI_ENTRIES_PER_PAGE (PAGE_SIZE / sizeof(struct guest_phys_info))
261
262 struct uisscsi_dest {
263 U32 channel; /* channel == bus number */
264 U32 id; /* id == target number */
265 U32 lun; /* lun == logical unit number */
266 };
267
268 struct vhba_wwnn {
269 U32 wwnn1;
270 U32 wwnn2;
271 };
272
273 /* WARNING: Values stired in this structure must contain maximum counts (not
274 * maximum values). */
275 struct vhba_config_max { /* 20 bytes */
276 U32 max_channel; /* maximum channel for devices attached to this
277 * bus */
278 U32 max_id; /* maximum SCSI ID for devices attached to this
279 * bus */
280 U32 max_lun; /* maximum SCSI LUN for devices attached to this
281 * bus */
282 U32 cmd_per_lun; /* maximum number of outstanding commands per
283 * lun that are allowed at one time */
284 U32 max_io_size; /* maximum io size for devices attached to this
285 * bus */
286 /* max io size is often determined by the resource of the hba. e.g */
287 /* max scatter gather list length * page size / sector size */
288 };
289
290 struct uiscmdrsp_scsi {
291 void *scsicmd; /* the handle to the cmd that was received -
292 * send it back as is in the rsp packet. */
293 U8 cmnd[MAX_CMND_SIZE]; /* the cdb for the command */
294 U32 bufflen; /* length of data to be transferred out or in */
295 U16 guest_phys_entries; /* Number of entries in scatter-gather (sg)
296 * list */
297 struct guest_phys_info gpi_list[MAX_PHYS_INFO]; /* physical address
298 * information for each
299 * fragment */
300 enum dma_data_dir data_dir; /* direction of the data, if any */
301 struct uisscsi_dest vdest; /* identifies the virtual hba, id,
302 * channel, lun to which cmd was sent */
303
304 /* the following fields are needed to queue the rsp back to cmd
305 * originator */
306 int linuxstat; /* the original Linux status - for use by linux
307 * vdisk code */
308 U8 scsistat; /* the scsi status */
309 U8 addlstat; /* non-scsi status - covers cases like timeout
310 * needed by windows guests */
311 #define ADDL_RESET 1
312 #define ADDL_TIMEOUT 2
313 #define ADDL_INTERNAL_ERROR 3
314 #define ADDL_SEL_TIMEOUT 4
315 #define ADDL_CMD_TIMEOUT 5
316 #define ADDL_BAD_TARGET 6
317 #define ADDL_RETRY 7
318
319 /* the following fields are need to determine the result of command */
320 U8 sensebuf[MAX_SENSE_SIZE]; /* sense info in case cmd failed; */
321 /* it holds the sense_data struct; */
322 /* see that struct for details. */
323 void *vdisk; /* contains pointer to the vdisk so that we can clean up
324 * when the IO completes. */
325 int no_disk_result; /* used to return no disk inquiry result */
326 /* when no_disk_result is set to 1, */
327 /* scsi.scsistat is SAM_STAT_GOOD */
328 /* scsi.addlstat is 0 */
329 /* scsi.linuxstat is SAM_STAT_GOOD */
330 /* That is, there is NO error. */
331 };
332
333 /*
334 * Defines to support sending correct inquiry result when no disk is
335 * configured. */
336
337 /* From SCSI SPC2 -
338 *
339 * If the target is not capable of supporting a device on this logical unit, the
340 * device server shall set this field to 7Fh (PERIPHERAL QUALIFIER set to 011b
341 * and PERIPHERAL DEVICE TYPE set to 1Fh).
342 *
343 *The device server is capable of supporting the specified peripheral device
344 *type on this logical unit. However, the physical device is not currently
345 *connected to this logical unit.
346 */
347
348 #define DEV_NOT_PRESENT 0x7f /* old name - compatibility */
349 #define DEV_NOT_CAPABLE 0x7f /* peripheral qualifier of 0x3 */
350 /* peripheral type of 0x1f */
351 /* specifies no device but target present */
352
353 #define DEV_DISK_CAPABLE_NOT_PRESENT 0x20 /* peripheral qualifier of 0x1 */
354 /* peripheral type of 0 - disk */
355 /* specifies device capable, but not present */
356
357 #define DEV_PROC_CAPABLE_NOT_PRESENT 0x23 /* peripheral qualifier of 0x1 */
358 /* peripheral type of 3 - processor */
359 /* specifies device capable, but not present */
360
361 #define DEV_HISUPPORT 0x10; /* HiSup = 1; shows support for report luns */
362 /* must be returned for lun 0. */
363
364 /* NOTE: Linux code assumes inquiry contains 36 bytes. Without checking length
365 * in buf[4] some linux code accesses bytes beyond 5 to retrieve vendor, product
366 * & revision. Yikes! So let us always send back 36 bytes, the minimum for
367 * inquiry result. */
368 #define NO_DISK_INQUIRY_RESULT_LEN 36
369
370 #define MIN_INQUIRY_RESULT_LEN 5 /* we need at least 5 bytes minimum for inquiry
371 * result */
372
373 /* SCSI device version for no disk inquiry result */
374 #define SCSI_SPC2_VER 4 /* indicates SCSI SPC2 (SPC3 is 5) */
375
376 /* Windows and Linux want different things for a non-existent lun. So, we'll let
377 * caller pass in the peripheral qualifier and type.
378 * NOTE:[4] SCSI returns (n-4); so we return length-1-4 or length-5. */
379
380 #define SET_NO_DISK_INQUIRY_RESULT(buf, len, lun, lun0notpresent, notpresent) \
381 do { \
382 MEMSET(buf, 0, \
383 MINNUM(len, \
384 (unsigned int) NO_DISK_INQUIRY_RESULT_LEN)); \
385 buf[2] = (U8) SCSI_SPC2_VER; \
386 if (lun == 0) { \
387 buf[0] = (U8) lun0notpresent; \
388 buf[3] = (U8) DEV_HISUPPORT; \
389 } else \
390 buf[0] = (U8) notpresent; \
391 buf[4] = (U8) ( \
392 MINNUM(len, \
393 (unsigned int) NO_DISK_INQUIRY_RESULT_LEN) - 5); \
394 if (len >= NO_DISK_INQUIRY_RESULT_LEN) { \
395 buf[8] = 'D'; \
396 buf[9] = 'E'; \
397 buf[10] = 'L'; \
398 buf[11] = 'L'; \
399 buf[16] = 'P'; \
400 buf[17] = 'S'; \
401 buf[18] = 'E'; \
402 buf[19] = 'U'; \
403 buf[20] = 'D'; \
404 buf[21] = 'O'; \
405 buf[22] = ' '; \
406 buf[23] = 'D'; \
407 buf[24] = 'E'; \
408 buf[25] = 'V'; \
409 buf[26] = 'I'; \
410 buf[27] = 'C'; \
411 buf[28] = 'E'; \
412 buf[30] = ' '; \
413 buf[31] = '.'; \
414 } \
415 } while (0)
416
417
418 /*
419 * Struct & Defines to support sense information.
420 */
421
422
423 /* The following struct is returned in sensebuf field in uiscmdrsp_scsi. It is
424 * initialized in exactly the manner that is recommended in Windows (hence the
425 * odd values).
426 * When set, these fields will have the following values:
427 * ErrorCode = 0x70 indicates current error
428 * Valid = 1 indicates sense info is valid
429 * SenseKey contains sense key as defined by SCSI specs.
430 * AdditionalSenseCode contains sense key as defined by SCSI specs.
431 * AdditionalSenseCodeQualifier contains qualifier to sense code as defined by
432 * scsi docs.
433 * AdditionalSenseLength contains will be sizeof(sense_data)-8=10.
434 */
435 struct sense_data {
436 U8 ErrorCode:7;
437 U8 Valid:1;
438 U8 SegmentNumber;
439 U8 SenseKey:4;
440 U8 Reserved:1;
441 U8 IncorrectLength:1;
442 U8 EndOfMedia:1;
443 U8 FileMark:1;
444 U8 Information[4];
445 U8 AdditionalSenseLength;
446 U8 CommandSpecificInformation[4];
447 U8 AdditionalSenseCode;
448 U8 AdditionalSenseCodeQualifier;
449 U8 FieldReplaceableUnitCode;
450 U8 SenseKeySpecific[3];
451 };
452
453 /* some SCSI ADSENSE codes */
454 #ifndef SCSI_ADSENSE_LUN_NOT_READY
455 #define SCSI_ADSENSE_LUN_NOT_READY 0x04
456 #endif /* */
457 #ifndef SCSI_ADSENSE_ILLEGAL_COMMAND
458 #define SCSI_ADSENSE_ILLEGAL_COMMAND 0x20
459 #endif /* */
460 #ifndef SCSI_ADSENSE_ILLEGAL_BLOCK
461 #endif /* */
462 #ifndef SCSI_ADSENSE_ILLEGAL_BLOCK
463 #define SCSI_ADSENSE_ILLEGAL_BLOCK 0x21
464 #endif /* */
465 #ifndef SCSI_ADSENSE_INVALID_CDB
466 #define SCSI_ADSENSE_INVALID_CDB 0x24
467 #endif /* */
468 #ifndef SCSI_ADSENSE_INVALID_LUN
469 #define SCSI_ADSENSE_INVALID_LUN 0x25
470 #endif /* */
471 #ifndef SCSI_ADWRITE_PROTECT
472 #define SCSI_ADWRITE_PROTECT 0x27
473 #endif /* */
474 #ifndef SCSI_ADSENSE_MEDIUM_CHANGED
475 #define SCSI_ADSENSE_MEDIUM_CHANGED 0x28
476 #endif /* */
477 #ifndef SCSI_ADSENSE_BUS_RESET
478 #define SCSI_ADSENSE_BUS_RESET 0x29
479 #endif /* */
480 #ifndef SCSI_ADSENSE_NO_MEDIA_IN_DEVICE
481 #define SCSI_ADSENSE_NO_MEDIA_IN_DEVICE 0x3a
482 #endif /* */
483
484 struct net_pkt_xmt {
485 int len; /* full length of data in the packet */
486 int num_frags; /* number of fragments in frags containing data */
487 struct phys_info frags[MAX_PHYS_INFO]; /* physical page information for
488 * each fragment */
489 char ethhdr[ETH_HEADER_SIZE]; /* the ethernet header */
490 struct {
491
492 /* these are needed for csum at uisnic end */
493 U8 valid; /* 1 = rest of this struct is valid - else
494 * ignore */
495 U8 hrawoffv; /* 1 = hwrafoff is valid */
496 U8 nhrawoffv; /* 1 = nhwrafoff is valid */
497 U16 protocol; /* specifies packet protocol */
498 U32 csum; /* value used to set skb->csum at IOPart */
499 U32 hrawoff; /* value used to set skb->h.raw at IOPart */
500 /* hrawoff points to the start of the TRANSPORT LAYER HEADER */
501 U32 nhrawoff; /* value used to set skb->nh.raw at IOPart */
502 /* nhrawoff points to the start of the NETWORK LAYER HEADER */
503 } lincsum;
504
505 /* **** NOTE ****
506 * The full packet is described in frags but the ethernet header is
507 * separately kept in ethhdr so that uisnic doesn't have "MAP" the
508 * guest memory to get to the header. uisnic needs ethhdr to
509 * determine how to route the packet.
510 */
511 };
512
513 struct net_pkt_xmtdone {
514 U32 xmt_done_result; /* result of NET_XMIT */
515 #define XMIT_SUCCESS 0
516 #define XMIT_FAILED 1
517 };
518
519 /* RCVPOST_BUF_SIZe must be at most page_size(4096) - cache_line_size (64) The
520 * reason is because dev_skb_alloc which is used to generate RCV_POST skbs in
521 * virtnic requires that there is "overhead" in the buffer, and pads 16 bytes. I
522 * prefer to use 1 full cache line size for "overhead" so that transfers are
523 * better. IOVM requires that a buffer be represented by 1 phys_info structure
524 * which can only cover page_size. */
525 #define RCVPOST_BUF_SIZE 4032
526 #define MAX_NET_RCV_CHAIN \
527 ((ETH_MAX_MTU+ETH_HEADER_SIZE + RCVPOST_BUF_SIZE-1) / RCVPOST_BUF_SIZE)
528
529 struct net_pkt_rcvpost {
530 /* rcv buf size must be large enough to include ethernet data len +
531 * ethernet header len - we are choosing 2K because it is guaranteed
532 * to be describable */
533 struct phys_info frag; /* physical page information for the
534 * single fragment 2K rcv buf */
535 U64 UniqueNum; /* This is used to make sure that
536 * receive posts are returned to */
537 /* the Adapter which sent them origonally. */
538 };
539
540 struct net_pkt_rcv {
541
542 /* the number of receive buffers that can be chained */
543 /* is based on max mtu and size of each rcv buf */
544 U32 rcv_done_len; /* length of received data */
545 U8 numrcvbufs; /* number of receive buffers that contain the */
546 /* incoming data; guest end MUST chain these together. */
547 void *rcvbuf[MAX_NET_RCV_CHAIN]; /* the list of receive buffers
548 * that must be chained; */
549 /* each entry is a receive buffer provided by NET_RCV_POST. */
550 /* NOTE: first rcvbuf in the chain will also be provided in net.buf. */
551 U64 UniqueNum;
552 U32 RcvsDroppedDelta;
553 };
554
555 struct net_pkt_enbdis {
556 void *context;
557 U16 enable; /* 1 = enable, 0 = disable */
558 };
559
560 struct net_pkt_macaddr {
561 void *context;
562 U8 macaddr[MAX_MACADDR_LEN]; /* 6 bytes */
563 };
564
565 /* cmd rsp packet used for VNIC network traffic */
566 struct uiscmdrsp_net {
567 NET_TYPES type;
568 void *buf;
569 union {
570 struct net_pkt_xmt xmt; /* used for NET_XMIT */
571 struct net_pkt_xmtdone xmtdone; /* used for NET_XMIT_DONE */
572 struct net_pkt_rcvpost rcvpost; /* used for NET_RCV_POST */
573 struct net_pkt_rcv rcv; /* used for NET_RCV */
574 struct net_pkt_enbdis enbdis; /* used for NET_RCV_ENBDIS, */
575 /* NET_RCV_ENBDIS_ACK, */
576 /* NET_RCV_PROMSIC, */
577 /* and NET_CONNECT_STATUS */
578 struct net_pkt_macaddr macaddr;
579 };
580 };
581
582 struct uiscmdrsp_scsitaskmgmt {
583 TASK_MGMT_TYPES tasktype;
584
585 /* the type of task */
586 struct uisscsi_dest vdest;
587
588 /* the vdisk for which this task mgmt is generated */
589 void *scsicmd;
590
591 /* This is some handle that the guest has saved off for its own use.
592 * Its value is preserved by iopart & returned as is in the task mgmt
593 * rsp. */
594 void *notify;
595
596 /* For linux guests, this is a pointer to wait_queue_head that a
597 * thread is waiting on to see if the taskmgmt command has completed.
598 * For windows guests, this is a pointer to a location that a waiting
599 * thread is testing to see if the taskmgmt command has completed.
600 * When the rsp is received by guest, the thread receiving the
601 * response uses this to notify the the thread waiting for taskmgmt
602 * command completion. Its value is preserved by iopart & returned
603 * as is in the task mgmt rsp. */
604 void *notifyresult;
605
606 /* this is a handle to location in guest where the result of the
607 * taskmgmt command (result field) is to saved off when the response
608 * is handled. Its value is preserved by iopart & returned as is in
609 * the task mgmt rsp. */
610 char result;
611
612 /* result of taskmgmt command - set by IOPart - values are: */
613 #define TASK_MGMT_FAILED 0
614 #define TASK_MGMT_SUCCESS 1
615 };
616
617 /* The following is used by uissd to send disk add/remove notifications to
618 * Guest */
619 /* Note that the vHba pointer is not used by the Client/Guest side. */
620 struct uiscmdrsp_disknotify {
621 U8 add; /* 0-remove, 1-add */
622 void *vHba; /* Pointer to vhba_info for channel info to
623 * route msg */
624 U32 channel, id, lun; /* SCSI Path of Disk to added or removed */
625 };
626
627 /* The following is used by virthba/vSCSI to send the Acquire/Release commands
628 * to the IOVM. */
629 struct uiscmdrsp_vdiskmgmt {
630 VDISK_MGMT_TYPES vdisktype;
631
632 /* the type of task */
633 struct uisscsi_dest vdest;
634
635 /* the vdisk for which this task mgmt is generated */
636 void *scsicmd;
637
638 /* This is some handle that the guest has saved off for its own use.
639 * Its value is preserved by iopart & returned as is in the task mgmt
640 * rsp. */
641 void *notify;
642
643 /* For linux guests, this is a pointer to wait_queue_head that a
644 * thread is waiting on to see if the taskmgmt command has completed.
645 * For windows guests, this is a pointer to a location that a waiting
646 * thread is testing to see if the taskmgmt command has completed.
647 * When the rsp is received by guest, the thread receiving the
648 * response uses this to notify the the thread waiting for taskmgmt
649 * command completion. Its value is preserved by iopart & returned
650 * as is in the task mgmt rsp. */
651 void *notifyresult;
652
653 /* this is a handle to location in guest where the result of the
654 * taskmgmt command (result field) is to saved off when the response
655 * is handled. Its value is preserved by iopart & returned as is in
656 * the task mgmt rsp. */
657 char result;
658
659 /* result of taskmgmt command - set by IOPart - values are: */
660 #define VDISK_MGMT_FAILED 0
661 #define VDISK_MGMT_SUCCESS 1
662 };
663
664 /* keeping cmd & rsp info in one structure for now cmd rsp packet for scsi */
665 struct uiscmdrsp {
666 char cmdtype;
667
668 /* describes what type of information is in the struct */
669 #define CMD_SCSI_TYPE 1
670 #define CMD_NET_TYPE 2
671 #define CMD_SCSITASKMGMT_TYPE 3
672 #define CMD_NOTIFYGUEST_TYPE 4
673 #define CMD_VDISKMGMT_TYPE 5
674 union {
675 struct uiscmdrsp_scsi scsi;
676 struct uiscmdrsp_net net;
677 struct uiscmdrsp_scsitaskmgmt scsitaskmgmt;
678 struct uiscmdrsp_disknotify disknotify;
679 struct uiscmdrsp_vdiskmgmt vdiskmgmt;
680 };
681 void *private_data; /* used to send the response when the cmd is
682 * done (scsi & scsittaskmgmt). */
683 struct uiscmdrsp *next; /* General Purpose Queue Link */
684 struct uiscmdrsp *activeQ_next; /* Used to track active commands */
685 struct uiscmdrsp *activeQ_prev; /* Used to track active commands */
686 };
687
688 /* This is just the header of the IO channel. It is assumed that directly after
689 * this header there is a large region of memory which contains the command and
690 * response queues as specified in cmdQ and rspQ SIGNAL_QUEUE_HEADERS. */
691 typedef struct _ULTRA_IO_CHANNEL_PROTOCOL {
692 CHANNEL_HEADER ChannelHeader;
693 SIGNAL_QUEUE_HEADER cmdQ;
694 SIGNAL_QUEUE_HEADER rspQ;
695 union {
696 struct {
697 struct vhba_wwnn wwnn; /* 8 bytes */
698 struct vhba_config_max max; /* 20 bytes */
699 } vhba; /* 28 */
700 struct {
701 U8 macaddr[MAX_MACADDR_LEN]; /* 6 bytes */
702 U32 num_rcv_bufs; /* 4 */
703 U32 mtu; /* 4 */
704 GUID zoneGuid; /* 16 */
705 } vnic; /* total 30 */
706 };
707
708 #define MAX_CLIENTSTRING_LEN 1024
709 U8 clientString[MAX_CLIENTSTRING_LEN]; /* NULL terminated - so holds
710 * max - 1 bytes */
711 } ULTRA_IO_CHANNEL_PROTOCOL;
712
713 #pragma pack(pop)
714 /* ///////////// END PRAGMA PACK PUSH 1 /////////////////////////// */
715
716 /* define offsets to members of struct uiscmdrsp */
717 #define OFFSET_CMDTYPE OFFSETOF(struct uiscmdrsp, cmdtype)
718 #define OFFSET_SCSI OFFSETOF(struct uiscmdrsp, scsi)
719 #define OFFSET_NET OFFSETOF(struct uiscmdrsp, net)
720 #define OFFSET_SCSITASKMGMT OFFSETOF(struct uiscmdrsp, scsitaskmgmt)
721 #define OFFSET_NEXT OFFSETOF(struct uiscmdrsp, next)
722
723 /* define offsets to members of struct uiscmdrsp_net */
724 #define OFFSET_TYPE OFFSETOF(struct uiscmdrsp_net, type)
725 #define OFFSET_BUF OFFSETOF(struct uiscmdrsp_net, buf)
726 #define OFFSET_XMT OFFSETOF(struct uiscmdrsp_net, xmt)
727 #define OFFSET_XMT_DONE_RESULT OFFSETOF(struct uiscmdrsp_net, xmtdone)
728 #define OFFSET_RCVPOST OFFSETOF(struct uiscmdrsp_net, rcvpost)
729 #define OFFSET_RCV_DONE_LEN OFFSETOF(struct uiscmdrsp_net, rcv)
730 #define OFFSET_ENBDIS OFFSETOF(struct uiscmdrsp_net, enbdis)
731
732 /* define offsets to members of struct net_pkt_rcvpost */
733 #define OFFSET_TOTALLEN OFFSETOF(struct net_pkt_rcvpost, totallen)
734 #define OFFSET_FRAG OFFSETOF(struct net_pkt_rcvpost, frag)
735
736 /*
737 * INLINE functions for initializing and accessing I/O data channels
738 */
739
740
741 #define NUMSIGNALS(x, q) (((ULTRA_IO_CHANNEL_PROTOCOL *)(x))->q.MaxSignalSlots)
742 #define SIZEOF_PROTOCOL (COVER(sizeof(ULTRA_IO_CHANNEL_PROTOCOL), 64))
743 #define SIZEOF_CMDRSP (COVER(sizeof(struct uiscmdrsp), 64))
744
745 #define IO_CHANNEL_SIZE(x) COVER(SIZEOF_PROTOCOL + \
746 (NUMSIGNALS(x, cmdQ) + \
747 NUMSIGNALS(x, rspQ)) * SIZEOF_CMDRSP, 4096)
748 #define MIN_IO_CHANNEL_SIZE COVER(SIZEOF_PROTOCOL + \
749 2 * MIN_NUMSIGNALS * SIZEOF_CMDRSP, 4096)
750 #ifdef __GNUC__
751 /* These defines should only ever be used in service partitons */
752 /* because they rely on the size of uiscmdrsp */
753 #define QSLOTSFROMBYTES(bytes) (((bytes-SIZEOF_PROTOCOL)/2)/SIZEOF_CMDRSP)
754 #define QSIZEFROMBYTES(bytes) (QSLOTSFROMBYTES(bytes)*SIZEOF_CMDRSP)
755 #define SignalQInit(x) \
756 do { \
757 x->cmdQ.Size = QSIZEFROMBYTES(x->ChannelHeader.Size); \
758 x->cmdQ.oSignalBase = SIZEOF_PROTOCOL - \
759 OFFSETOF(ULTRA_IO_CHANNEL_PROTOCOL, cmdQ); \
760 x->cmdQ.SignalSize = SIZEOF_CMDRSP; \
761 x->cmdQ.MaxSignalSlots = \
762 QSLOTSFROMBYTES(x->ChannelHeader.Size); \
763 x->cmdQ.MaxSignals = x->cmdQ.MaxSignalSlots - 1; \
764 x->rspQ.Size = QSIZEFROMBYTES(x->ChannelHeader.Size); \
765 x->rspQ.oSignalBase = \
766 (SIZEOF_PROTOCOL + x->cmdQ.Size) - \
767 OFFSETOF(ULTRA_IO_CHANNEL_PROTOCOL, rspQ); \
768 x->rspQ.SignalSize = SIZEOF_CMDRSP; \
769 x->rspQ.MaxSignalSlots = \
770 QSLOTSFROMBYTES(x->ChannelHeader.Size); \
771 x->rspQ.MaxSignals = x->rspQ.MaxSignalSlots - 1; \
772 x->ChannelHeader.oChannelSpace = \
773 OFFSETOF(ULTRA_IO_CHANNEL_PROTOCOL, cmdQ); \
774 } while (0)
775
776 #define INIT_CLIENTSTRING(chan, type, clientStr, clientStrLen) \
777 do { \
778 if (clientStr) { \
779 chan->ChannelHeader.oClientString = \
780 OFFSETOF(type, clientString); \
781 MEMCPY(chan->clientString, clientStr, \
782 MINNUM(clientStrLen, \
783 (U32) (MAX_CLIENTSTRING_LEN - 1))); \
784 chan->clientString[MINNUM(clientStrLen, \
785 (U32) (MAX_CLIENTSTRING_LEN \
786 - 1))] \
787 = '\0'; \
788 } \
789 else \
790 if (clientStrLen > 0) \
791 return 0; \
792 } while (0)
793
794
795 #define ULTRA_IO_CHANNEL_SERVER_READY(x, chanId, logCtx) \
796 ULTRA_CHANNEL_SERVER_TRANSITION(x, chanId, SrvState, CHANNELSRV_READY, \
797 logCtx);
798
799 #define ULTRA_IO_CHANNEL_SERVER_NOTREADY(x, chanId, logCtx) \
800 ULTRA_CHANNEL_SERVER_TRANSITION(x, chanId, SrvState, \
801 CHANNELSRV_UNINITIALIZED, logCtx);
802
803 static inline int ULTRA_VHBA_init_channel(ULTRA_IO_CHANNEL_PROTOCOL *x,
804 struct vhba_wwnn *wwnn,
805 struct vhba_config_max *max,
806 unsigned char *clientStr,
807 U32 clientStrLen, U64 bytes) {
808 MEMSET(x, 0, sizeof(ULTRA_IO_CHANNEL_PROTOCOL));
809 x->ChannelHeader.VersionId = ULTRA_VHBA_CHANNEL_PROTOCOL_VERSIONID;
810 x->ChannelHeader.Signature = ULTRA_VHBA_CHANNEL_PROTOCOL_SIGNATURE;
811 x->ChannelHeader.SrvState = CHANNELSRV_UNINITIALIZED;
812 x->ChannelHeader.HeaderSize = sizeof(x->ChannelHeader);
813 x->ChannelHeader.Size = COVER(bytes, 4096);
814 x->ChannelHeader.Type = UltraVhbaChannelProtocolGuid;
815 x->ChannelHeader.ZoneGuid = Guid0;
816 x->vhba.wwnn = *wwnn;
817 x->vhba.max = *max;
818 INIT_CLIENTSTRING(x, ULTRA_IO_CHANNEL_PROTOCOL, clientStr,
819 clientStrLen);
820 SignalQInit(x);
821 if ((x->cmdQ.MaxSignalSlots > MAX_NUMSIGNALS) ||
822 (x->rspQ.MaxSignalSlots > MAX_NUMSIGNALS)) {
823 return 0;
824 }
825 if ((x->cmdQ.MaxSignalSlots < MIN_NUMSIGNALS) ||
826 (x->rspQ.MaxSignalSlots < MIN_NUMSIGNALS)) {
827 return 0;
828 }
829 return 1;
830 }
831
832 static inline void ULTRA_VHBA_set_max(ULTRA_IO_CHANNEL_PROTOCOL *x,
833 struct vhba_config_max *max) {
834 x->vhba.max = *max;
835 }
836
837 static inline int ULTRA_VNIC_init_channel(ULTRA_IO_CHANNEL_PROTOCOL *x,
838 unsigned char *macaddr,
839 U32 num_rcv_bufs, U32 mtu,
840 GUID zoneGuid,
841 unsigned char *clientStr,
842 U32 clientStrLen,
843 U64 bytes) {
844 MEMSET(x, 0, sizeof(ULTRA_IO_CHANNEL_PROTOCOL));
845 x->ChannelHeader.VersionId = ULTRA_VNIC_CHANNEL_PROTOCOL_VERSIONID;
846 x->ChannelHeader.Signature = ULTRA_VNIC_CHANNEL_PROTOCOL_SIGNATURE;
847 x->ChannelHeader.SrvState = CHANNELSRV_UNINITIALIZED;
848 x->ChannelHeader.HeaderSize = sizeof(x->ChannelHeader);
849 x->ChannelHeader.Size = COVER(bytes, 4096);
850 x->ChannelHeader.Type = UltraVnicChannelProtocolGuid;
851 x->ChannelHeader.ZoneGuid = Guid0;
852 MEMCPY(x->vnic.macaddr, macaddr, MAX_MACADDR_LEN);
853 x->vnic.num_rcv_bufs = num_rcv_bufs;
854 x->vnic.mtu = mtu;
855 x->vnic.zoneGuid = zoneGuid;
856 INIT_CLIENTSTRING(x, ULTRA_IO_CHANNEL_PROTOCOL, clientStr,
857 clientStrLen);
858 SignalQInit(x);
859 if ((x->cmdQ.MaxSignalSlots > MAX_NUMSIGNALS) ||
860 (x->rspQ.MaxSignalSlots > MAX_NUMSIGNALS)) {
861 return 0;
862 }
863 if ((x->cmdQ.MaxSignalSlots < MIN_NUMSIGNALS) ||
864 (x->rspQ.MaxSignalSlots < MIN_NUMSIGNALS)) {
865 return 0;
866 }
867 return 1;
868 }
869
870 #endif /* __GNUC__ */
871
872 /*
873 * INLINE function for expanding a guest's pfn-off-size into multiple 4K page
874 * pfn-off-size entires.
875 */
876
877
878 /* we deal with 4K page sizes when we it comes to passing page information
879 * between */
880 /* Guest and IOPartition. */
881 #define PI_PAGE_SIZE 0x1000
882 #define PI_PAGE_MASK 0x0FFF
883 #define PI_PAGE_SHIFT 12
884
885 /* returns next non-zero index on success or zero on failure (i.e. out of
886 * room)
887 */
888 static INLINE U16
889 add_physinfo_entries(U32 inp_pfn, /* input - specifies the pfn to be used
890 * to add entries */
891 U16 inp_off, /* input - specifies the off to be used
892 * to add entries */
893 U32 inp_len, /* input - specifies the len to be used
894 * to add entries */
895 U16 index, /* input - index in array at which new
896 * entries are added */
897 U16 max_pi_arr_entries, /* input - specifies the maximum
898 * entries pi_arr can hold */
899 struct phys_info pi_arr[]) /* input & output - array to
900 * which entries are added */
901 {
902 U32 len;
903 U16 i, firstlen;
904
905 firstlen = PI_PAGE_SIZE - inp_off;
906 if (inp_len <= firstlen) {
907
908 /* the input entry spans only one page - add as is */
909 if (index >= max_pi_arr_entries)
910 return 0;
911 pi_arr[index].pi_pfn = inp_pfn;
912 pi_arr[index].pi_off = (U16) inp_off;
913 pi_arr[index].pi_len = (U16) inp_len;
914 return index + 1;
915 }
916
917 /* this entry spans multiple pages */
918 for (len = inp_len, i = 0; len;
919 len -= pi_arr[index + i].pi_len, i++) {
920 if (index + i >= max_pi_arr_entries)
921 return 0;
922 pi_arr[index + i].pi_pfn = inp_pfn + i;
923 if (i == 0) {
924 pi_arr[index].pi_off = inp_off;
925 pi_arr[index].pi_len = firstlen;
926 }
927
928 else {
929 pi_arr[index + i].pi_off = 0;
930 pi_arr[index + i].pi_len =
931 (U16) MINNUM(len, (U32) PI_PAGE_SIZE);
932 }
933
934 }
935 return index + i;
936 }
937
938 #endif /* __IOCHANNEL_H__ */
This page took 0.060797 seconds and 5 git commands to generate.