staging: et131x: Remove trailing semicolon from macros in et131x.h
[deliverable/linux.git] / drivers / staging / unisys / visorchipset / visorchipset_main.c
CommitLineData
12e364b9
KC
1/* visorchipset_main.c
2 *
f6d0c1e6 3 * Copyright (C) 2010 - 2013 UNISYS CORPORATION
12e364b9
KC
4 * All rights reserved.
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or (at
9 * your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful, but
12 * WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE, GOOD TITLE or
14 * NON INFRINGEMENT. See the GNU General Public License for more
15 * details.
16 */
17
18#include "globals.h"
12e364b9
KC
19#include "visorchipset.h"
20#include "procobjecttree.h"
21#include "visorchannel.h"
22#include "periodic_work.h"
23#include "testing.h"
24#include "file.h"
25#include "parser.h"
26#include "uniklog.h"
27#include "uisutils.h"
12e364b9
KC
28#include "controlvmcompletionstatus.h"
29#include "guestlinuxdebug.h"
12e364b9
KC
30
31#include <linux/nls.h>
32#include <linux/netdevice.h>
33#include <linux/platform_device.h>
90addb02 34#include <linux/uuid.h>
12e364b9
KC
35
36#define CURRENT_FILE_PC VISOR_CHIPSET_PC_visorchipset_main_c
37#define TEST_VNIC_PHYSITF "eth0" /* physical network itf for
38 * vnic loopback test */
39#define TEST_VNIC_SWITCHNO 1
40#define TEST_VNIC_BUSNO 9
41
42#define MAX_NAME_SIZE 128
43#define MAX_IP_SIZE 50
44#define MAXOUTSTANDINGCHANNELCOMMAND 256
45#define POLLJIFFIES_CONTROLVMCHANNEL_FAST 1
46#define POLLJIFFIES_CONTROLVMCHANNEL_SLOW 100
47
48/* When the controlvm channel is idle for at least MIN_IDLE_SECONDS,
49* we switch to slow polling mode. As soon as we get a controlvm
50* message, we switch back to fast polling mode.
51*/
52#define MIN_IDLE_SECONDS 10
bd5b9b32
KC
53static ulong Poll_jiffies = POLLJIFFIES_CONTROLVMCHANNEL_FAST;
54static ulong Most_recent_message_jiffies; /* when we got our last
55 * controlvm message */
12e364b9
KC
56static inline char *
57NONULLSTR(char *s)
58{
59 if (s)
60 return s;
61 else
62 return "";
63}
64
65static int serverregistered;
66static int clientregistered;
67
68#define MAX_CHIPSET_EVENTS 2
69static U8 chipset_events[MAX_CHIPSET_EVENTS] = { 0, 0 };
70
71static struct delayed_work Periodic_controlvm_work;
72static struct workqueue_struct *Periodic_controlvm_workqueue;
bd5b9b32 73static DEFINE_SEMAPHORE(NotifierLock);
12e364b9
KC
74
75typedef struct {
76 CONTROLVM_MESSAGE message;
77 unsigned int crc;
78} MESSAGE_ENVELOPE;
79
80static CONTROLVM_MESSAGE_HEADER g_DiagMsgHdr;
81static CONTROLVM_MESSAGE_HEADER g_ChipSetMsgHdr;
82static CONTROLVM_MESSAGE_HEADER g_DelDumpMsgHdr;
90addb02 83static const uuid_le UltraDiagPoolChannelProtocolGuid =
12e364b9
KC
84 ULTRA_DIAG_POOL_CHANNEL_PROTOCOL_GUID;
85/* 0xffffff is an invalid Bus/Device number */
86static ulong g_diagpoolBusNo = 0xffffff;
87static ulong g_diagpoolDevNo = 0xffffff;
88static CONTROLVM_MESSAGE_PACKET g_DeviceChangeStatePacket;
89
90/* Only VNIC and VHBA channels are sent to visorclientbus (aka
91 * "visorhackbus")
92 */
93#define FOR_VISORHACKBUS(channel_type_guid) \
90addb02
BR
94 (((uuid_le_cmp(channel_type_guid, UltraVnicChannelProtocolGuid) == 0)\
95 || (uuid_le_cmp(channel_type_guid, UltraVhbaChannelProtocolGuid) == 0)))
12e364b9
KC
96#define FOR_VISORBUS(channel_type_guid) (!(FOR_VISORHACKBUS(channel_type_guid)))
97
98#define is_diagpool_channel(channel_type_guid) \
90addb02 99 (uuid_le_cmp(channel_type_guid, UltraDiagPoolChannelProtocolGuid) == 0)
12e364b9
KC
100
101typedef enum {
102 PARTPROP_invalid,
103 PARTPROP_name,
104 PARTPROP_description,
105 PARTPROP_handle,
106 PARTPROP_busNumber,
107 /* add new properties above, but don't forget to change
108 * InitPartitionProperties() and show_partition_property() also...
109 */
110 PARTPROP_last
111} PARTITION_property;
112static const char *PartitionTypeNames[] = { "partition", NULL };
113
114static char *PartitionPropertyNames[PARTPROP_last + 1];
115static void
116InitPartitionProperties(void)
117{
118 char **p = PartitionPropertyNames;
119 p[PARTPROP_invalid] = "";
120 p[PARTPROP_name] = "name";
121 p[PARTPROP_description] = "description";
122 p[PARTPROP_handle] = "handle";
123 p[PARTPROP_busNumber] = "busNumber";
124 p[PARTPROP_last] = NULL;
125}
126
12e364b9 127static MYPROCTYPE *PartitionType;
12e364b9
KC
128
129#define VISORCHIPSET_DIAG_PROC_ENTRY_FN "diagdump"
130static struct proc_dir_entry *diag_proc_dir;
131
132#define VISORCHIPSET_CHIPSET_PROC_ENTRY_FN "chipsetready"
133static struct proc_dir_entry *chipset_proc_dir;
134
135#define VISORCHIPSET_PARAHOTPLUG_PROC_ENTRY_FN "parahotplug"
136static struct proc_dir_entry *parahotplug_proc_dir;
137
138static LIST_HEAD(BusInfoList);
139static LIST_HEAD(DevInfoList);
140
141static struct proc_dir_entry *ProcDir;
142static VISORCHANNEL *ControlVm_channel;
143
144static ssize_t visorchipset_proc_read_writeonly(struct file *file,
145 char __user *buf,
146 size_t len, loff_t *offset);
147static ssize_t proc_read_installer(struct file *file, char __user *buf,
148 size_t len, loff_t *offset);
149static ssize_t proc_write_installer(struct file *file,
150 const char __user *buffer,
151 size_t count, loff_t *ppos);
54b31229 152
12e364b9
KC
153static const struct file_operations proc_installer_fops = {
154 .read = proc_read_installer,
155 .write = proc_write_installer,
156};
157
12e364b9 158typedef struct {
bd5b9b32 159 U8 __iomem *ptr; /* pointer to base address of payload pool */
12e364b9
KC
160 U64 offset; /* offset from beginning of controlvm
161 * channel to beginning of payload * pool */
162 U32 bytes; /* number of bytes in payload pool */
163} CONTROLVM_PAYLOAD_INFO;
164
165/* Manages the request payload in the controlvm channel */
166static CONTROLVM_PAYLOAD_INFO ControlVm_payload_info;
167
168static pCHANNEL_HEADER Test_Vnic_channel;
169
170typedef struct {
171 CONTROLVM_MESSAGE_HEADER Dumpcapture_header;
172 CONTROLVM_MESSAGE_HEADER Gettextdump_header;
173 CONTROLVM_MESSAGE_HEADER Dumpcomplete_header;
174 BOOL Gettextdump_outstanding;
175 u32 crc32;
176 ulong length;
177 atomic_t buffers_in_use;
178 ulong destination;
179} LIVEDUMP_INFO;
180/* Manages the info for a CONTROLVM_DUMP_CAPTURESTATE /
181 * CONTROLVM_DUMP_GETTEXTDUMP / CONTROLVM_DUMP_COMPLETE conversation.
182 */
183static LIVEDUMP_INFO LiveDump_info;
184
185/* The following globals are used to handle the scenario where we are unable to
186 * offload the payload from a controlvm message due to memory requirements. In
187 * this scenario, we simply stash the controlvm message, then attempt to
188 * process it again the next time controlvm_periodic_work() runs.
189 */
190static CONTROLVM_MESSAGE ControlVm_Pending_Msg;
191static BOOL ControlVm_Pending_Msg_Valid = FALSE;
192
193/* Pool of struct putfile_buffer_entry, for keeping track of pending (incoming)
194 * TRANSMIT_FILE PutFile payloads.
195 */
196static struct kmem_cache *Putfile_buffer_list_pool;
197static const char Putfile_buffer_list_pool_name[] =
198 "controlvm_putfile_buffer_list_pool";
199
200/* This identifies a data buffer that has been received via a controlvm messages
201 * in a remote --> local CONTROLVM_TRANSMIT_FILE conversation.
202 */
203struct putfile_buffer_entry {
204 struct list_head next; /* putfile_buffer_entry list */
205 PARSER_CONTEXT *parser_ctx; /* points to buffer containing input data */
206};
207
208/* List of struct putfile_request *, via next_putfile_request member.
209 * Each entry in this list identifies an outstanding TRANSMIT_FILE
210 * conversation.
211 */
212static LIST_HEAD(Putfile_request_list);
213
214/* This describes a buffer and its current state of transfer (e.g., how many
215 * bytes have already been supplied as putfile data, and how many bytes are
216 * remaining) for a putfile_request.
217 */
218struct putfile_active_buffer {
219 /* a payload from a controlvm message, containing a file data buffer */
220 PARSER_CONTEXT *parser_ctx;
221 /* points within data area of parser_ctx to next byte of data */
222 u8 *pnext;
223 /* # bytes left from <pnext> to the end of this data buffer */
224 size_t bytes_remaining;
225};
226
227#define PUTFILE_REQUEST_SIG 0x0906101302281211
228/* This identifies a single remote --> local CONTROLVM_TRANSMIT_FILE
229 * conversation. Structs of this type are dynamically linked into
230 * <Putfile_request_list>.
231 */
232struct putfile_request {
233 u64 sig; /* PUTFILE_REQUEST_SIG */
234
235 /* header from original TransmitFile request */
236 CONTROLVM_MESSAGE_HEADER controlvm_header;
237 u64 file_request_number; /* from original TransmitFile request */
238
239 /* link to next struct putfile_request */
240 struct list_head next_putfile_request;
241
242 /* most-recent sequence number supplied via a controlvm message */
243 u64 data_sequence_number;
244
245 /* head of putfile_buffer_entry list, which describes the data to be
246 * supplied as putfile data;
247 * - this list is added to when controlvm messages come in that supply
248 * file data
249 * - this list is removed from via the hotplug program that is actually
250 * consuming these buffers to write as file data */
251 struct list_head input_buffer_list;
252 spinlock_t req_list_lock; /* lock for input_buffer_list */
253
254 /* waiters for input_buffer_list to go non-empty */
255 wait_queue_head_t input_buffer_wq;
256
257 /* data not yet read within current putfile_buffer_entry */
258 struct putfile_active_buffer active_buf;
259
260 /* <0 = failed, 0 = in-progress, >0 = successful; */
261 /* note that this must be set with req_list_lock, and if you set <0, */
262 /* it is your responsibility to also free up all of the other objects */
263 /* in this struct (like input_buffer_list, active_buf.parser_ctx) */
264 /* before releasing the lock */
265 int completion_status;
266};
267
bd5b9b32 268static atomic_t Visorchipset_cache_buffers_in_use = ATOMIC_INIT(0);
12e364b9
KC
269
270struct parahotplug_request {
271 struct list_head list;
272 int id;
273 unsigned long expiration;
274 CONTROLVM_MESSAGE msg;
275};
276
277static LIST_HEAD(Parahotplug_request_list);
278static DEFINE_SPINLOCK(Parahotplug_request_list_lock); /* lock for above */
279static void parahotplug_process_list(void);
280
281/* Manages the info for a CONTROLVM_DUMP_CAPTURESTATE /
282 * CONTROLVM_REPORTEVENT.
283 */
284static VISORCHIPSET_BUSDEV_NOTIFIERS BusDev_Server_Notifiers;
285static VISORCHIPSET_BUSDEV_NOTIFIERS BusDev_Client_Notifiers;
286
287static void bus_create_response(ulong busNo, int response);
288static void bus_destroy_response(ulong busNo, int response);
289static void device_create_response(ulong busNo, ulong devNo, int response);
290static void device_destroy_response(ulong busNo, ulong devNo, int response);
291static void device_resume_response(ulong busNo, ulong devNo, int response);
292
293static VISORCHIPSET_BUSDEV_RESPONDERS BusDev_Responders = {
294 .bus_create = bus_create_response,
295 .bus_destroy = bus_destroy_response,
296 .device_create = device_create_response,
297 .device_destroy = device_destroy_response,
927c7927 298 .device_pause = visorchipset_device_pause_response,
12e364b9
KC
299 .device_resume = device_resume_response,
300};
301
302/* info for /dev/visorchipset */
303static dev_t MajorDev = -1; /**< indicates major num for device */
304
19f6634f
BR
305/* prototypes for attributes */
306static ssize_t toolaction_show(struct device *dev,
307 struct device_attribute *attr, char *buf);
308static ssize_t toolaction_store(struct device *dev,
309 struct device_attribute *attr, const char *buf, size_t count);
310static DEVICE_ATTR_RW(toolaction);
311
54b31229
BR
312static ssize_t boottotool_show(struct device *dev,
313 struct device_attribute *attr, char *buf);
314static ssize_t boottotool_store(struct device *dev,
315 struct device_attribute *attr, const char *buf, size_t count);
316static DEVICE_ATTR_RW(boottotool);
317
19f6634f
BR
318static struct attribute *visorchipset_install_attrs[] = {
319 &dev_attr_toolaction.attr,
54b31229 320 &dev_attr_boottotool.attr,
19f6634f
BR
321 NULL
322};
323
324static struct attribute_group visorchipset_install_group = {
325 .name = "install",
326 .attrs = visorchipset_install_attrs
327};
328
329static const struct attribute_group *visorchipset_dev_groups[] = {
330 &visorchipset_install_group,
331 NULL
332};
333
12e364b9
KC
334/* /sys/devices/platform/visorchipset */
335static struct platform_device Visorchipset_platform_device = {
336 .name = "visorchipset",
337 .id = -1,
19f6634f 338 .dev.groups = visorchipset_dev_groups,
12e364b9
KC
339};
340
341/* Function prototypes */
342static void controlvm_respond(CONTROLVM_MESSAGE_HEADER *msgHdr, int response);
343static void controlvm_respond_chipset_init(CONTROLVM_MESSAGE_HEADER *msgHdr,
344 int response,
345 ULTRA_CHIPSET_FEATURE features);
346static void controlvm_respond_physdev_changestate(CONTROLVM_MESSAGE_HEADER *
347 msgHdr, int response,
348 ULTRA_SEGMENT_STATE state);
349
19f6634f
BR
350ssize_t toolaction_show(struct device *dev, struct device_attribute *attr,
351 char *buf)
352{
353 U8 toolAction;
354
355 visorchannel_read(ControlVm_channel,
356 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
357 ToolAction), &toolAction, sizeof(U8));
358 return scnprintf(buf, PAGE_SIZE, "%u\n", toolAction);
359}
360
361ssize_t toolaction_store(struct device *dev, struct device_attribute *attr,
362 const char *buf, size_t count)
363{
364 U8 toolAction;
365
366 if (sscanf(buf, "%hhu\n", &toolAction) == 1) {
367 if (visorchannel_write(ControlVm_channel,
368 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
369 ToolAction),
370 &toolAction, sizeof(U8)) < 0)
371 return -EFAULT;
372 else
373 return count;
374 } else
375 return -EIO;
376}
377
54b31229
BR
378ssize_t boottotool_show(struct device *dev, struct device_attribute *attr,
379 char *buf)
380{
381 ULTRA_EFI_SPAR_INDICATION efiSparIndication;
382
383 visorchannel_read(ControlVm_channel,
384 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
385 EfiSparIndication), &efiSparIndication,
386 sizeof(ULTRA_EFI_SPAR_INDICATION));
387 return scnprintf(buf, PAGE_SIZE, "%u\n",
388 efiSparIndication.BootToTool);
389}
390
391ssize_t boottotool_store(struct device *dev, struct device_attribute *attr,
392 const char *buf, size_t count)
393{
394 int val;
395 ULTRA_EFI_SPAR_INDICATION efiSparIndication;
396
397 if (sscanf(buf, "%u\n", &val) == 1) {
398 efiSparIndication.BootToTool = val;
399 if (visorchannel_write(ControlVm_channel,
400 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
401 EfiSparIndication),
402 &(efiSparIndication),
403 sizeof(ULTRA_EFI_SPAR_INDICATION)) < 0)
404 return -EFAULT;
405 else
406 return count;
407 } else
408 return -EIO;
409}
12e364b9
KC
410static void
411show_partition_property(struct seq_file *f, void *ctx, int property)
412{
413 VISORCHIPSET_BUS_INFO *info = (VISORCHIPSET_BUS_INFO *) (ctx);
414
415 switch (property) {
416 case PARTPROP_name:
417 seq_printf(f, "%s\n", NONULLSTR(info->name));
418 break;
419 case PARTPROP_description:
420 seq_printf(f, "%s\n", NONULLSTR(info->description));
421 break;
422 case PARTPROP_handle:
423 seq_printf(f, "0x%-16.16Lx\n", info->partitionHandle);
424 break;
425 case PARTPROP_busNumber:
426 seq_printf(f, "%d\n", info->busNo);
427 break;
428 default:
429 seq_printf(f, "(%d??)\n", property);
430 break;
431 }
432}
433
12e364b9
KC
434static void
435proc_Init(void)
436{
437 if (ProcDir == NULL) {
438 ProcDir = proc_mkdir(MYDRVNAME, NULL);
439 if (ProcDir == NULL) {
440 LOGERR("failed to create /proc directory %s",
441 MYDRVNAME);
442 POSTCODE_LINUX_2(CHIPSET_INIT_FAILURE_PC,
443 POSTCODE_SEVERITY_ERR);
444 }
445 }
446}
447
448static void
449proc_DeInit(void)
450{
451 if (ProcDir != NULL)
452 remove_proc_entry(MYDRVNAME, NULL);
453 ProcDir = NULL;
454}
455
456#if 0
457static void
458testUnicode(void)
459{
460 wchar_t unicodeString[] = { 'a', 'b', 'c', 0 };
461 char s[sizeof(unicodeString) * NLS_MAX_CHARSET_SIZE];
462 wchar_t unicode2[99];
463
464 /* NOTE: Either due to a bug, or feature I don't understand, the
465 * kernel utf8_mbstowcs() and utf_wcstombs() do NOT copy the
466 * trailed NUL byte!! REALLY!!!!! Arrrrgggghhhhh
467 */
468
469 LOGINF("sizeof(wchar_t) = %d", sizeof(wchar_t));
470 LOGINF("utf8_wcstombs=%d",
471 chrs = utf8_wcstombs(s, unicodeString, sizeof(s)));
472 if (chrs >= 0)
473 s[chrs] = '\0'; /* GRRRRRRRR */
474 LOGINF("s='%s'", s);
475 LOGINF("utf8_mbstowcs=%d", chrs = utf8_mbstowcs(unicode2, s, 100));
476 if (chrs >= 0)
477 unicode2[chrs] = 0; /* GRRRRRRRR */
478 if (memcmp(unicodeString, unicode2, sizeof(unicodeString)) == 0)
479 LOGINF("strings match... good");
480 else
481 LOGINF("strings did not match!!");
482}
483#endif
484
485static void
486busInfo_clear(void *v)
487{
488 VISORCHIPSET_BUS_INFO *p = (VISORCHIPSET_BUS_INFO *) (v);
489
490 if (p->procObject) {
927c7927 491 visor_proc_DestroyObject(p->procObject);
12e364b9
KC
492 p->procObject = NULL;
493 }
494 kfree(p->name);
495 p->name = NULL;
496
497 kfree(p->description);
498 p->description = NULL;
499
500 p->state.created = 0;
501 memset(p, 0, sizeof(VISORCHIPSET_BUS_INFO));
502}
503
504static void
505devInfo_clear(void *v)
506{
507 VISORCHIPSET_DEVICE_INFO *p = (VISORCHIPSET_DEVICE_INFO *) (v);
508 p->state.created = 0;
509 memset(p, 0, sizeof(VISORCHIPSET_DEVICE_INFO));
510}
511
512static U8
513check_chipset_events(void)
514{
515 int i;
516 U8 send_msg = 1;
517 /* Check events to determine if response should be sent */
518 for (i = 0; i < MAX_CHIPSET_EVENTS; i++)
519 send_msg &= chipset_events[i];
520 return send_msg;
521}
522
523static void
524clear_chipset_events(void)
525{
526 int i;
527 /* Clear chipset_events */
528 for (i = 0; i < MAX_CHIPSET_EVENTS; i++)
529 chipset_events[i] = 0;
530}
531
532void
533visorchipset_register_busdev_server(VISORCHIPSET_BUSDEV_NOTIFIERS *notifiers,
534 VISORCHIPSET_BUSDEV_RESPONDERS *responders,
535 ULTRA_VBUS_DEVICEINFO *driverInfo)
536{
537 LOCKSEM_UNINTERRUPTIBLE(&NotifierLock);
538 if (notifiers == NULL) {
539 memset(&BusDev_Server_Notifiers, 0,
540 sizeof(BusDev_Server_Notifiers));
541 serverregistered = 0; /* clear flag */
542 } else {
543 BusDev_Server_Notifiers = *notifiers;
544 serverregistered = 1; /* set flag */
545 }
546 if (responders)
547 *responders = BusDev_Responders;
548 if (driverInfo)
549 BusDeviceInfo_Init(driverInfo, "chipset", "visorchipset",
836bee9e 550 VERSION, NULL);
12e364b9
KC
551
552 UNLOCKSEM(&NotifierLock);
553}
554EXPORT_SYMBOL_GPL(visorchipset_register_busdev_server);
555
556void
557visorchipset_register_busdev_client(VISORCHIPSET_BUSDEV_NOTIFIERS *notifiers,
558 VISORCHIPSET_BUSDEV_RESPONDERS *responders,
559 ULTRA_VBUS_DEVICEINFO *driverInfo)
560{
561 LOCKSEM_UNINTERRUPTIBLE(&NotifierLock);
562 if (notifiers == NULL) {
563 memset(&BusDev_Client_Notifiers, 0,
564 sizeof(BusDev_Client_Notifiers));
565 clientregistered = 0; /* clear flag */
566 } else {
567 BusDev_Client_Notifiers = *notifiers;
568 clientregistered = 1; /* set flag */
569 }
570 if (responders)
571 *responders = BusDev_Responders;
572 if (driverInfo)
573 BusDeviceInfo_Init(driverInfo, "chipset(bolts)", "visorchipset",
836bee9e 574 VERSION, NULL);
12e364b9
KC
575 UNLOCKSEM(&NotifierLock);
576}
577EXPORT_SYMBOL_GPL(visorchipset_register_busdev_client);
578
579static void
580cleanup_controlvm_structures(void)
581{
e6b1ea77
DC
582 VISORCHIPSET_BUS_INFO *bi, *tmp_bi;
583 VISORCHIPSET_DEVICE_INFO *di, *tmp_di;
12e364b9 584
e6b1ea77 585 list_for_each_entry_safe(bi, tmp_bi, &BusInfoList, entry) {
12e364b9
KC
586 busInfo_clear(bi);
587 list_del(&bi->entry);
588 kfree(bi);
589 }
590
e6b1ea77 591 list_for_each_entry_safe(di, tmp_di, &DevInfoList, entry) {
12e364b9
KC
592 devInfo_clear(di);
593 list_del(&di->entry);
594 kfree(di);
595 }
596}
597
598static void
599chipset_init(CONTROLVM_MESSAGE *inmsg)
600{
601 static int chipset_inited;
602 ULTRA_CHIPSET_FEATURE features = 0;
603 int rc = CONTROLVM_RESP_SUCCESS;
604
605 POSTCODE_LINUX_2(CHIPSET_INIT_ENTRY_PC, POSTCODE_SEVERITY_INFO);
606 if (chipset_inited) {
607 LOGERR("CONTROLVM_CHIPSET_INIT Failed: Already Done.");
22ad57ba
KC
608 rc = -CONTROLVM_RESP_ERROR_ALREADY_DONE;
609 goto Away;
12e364b9
KC
610 }
611 chipset_inited = 1;
612 POSTCODE_LINUX_2(CHIPSET_INIT_EXIT_PC, POSTCODE_SEVERITY_INFO);
613
614 /* Set features to indicate we support parahotplug (if Command
615 * also supports it). */
616 features =
617 inmsg->cmd.initChipset.
618 features & ULTRA_CHIPSET_FEATURE_PARA_HOTPLUG;
619
620 /* Set the "reply" bit so Command knows this is a
621 * features-aware driver. */
622 features |= ULTRA_CHIPSET_FEATURE_REPLY;
623
624Away:
625 if (rc < 0)
626 cleanup_controlvm_structures();
627 if (inmsg->hdr.Flags.responseExpected)
628 controlvm_respond_chipset_init(&inmsg->hdr, rc, features);
629}
630
631static void
632controlvm_init_response(CONTROLVM_MESSAGE *msg,
633 CONTROLVM_MESSAGE_HEADER *msgHdr, int response)
634{
635 memset(msg, 0, sizeof(CONTROLVM_MESSAGE));
636 memcpy(&msg->hdr, msgHdr, sizeof(CONTROLVM_MESSAGE_HEADER));
637 msg->hdr.PayloadBytes = 0;
638 msg->hdr.PayloadVmOffset = 0;
639 msg->hdr.PayloadMaxBytes = 0;
640 if (response < 0) {
641 msg->hdr.Flags.failed = 1;
642 msg->hdr.CompletionStatus = (U32) (-response);
643 }
644}
645
646static void
647controlvm_respond(CONTROLVM_MESSAGE_HEADER *msgHdr, int response)
648{
649 CONTROLVM_MESSAGE outmsg;
12e364b9
KC
650 controlvm_init_response(&outmsg, msgHdr, response);
651 /* For DiagPool channel DEVICE_CHANGESTATE, we need to send
652 * back the deviceChangeState structure in the packet. */
653 if (msgHdr->Id == CONTROLVM_DEVICE_CHANGESTATE
654 && g_DeviceChangeStatePacket.deviceChangeState.busNo ==
655 g_diagpoolBusNo
656 && g_DeviceChangeStatePacket.deviceChangeState.devNo ==
657 g_diagpoolDevNo)
658 outmsg.cmd = g_DeviceChangeStatePacket;
659 if (outmsg.hdr.Flags.testMessage == 1) {
660 LOGINF("%s controlvm_msg=0x%x response=%d for test message",
661 __func__, outmsg.hdr.Id, response);
662 return;
663 }
664 if (!visorchannel_signalinsert(ControlVm_channel,
665 CONTROLVM_QUEUE_REQUEST, &outmsg)) {
666 LOGERR("signalinsert failed!");
667 return;
668 }
669}
670
671static void
672controlvm_respond_chipset_init(CONTROLVM_MESSAGE_HEADER *msgHdr, int response,
673 ULTRA_CHIPSET_FEATURE features)
674{
675 CONTROLVM_MESSAGE outmsg;
12e364b9
KC
676 controlvm_init_response(&outmsg, msgHdr, response);
677 outmsg.cmd.initChipset.features = features;
678 if (!visorchannel_signalinsert(ControlVm_channel,
679 CONTROLVM_QUEUE_REQUEST, &outmsg)) {
680 LOGERR("signalinsert failed!");
681 return;
682 }
683}
684
685static void
686controlvm_respond_physdev_changestate(CONTROLVM_MESSAGE_HEADER *msgHdr,
687 int response, ULTRA_SEGMENT_STATE state)
688{
689 CONTROLVM_MESSAGE outmsg;
12e364b9
KC
690 controlvm_init_response(&outmsg, msgHdr, response);
691 outmsg.cmd.deviceChangeState.state = state;
692 outmsg.cmd.deviceChangeState.flags.physicalDevice = 1;
693 if (!visorchannel_signalinsert(ControlVm_channel,
694 CONTROLVM_QUEUE_REQUEST, &outmsg)) {
695 LOGERR("signalinsert failed!");
696 return;
697 }
698}
699
700void
701visorchipset_save_message(CONTROLVM_MESSAGE *msg, CRASH_OBJ_TYPE type)
702{
703 U32 localSavedCrashMsgOffset;
704 U16 localSavedCrashMsgCount;
705
706 /* get saved message count */
707 if (visorchannel_read(ControlVm_channel,
708 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
709 SavedCrashMsgCount),
710 &localSavedCrashMsgCount, sizeof(U16)) < 0) {
711 LOGERR("failed to get Saved Message Count");
712 POSTCODE_LINUX_2(CRASH_DEV_CTRL_RD_FAILURE_PC,
713 POSTCODE_SEVERITY_ERR);
714 return;
715 }
716
717 if (localSavedCrashMsgCount != CONTROLVM_CRASHMSG_MAX) {
718 LOGERR("Saved Message Count incorrect %d",
719 localSavedCrashMsgCount);
720 POSTCODE_LINUX_3(CRASH_DEV_COUNT_FAILURE_PC,
721 localSavedCrashMsgCount,
722 POSTCODE_SEVERITY_ERR);
723 return;
724 }
725
726 /* get saved crash message offset */
727 if (visorchannel_read(ControlVm_channel,
728 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
729 SavedCrashMsgOffset),
730 &localSavedCrashMsgOffset, sizeof(U32)) < 0) {
731 LOGERR("failed to get Saved Message Offset");
732 POSTCODE_LINUX_2(CRASH_DEV_CTRL_RD_FAILURE_PC,
733 POSTCODE_SEVERITY_ERR);
734 return;
735 }
736
737 if (type == CRASH_bus) {
738 if (visorchannel_write(ControlVm_channel,
739 localSavedCrashMsgOffset,
740 msg, sizeof(CONTROLVM_MESSAGE)) < 0) {
741 LOGERR("SAVE_MSG_BUS_FAILURE: Failed to write CrashCreateBusMsg!");
742 POSTCODE_LINUX_2(SAVE_MSG_BUS_FAILURE_PC,
743 POSTCODE_SEVERITY_ERR);
744 return;
745 }
746 } else {
747 if (visorchannel_write(ControlVm_channel,
748 localSavedCrashMsgOffset +
749 sizeof(CONTROLVM_MESSAGE), msg,
750 sizeof(CONTROLVM_MESSAGE)) < 0) {
751 LOGERR("SAVE_MSG_DEV_FAILURE: Failed to write CrashCreateDevMsg!");
752 POSTCODE_LINUX_2(SAVE_MSG_DEV_FAILURE_PC,
753 POSTCODE_SEVERITY_ERR);
754 return;
755 }
756 }
757}
758EXPORT_SYMBOL_GPL(visorchipset_save_message);
759
760static void
761bus_responder(CONTROLVM_ID cmdId, ulong busNo, int response)
762{
763 VISORCHIPSET_BUS_INFO *p = NULL;
764 BOOL need_clear = FALSE;
765
766 p = findbus(&BusInfoList, busNo);
767 if (!p) {
768 LOGERR("internal error busNo=%lu", busNo);
769 return;
770 }
771 if (response < 0) {
772 if ((cmdId == CONTROLVM_BUS_CREATE) &&
773 (response != (-CONTROLVM_RESP_ERROR_ALREADY_DONE)))
774 /* undo the row we just created... */
775 delbusdevices(&DevInfoList, busNo);
776 } else {
777 if (cmdId == CONTROLVM_BUS_CREATE)
778 p->state.created = 1;
779 if (cmdId == CONTROLVM_BUS_DESTROY)
780 need_clear = TRUE;
781 }
782
783 if (p->pendingMsgHdr.Id == CONTROLVM_INVALID) {
784 LOGERR("bus_responder no pending msg");
785 return; /* no controlvm response needed */
786 }
787 if (p->pendingMsgHdr.Id != (U32) cmdId) {
788 LOGERR("expected=%d, found=%d", cmdId, p->pendingMsgHdr.Id);
789 return;
790 }
791 controlvm_respond(&p->pendingMsgHdr, response);
792 p->pendingMsgHdr.Id = CONTROLVM_INVALID;
793 if (need_clear) {
794 busInfo_clear(p);
795 delbusdevices(&DevInfoList, busNo);
796 }
797}
798
799static void
800device_changestate_responder(CONTROLVM_ID cmdId,
801 ulong busNo, ulong devNo, int response,
802 ULTRA_SEGMENT_STATE responseState)
803{
804 VISORCHIPSET_DEVICE_INFO *p = NULL;
805 CONTROLVM_MESSAGE outmsg;
806
12e364b9
KC
807 p = finddevice(&DevInfoList, busNo, devNo);
808 if (!p) {
809 LOGERR("internal error; busNo=%lu, devNo=%lu", busNo, devNo);
810 return;
811 }
812 if (p->pendingMsgHdr.Id == CONTROLVM_INVALID) {
813 LOGERR("device_responder no pending msg");
814 return; /* no controlvm response needed */
815 }
816 if (p->pendingMsgHdr.Id != cmdId) {
817 LOGERR("expected=%d, found=%d", cmdId, p->pendingMsgHdr.Id);
818 return;
819 }
820
821 controlvm_init_response(&outmsg, &p->pendingMsgHdr, response);
822
823 outmsg.cmd.deviceChangeState.busNo = busNo;
824 outmsg.cmd.deviceChangeState.devNo = devNo;
825 outmsg.cmd.deviceChangeState.state = responseState;
826
827 if (!visorchannel_signalinsert(ControlVm_channel,
828 CONTROLVM_QUEUE_REQUEST, &outmsg)) {
829 LOGERR("signalinsert failed!");
830 return;
831 }
832
833 p->pendingMsgHdr.Id = CONTROLVM_INVALID;
834}
835
836static void
837device_responder(CONTROLVM_ID cmdId, ulong busNo, ulong devNo, int response)
838{
839 VISORCHIPSET_DEVICE_INFO *p = NULL;
840 BOOL need_clear = FALSE;
841
842 p = finddevice(&DevInfoList, busNo, devNo);
843 if (!p) {
844 LOGERR("internal error; busNo=%lu, devNo=%lu", busNo, devNo);
845 return;
846 }
847 if (response >= 0) {
848 if (cmdId == CONTROLVM_DEVICE_CREATE)
849 p->state.created = 1;
850 if (cmdId == CONTROLVM_DEVICE_DESTROY)
851 need_clear = TRUE;
852 }
853
854 if (p->pendingMsgHdr.Id == CONTROLVM_INVALID) {
855 LOGERR("device_responder no pending msg");
856 return; /* no controlvm response needed */
857 }
858 if (p->pendingMsgHdr.Id != (U32) cmdId) {
859 LOGERR("expected=%d, found=%d", cmdId, p->pendingMsgHdr.Id);
860 return;
861 }
862 controlvm_respond(&p->pendingMsgHdr, response);
863 p->pendingMsgHdr.Id = CONTROLVM_INVALID;
864 if (need_clear)
865 devInfo_clear(p);
866}
867
868static void
869bus_epilog(U32 busNo,
870 U32 cmd, CONTROLVM_MESSAGE_HEADER *msgHdr,
871 int response, BOOL needResponse)
872{
873 BOOL notified = FALSE;
874
875 VISORCHIPSET_BUS_INFO *pBusInfo = findbus(&BusInfoList, busNo);
876
877 if (!pBusInfo) {
878 LOGERR("HUH? bad busNo=%d", busNo);
879 return;
880 }
881 if (needResponse) {
882 memcpy(&pBusInfo->pendingMsgHdr, msgHdr,
883 sizeof(CONTROLVM_MESSAGE_HEADER));
884 } else
885 pBusInfo->pendingMsgHdr.Id = CONTROLVM_INVALID;
886
887 LOCKSEM_UNINTERRUPTIBLE(&NotifierLock);
888 if (response == CONTROLVM_RESP_SUCCESS) {
889 switch (cmd) {
890 case CONTROLVM_BUS_CREATE:
891 /* We can't tell from the bus_create
892 * information which of our 2 bus flavors the
893 * devices on this bus will ultimately end up.
894 * FORTUNATELY, it turns out it is harmless to
895 * send the bus_create to both of them. We can
896 * narrow things down a little bit, though,
897 * because we know: - BusDev_Server can handle
898 * either server or client devices
899 * - BusDev_Client can handle ONLY client
900 * devices */
901 if (BusDev_Server_Notifiers.bus_create) {
902 (*BusDev_Server_Notifiers.bus_create) (busNo);
903 notified = TRUE;
904 }
905 if ((!pBusInfo->flags.server) /*client */ &&
906 BusDev_Client_Notifiers.bus_create) {
907 (*BusDev_Client_Notifiers.bus_create) (busNo);
908 notified = TRUE;
909 }
910 break;
911 case CONTROLVM_BUS_DESTROY:
912 if (BusDev_Server_Notifiers.bus_destroy) {
913 (*BusDev_Server_Notifiers.bus_destroy) (busNo);
914 notified = TRUE;
915 }
916 if ((!pBusInfo->flags.server) /*client */ &&
917 BusDev_Client_Notifiers.bus_destroy) {
918 (*BusDev_Client_Notifiers.bus_destroy) (busNo);
919 notified = TRUE;
920 }
921 break;
922 }
923 }
924 if (notified)
925 /* The callback function just called above is responsible
926 * for calling the appropriate VISORCHIPSET_BUSDEV_RESPONDERS
927 * function, which will call bus_responder()
928 */
929 ;
930 else
931 bus_responder(cmd, busNo, response);
932 UNLOCKSEM(&NotifierLock);
933}
934
935static void
936device_epilog(U32 busNo, U32 devNo, ULTRA_SEGMENT_STATE state, U32 cmd,
937 CONTROLVM_MESSAGE_HEADER *msgHdr, int response,
938 BOOL needResponse, BOOL for_visorbus)
939{
940 VISORCHIPSET_BUSDEV_NOTIFIERS *notifiers = NULL;
941 BOOL notified = FALSE;
942
943 VISORCHIPSET_DEVICE_INFO *pDevInfo =
944 finddevice(&DevInfoList, busNo, devNo);
945 char *envp[] = {
946 "SPARSP_DIAGPOOL_PAUSED_STATE = 1",
947 NULL
948 };
949
950 if (!pDevInfo) {
951 LOGERR("HUH? bad busNo=%d, devNo=%d", busNo, devNo);
952 return;
953 }
954 if (for_visorbus)
955 notifiers = &BusDev_Server_Notifiers;
956 else
957 notifiers = &BusDev_Client_Notifiers;
958 if (needResponse) {
959 memcpy(&pDevInfo->pendingMsgHdr, msgHdr,
960 sizeof(CONTROLVM_MESSAGE_HEADER));
961 } else
962 pDevInfo->pendingMsgHdr.Id = CONTROLVM_INVALID;
963
964 LOCKSEM_UNINTERRUPTIBLE(&NotifierLock);
965 if (response >= 0) {
966 switch (cmd) {
967 case CONTROLVM_DEVICE_CREATE:
968 if (notifiers->device_create) {
969 (*notifiers->device_create) (busNo, devNo);
970 notified = TRUE;
971 }
972 break;
973 case CONTROLVM_DEVICE_CHANGESTATE:
974 /* ServerReady / ServerRunning / SegmentStateRunning */
975 if (state.Alive == SegmentStateRunning.Alive &&
976 state.Operating == SegmentStateRunning.Operating) {
977 if (notifiers->device_resume) {
978 (*notifiers->device_resume) (busNo,
979 devNo);
980 notified = TRUE;
981 }
982 }
983 /* ServerNotReady / ServerLost / SegmentStateStandby */
984 else if (state.Alive == SegmentStateStandby.Alive &&
985 state.Operating ==
986 SegmentStateStandby.Operating) {
987 /* technically this is standby case
988 * where server is lost
989 */
990 if (notifiers->device_pause) {
991 (*notifiers->device_pause) (busNo,
992 devNo);
993 notified = TRUE;
994 }
995 } else if (state.Alive == SegmentStatePaused.Alive &&
996 state.Operating ==
997 SegmentStatePaused.Operating) {
998 /* this is lite pause where channel is
999 * still valid just 'pause' of it
1000 */
1001 if (busNo == g_diagpoolBusNo
1002 && devNo == g_diagpoolDevNo) {
1003 LOGINF("DEVICE_CHANGESTATE(DiagpoolChannel busNo=%d devNo=%d is pausing...)",
1004 busNo, devNo);
1005 /* this will trigger the
1006 * diag_shutdown.sh script in
1007 * the visorchipset hotplug */
1008 kobject_uevent_env
1009 (&Visorchipset_platform_device.dev.
1010 kobj, KOBJ_ONLINE, envp);
1011 }
1012 }
1013 break;
1014 case CONTROLVM_DEVICE_DESTROY:
1015 if (notifiers->device_destroy) {
1016 (*notifiers->device_destroy) (busNo, devNo);
1017 notified = TRUE;
1018 }
1019 break;
1020 }
1021 }
1022 if (notified)
1023 /* The callback function just called above is responsible
1024 * for calling the appropriate VISORCHIPSET_BUSDEV_RESPONDERS
1025 * function, which will call device_responder()
1026 */
1027 ;
1028 else
1029 device_responder(cmd, busNo, devNo, response);
1030 UNLOCKSEM(&NotifierLock);
1031}
1032
1033static void
1034bus_create(CONTROLVM_MESSAGE *inmsg)
1035{
1036 CONTROLVM_MESSAGE_PACKET *cmd = &inmsg->cmd;
1037 ulong busNo = cmd->createBus.busNo;
1038 int rc = CONTROLVM_RESP_SUCCESS;
1039 VISORCHIPSET_BUS_INFO *pBusInfo = NULL;
1040
1041
1042 pBusInfo = findbus(&BusInfoList, busNo);
1043 if (pBusInfo && (pBusInfo->state.created == 1)) {
1044 LOGERR("CONTROLVM_BUS_CREATE Failed: bus %lu already exists",
1045 busNo);
1046 POSTCODE_LINUX_3(BUS_CREATE_FAILURE_PC, busNo,
1047 POSTCODE_SEVERITY_ERR);
22ad57ba
KC
1048 rc = -CONTROLVM_RESP_ERROR_ALREADY_DONE;
1049 goto Away;
12e364b9 1050 }
97a84f12 1051 pBusInfo = kzalloc(sizeof(VISORCHIPSET_BUS_INFO), GFP_KERNEL);
12e364b9 1052 if (pBusInfo == NULL) {
97a84f12 1053 LOGERR("CONTROLVM_BUS_CREATE Failed: bus %lu kzalloc failed",
12e364b9
KC
1054 busNo);
1055 POSTCODE_LINUX_3(BUS_CREATE_FAILURE_PC, busNo,
1056 POSTCODE_SEVERITY_ERR);
22ad57ba
KC
1057 rc = -CONTROLVM_RESP_ERROR_KMALLOC_FAILED;
1058 goto Away;
12e364b9
KC
1059 }
1060
12e364b9
KC
1061 INIT_LIST_HEAD(&pBusInfo->entry);
1062 pBusInfo->busNo = busNo;
1063 pBusInfo->devNo = cmd->createBus.deviceCount;
1064
1065 POSTCODE_LINUX_3(BUS_CREATE_ENTRY_PC, busNo, POSTCODE_SEVERITY_INFO);
1066
1067 if (inmsg->hdr.Flags.testMessage == 1)
1068 pBusInfo->chanInfo.addrType = ADDRTYPE_localTest;
1069 else
1070 pBusInfo->chanInfo.addrType = ADDRTYPE_localPhysical;
1071
1072 pBusInfo->flags.server = inmsg->hdr.Flags.server;
1073 pBusInfo->chanInfo.channelAddr = cmd->createBus.channelAddr;
1074 pBusInfo->chanInfo.nChannelBytes = cmd->createBus.channelBytes;
1075 pBusInfo->chanInfo.channelTypeGuid = cmd->createBus.busDataTypeGuid;
1076 pBusInfo->chanInfo.channelInstGuid = cmd->createBus.busInstGuid;
1077
1078 list_add(&pBusInfo->entry, &BusInfoList);
1079
1080 POSTCODE_LINUX_3(BUS_CREATE_EXIT_PC, busNo, POSTCODE_SEVERITY_INFO);
1081
1082Away:
1083 bus_epilog(busNo, CONTROLVM_BUS_CREATE, &inmsg->hdr,
1084 rc, inmsg->hdr.Flags.responseExpected == 1);
1085}
1086
1087static void
1088bus_destroy(CONTROLVM_MESSAGE *inmsg)
1089{
1090 CONTROLVM_MESSAGE_PACKET *cmd = &inmsg->cmd;
1091 ulong busNo = cmd->destroyBus.busNo;
1092 VISORCHIPSET_BUS_INFO *pBusInfo;
1093 int rc = CONTROLVM_RESP_SUCCESS;
1094
1095 pBusInfo = findbus(&BusInfoList, busNo);
1096 if (!pBusInfo) {
1097 LOGERR("CONTROLVM_BUS_DESTROY Failed: bus %lu invalid", busNo);
22ad57ba
KC
1098 rc = -CONTROLVM_RESP_ERROR_BUS_INVALID;
1099 goto Away;
12e364b9
KC
1100 }
1101 if (pBusInfo->state.created == 0) {
1102 LOGERR("CONTROLVM_BUS_DESTROY Failed: bus %lu already destroyed",
1103 busNo);
22ad57ba
KC
1104 rc = -CONTROLVM_RESP_ERROR_ALREADY_DONE;
1105 goto Away;
12e364b9
KC
1106 }
1107
1108Away:
1109 bus_epilog(busNo, CONTROLVM_BUS_DESTROY, &inmsg->hdr,
1110 rc, inmsg->hdr.Flags.responseExpected == 1);
1111}
1112
1113static void
1114bus_configure(CONTROLVM_MESSAGE *inmsg, PARSER_CONTEXT *parser_ctx)
1115{
1116 CONTROLVM_MESSAGE_PACKET *cmd = &inmsg->cmd;
1117 ulong busNo = cmd->configureBus.busNo;
1118 VISORCHIPSET_BUS_INFO *pBusInfo = NULL;
1119 int rc = CONTROLVM_RESP_SUCCESS;
1120 char s[99];
1121
1122 busNo = cmd->configureBus.busNo;
1123 POSTCODE_LINUX_3(BUS_CONFIGURE_ENTRY_PC, busNo, POSTCODE_SEVERITY_INFO);
1124
1125 pBusInfo = findbus(&BusInfoList, busNo);
1126 if (!pBusInfo) {
1127 LOGERR("CONTROLVM_BUS_CONFIGURE Failed: bus %lu invalid",
1128 busNo);
1129 POSTCODE_LINUX_3(BUS_CONFIGURE_FAILURE_PC, busNo,
1130 POSTCODE_SEVERITY_ERR);
22ad57ba
KC
1131 rc = -CONTROLVM_RESP_ERROR_BUS_INVALID;
1132 goto Away;
12e364b9
KC
1133 }
1134 if (pBusInfo->state.created == 0) {
1135 LOGERR("CONTROLVM_BUS_CONFIGURE Failed: Invalid bus %lu - not created yet",
1136 busNo);
1137 POSTCODE_LINUX_3(BUS_CONFIGURE_FAILURE_PC, busNo,
1138 POSTCODE_SEVERITY_ERR);
22ad57ba
KC
1139 rc = -CONTROLVM_RESP_ERROR_BUS_INVALID;
1140 goto Away;
12e364b9
KC
1141 }
1142 /* TBD - add this check to other commands also... */
1143 if (pBusInfo->pendingMsgHdr.Id != CONTROLVM_INVALID) {
1144 LOGERR("CONTROLVM_BUS_CONFIGURE Failed: bus %lu MsgId=%u outstanding",
1145 busNo, (uint) pBusInfo->pendingMsgHdr.Id);
1146 POSTCODE_LINUX_3(BUS_CONFIGURE_FAILURE_PC, busNo,
1147 POSTCODE_SEVERITY_ERR);
22ad57ba
KC
1148 rc = -CONTROLVM_RESP_ERROR_MESSAGE_ID_INVALID_FOR_CLIENT;
1149 goto Away;
12e364b9
KC
1150 }
1151
1152 pBusInfo->partitionHandle = cmd->configureBus.guestHandle;
1153 pBusInfo->partitionGuid = parser_id_get(parser_ctx);
1154 parser_param_start(parser_ctx, PARSERSTRING_NAME);
1155 pBusInfo->name = parser_string_get(parser_ctx);
1156
90addb02 1157 visorchannel_uuid_id(&pBusInfo->partitionGuid, s);
12e364b9 1158 pBusInfo->procObject =
927c7927 1159 visor_proc_CreateObject(PartitionType, s, (void *) (pBusInfo));
12e364b9
KC
1160 if (pBusInfo->procObject == NULL) {
1161 LOGERR("CONTROLVM_BUS_CONFIGURE Failed: busNo=%lu failed to create /proc entry",
1162 busNo);
1163 POSTCODE_LINUX_3(BUS_CONFIGURE_FAILURE_PC, busNo,
1164 POSTCODE_SEVERITY_ERR);
22ad57ba
KC
1165 rc = -CONTROLVM_RESP_ERROR_KMALLOC_FAILED;
1166 goto Away;
12e364b9
KC
1167 }
1168 POSTCODE_LINUX_3(BUS_CONFIGURE_EXIT_PC, busNo, POSTCODE_SEVERITY_INFO);
1169Away:
1170 bus_epilog(busNo, CONTROLVM_BUS_CONFIGURE, &inmsg->hdr,
1171 rc, inmsg->hdr.Flags.responseExpected == 1);
1172}
1173
1174static void
1175my_device_create(CONTROLVM_MESSAGE *inmsg)
1176{
1177 CONTROLVM_MESSAGE_PACKET *cmd = &inmsg->cmd;
1178 ulong busNo = cmd->createDevice.busNo;
1179 ulong devNo = cmd->createDevice.devNo;
1180 VISORCHIPSET_DEVICE_INFO *pDevInfo = NULL;
1181 VISORCHIPSET_BUS_INFO *pBusInfo = NULL;
1182 int rc = CONTROLVM_RESP_SUCCESS;
1183
1184 pDevInfo = finddevice(&DevInfoList, busNo, devNo);
1185 if (pDevInfo && (pDevInfo->state.created == 1)) {
1186 LOGERR("CONTROLVM_DEVICE_CREATE Failed: busNo=%lu, devNo=%lu already exists",
1187 busNo, devNo);
1188 POSTCODE_LINUX_4(DEVICE_CREATE_FAILURE_PC, devNo, busNo,
1189 POSTCODE_SEVERITY_ERR);
22ad57ba
KC
1190 rc = -CONTROLVM_RESP_ERROR_ALREADY_DONE;
1191 goto Away;
12e364b9
KC
1192 }
1193 pBusInfo = findbus(&BusInfoList, busNo);
1194 if (!pBusInfo) {
1195 LOGERR("CONTROLVM_DEVICE_CREATE Failed: Invalid bus %lu - out of range",
1196 busNo);
1197 POSTCODE_LINUX_4(DEVICE_CREATE_FAILURE_PC, devNo, busNo,
1198 POSTCODE_SEVERITY_ERR);
22ad57ba
KC
1199 rc = -CONTROLVM_RESP_ERROR_BUS_INVALID;
1200 goto Away;
12e364b9
KC
1201 }
1202 if (pBusInfo->state.created == 0) {
1203 LOGERR("CONTROLVM_DEVICE_CREATE Failed: Invalid bus %lu - not created yet",
1204 busNo);
1205 POSTCODE_LINUX_4(DEVICE_CREATE_FAILURE_PC, devNo, busNo,
1206 POSTCODE_SEVERITY_ERR);
22ad57ba
KC
1207 rc = -CONTROLVM_RESP_ERROR_BUS_INVALID;
1208 goto Away;
12e364b9 1209 }
97a84f12 1210 pDevInfo = kzalloc(sizeof(VISORCHIPSET_DEVICE_INFO), GFP_KERNEL);
12e364b9
KC
1211 if (pDevInfo == NULL) {
1212 LOGERR("CONTROLVM_DEVICE_CREATE Failed: busNo=%lu, devNo=%lu kmaloc failed",
1213 busNo, devNo);
1214 POSTCODE_LINUX_4(DEVICE_CREATE_FAILURE_PC, devNo, busNo,
1215 POSTCODE_SEVERITY_ERR);
22ad57ba
KC
1216 rc = -CONTROLVM_RESP_ERROR_KMALLOC_FAILED;
1217 goto Away;
12e364b9 1218 }
97a84f12 1219
12e364b9
KC
1220 INIT_LIST_HEAD(&pDevInfo->entry);
1221 pDevInfo->busNo = busNo;
1222 pDevInfo->devNo = devNo;
1223 pDevInfo->devInstGuid = cmd->createDevice.devInstGuid;
1224 POSTCODE_LINUX_4(DEVICE_CREATE_ENTRY_PC, devNo, busNo,
1225 POSTCODE_SEVERITY_INFO);
1226
1227 if (inmsg->hdr.Flags.testMessage == 1)
1228 pDevInfo->chanInfo.addrType = ADDRTYPE_localTest;
1229 else
1230 pDevInfo->chanInfo.addrType = ADDRTYPE_localPhysical;
1231 pDevInfo->chanInfo.channelAddr = cmd->createDevice.channelAddr;
1232 pDevInfo->chanInfo.nChannelBytes = cmd->createDevice.channelBytes;
1233 pDevInfo->chanInfo.channelTypeGuid = cmd->createDevice.dataTypeGuid;
1234 pDevInfo->chanInfo.intr = cmd->createDevice.intr;
1235 list_add(&pDevInfo->entry, &DevInfoList);
1236 POSTCODE_LINUX_4(DEVICE_CREATE_EXIT_PC, devNo, busNo,
1237 POSTCODE_SEVERITY_INFO);
1238Away:
1239 /* get the bus and devNo for DiagPool channel */
1240 if (is_diagpool_channel(pDevInfo->chanInfo.channelTypeGuid)) {
1241 g_diagpoolBusNo = busNo;
1242 g_diagpoolDevNo = devNo;
1243 LOGINF("CONTROLVM_DEVICE_CREATE for DiagPool channel: busNo=%lu, devNo=%lu",
1244 g_diagpoolBusNo, g_diagpoolDevNo);
1245 }
1246 device_epilog(busNo, devNo, SegmentStateRunning,
1247 CONTROLVM_DEVICE_CREATE, &inmsg->hdr, rc,
1248 inmsg->hdr.Flags.responseExpected == 1,
1249 FOR_VISORBUS(pDevInfo->chanInfo.channelTypeGuid));
1250}
1251
1252static void
1253my_device_changestate(CONTROLVM_MESSAGE *inmsg)
1254{
1255 CONTROLVM_MESSAGE_PACKET *cmd = &inmsg->cmd;
1256 ulong busNo = cmd->deviceChangeState.busNo;
1257 ulong devNo = cmd->deviceChangeState.devNo;
1258 ULTRA_SEGMENT_STATE state = cmd->deviceChangeState.state;
1259 VISORCHIPSET_DEVICE_INFO *pDevInfo = NULL;
1260 int rc = CONTROLVM_RESP_SUCCESS;
1261
1262 pDevInfo = finddevice(&DevInfoList, busNo, devNo);
1263 if (!pDevInfo) {
1264 LOGERR("CONTROLVM_DEVICE_CHANGESTATE Failed: busNo=%lu, devNo=%lu invalid (doesn't exist)",
1265 busNo, devNo);
1266 POSTCODE_LINUX_4(DEVICE_CHANGESTATE_FAILURE_PC, devNo, busNo,
1267 POSTCODE_SEVERITY_ERR);
22ad57ba
KC
1268 rc = -CONTROLVM_RESP_ERROR_DEVICE_INVALID;
1269 goto Away;
12e364b9
KC
1270 }
1271 if (pDevInfo->state.created == 0) {
1272 LOGERR("CONTROLVM_DEVICE_CHANGESTATE Failed: busNo=%lu, devNo=%lu invalid (not created)",
1273 busNo, devNo);
1274 POSTCODE_LINUX_4(DEVICE_CHANGESTATE_FAILURE_PC, devNo, busNo,
1275 POSTCODE_SEVERITY_ERR);
22ad57ba 1276 rc = -CONTROLVM_RESP_ERROR_DEVICE_INVALID;
12e364b9
KC
1277 }
1278Away:
1279 if ((rc >= CONTROLVM_RESP_SUCCESS) && pDevInfo)
1280 device_epilog(busNo, devNo, state, CONTROLVM_DEVICE_CHANGESTATE,
1281 &inmsg->hdr, rc,
1282 inmsg->hdr.Flags.responseExpected == 1,
1283 FOR_VISORBUS(pDevInfo->chanInfo.channelTypeGuid));
1284}
1285
1286static void
1287my_device_destroy(CONTROLVM_MESSAGE *inmsg)
1288{
1289 CONTROLVM_MESSAGE_PACKET *cmd = &inmsg->cmd;
1290 ulong busNo = cmd->destroyDevice.busNo;
1291 ulong devNo = cmd->destroyDevice.devNo;
1292 VISORCHIPSET_DEVICE_INFO *pDevInfo = NULL;
1293 int rc = CONTROLVM_RESP_SUCCESS;
1294
1295 pDevInfo = finddevice(&DevInfoList, busNo, devNo);
1296 if (!pDevInfo) {
1297 LOGERR("CONTROLVM_DEVICE_DESTROY Failed: busNo=%lu, devNo=%lu invalid",
1298 busNo, devNo);
22ad57ba
KC
1299 rc = -CONTROLVM_RESP_ERROR_DEVICE_INVALID;
1300 goto Away;
12e364b9
KC
1301 }
1302 if (pDevInfo->state.created == 0) {
1303 LOGERR("CONTROLVM_DEVICE_DESTROY Failed: busNo=%lu, devNo=%lu already destroyed",
1304 busNo, devNo);
22ad57ba 1305 rc = -CONTROLVM_RESP_ERROR_ALREADY_DONE;
12e364b9
KC
1306 }
1307
1308Away:
1309 if ((rc >= CONTROLVM_RESP_SUCCESS) && pDevInfo)
1310 device_epilog(busNo, devNo, SegmentStateRunning,
1311 CONTROLVM_DEVICE_DESTROY, &inmsg->hdr, rc,
1312 inmsg->hdr.Flags.responseExpected == 1,
1313 FOR_VISORBUS(pDevInfo->chanInfo.channelTypeGuid));
1314}
1315
1316/* When provided with the physical address of the controlvm channel
1317 * (phys_addr), the offset to the payload area we need to manage
1318 * (offset), and the size of this payload area (bytes), fills in the
1319 * CONTROLVM_PAYLOAD_INFO struct. Returns TRUE for success or FALSE
1320 * for failure.
1321 */
1322static int
1323initialize_controlvm_payload_info(HOSTADDRESS phys_addr, U64 offset, U32 bytes,
1324 CONTROLVM_PAYLOAD_INFO *info)
1325{
bd5b9b32 1326 U8 __iomem *payload = NULL;
12e364b9
KC
1327 int rc = CONTROLVM_RESP_SUCCESS;
1328
1329 if (info == NULL) {
1330 LOGERR("HUH ? CONTROLVM_PAYLOAD_INIT Failed : Programmer check at %s:%d",
1331 __FILE__, __LINE__);
22ad57ba
KC
1332 rc = -CONTROLVM_RESP_ERROR_PAYLOAD_INVALID;
1333 goto Away;
12e364b9
KC
1334 }
1335 memset(info, 0, sizeof(CONTROLVM_PAYLOAD_INFO));
1336 if ((offset == 0) || (bytes == 0)) {
1337 LOGERR("CONTROLVM_PAYLOAD_INIT Failed: RequestPayloadOffset=%llu RequestPayloadBytes=%llu!",
1338 (u64) offset, (u64) bytes);
22ad57ba
KC
1339 rc = -CONTROLVM_RESP_ERROR_PAYLOAD_INVALID;
1340 goto Away;
12e364b9
KC
1341 }
1342 payload = ioremap_cache(phys_addr + offset, bytes);
1343 if (payload == NULL) {
1344 LOGERR("CONTROLVM_PAYLOAD_INIT Failed: ioremap_cache %llu for %llu bytes failed",
1345 (u64) offset, (u64) bytes);
22ad57ba
KC
1346 rc = -CONTROLVM_RESP_ERROR_IOREMAP_FAILED;
1347 goto Away;
12e364b9
KC
1348 }
1349
1350 info->offset = offset;
1351 info->bytes = bytes;
1352 info->ptr = payload;
1353 LOGINF("offset=%llu, bytes=%lu, ptr=%p",
1354 (u64) (info->offset), (ulong) (info->bytes), info->ptr);
1355
1356Away:
1357 if (rc < 0) {
1358 if (payload != NULL) {
1359 iounmap(payload);
1360 payload = NULL;
1361 }
1362 }
1363 return rc;
1364}
1365
1366static void
1367destroy_controlvm_payload_info(CONTROLVM_PAYLOAD_INFO *info)
1368{
1369 if (info->ptr != NULL) {
1370 iounmap(info->ptr);
1371 info->ptr = NULL;
1372 }
1373 memset(info, 0, sizeof(CONTROLVM_PAYLOAD_INFO));
1374}
1375
1376static void
1377initialize_controlvm_payload(void)
1378{
1379 HOSTADDRESS phys_addr = visorchannel_get_physaddr(ControlVm_channel);
1380 U64 payloadOffset = 0;
1381 U32 payloadBytes = 0;
1382 if (visorchannel_read(ControlVm_channel,
1383 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
1384 RequestPayloadOffset),
1385 &payloadOffset, sizeof(payloadOffset)) < 0) {
1386 LOGERR("CONTROLVM_PAYLOAD_INIT Failed to read controlvm channel!");
1387 POSTCODE_LINUX_2(CONTROLVM_INIT_FAILURE_PC,
1388 POSTCODE_SEVERITY_ERR);
1389 return;
1390 }
1391 if (visorchannel_read(ControlVm_channel,
1392 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
1393 RequestPayloadBytes),
1394 &payloadBytes, sizeof(payloadBytes)) < 0) {
1395 LOGERR("CONTROLVM_PAYLOAD_INIT Failed to read controlvm channel!");
1396 POSTCODE_LINUX_2(CONTROLVM_INIT_FAILURE_PC,
1397 POSTCODE_SEVERITY_ERR);
1398 return;
1399 }
1400 initialize_controlvm_payload_info(phys_addr,
1401 payloadOffset, payloadBytes,
1402 &ControlVm_payload_info);
1403}
1404
1405/* Send ACTION=online for DEVPATH=/sys/devices/platform/visorchipset.
1406 * Returns CONTROLVM_RESP_xxx code.
1407 */
1408int
1409visorchipset_chipset_ready(void)
1410{
1411 kobject_uevent(&Visorchipset_platform_device.dev.kobj, KOBJ_ONLINE);
1412 return CONTROLVM_RESP_SUCCESS;
1413}
1414EXPORT_SYMBOL_GPL(visorchipset_chipset_ready);
1415
1416int
1417visorchipset_chipset_selftest(void)
1418{
1419 char env_selftest[20];
1420 char *envp[] = { env_selftest, NULL };
1421 sprintf(env_selftest, "SPARSP_SELFTEST=%d", 1);
1422 kobject_uevent_env(&Visorchipset_platform_device.dev.kobj, KOBJ_CHANGE,
1423 envp);
1424 return CONTROLVM_RESP_SUCCESS;
1425}
1426EXPORT_SYMBOL_GPL(visorchipset_chipset_selftest);
1427
1428/* Send ACTION=offline for DEVPATH=/sys/devices/platform/visorchipset.
1429 * Returns CONTROLVM_RESP_xxx code.
1430 */
1431int
1432visorchipset_chipset_notready(void)
1433{
1434 kobject_uevent(&Visorchipset_platform_device.dev.kobj, KOBJ_OFFLINE);
1435 return CONTROLVM_RESP_SUCCESS;
1436}
1437EXPORT_SYMBOL_GPL(visorchipset_chipset_notready);
1438
1439static void
1440chipset_ready(CONTROLVM_MESSAGE_HEADER *msgHdr)
1441{
1442 int rc = visorchipset_chipset_ready();
1443 if (rc != CONTROLVM_RESP_SUCCESS)
1444 rc = -rc;
1445 if (msgHdr->Flags.responseExpected && !visorchipset_holdchipsetready)
1446 controlvm_respond(msgHdr, rc);
1447 if (msgHdr->Flags.responseExpected && visorchipset_holdchipsetready) {
1448 /* Send CHIPSET_READY response when all modules have been loaded
1449 * and disks mounted for the partition
1450 */
1451 g_ChipSetMsgHdr = *msgHdr;
1452 LOGINF("Holding CHIPSET_READY response");
1453 }
1454}
1455
1456static void
1457chipset_selftest(CONTROLVM_MESSAGE_HEADER *msgHdr)
1458{
1459 int rc = visorchipset_chipset_selftest();
1460 if (rc != CONTROLVM_RESP_SUCCESS)
1461 rc = -rc;
1462 if (msgHdr->Flags.responseExpected)
1463 controlvm_respond(msgHdr, rc);
1464}
1465
1466static void
1467chipset_notready(CONTROLVM_MESSAGE_HEADER *msgHdr)
1468{
1469 int rc = visorchipset_chipset_notready();
1470 if (rc != CONTROLVM_RESP_SUCCESS)
1471 rc = -rc;
1472 if (msgHdr->Flags.responseExpected)
1473 controlvm_respond(msgHdr, rc);
1474}
1475
1476/* This is your "one-stop" shop for grabbing the next message from the
1477 * CONTROLVM_QUEUE_EVENT queue in the controlvm channel.
1478 */
1479static BOOL
1480read_controlvm_event(CONTROLVM_MESSAGE *msg)
1481{
1482 if (visorchannel_signalremove(ControlVm_channel,
1483 CONTROLVM_QUEUE_EVENT, msg)) {
1484 /* got a message */
1485 if (msg->hdr.Flags.testMessage == 1) {
1486 LOGERR("ignoring bad CONTROLVM_QUEUE_EVENT msg with controlvm_msg_id=0x%x because Flags.testMessage is nonsensical (=1)", msg->hdr.Id);
1487 return FALSE;
1488 } else
1489 return TRUE;
1490 }
1491 return FALSE;
1492}
1493
1494/*
1495 * The general parahotplug flow works as follows. The visorchipset
1496 * driver receives a DEVICE_CHANGESTATE message from Command
1497 * specifying a physical device to enable or disable. The CONTROLVM
1498 * message handler calls parahotplug_process_message, which then adds
1499 * the message to a global list and kicks off a udev event which
1500 * causes a user level script to enable or disable the specified
1501 * device. The udev script then writes to
1502 * /proc/visorchipset/parahotplug, which causes parahotplug_proc_write
1503 * to get called, at which point the appropriate CONTROLVM message is
1504 * retrieved from the list and responded to.
1505 */
1506
1507#define PARAHOTPLUG_TIMEOUT_MS 2000
1508
1509/*
1510 * Generate unique int to match an outstanding CONTROLVM message with a
1511 * udev script /proc response
1512 */
1513static int
1514parahotplug_next_id(void)
1515{
1516 static atomic_t id = ATOMIC_INIT(0);
1517 return atomic_inc_return(&id);
1518}
1519
1520/*
1521 * Returns the time (in jiffies) when a CONTROLVM message on the list
1522 * should expire -- PARAHOTPLUG_TIMEOUT_MS in the future
1523 */
1524static unsigned long
1525parahotplug_next_expiration(void)
1526{
1527 return jiffies + PARAHOTPLUG_TIMEOUT_MS * HZ / 1000;
1528}
1529
1530/*
1531 * Create a parahotplug_request, which is basically a wrapper for a
1532 * CONTROLVM_MESSAGE that we can stick on a list
1533 */
1534static struct parahotplug_request *
1535parahotplug_request_create(CONTROLVM_MESSAGE *msg)
1536{
1537 struct parahotplug_request *req =
1538 kmalloc(sizeof(struct parahotplug_request),
1539 GFP_KERNEL|__GFP_NORETRY);
1540 if (req == NULL)
1541 return NULL;
1542
1543 req->id = parahotplug_next_id();
1544 req->expiration = parahotplug_next_expiration();
1545 req->msg = *msg;
1546
1547 return req;
1548}
1549
1550/*
1551 * Free a parahotplug_request.
1552 */
1553static void
1554parahotplug_request_destroy(struct parahotplug_request *req)
1555{
1556 kfree(req);
1557}
1558
1559/*
1560 * Cause uevent to run the user level script to do the disable/enable
1561 * specified in (the CONTROLVM message in) the specified
1562 * parahotplug_request
1563 */
1564static void
1565parahotplug_request_kickoff(struct parahotplug_request *req)
1566{
1567 CONTROLVM_MESSAGE_PACKET *cmd = &req->msg.cmd;
1568 char env_cmd[40], env_id[40], env_state[40], env_bus[40], env_dev[40],
1569 env_func[40];
1570 char *envp[] = {
1571 env_cmd, env_id, env_state, env_bus, env_dev, env_func, NULL
1572 };
1573
1574 sprintf(env_cmd, "SPAR_PARAHOTPLUG=1");
1575 sprintf(env_id, "SPAR_PARAHOTPLUG_ID=%d", req->id);
1576 sprintf(env_state, "SPAR_PARAHOTPLUG_STATE=%d",
1577 cmd->deviceChangeState.state.Active);
1578 sprintf(env_bus, "SPAR_PARAHOTPLUG_BUS=%d",
1579 cmd->deviceChangeState.busNo);
1580 sprintf(env_dev, "SPAR_PARAHOTPLUG_DEVICE=%d",
1581 cmd->deviceChangeState.devNo >> 3);
1582 sprintf(env_func, "SPAR_PARAHOTPLUG_FUNCTION=%d",
1583 cmd->deviceChangeState.devNo & 0x7);
1584
1585 LOGINF("parahotplug_request_kickoff: state=%d, bdf=%d/%d/%d, id=%u\n",
1586 cmd->deviceChangeState.state.Active,
1587 cmd->deviceChangeState.busNo, cmd->deviceChangeState.devNo >> 3,
1588 cmd->deviceChangeState.devNo & 7, req->id);
1589
1590 kobject_uevent_env(&Visorchipset_platform_device.dev.kobj, KOBJ_CHANGE,
1591 envp);
1592}
1593
1594/*
1595 * Remove any request from the list that's been on there too long and
1596 * respond with an error.
1597 */
1598static void
1599parahotplug_process_list(void)
1600{
1601 struct list_head *pos = NULL;
1602 struct list_head *tmp = NULL;
1603
1604 spin_lock(&Parahotplug_request_list_lock);
1605
1606 list_for_each_safe(pos, tmp, &Parahotplug_request_list) {
1607 struct parahotplug_request *req =
1608 list_entry(pos, struct parahotplug_request, list);
1609 if (time_after_eq(jiffies, req->expiration)) {
1610 list_del(pos);
1611 if (req->msg.hdr.Flags.responseExpected)
1612 controlvm_respond_physdev_changestate(
1613 &req->msg.hdr,
1614 CONTROLVM_RESP_ERROR_DEVICE_UDEV_TIMEOUT,
1615 req->msg.cmd.deviceChangeState.state);
1616 parahotplug_request_destroy(req);
1617 }
1618 }
1619
1620 spin_unlock(&Parahotplug_request_list_lock);
1621}
1622
1623/*
1624 * Called from the /proc handler, which means the user script has
1625 * finished the enable/disable. Find the matching identifier, and
1626 * respond to the CONTROLVM message with success.
1627 */
1628static int
1629parahotplug_request_complete(int id, U16 active)
1630{
1631 struct list_head *pos = NULL;
1632 struct list_head *tmp = NULL;
1633
1634 spin_lock(&Parahotplug_request_list_lock);
1635
1636 /* Look for a request matching "id". */
1637 list_for_each_safe(pos, tmp, &Parahotplug_request_list) {
1638 struct parahotplug_request *req =
1639 list_entry(pos, struct parahotplug_request, list);
1640 if (req->id == id) {
1641 /* Found a match. Remove it from the list and
1642 * respond.
1643 */
1644 list_del(pos);
1645 spin_unlock(&Parahotplug_request_list_lock);
1646 req->msg.cmd.deviceChangeState.state.Active = active;
1647 if (req->msg.hdr.Flags.responseExpected)
1648 controlvm_respond_physdev_changestate(
1649 &req->msg.hdr, CONTROLVM_RESP_SUCCESS,
1650 req->msg.cmd.deviceChangeState.state);
1651 parahotplug_request_destroy(req);
1652 return 0;
1653 }
1654 }
1655
1656 spin_unlock(&Parahotplug_request_list_lock);
1657 return -1;
1658}
1659
1660/*
1661 * Enables or disables a PCI device by kicking off a udev script
1662 */
bd5b9b32 1663static void
12e364b9
KC
1664parahotplug_process_message(CONTROLVM_MESSAGE *inmsg)
1665{
1666 struct parahotplug_request *req;
1667
1668 req = parahotplug_request_create(inmsg);
1669
1670 if (req == NULL) {
1671 LOGERR("parahotplug_process_message: couldn't allocate request");
1672 return;
1673 }
1674
1675 if (inmsg->cmd.deviceChangeState.state.Active) {
1676 /* For enable messages, just respond with success
1677 * right away. This is a bit of a hack, but there are
1678 * issues with the early enable messages we get (with
1679 * either the udev script not detecting that the device
1680 * is up, or not getting called at all). Fortunately
1681 * the messages that get lost don't matter anyway, as
1682 * devices are automatically enabled at
1683 * initialization.
1684 */
1685 parahotplug_request_kickoff(req);
1686 controlvm_respond_physdev_changestate(&inmsg->hdr,
1687 CONTROLVM_RESP_SUCCESS,
1688 inmsg->cmd.
1689 deviceChangeState.state);
1690 parahotplug_request_destroy(req);
1691 } else {
1692 /* For disable messages, add the request to the
1693 * request list before kicking off the udev script. It
1694 * won't get responded to until the script has
1695 * indicated it's done.
1696 */
1697 spin_lock(&Parahotplug_request_list_lock);
1698 list_add_tail(&(req->list), &Parahotplug_request_list);
1699 spin_unlock(&Parahotplug_request_list_lock);
1700
1701 parahotplug_request_kickoff(req);
1702 }
1703}
1704
1705/*
1706 * Gets called when the udev script writes to
1707 * /proc/visorchipset/parahotplug. Expects input in the form of "<id>
1708 * <active>" where <id> is the identifier passed to the script that
1709 * matches a request on the request list, and <active> is 0 or 1
1710 * indicating whether the device is now enabled or not.
1711 */
1712static ssize_t
1713parahotplug_proc_write(struct file *file, const char __user *buffer,
1714 size_t count, loff_t *ppos)
1715{
1716 char buf[64];
1717 uint id;
1718 ushort active;
1719
1720 if (count > sizeof(buf) - 1) {
1721 LOGERR("parahotplug_proc_write: count (%d) exceeds size of buffer (%d)",
1722 (int) count, (int) sizeof(buf));
1723 return -EINVAL;
1724 }
1725 if (copy_from_user(buf, buffer, count)) {
1726 LOGERR("parahotplug_proc_write: copy_from_user failed");
1727 return -EFAULT;
1728 }
1729 buf[count] = '\0';
1730
1731 if (sscanf(buf, "%u %hu", &id, &active) != 2) {
1732 id = 0;
1733 active = 0;
1734 }
1735
1736 if (active != 1 && active != 0) {
1737 LOGERR("parahotplug_proc_write: invalid active field");
1738 return -EINVAL;
1739 }
1740
1741 parahotplug_request_complete((int) id, (U16) active);
1742
1743 return count;
1744}
1745
1746static const struct file_operations parahotplug_proc_fops = {
1747 .owner = THIS_MODULE,
1748 .read = visorchipset_proc_read_writeonly,
1749 .write = parahotplug_proc_write,
1750};
1751
1752/* Process a controlvm message.
1753 * Return result:
1754 * FALSE - this function will return FALSE only in the case where the
1755 * controlvm message was NOT processed, but processing must be
1756 * retried before reading the next controlvm message; a
1757 * scenario where this can occur is when we need to throttle
1758 * the allocation of memory in which to copy out controlvm
1759 * payload data
1760 * TRUE - processing of the controlvm message completed,
1761 * either successfully or with an error.
1762 */
1763static BOOL
1764handle_command(CONTROLVM_MESSAGE inmsg, HOSTADDRESS channel_addr)
1765{
1766 CONTROLVM_MESSAGE_PACKET *cmd = &inmsg.cmd;
1767 U64 parametersAddr = 0;
1768 U32 parametersBytes = 0;
1769 PARSER_CONTEXT *parser_ctx = NULL;
1770 BOOL isLocalAddr = FALSE;
1771 CONTROLVM_MESSAGE ackmsg;
1772
1773 /* create parsing context if necessary */
1774 isLocalAddr = (inmsg.hdr.Flags.testMessage == 1);
1775 if (channel_addr == 0) {
1776 LOGERR("HUH? channel_addr is 0!");
1777 return TRUE;
1778 }
1779 parametersAddr = channel_addr + inmsg.hdr.PayloadVmOffset;
1780 parametersBytes = inmsg.hdr.PayloadBytes;
1781
1782 /* Parameter and channel addresses within test messages actually lie
1783 * within our OS-controlled memory. We need to know that, because it
1784 * makes a difference in how we compute the virtual address.
1785 */
1786 if (parametersAddr != 0 && parametersBytes != 0) {
1787 BOOL retry = FALSE;
1788 parser_ctx =
1789 parser_init_byteStream(parametersAddr, parametersBytes,
1790 isLocalAddr, &retry);
1791 if (!parser_ctx) {
1792 if (retry) {
1793 LOGWRN("throttling to copy payload");
1794 return FALSE;
1795 }
1796 LOGWRN("parsing failed");
1797 LOGWRN("inmsg.hdr.Id=0x%lx", (ulong) inmsg.hdr.Id);
1798 LOGWRN("parametersAddr=0x%llx", (u64) parametersAddr);
1799 LOGWRN("parametersBytes=%lu", (ulong) parametersBytes);
1800 LOGWRN("isLocalAddr=%d", isLocalAddr);
1801 }
1802 }
1803
1804 if (!isLocalAddr) {
1805 controlvm_init_response(&ackmsg, &inmsg.hdr,
1806 CONTROLVM_RESP_SUCCESS);
1807 if ((ControlVm_channel)
1808 &&
1809 (!visorchannel_signalinsert
1810 (ControlVm_channel, CONTROLVM_QUEUE_ACK, &ackmsg)))
1811 LOGWRN("failed to send ACK failed");
1812 }
1813 switch (inmsg.hdr.Id) {
1814 case CONTROLVM_CHIPSET_INIT:
1815 LOGINF("CHIPSET_INIT(#busses=%lu,#switches=%lu)",
1816 (ulong) inmsg.cmd.initChipset.busCount,
1817 (ulong) inmsg.cmd.initChipset.switchCount);
1818 chipset_init(&inmsg);
1819 break;
1820 case CONTROLVM_BUS_CREATE:
1821 LOGINF("BUS_CREATE(%lu,#devs=%lu)",
1822 (ulong) cmd->createBus.busNo,
1823 (ulong) cmd->createBus.deviceCount);
1824 bus_create(&inmsg);
1825 break;
1826 case CONTROLVM_BUS_DESTROY:
1827 LOGINF("BUS_DESTROY(%lu)", (ulong) cmd->destroyBus.busNo);
1828 bus_destroy(&inmsg);
1829 break;
1830 case CONTROLVM_BUS_CONFIGURE:
1831 LOGINF("BUS_CONFIGURE(%lu)", (ulong) cmd->configureBus.busNo);
1832 bus_configure(&inmsg, parser_ctx);
1833 break;
1834 case CONTROLVM_DEVICE_CREATE:
1835 LOGINF("DEVICE_CREATE(%lu,%lu)",
1836 (ulong) cmd->createDevice.busNo,
1837 (ulong) cmd->createDevice.devNo);
1838 my_device_create(&inmsg);
1839 break;
1840 case CONTROLVM_DEVICE_CHANGESTATE:
1841 if (cmd->deviceChangeState.flags.physicalDevice) {
1842 LOGINF("DEVICE_CHANGESTATE for physical device (%lu,%lu, active=%lu)",
1843 (ulong) cmd->deviceChangeState.busNo,
1844 (ulong) cmd->deviceChangeState.devNo,
1845 (ulong) cmd->deviceChangeState.state.Active);
1846 parahotplug_process_message(&inmsg);
1847 } else {
1848 LOGINF("DEVICE_CHANGESTATE for virtual device (%lu,%lu, state.Alive=0x%lx)",
1849 (ulong) cmd->deviceChangeState.busNo,
1850 (ulong) cmd->deviceChangeState.devNo,
1851 (ulong) cmd->deviceChangeState.state.Alive);
1852 /* save the hdr and cmd structures for later use */
1853 /* when sending back the response to Command */
1854 my_device_changestate(&inmsg);
1855 g_DiagMsgHdr = inmsg.hdr;
1856 g_DeviceChangeStatePacket = inmsg.cmd;
1857 break;
1858 }
1859 break;
1860 case CONTROLVM_DEVICE_DESTROY:
1861 LOGINF("DEVICE_DESTROY(%lu,%lu)",
1862 (ulong) cmd->destroyDevice.busNo,
1863 (ulong) cmd->destroyDevice.devNo);
1864 my_device_destroy(&inmsg);
1865 break;
1866 case CONTROLVM_DEVICE_CONFIGURE:
1867 LOGINF("DEVICE_CONFIGURE(%lu,%lu)",
1868 (ulong) cmd->configureDevice.busNo,
1869 (ulong) cmd->configureDevice.devNo);
1870 /* no op for now, just send a respond that we passed */
1871 if (inmsg.hdr.Flags.responseExpected)
1872 controlvm_respond(&inmsg.hdr, CONTROLVM_RESP_SUCCESS);
1873 break;
1874 case CONTROLVM_CHIPSET_READY:
1875 LOGINF("CHIPSET_READY");
1876 chipset_ready(&inmsg.hdr);
1877 break;
1878 case CONTROLVM_CHIPSET_SELFTEST:
1879 LOGINF("CHIPSET_SELFTEST");
1880 chipset_selftest(&inmsg.hdr);
1881 break;
1882 case CONTROLVM_CHIPSET_STOP:
1883 LOGINF("CHIPSET_STOP");
1884 chipset_notready(&inmsg.hdr);
1885 break;
1886 default:
1887 LOGERR("unrecognized controlvm cmd=%d", (int) inmsg.hdr.Id);
1888 if (inmsg.hdr.Flags.responseExpected)
1889 controlvm_respond(&inmsg.hdr,
1890 -CONTROLVM_RESP_ERROR_MESSAGE_ID_UNKNOWN);
1891 break;
1892 }
1893
1894 if (parser_ctx != NULL) {
1895 parser_done(parser_ctx);
1896 parser_ctx = NULL;
1897 }
1898 return TRUE;
1899}
1900
524b0b63
BR
1901HOSTADDRESS controlvm_get_channel_address(void)
1902{
1903 U64 addr = 0;
1904 U32 size = 0;
1905
1906 if (!VMCALL_SUCCESSFUL(Issue_VMCALL_IO_CONTROLVM_ADDR(&addr, &size))) {
1907 ERRDRV("%s - vmcall to determine controlvm channel addr failed",
1908 __func__);
1909 return 0;
1910 }
1911 INFODRV("controlvm addr=%Lx", addr);
1912 return addr;
1913}
1914
12e364b9
KC
1915static void
1916controlvm_periodic_work(struct work_struct *work)
1917{
1918 VISORCHIPSET_CHANNEL_INFO chanInfo;
1919 CONTROLVM_MESSAGE inmsg;
12e364b9
KC
1920 BOOL gotACommand = FALSE;
1921 BOOL handle_command_failed = FALSE;
1922 static U64 Poll_Count;
1923
1924 /* make sure visorbus server is registered for controlvm callbacks */
1925 if (visorchipset_serverregwait && !serverregistered)
097f4c19 1926 goto Away;
12e364b9
KC
1927 /* make sure visorclientbus server is regsitered for controlvm
1928 * callbacks
1929 */
1930 if (visorchipset_clientregwait && !clientregistered)
097f4c19 1931 goto Away;
12e364b9
KC
1932
1933 memset(&chanInfo, 0, sizeof(VISORCHIPSET_CHANNEL_INFO));
12e364b9
KC
1934
1935 Poll_Count++;
8a1182eb 1936 if (Poll_Count >= 250)
12e364b9
KC
1937 ; /* keep going */
1938 else
097f4c19 1939 goto Away;
12e364b9
KC
1940
1941 /* Check events to determine if response to CHIPSET_READY
1942 * should be sent
1943 */
1944 if (visorchipset_holdchipsetready
1945 && (g_ChipSetMsgHdr.Id != CONTROLVM_INVALID)) {
1946 if (check_chipset_events() == 1) {
1947 LOGINF("Sending CHIPSET_READY response");
1948 controlvm_respond(&g_ChipSetMsgHdr, 0);
1949 clear_chipset_events();
1950 memset(&g_ChipSetMsgHdr, 0,
1951 sizeof(CONTROLVM_MESSAGE_HEADER));
1952 }
1953 }
1954
8a1182eb
BR
1955 while (visorchannel_signalremove(ControlVm_channel,
1956 CONTROLVM_QUEUE_RESPONSE,
1957 &inmsg)) {
1958 if (inmsg.hdr.PayloadMaxBytes != 0) {
1959 LOGERR("Payload of size %lu returned @%lu with unexpected message id %d.",
1960 (ulong) inmsg.hdr.PayloadMaxBytes,
1961 (ulong) inmsg.hdr.PayloadVmOffset,
1962 inmsg.hdr.Id);
12e364b9
KC
1963 }
1964 }
8a1182eb
BR
1965 if (!gotACommand) {
1966 if (ControlVm_Pending_Msg_Valid) {
1967 /* we throttled processing of a prior
1968 * msg, so try to process it again
1969 * rather than reading a new one
1970 */
1971 inmsg = ControlVm_Pending_Msg;
1972 ControlVm_Pending_Msg_Valid = FALSE;
1973 gotACommand = TRUE;
1974 } else
1975 gotACommand = read_controlvm_event(&inmsg);
1976 }
12e364b9
KC
1977
1978 handle_command_failed = FALSE;
1979 while (gotACommand && (!handle_command_failed)) {
1980 Most_recent_message_jiffies = jiffies;
8a1182eb
BR
1981 if (handle_command(inmsg,
1982 visorchannel_get_physaddr
1983 (ControlVm_channel)))
1984 gotACommand = read_controlvm_event(&inmsg);
1985 else {
1986 /* this is a scenario where throttling
1987 * is required, but probably NOT an
1988 * error...; we stash the current
1989 * controlvm msg so we will attempt to
1990 * reprocess it on our next loop
1991 */
1992 handle_command_failed = TRUE;
1993 ControlVm_Pending_Msg = inmsg;
1994 ControlVm_Pending_Msg_Valid = TRUE;
12e364b9
KC
1995 }
1996 }
1997
1998 /* parahotplug_worker */
1999 parahotplug_process_list();
2000
12e364b9
KC
2001Away:
2002
2003 if (time_after(jiffies,
2004 Most_recent_message_jiffies + (HZ * MIN_IDLE_SECONDS))) {
2005 /* it's been longer than MIN_IDLE_SECONDS since we
2006 * processed our last controlvm message; slow down the
2007 * polling
2008 */
2009 if (Poll_jiffies != POLLJIFFIES_CONTROLVMCHANNEL_SLOW) {
2010 LOGINF("switched to slow controlvm polling");
2011 Poll_jiffies = POLLJIFFIES_CONTROLVMCHANNEL_SLOW;
2012 }
2013 } else {
2014 if (Poll_jiffies != POLLJIFFIES_CONTROLVMCHANNEL_FAST) {
2015 Poll_jiffies = POLLJIFFIES_CONTROLVMCHANNEL_FAST;
2016 LOGINF("switched to fast controlvm polling");
2017 }
2018 }
2019
4b4b535e
DY
2020 queue_delayed_work(Periodic_controlvm_workqueue,
2021 &Periodic_controlvm_work, Poll_jiffies);
12e364b9
KC
2022}
2023
2024static void
2025setup_crash_devices_work_queue(struct work_struct *work)
2026{
2027
2028 CONTROLVM_MESSAGE localCrashCreateBusMsg;
2029 CONTROLVM_MESSAGE localCrashCreateDevMsg;
2030 CONTROLVM_MESSAGE msg;
12e364b9
KC
2031 U32 localSavedCrashMsgOffset;
2032 U16 localSavedCrashMsgCount;
2033
2034 /* make sure visorbus server is registered for controlvm callbacks */
2035 if (visorchipset_serverregwait && !serverregistered)
097f4c19 2036 goto Away;
12e364b9
KC
2037
2038 /* make sure visorclientbus server is regsitered for controlvm
2039 * callbacks
2040 */
2041 if (visorchipset_clientregwait && !clientregistered)
097f4c19 2042 goto Away;
12e364b9
KC
2043
2044 POSTCODE_LINUX_2(CRASH_DEV_ENTRY_PC, POSTCODE_SEVERITY_INFO);
2045
2046 /* send init chipset msg */
2047 msg.hdr.Id = CONTROLVM_CHIPSET_INIT;
2048 msg.cmd.initChipset.busCount = 23;
2049 msg.cmd.initChipset.switchCount = 0;
2050
2051 chipset_init(&msg);
2052
12e364b9
KC
2053 /* get saved message count */
2054 if (visorchannel_read(ControlVm_channel,
2055 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
2056 SavedCrashMsgCount),
2057 &localSavedCrashMsgCount, sizeof(U16)) < 0) {
2058 LOGERR("failed to get Saved Message Count");
2059 POSTCODE_LINUX_2(CRASH_DEV_CTRL_RD_FAILURE_PC,
2060 POSTCODE_SEVERITY_ERR);
2061 return;
2062 }
2063
2064 if (localSavedCrashMsgCount != CONTROLVM_CRASHMSG_MAX) {
2065 LOGERR("Saved Message Count incorrect %d",
2066 localSavedCrashMsgCount);
2067 POSTCODE_LINUX_3(CRASH_DEV_COUNT_FAILURE_PC,
2068 localSavedCrashMsgCount,
2069 POSTCODE_SEVERITY_ERR);
2070 return;
2071 }
2072
2073 /* get saved crash message offset */
2074 if (visorchannel_read(ControlVm_channel,
2075 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
2076 SavedCrashMsgOffset),
2077 &localSavedCrashMsgOffset, sizeof(U32)) < 0) {
2078 LOGERR("failed to get Saved Message Offset");
2079 POSTCODE_LINUX_2(CRASH_DEV_CTRL_RD_FAILURE_PC,
2080 POSTCODE_SEVERITY_ERR);
2081 return;
2082 }
2083
2084 /* read create device message for storage bus offset */
2085 if (visorchannel_read(ControlVm_channel,
2086 localSavedCrashMsgOffset,
2087 &localCrashCreateBusMsg,
2088 sizeof(CONTROLVM_MESSAGE)) < 0) {
2089 LOGERR("CRASH_DEV_RD_BUS_FAIULRE: Failed to read CrashCreateBusMsg!");
2090 POSTCODE_LINUX_2(CRASH_DEV_RD_BUS_FAIULRE_PC,
2091 POSTCODE_SEVERITY_ERR);
2092 return;
2093 }
2094
2095 /* read create device message for storage device */
2096 if (visorchannel_read(ControlVm_channel,
2097 localSavedCrashMsgOffset +
2098 sizeof(CONTROLVM_MESSAGE),
2099 &localCrashCreateDevMsg,
2100 sizeof(CONTROLVM_MESSAGE)) < 0) {
2101 LOGERR("CRASH_DEV_RD_DEV_FAIULRE: Failed to read CrashCreateDevMsg!");
2102 POSTCODE_LINUX_2(CRASH_DEV_RD_DEV_FAIULRE_PC,
2103 POSTCODE_SEVERITY_ERR);
2104 return;
2105 }
2106
2107 /* reuse IOVM create bus message */
2108 if (localCrashCreateBusMsg.cmd.createBus.channelAddr != 0)
2109 bus_create(&localCrashCreateBusMsg);
2110 else {
2111 LOGERR("CrashCreateBusMsg is null, no dump will be taken");
2112 POSTCODE_LINUX_2(CRASH_DEV_BUS_NULL_FAILURE_PC,
2113 POSTCODE_SEVERITY_ERR);
2114 return;
2115 }
2116
2117 /* reuse create device message for storage device */
2118 if (localCrashCreateDevMsg.cmd.createDevice.channelAddr != 0)
2119 my_device_create(&localCrashCreateDevMsg);
2120 else {
2121 LOGERR("CrashCreateDevMsg is null, no dump will be taken");
2122 POSTCODE_LINUX_2(CRASH_DEV_DEV_NULL_FAILURE_PC,
2123 POSTCODE_SEVERITY_ERR);
2124 return;
2125 }
2126 LOGINF("Bus and device ready for dumping");
2127 POSTCODE_LINUX_2(CRASH_DEV_EXIT_PC, POSTCODE_SEVERITY_INFO);
2128 return;
2129
2130Away:
2131
2132 Poll_jiffies = POLLJIFFIES_CONTROLVMCHANNEL_SLOW;
2133
4b4b535e
DY
2134 queue_delayed_work(Periodic_controlvm_workqueue,
2135 &Periodic_controlvm_work, Poll_jiffies);
12e364b9
KC
2136}
2137
2138static void
2139bus_create_response(ulong busNo, int response)
2140{
2141 bus_responder(CONTROLVM_BUS_CREATE, busNo, response);
2142}
2143
2144static void
2145bus_destroy_response(ulong busNo, int response)
2146{
2147 bus_responder(CONTROLVM_BUS_DESTROY, busNo, response);
2148}
2149
2150static void
2151device_create_response(ulong busNo, ulong devNo, int response)
2152{
2153 device_responder(CONTROLVM_DEVICE_CREATE, busNo, devNo, response);
2154}
2155
2156static void
2157device_destroy_response(ulong busNo, ulong devNo, int response)
2158{
2159 device_responder(CONTROLVM_DEVICE_DESTROY, busNo, devNo, response);
2160}
2161
2162void
927c7927 2163visorchipset_device_pause_response(ulong busNo, ulong devNo, int response)
12e364b9
KC
2164{
2165
2166 device_changestate_responder(CONTROLVM_DEVICE_CHANGESTATE,
2167 busNo, devNo, response,
2168 SegmentStateStandby);
2169}
927c7927 2170EXPORT_SYMBOL_GPL(visorchipset_device_pause_response);
12e364b9
KC
2171
2172static void
2173device_resume_response(ulong busNo, ulong devNo, int response)
2174{
2175 device_changestate_responder(CONTROLVM_DEVICE_CHANGESTATE,
2176 busNo, devNo, response,
2177 SegmentStateRunning);
2178}
2179
2180BOOL
2181visorchipset_get_bus_info(ulong busNo, VISORCHIPSET_BUS_INFO *busInfo)
2182{
2183 void *p = findbus(&BusInfoList, busNo);
2184 if (!p) {
2185 LOGERR("(%lu) failed", busNo);
2186 return FALSE;
2187 }
2188 memcpy(busInfo, p, sizeof(VISORCHIPSET_BUS_INFO));
2189 return TRUE;
2190}
2191EXPORT_SYMBOL_GPL(visorchipset_get_bus_info);
2192
2193BOOL
2194visorchipset_set_bus_context(ulong busNo, void *context)
2195{
2196 VISORCHIPSET_BUS_INFO *p = findbus(&BusInfoList, busNo);
2197 if (!p) {
2198 LOGERR("(%lu) failed", busNo);
2199 return FALSE;
2200 }
2201 p->bus_driver_context = context;
2202 return TRUE;
2203}
2204EXPORT_SYMBOL_GPL(visorchipset_set_bus_context);
2205
2206BOOL
2207visorchipset_get_device_info(ulong busNo, ulong devNo,
2208 VISORCHIPSET_DEVICE_INFO *devInfo)
2209{
2210 void *p = finddevice(&DevInfoList, busNo, devNo);
2211 if (!p) {
2212 LOGERR("(%lu,%lu) failed", busNo, devNo);
2213 return FALSE;
2214 }
2215 memcpy(devInfo, p, sizeof(VISORCHIPSET_DEVICE_INFO));
2216 return TRUE;
2217}
2218EXPORT_SYMBOL_GPL(visorchipset_get_device_info);
2219
2220BOOL
2221visorchipset_set_device_context(ulong busNo, ulong devNo, void *context)
2222{
2223 VISORCHIPSET_DEVICE_INFO *p = finddevice(&DevInfoList, busNo, devNo);
2224 if (!p) {
2225 LOGERR("(%lu,%lu) failed", busNo, devNo);
2226 return FALSE;
2227 }
2228 p->bus_driver_context = context;
2229 return TRUE;
2230}
2231EXPORT_SYMBOL_GPL(visorchipset_set_device_context);
2232
2233/* Generic wrapper function for allocating memory from a kmem_cache pool.
2234 */
2235void *
2236visorchipset_cache_alloc(struct kmem_cache *pool, BOOL ok_to_block,
2237 char *fn, int ln)
2238{
2239 gfp_t gfp;
2240 void *p;
2241
2242 if (ok_to_block)
2243 gfp = GFP_KERNEL;
2244 else
2245 gfp = GFP_ATOMIC;
2246 /* __GFP_NORETRY means "ok to fail", meaning
2247 * kmem_cache_alloc() can return NULL, implying the caller CAN
2248 * cope with failure. If you do NOT specify __GFP_NORETRY,
2249 * Linux will go to extreme measures to get memory for you
2250 * (like, invoke oom killer), which will probably cripple the
2251 * system.
2252 */
2253 gfp |= __GFP_NORETRY;
2254 p = kmem_cache_alloc(pool, gfp);
2255 if (!p) {
2256 LOGERR("kmem_cache_alloc failed early @%s:%d\n", fn, ln);
2257 return NULL;
2258 }
2259 atomic_inc(&Visorchipset_cache_buffers_in_use);
2260 return p;
2261}
2262
2263/* Generic wrapper function for freeing memory from a kmem_cache pool.
2264 */
2265void
2266visorchipset_cache_free(struct kmem_cache *pool, void *p, char *fn, int ln)
2267{
2268 if (!p) {
2269 LOGERR("NULL pointer @%s:%d\n", fn, ln);
2270 return;
2271 }
2272 atomic_dec(&Visorchipset_cache_buffers_in_use);
2273 kmem_cache_free(pool, p);
2274}
2275
2276#define gettoken(bufp) strsep(bufp, " -\t\n")
2277
2278static ssize_t
2279chipset_proc_write(struct file *file, const char __user *buffer,
2280 size_t count, loff_t *ppos)
2281{
2282 char buf[512];
2283 char *token, *p;
2284
2285 if (count > sizeof(buf) - 1) {
2286 LOGERR("chipset_proc_write: count (%d) exceeds size of buffer (%d)",
2287 (int) count, (int) sizeof(buffer));
2288 return -EINVAL;
2289 }
2290 if (copy_from_user(buf, buffer, count)) {
2291 LOGERR("chipset_proc_write: copy_from_user failed");
2292 return -EFAULT;
2293 }
2294 buf[count] = '\0';
2295
2296 p = buf;
2297 token = gettoken(&p);
2298
2299 if (strcmp(token, "CALLHOMEDISK_MOUNTED") == 0) {
2300 token = gettoken(&p);
2301 /* The Call Home Disk has been mounted */
2302 if (strcmp(token, "0") == 0)
2303 chipset_events[0] = 1;
2304 } else if (strcmp(token, "MODULES_LOADED") == 0) {
2305 token = gettoken(&p);
2306 /* All modules for the partition have been loaded */
2307 if (strcmp(token, "0") == 0)
2308 chipset_events[1] = 1;
2309 } else if (token == NULL) {
2310 /* No event specified */
2311 LOGERR("No event was specified to send CHIPSET_READY response");
2312 return -1;
2313 } else {
2314 /* Unsupported event specified */
2315 LOGERR("%s is an invalid event for sending CHIPSET_READY response", token);
2316 return -1;
2317 }
2318
2319 return count;
2320}
2321
2322static ssize_t
2323visorchipset_proc_read_writeonly(struct file *file, char __user *buf,
2324 size_t len, loff_t *offset)
2325{
2326 return 0;
2327}
2328
2329/**
2330 * Reads the InstallationError, InstallationTextId,
2331 * InstallationRemainingSteps fields of ControlVMChannel.
2332 */
2333static ssize_t
2334proc_read_installer(struct file *file, char __user *buf,
2335 size_t len, loff_t *offset)
2336{
2337 int length = 0;
2338 U16 remainingSteps;
2339 U32 error, textId;
2340 char *vbuf;
2341 loff_t pos = *offset;
2342
2343 if (pos < 0)
2344 return -EINVAL;
2345
2346 if (pos > 0 || !len)
2347 return 0;
2348
2349 vbuf = kzalloc(len, GFP_KERNEL);
2350 if (!vbuf)
2351 return -ENOMEM;
2352
2353 visorchannel_read(ControlVm_channel,
2354 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
2355 InstallationRemainingSteps), &remainingSteps,
2356 sizeof(U16));
2357 visorchannel_read(ControlVm_channel,
2358 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
2359 InstallationError), &error, sizeof(U32));
2360 visorchannel_read(ControlVm_channel,
2361 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
2362 InstallationTextId), &textId, sizeof(U32));
2363
2364 length = sprintf(vbuf, "%u %u %u\n", remainingSteps, error, textId);
2365 if (copy_to_user(buf, vbuf, length)) {
2366 kfree(vbuf);
2367 return -EFAULT;
2368 }
2369
2370 kfree(vbuf);
2371 *offset += length;
2372 return length;
2373}
2374
2375/**
2376 * Writes to the InstallationError, InstallationTextId,
2377 * InstallationRemainingSteps fields of
2378 * ControlVMChannel.
2379 * Input: RemainingSteps Error TextId
2380 * Limit 32 characters input
2381 */
2382#define UINT16_MAX (65535U)
2383#define UINT32_MAX (4294967295U)
2384static ssize_t
2385proc_write_installer(struct file *file,
2386 const char __user *buffer, size_t count, loff_t *ppos)
2387{
2388 char buf[32];
2389 U16 remainingSteps;
2390 U32 error, textId;
2391
2392 /* Check to make sure there is no buffer overflow */
2393 if (count > (sizeof(buf) - 1))
2394 return -EINVAL;
2395
2396 if (copy_from_user(buf, buffer, count)) {
2397 WARN(1, "Error copying from user space\n");
2398 return -EFAULT;
2399 }
2400
2401 if (sscanf(buf, "%hu %i %i", &remainingSteps, &error, &textId) != 3) {
2402 remainingSteps = UINT16_MAX;
2403 error = UINT32_MAX;
2404 textId = UINT32_MAX;
2405 }
2406
2407 if (remainingSteps != UINT16_MAX) {
2408 if (visorchannel_write
2409 (ControlVm_channel,
2410 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
2411 InstallationRemainingSteps), &remainingSteps,
2412 sizeof(U16)) < 0)
2413 WARN(1, "Installation Status Write Failed - Write function error - RemainingSteps = %d\n",
2414 remainingSteps);
2415 }
2416
2417 if (error != UINT32_MAX) {
2418 if (visorchannel_write
2419 (ControlVm_channel,
2420 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
2421 InstallationError), &error, sizeof(U32)) < 0)
2422 WARN(1, "Installation Status Write Failed - Write function error - Error = %d\n",
2423 error);
2424 }
2425
2426 if (textId != UINT32_MAX) {
2427 if (visorchannel_write
2428 (ControlVm_channel,
2429 offsetof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL,
2430 InstallationTextId), &textId, sizeof(U32)) < 0)
2431 WARN(1, "Installation Status Write Failed - Write function error - TextId = %d\n",
2432 textId);
2433 }
2434
2435 /* So this function isn't called multiple times, must return
2436 * size of buffer
2437 */
2438 return count;
2439}
2440
12e364b9
KC
2441static const struct file_operations chipset_proc_fops = {
2442 .owner = THIS_MODULE,
2443 .read = visorchipset_proc_read_writeonly,
2444 .write = chipset_proc_write,
2445};
2446
2447static int __init
2448visorchipset_init(void)
2449{
2450 int rc = 0, x = 0;
8a1182eb 2451 char s[64];
12e364b9 2452 struct proc_dir_entry *installer_file;
8a1182eb 2453 HOSTADDRESS addr;
12e364b9 2454
fcd0157e
KC
2455 if (!unisys_spar_platform)
2456 return -ENODEV;
2457
12e364b9
KC
2458 LOGINF("chipset driver version %s loaded", VERSION);
2459 /* process module options */
2460 POSTCODE_LINUX_2(DRIVER_ENTRY_PC, POSTCODE_SEVERITY_INFO);
2461
2462 LOGINF("option - testvnic=%d", visorchipset_testvnic);
2463 LOGINF("option - testvnicclient=%d", visorchipset_testvnicclient);
2464 LOGINF("option - testmsg=%d", visorchipset_testmsg);
2465 LOGINF("option - testteardown=%d", visorchipset_testteardown);
2466 LOGINF("option - major=%d", visorchipset_major);
2467 LOGINF("option - serverregwait=%d", visorchipset_serverregwait);
2468 LOGINF("option - clientregwait=%d", visorchipset_clientregwait);
2469 LOGINF("option - holdchipsetready=%d", visorchipset_holdchipsetready);
2470
2471 memset(&BusDev_Server_Notifiers, 0, sizeof(BusDev_Server_Notifiers));
2472 memset(&BusDev_Client_Notifiers, 0, sizeof(BusDev_Client_Notifiers));
2473 memset(&ControlVm_payload_info, 0, sizeof(ControlVm_payload_info));
2474 memset(&LiveDump_info, 0, sizeof(LiveDump_info));
2475 atomic_set(&LiveDump_info.buffers_in_use, 0);
2476
9f8d0e8b
KC
2477 if (visorchipset_testvnic) {
2478 ERRDRV("testvnic option no longer supported: (status = %d)\n",
2479 x);
2480 POSTCODE_LINUX_3(CHIPSET_INIT_FAILURE_PC, x, DIAG_SEVERITY_ERR);
2481 rc = x;
2482 goto Away;
2483 }
12e364b9 2484
8a1182eb
BR
2485 addr = controlvm_get_channel_address();
2486 if (addr != 0) {
2487 ControlVm_channel =
2488 visorchannel_create_with_lock
2489 (addr,
2490 sizeof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL),
2491 UltraControlvmChannelProtocolGuid);
2492 if (ULTRA_CONTROLVM_CHANNEL_OK_CLIENT
2493 (visorchannel_get_header(ControlVm_channel),
2494 NULL)) {
2495 LOGINF("Channel %s (ControlVm) discovered",
2496 visorchannel_id(ControlVm_channel, s));
2497 initialize_controlvm_payload();
2498 } else {
2499 LOGERR("controlvm channel is invalid");
2500 visorchannel_destroy(ControlVm_channel);
2501 ControlVm_channel = NULL;
2502 return -ENODEV;
2503 }
2504 } else {
2505 LOGERR("no controlvm channel discovered");
2506 return -ENODEV;
2507 }
2508
12e364b9 2509 MajorDev = MKDEV(visorchipset_major, 0);
9f8d0e8b 2510 rc = visorchipset_file_init(MajorDev, &ControlVm_channel);
4cb005a9
KC
2511 if (rc < 0) {
2512 ERRDRV("visorchipset_file_init(MajorDev, &ControlVm_channel): error (status=%d)\n", rc);
2513 POSTCODE_LINUX_2(CHIPSET_INIT_FAILURE_PC, DIAG_SEVERITY_ERR);
2514 goto Away;
2515 }
9f8d0e8b 2516
12e364b9
KC
2517 proc_Init();
2518 memset(PartitionPropertyNames, 0, sizeof(PartitionPropertyNames));
12e364b9 2519 InitPartitionProperties();
12e364b9 2520
927c7927
KC
2521 PartitionType = visor_proc_CreateType(ProcDir, PartitionTypeNames,
2522 (const char **)
2523 PartitionPropertyNames,
2524 &show_partition_property);
12e364b9
KC
2525
2526 /* Setup Installation fields */
2527 installer_file = proc_create("installer", 0644, ProcDir,
2528 &proc_installer_fops);
12e364b9
KC
2529
2530 memset(&g_DiagMsgHdr, 0, sizeof(CONTROLVM_MESSAGE_HEADER));
2531
2532 chipset_proc_dir = proc_create(VISORCHIPSET_CHIPSET_PROC_ENTRY_FN,
2533 0644, ProcDir, &chipset_proc_fops);
2534 memset(&g_ChipSetMsgHdr, 0, sizeof(CONTROLVM_MESSAGE_HEADER));
2535
2536 parahotplug_proc_dir =
2537 proc_create(VISORCHIPSET_PARAHOTPLUG_PROC_ENTRY_FN, 0200,
2538 ProcDir, &parahotplug_proc_fops);
2539 memset(&g_DelDumpMsgHdr, 0, sizeof(CONTROLVM_MESSAGE_HEADER));
2540
12e364b9
KC
2541 Putfile_buffer_list_pool =
2542 kmem_cache_create(Putfile_buffer_list_pool_name,
2543 sizeof(struct putfile_buffer_entry),
2544 0, SLAB_HWCACHE_ALIGN, NULL);
2545 if (!Putfile_buffer_list_pool) {
4cb005a9
KC
2546 ERRDRV("failed to alloc Putfile_buffer_list_pool: (status=-1)\n");
2547 POSTCODE_LINUX_2(CHIPSET_INIT_FAILURE_PC, DIAG_SEVERITY_ERR);
2548 rc = -1;
2549 goto Away;
12e364b9
KC
2550 }
2551 if (visorchipset_disable_controlvm) {
2552 LOGINF("visorchipset_init:controlvm disabled");
2553 } else {
2554 /* if booting in a crash kernel */
2555 if (visorchipset_crash_kernel)
2556 INIT_DELAYED_WORK(&Periodic_controlvm_work,
2557 setup_crash_devices_work_queue);
2558 else
2559 INIT_DELAYED_WORK(&Periodic_controlvm_work,
2560 controlvm_periodic_work);
2561 Periodic_controlvm_workqueue =
2562 create_singlethread_workqueue("visorchipset_controlvm");
2563
4cb005a9
KC
2564 if (Periodic_controlvm_workqueue == NULL) {
2565 ERRDRV("cannot create controlvm workqueue: (status=%d)\n",
2566 -ENOMEM);
2567 POSTCODE_LINUX_2(CREATE_WORKQUEUE_FAILED_PC,
2568 DIAG_SEVERITY_ERR);
2569 rc = -ENOMEM;
2570 goto Away;
2571 }
12e364b9
KC
2572 Most_recent_message_jiffies = jiffies;
2573 Poll_jiffies = POLLJIFFIES_CONTROLVMCHANNEL_FAST;
9f8d0e8b
KC
2574 rc = queue_delayed_work(Periodic_controlvm_workqueue,
2575 &Periodic_controlvm_work, Poll_jiffies);
4cb005a9
KC
2576 if (rc < 0) {
2577 ERRDRV("queue_delayed_work(Periodic_controlvm_workqueue, &Periodic_controlvm_work, Poll_jiffies): error (status=%d)\n", rc);
2578 POSTCODE_LINUX_2(QUEUE_DELAYED_WORK_PC,
2579 DIAG_SEVERITY_ERR);
2580 goto Away;
2581 }
9f8d0e8b 2582
12e364b9
KC
2583 }
2584
2585 Visorchipset_platform_device.dev.devt = MajorDev;
4cb005a9
KC
2586 if (platform_device_register(&Visorchipset_platform_device) < 0) {
2587 ERRDRV("platform_device_register(visorchipset) failed: (status=-1)\n");
2588 POSTCODE_LINUX_2(DEVICE_REGISTER_FAILURE_PC, DIAG_SEVERITY_ERR);
2589 rc = -1;
2590 goto Away;
2591 }
12e364b9
KC
2592 LOGINF("visorchipset device created");
2593 POSTCODE_LINUX_2(CHIPSET_INIT_SUCCESS_PC, POSTCODE_SEVERITY_INFO);
22ad57ba 2594 rc = 0;
12e364b9 2595Away:
12e364b9
KC
2596 if (rc) {
2597 LOGERR("visorchipset_init failed");
2598 POSTCODE_LINUX_3(CHIPSET_INIT_FAILURE_PC, rc,
2599 POSTCODE_SEVERITY_ERR);
2600 }
2601 return rc;
2602}
2603
2604static void
2605visorchipset_exit(void)
2606{
2607 char s[99];
2608 POSTCODE_LINUX_2(DRIVER_EXIT_PC, POSTCODE_SEVERITY_INFO);
2609
2610 if (visorchipset_disable_controlvm) {
2611 ;
2612 } else {
2613 cancel_delayed_work(&Periodic_controlvm_work);
2614 flush_workqueue(Periodic_controlvm_workqueue);
2615 destroy_workqueue(Periodic_controlvm_workqueue);
2616 Periodic_controlvm_workqueue = NULL;
2617 destroy_controlvm_payload_info(&ControlVm_payload_info);
2618 }
2619 Test_Vnic_channel = NULL;
2620 if (Putfile_buffer_list_pool) {
2621 kmem_cache_destroy(Putfile_buffer_list_pool);
2622 Putfile_buffer_list_pool = NULL;
2623 }
1783319f 2624
12e364b9
KC
2625 cleanup_controlvm_structures();
2626
12e364b9 2627 if (PartitionType) {
927c7927 2628 visor_proc_DestroyType(PartitionType);
12e364b9
KC
2629 PartitionType = NULL;
2630 }
2631 if (diag_proc_dir) {
2632 remove_proc_entry(VISORCHIPSET_DIAG_PROC_ENTRY_FN, ProcDir);
2633 diag_proc_dir = NULL;
2634 }
2635 memset(&g_DiagMsgHdr, 0, sizeof(CONTROLVM_MESSAGE_HEADER));
2636
2637 if (chipset_proc_dir) {
2638 remove_proc_entry(VISORCHIPSET_CHIPSET_PROC_ENTRY_FN, ProcDir);
2639 chipset_proc_dir = NULL;
2640 }
2641 memset(&g_ChipSetMsgHdr, 0, sizeof(CONTROLVM_MESSAGE_HEADER));
2642
2643 if (parahotplug_proc_dir) {
2644 remove_proc_entry(VISORCHIPSET_PARAHOTPLUG_PROC_ENTRY_FN,
2645 ProcDir);
2646 parahotplug_proc_dir = NULL;
2647 }
2648
2649 memset(&g_DelDumpMsgHdr, 0, sizeof(CONTROLVM_MESSAGE_HEADER));
2650
2651 proc_DeInit();
8a1182eb
BR
2652 LOGINF("Channel %s (ControlVm) disconnected",
2653 visorchannel_id(ControlVm_channel, s));
2654 visorchannel_destroy(ControlVm_channel);
2655
12e364b9
KC
2656 visorchipset_file_cleanup();
2657 POSTCODE_LINUX_2(DRIVER_EXIT_PC, POSTCODE_SEVERITY_INFO);
2658 LOGINF("chipset driver unloaded");
2659}
2660
2661module_param_named(testvnic, visorchipset_testvnic, int, S_IRUGO);
2662MODULE_PARM_DESC(visorchipset_testvnic, "1 to test vnic, using dummy VNIC connected via a loopback to a physical ethernet");
2663int visorchipset_testvnic = 0;
2664
2665module_param_named(testvnicclient, visorchipset_testvnicclient, int, S_IRUGO);
2666MODULE_PARM_DESC(visorchipset_testvnicclient, "1 to test vnic, using real VNIC channel attached to a separate IOVM guest");
2667int visorchipset_testvnicclient = 0;
2668
2669module_param_named(testmsg, visorchipset_testmsg, int, S_IRUGO);
2670MODULE_PARM_DESC(visorchipset_testmsg,
2671 "1 to manufacture the chipset, bus, and switch messages");
2672int visorchipset_testmsg = 0;
2673
2674module_param_named(major, visorchipset_major, int, S_IRUGO);
2675MODULE_PARM_DESC(visorchipset_major, "major device number to use for the device node");
2676int visorchipset_major = 0;
2677
2678module_param_named(serverregwait, visorchipset_serverregwait, int, S_IRUGO);
2679MODULE_PARM_DESC(visorchipset_serverreqwait,
2680 "1 to have the module wait for the visor bus to register");
2681int visorchipset_serverregwait = 0; /* default is off */
2682module_param_named(clientregwait, visorchipset_clientregwait, int, S_IRUGO);
2683MODULE_PARM_DESC(visorchipset_clientregwait, "1 to have the module wait for the visorclientbus to register");
2684int visorchipset_clientregwait = 1; /* default is on */
2685module_param_named(testteardown, visorchipset_testteardown, int, S_IRUGO);
2686MODULE_PARM_DESC(visorchipset_testteardown,
2687 "1 to test teardown of the chipset, bus, and switch");
2688int visorchipset_testteardown = 0; /* default is off */
2689module_param_named(disable_controlvm, visorchipset_disable_controlvm, int,
2690 S_IRUGO);
2691MODULE_PARM_DESC(visorchipset_disable_controlvm,
2692 "1 to disable polling of controlVm channel");
2693int visorchipset_disable_controlvm = 0; /* default is off */
2694module_param_named(crash_kernel, visorchipset_crash_kernel, int, S_IRUGO);
2695MODULE_PARM_DESC(visorchipset_crash_kernel,
2696 "1 means we are running in crash kernel");
2697int visorchipset_crash_kernel = 0; /* default is running in non-crash kernel */
2698module_param_named(holdchipsetready, visorchipset_holdchipsetready,
2699 int, S_IRUGO);
2700MODULE_PARM_DESC(visorchipset_holdchipsetready,
2701 "1 to hold response to CHIPSET_READY");
2702int visorchipset_holdchipsetready = 0; /* default is to send CHIPSET_READY
2703 * response immediately */
2704module_init(visorchipset_init);
2705module_exit(visorchipset_exit);
2706
2707MODULE_AUTHOR("Unisys");
2708MODULE_LICENSE("GPL");
2709MODULE_DESCRIPTION("Supervisor chipset driver for service partition: ver "
2710 VERSION);
2711MODULE_VERSION(VERSION);
This page took 0.240659 seconds and 5 git commands to generate.