Merge tag 'gpio-v3.17-1' of git://git.kernel.org/pub/scm/linux/kernel/git/linusw...
[firefly-linux-kernel-4.4.55.git] / drivers / staging / unisys / uislib / uislib.c
1 /* uislib.c
2  *
3  * Copyright (C) 2010 - 2013 UNISYS CORPORATION
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 /* @ALL_INSPECTED */
19 #define EXPORT_SYMTAB
20 #include <linux/kernel.h>
21 #include <linux/highmem.h>
22 #ifdef CONFIG_MODVERSIONS
23 #include <config/modversions.h>
24 #endif
25 #include <linux/module.h>
26 #include <linux/debugfs.h>
27
28 #include "commontypes.h"
29
30 #include <linux/version.h>
31 #include "uniklog.h"
32 #include "diagnostics/appos_subsystems.h"
33 #include "uisutils.h"
34 #include "vbuschannel.h"
35
36 #include <linux/proc_fs.h>
37 #include <linux/uaccess.h>      /* for copy_from_user */
38 #include <linux/ctype.h>        /* for toupper */
39 #include <linux/list.h>
40
41 #include "sparstop.h"
42 #include "visorchipset.h"
43 #include "chanstub.h"
44 #include "version.h"
45 #include "guestlinuxdebug.h"
46
47 #define SET_PROC_OWNER(x, y)
48
49 #define POLLJIFFIES_NORMAL 1
50 /* Choose whether or not you want to wakeup the request-polling thread
51  * after an IO termination:
52  * this is shorter than using __FILE__ (full path name) in
53  * debug/info/error messages
54  */
55 #define CURRENT_FILE_PC UISLIB_PC_uislib_c
56 #define __MYFILE__ "uislib.c"
57
58 /* global function pointers that act as callback functions into virtpcimod */
59 int (*VirtControlChanFunc)(struct guest_msgs *);
60
61 static int ProcReadBufferValid;
62 static char *ProcReadBuffer;    /* Note this MUST be global,
63                                          * because the contents must */
64 static unsigned int chipset_inited;
65
66 #define WAIT_ON_CALLBACK(handle)        \
67         do {                    \
68                 if (handle)             \
69                         break;          \
70                 UIS_THREAD_WAIT;        \
71         } while (1)
72
73 static struct bus_info *BusListHead;
74 static rwlock_t BusListLock;
75 static int BusListCount;        /* number of buses in the list */
76 static int MaxBusCount;         /* maximum number of buses expected */
77 static u64 PhysicalDataChan;
78 static int PlatformNumber;
79
80 static struct uisthread_info Incoming_ThreadInfo;
81 static BOOL Incoming_Thread_Started = FALSE;
82 static LIST_HEAD(List_Polling_Device_Channels);
83 static unsigned long long tot_moved_to_tail_cnt;
84 static unsigned long long tot_wait_cnt;
85 static unsigned long long tot_wakeup_cnt;
86 static unsigned long long tot_schedule_cnt;
87 static int en_smart_wakeup = 1;
88 static DEFINE_SEMAPHORE(Lock_Polling_Device_Channels);  /* unlocked */
89 static DECLARE_WAIT_QUEUE_HEAD(Wakeup_Polling_Device_Channels);
90 static int Go_Polling_Device_Channels;
91
92 #define CALLHOME_PROC_ENTRY_FN "callhome"
93 #define CALLHOME_THROTTLED_PROC_ENTRY_FN "callhome_throttled"
94
95 #define DIR_DEBUGFS_ENTRY "uislib"
96 static struct dentry *dir_debugfs;
97
98 #define PLATFORMNUMBER_DEBUGFS_ENTRY_FN "platform"
99 static struct dentry *platformnumber_debugfs_read;
100
101 #define CYCLES_BEFORE_WAIT_DEBUGFS_ENTRY_FN "cycles_before_wait"
102 static struct dentry *cycles_before_wait_debugfs_read;
103
104 #define SMART_WAKEUP_DEBUGFS_ENTRY_FN "smart_wakeup"
105 static struct dentry *smart_wakeup_debugfs_entry;
106
107 #define INFO_DEBUGFS_ENTRY_FN "info"
108 static struct dentry *info_debugfs_entry;
109
110 static unsigned long long cycles_before_wait, wait_cycles;
111
112 /*****************************************************/
113 /* local functions                                   */
114 /*****************************************************/
115
116 static ssize_t info_debugfs_read(struct file *file, char __user *buf,
117                               size_t len, loff_t *offset);
118 static const struct file_operations debugfs_info_fops = {
119         .read = info_debugfs_read,
120 };
121
122 static void
123 init_msg_header(CONTROLVM_MESSAGE *msg, u32 id, uint rsp, uint svr)
124 {
125         memset(msg, 0, sizeof(CONTROLVM_MESSAGE));
126         msg->hdr.Id = id;
127         msg->hdr.Flags.responseExpected = rsp;
128         msg->hdr.Flags.server = svr;
129 }
130
131 static __iomem void *
132 init_vbus_channel(u64 channelAddr, u32 channelBytes)
133 {
134         void __iomem *rc = NULL;
135         void __iomem *pChan = uislib_ioremap_cache(channelAddr, channelBytes);
136         if (!pChan) {
137                 LOGERR("CONTROLVM_BUS_CREATE error: ioremap_cache of channelAddr:%Lx for channelBytes:%llu failed",
138                      (unsigned long long) channelAddr,
139                      (unsigned long long) channelBytes);
140                 rc = NULL;
141                 goto Away;
142         }
143         if (!ULTRA_VBUS_CHANNEL_OK_CLIENT(pChan, NULL)) {
144                 ERRDRV("%s channel cannot be used", __func__);
145                 uislib_iounmap(pChan);
146                 rc = NULL;
147                 goto Away;
148         }
149         rc = pChan;
150 Away:
151         return rc;
152 }
153
154 static int
155 create_bus(CONTROLVM_MESSAGE *msg, char *buf)
156 {
157         u32 busNo, deviceCount;
158         struct bus_info *tmp, *bus;
159         size_t size;
160
161         if (MaxBusCount == BusListCount) {
162                 LOGERR("CONTROLVM_BUS_CREATE Failed: max buses:%d already created\n",
163                      MaxBusCount);
164                 POSTCODE_LINUX_3(BUS_CREATE_FAILURE_PC, MaxBusCount,
165                                  POSTCODE_SEVERITY_ERR);
166                 return CONTROLVM_RESP_ERROR_MAX_BUSES;
167         }
168
169         busNo = msg->cmd.createBus.busNo;
170         deviceCount = msg->cmd.createBus.deviceCount;
171
172         POSTCODE_LINUX_4(BUS_CREATE_ENTRY_PC, busNo, deviceCount,
173                          POSTCODE_SEVERITY_INFO);
174
175         size =
176             sizeof(struct bus_info) +
177             (deviceCount * sizeof(struct device_info *));
178         bus = kzalloc(size, GFP_ATOMIC);
179         if (!bus) {
180                 LOGERR("CONTROLVM_BUS_CREATE Failed: kmalloc for bus failed.\n");
181                 POSTCODE_LINUX_3(BUS_CREATE_FAILURE_PC, busNo,
182                                  POSTCODE_SEVERITY_ERR);
183                 return CONTROLVM_RESP_ERROR_KMALLOC_FAILED;
184         }
185
186         /* Currently by default, the bus Number is the GuestHandle.
187          * Configure Bus message can override this.
188          */
189         if (msg->hdr.Flags.testMessage) {
190                 /* This implies we're the IOVM so set guest handle to 0... */
191                 bus->guestHandle = 0;
192                 bus->busNo = busNo;
193                 bus->localVnic = 1;
194         } else
195                 bus->busNo = bus->guestHandle = busNo;
196         sprintf(bus->name, "%d", (int) bus->busNo);
197         bus->deviceCount = deviceCount;
198         bus->device =
199             (struct device_info **) ((char *) bus + sizeof(struct bus_info));
200         bus->busInstGuid = msg->cmd.createBus.busInstGuid;
201         bus->busChannelBytes = 0;
202         bus->pBusChannel = NULL;
203
204         /* add bus to our bus list - but check for duplicates first */
205         read_lock(&BusListLock);
206         for (tmp = BusListHead; tmp; tmp = tmp->next) {
207                 if (tmp->busNo == bus->busNo)
208                         break;
209         }
210         read_unlock(&BusListLock);
211         if (tmp) {
212                 /* found a bus already in the list with same busNo -
213                  * reject add
214                  */
215                 LOGERR("CONTROLVM_BUS_CREATE Failed: bus %d already exists.\n",
216                        bus->busNo);
217                 POSTCODE_LINUX_3(BUS_CREATE_FAILURE_PC, bus->busNo,
218                                  POSTCODE_SEVERITY_ERR);
219                 kfree(bus);
220                 return CONTROLVM_RESP_ERROR_ALREADY_DONE;
221         }
222         if ((msg->cmd.createBus.channelAddr != 0)
223             && (msg->cmd.createBus.channelBytes != 0)) {
224                 bus->busChannelBytes = msg->cmd.createBus.channelBytes;
225                 bus->pBusChannel =
226                     init_vbus_channel(msg->cmd.createBus.channelAddr,
227                                       msg->cmd.createBus.channelBytes);
228         }
229         /* the msg is bound for virtpci; send guest_msgs struct to callback */
230         if (!msg->hdr.Flags.server) {
231                 struct guest_msgs cmd;
232                 cmd.msgtype = GUEST_ADD_VBUS;
233                 cmd.add_vbus.busNo = busNo;
234                 cmd.add_vbus.chanptr = bus->pBusChannel;
235                 cmd.add_vbus.deviceCount = deviceCount;
236                 cmd.add_vbus.busTypeGuid = msg->cmd.createBus.busDataTypeGuid;
237                 cmd.add_vbus.busInstGuid = msg->cmd.createBus.busInstGuid;
238                 if (!VirtControlChanFunc) {
239                         LOGERR("CONTROLVM_BUS_CREATE Failed: virtpci callback not registered.");
240                         POSTCODE_LINUX_3(BUS_CREATE_FAILURE_PC, bus->busNo,
241                                          POSTCODE_SEVERITY_ERR);
242                         kfree(bus);
243                         return CONTROLVM_RESP_ERROR_VIRTPCI_DRIVER_FAILURE;
244                 }
245                 if (!VirtControlChanFunc(&cmd)) {
246                         LOGERR("CONTROLVM_BUS_CREATE Failed: virtpci GUEST_ADD_VBUS returned error.");
247                         POSTCODE_LINUX_3(BUS_CREATE_FAILURE_PC, bus->busNo,
248                                          POSTCODE_SEVERITY_ERR);
249                         kfree(bus);
250                         return
251                             CONTROLVM_RESP_ERROR_VIRTPCI_DRIVER_CALLBACK_ERROR;
252                 }
253         }
254
255         /* add bus at the head of our list */
256         write_lock(&BusListLock);
257         if (!BusListHead)
258                 BusListHead = bus;
259         else {
260                 bus->next = BusListHead;
261                 BusListHead = bus;
262         }
263         BusListCount++;
264         write_unlock(&BusListLock);
265
266         POSTCODE_LINUX_3(BUS_CREATE_EXIT_PC, bus->busNo,
267                          POSTCODE_SEVERITY_INFO);
268         return CONTROLVM_RESP_SUCCESS;
269 }
270
271 static int
272 destroy_bus(CONTROLVM_MESSAGE *msg, char *buf)
273 {
274         int i;
275         struct bus_info *bus, *prev = NULL;
276         u32 busNo;
277
278         busNo = msg->cmd.destroyBus.busNo;
279
280         /* find and delete the bus */
281         read_lock(&BusListLock);
282         for (bus = BusListHead; bus; prev = bus, bus = bus->next) {
283                 if (bus->busNo == busNo) {
284                         /* found the bus - ensure that all device
285                          * slots are NULL
286                          */
287                         for (i = 0; i < bus->deviceCount; i++) {
288                                 if (bus->device[i] != NULL) {
289                                         LOGERR("CONTROLVM_BUS_DESTROY Failed: device %i attached to bus %d.",
290                                              i, busNo);
291                                         read_unlock(&BusListLock);
292                                         return CONTROLVM_RESP_ERROR_BUS_DEVICE_ATTACHED;
293                                 }
294                         }
295                         read_unlock(&BusListLock);
296                         /* the msg is bound for virtpci; send
297                          * guest_msgs struct to callback
298                          */
299                         if (!msg->hdr.Flags.server) {
300                                 struct guest_msgs cmd;
301                                 cmd.msgtype = GUEST_DEL_VBUS;
302                                 cmd.del_vbus.busNo = busNo;
303                                 if (!VirtControlChanFunc) {
304                                         LOGERR("CONTROLVM_BUS_DESTROY Failed: virtpci callback not registered.");
305                                         return CONTROLVM_RESP_ERROR_VIRTPCI_DRIVER_FAILURE;
306                                 }
307                                 if (!VirtControlChanFunc(&cmd)) {
308                                         LOGERR("CONTROLVM_BUS_DESTROY Failed: virtpci GUEST_DEL_VBUS returned error.");
309                                         return CONTROLVM_RESP_ERROR_VIRTPCI_DRIVER_CALLBACK_ERROR;
310                                 }
311                         }
312                         /* remove the bus from the list */
313                         write_lock(&BusListLock);
314                         if (prev)       /* not at head */
315                                 prev->next = bus->next;
316                         else
317                                 BusListHead = bus->next;
318                         BusListCount--;
319                         write_unlock(&BusListLock);
320                         break;
321                 }
322         }
323
324         if (!bus) {
325                 LOGERR("CONTROLVM_BUS_DESTROY Failed: failed to find bus %d.\n",
326                        busNo);
327                 read_unlock(&BusListLock);
328                 return CONTROLVM_RESP_ERROR_ALREADY_DONE;
329         }
330         if (bus->pBusChannel) {
331                 uislib_iounmap(bus->pBusChannel);
332                 bus->pBusChannel = NULL;
333         }
334
335         kfree(bus);
336         return CONTROLVM_RESP_SUCCESS;
337 }
338
339 static int
340 create_device(CONTROLVM_MESSAGE *msg, char *buf)
341 {
342         struct device_info *dev;
343         struct bus_info *bus;
344         u32 busNo, devNo;
345         int result = CONTROLVM_RESP_SUCCESS;
346         u64 minSize = MIN_IO_CHANNEL_SIZE;
347         ReqHandlerInfo_t *pReqHandler;
348
349         busNo = msg->cmd.createDevice.busNo;
350         devNo = msg->cmd.createDevice.devNo;
351
352         POSTCODE_LINUX_4(DEVICE_CREATE_ENTRY_PC, devNo, busNo,
353                          POSTCODE_SEVERITY_INFO);
354
355         dev = kzalloc(sizeof(struct device_info), GFP_ATOMIC);
356         if (!dev) {
357                 LOGERR("CONTROLVM_DEVICE_CREATE Failed: kmalloc for dev failed.\n");
358                 POSTCODE_LINUX_4(DEVICE_CREATE_FAILURE_PC, devNo, busNo,
359                                  POSTCODE_SEVERITY_ERR);
360                 return CONTROLVM_RESP_ERROR_KMALLOC_FAILED;
361         }
362
363         dev->channelTypeGuid = msg->cmd.createDevice.dataTypeGuid;
364         dev->intr = msg->cmd.createDevice.intr;
365         dev->channelAddr = msg->cmd.createDevice.channelAddr;
366         dev->busNo = busNo;
367         dev->devNo = devNo;
368         sema_init(&dev->interrupt_callback_lock, 1);    /* unlocked */
369         sprintf(dev->devid, "vbus%u:dev%u", (unsigned) busNo, (unsigned) devNo);
370         /* map the channel memory for the device. */
371         if (msg->hdr.Flags.testMessage)
372                 dev->chanptr = (void __iomem *)__va(dev->channelAddr);
373         else {
374                 pReqHandler = ReqHandlerFind(dev->channelTypeGuid);
375                 if (pReqHandler)
376                         /* generic service handler registered for this
377                          * channel
378                          */
379                         minSize = pReqHandler->min_channel_bytes;
380                 if (minSize > msg->cmd.createDevice.channelBytes) {
381                         LOGERR("CONTROLVM_DEVICE_CREATE Failed: channel size is too small, channel size:0x%lx, required size:0x%lx",
382                              (ulong) msg->cmd.createDevice.channelBytes,
383                              (ulong) minSize);
384                         POSTCODE_LINUX_4(DEVICE_CREATE_FAILURE_PC, devNo, busNo,
385                                          POSTCODE_SEVERITY_ERR);
386                         result = CONTROLVM_RESP_ERROR_CHANNEL_SIZE_TOO_SMALL;
387                         goto Away;
388                 }
389                 dev->chanptr =
390                     uislib_ioremap_cache(dev->channelAddr,
391                                          msg->cmd.createDevice.channelBytes);
392                 if (!dev->chanptr) {
393                         LOGERR("CONTROLVM_DEVICE_CREATE Failed: ioremap_cache of channelAddr:%Lx for channelBytes:%llu failed",
394                              dev->channelAddr,
395                              msg->cmd.createDevice.channelBytes);
396                         result = CONTROLVM_RESP_ERROR_IOREMAP_FAILED;
397                         POSTCODE_LINUX_4(DEVICE_CREATE_FAILURE_PC, devNo, busNo,
398                                          POSTCODE_SEVERITY_ERR);
399                         goto Away;
400                 }
401         }
402         dev->devInstGuid = msg->cmd.createDevice.devInstGuid;
403         dev->channelBytes = msg->cmd.createDevice.channelBytes;
404
405         read_lock(&BusListLock);
406         for (bus = BusListHead; bus; bus = bus->next) {
407                 if (bus->busNo == busNo) {
408                         /* make sure the device number is valid */
409                         if (devNo >= bus->deviceCount) {
410                                 LOGERR("CONTROLVM_DEVICE_CREATE Failed: device (%d) >= deviceCount (%d).",
411                                      devNo, bus->deviceCount);
412                                 result = CONTROLVM_RESP_ERROR_MAX_DEVICES;
413                                 POSTCODE_LINUX_4(DEVICE_CREATE_FAILURE_PC,
414                                                  devNo, busNo,
415                                                  POSTCODE_SEVERITY_ERR);
416                                 read_unlock(&BusListLock);
417                                 goto Away;
418                         }
419                         /* make sure this device is not already set */
420                         if (bus->device[devNo]) {
421                                 LOGERR("CONTROLVM_DEVICE_CREATE Failed: device %d is already exists.",
422                                      devNo);
423                                 POSTCODE_LINUX_4(DEVICE_CREATE_FAILURE_PC,
424                                                  devNo, busNo,
425                                                  POSTCODE_SEVERITY_ERR);
426                                 result = CONTROLVM_RESP_ERROR_ALREADY_DONE;
427                                 read_unlock(&BusListLock);
428                                 goto Away;
429                         }
430                         read_unlock(&BusListLock);
431                         /* the msg is bound for virtpci; send
432                          * guest_msgs struct to callback
433                          */
434                         if (!msg->hdr.Flags.server) {
435                                 struct guest_msgs cmd;
436                                 if (!uuid_le_cmp(dev->channelTypeGuid,
437                                      UltraVhbaChannelProtocolGuid)) {
438                                         wait_for_valid_guid(&((CHANNEL_HEADER
439                                                               __iomem *) (dev->
440                                                                   chanptr))->
441                                                             Type);
442                                         if (!ULTRA_VHBA_CHANNEL_OK_CLIENT
443                                             (dev->chanptr, NULL)) {
444                                                 LOGERR("CONTROLVM_DEVICE_CREATE Failed:[CLIENT]VHBA dev %d chan invalid.",
445                                                      devNo);
446                                                 POSTCODE_LINUX_4
447                                                     (DEVICE_CREATE_FAILURE_PC,
448                                                      devNo, busNo,
449                                                      POSTCODE_SEVERITY_ERR);
450                                                 result = CONTROLVM_RESP_ERROR_CHANNEL_INVALID;
451                                                 goto Away;
452                                         }
453                                         cmd.msgtype = GUEST_ADD_VHBA;
454                                         cmd.add_vhba.chanptr = dev->chanptr;
455                                         cmd.add_vhba.busNo = busNo;
456                                         cmd.add_vhba.deviceNo = devNo;
457                                         cmd.add_vhba.devInstGuid =
458                                             dev->devInstGuid;
459                                         cmd.add_vhba.intr = dev->intr;
460                                 } else
461                                     if (!uuid_le_cmp(dev->channelTypeGuid,
462                                          UltraVnicChannelProtocolGuid)) {
463                                         wait_for_valid_guid(&((CHANNEL_HEADER
464                                                               __iomem *) (dev->
465                                                                   chanptr))->
466                                                             Type);
467                                         if (!ULTRA_VNIC_CHANNEL_OK_CLIENT
468                                             (dev->chanptr, NULL)) {
469                                                 LOGERR("CONTROLVM_DEVICE_CREATE Failed: VNIC[CLIENT] dev %d chan invalid.",
470                                                      devNo);
471                                                 POSTCODE_LINUX_4
472                                                     (DEVICE_CREATE_FAILURE_PC,
473                                                      devNo, busNo,
474                                                      POSTCODE_SEVERITY_ERR);
475                                                 result = CONTROLVM_RESP_ERROR_CHANNEL_INVALID;
476                                                 goto Away;
477                                         }
478                                         cmd.msgtype = GUEST_ADD_VNIC;
479                                         cmd.add_vnic.chanptr = dev->chanptr;
480                                         cmd.add_vnic.busNo = busNo;
481                                         cmd.add_vnic.deviceNo = devNo;
482                                         cmd.add_vnic.devInstGuid =
483                                             dev->devInstGuid;
484                                         cmd.add_vhba.intr = dev->intr;
485                                 } else {
486                                         LOGERR("CONTROLVM_DEVICE_CREATE Failed: unknown channelTypeGuid.\n");
487                                         POSTCODE_LINUX_4
488                                             (DEVICE_CREATE_FAILURE_PC, devNo,
489                                              busNo, POSTCODE_SEVERITY_ERR);
490                                         result = CONTROLVM_RESP_ERROR_CHANNEL_TYPE_UNKNOWN;
491                                         goto Away;
492                                 }
493
494                                 if (!VirtControlChanFunc) {
495                                         LOGERR("CONTROLVM_DEVICE_CREATE Failed: virtpci callback not registered.");
496                                         POSTCODE_LINUX_4
497                                             (DEVICE_CREATE_FAILURE_PC, devNo,
498                                              busNo, POSTCODE_SEVERITY_ERR);
499                                         result = CONTROLVM_RESP_ERROR_VIRTPCI_DRIVER_FAILURE;
500                                         goto Away;
501                                 }
502
503                                 if (!VirtControlChanFunc(&cmd)) {
504                                         LOGERR("CONTROLVM_DEVICE_CREATE Failed: virtpci GUEST_ADD_[VHBA||VNIC] returned error.");
505                                         POSTCODE_LINUX_4
506                                             (DEVICE_CREATE_FAILURE_PC, devNo,
507                                              busNo, POSTCODE_SEVERITY_ERR);
508                                         result = CONTROLVM_RESP_ERROR_VIRTPCI_DRIVER_CALLBACK_ERROR;
509                                         goto Away;
510                                 }
511                         }
512                         bus->device[devNo] = dev;
513                         POSTCODE_LINUX_4(DEVICE_CREATE_SUCCESS_PC, devNo, busNo,
514                                          POSTCODE_SEVERITY_INFO);
515                         return CONTROLVM_RESP_SUCCESS;
516                 }
517         }
518         read_unlock(&BusListLock);
519
520         LOGERR("CONTROLVM_DEVICE_CREATE Failed: failed to find bus %d.", busNo);
521         POSTCODE_LINUX_4(DEVICE_CREATE_FAILURE_PC, devNo, busNo,
522                          POSTCODE_SEVERITY_ERR);
523         result = CONTROLVM_RESP_ERROR_BUS_INVALID;
524
525 Away:
526         if (!msg->hdr.Flags.testMessage) {
527                 uislib_iounmap(dev->chanptr);
528                 dev->chanptr = NULL;
529         }
530
531         kfree(dev);
532         return result;
533 }
534
535 static int
536 pause_device(CONTROLVM_MESSAGE *msg)
537 {
538         u32 busNo, devNo;
539         struct bus_info *bus;
540         struct device_info *dev;
541         struct guest_msgs cmd;
542
543         busNo = msg->cmd.deviceChangeState.busNo;
544         devNo = msg->cmd.deviceChangeState.devNo;
545
546         read_lock(&BusListLock);
547         for (bus = BusListHead; bus; bus = bus->next) {
548                 if (bus->busNo == busNo) {
549                         /* make sure the device number is valid */
550                         if (devNo >= bus->deviceCount) {
551                                 LOGERR("CONTROLVM_DEVICE_CHANGESTATE:pause Failed: device(%d) >= deviceCount(%d).",
552                                      devNo, bus->deviceCount);
553                                 read_unlock(&BusListLock);
554                                 return CONTROLVM_RESP_ERROR_DEVICE_INVALID;
555                         }
556                         /* make sure this device exists */
557                         dev = bus->device[devNo];
558                         if (!dev) {
559                                 LOGERR("CONTROLVM_DEVICE_CHANGESTATE:pause Failed: device %d does not exist.",
560                                      devNo);
561                                 read_unlock(&BusListLock);
562                                 return CONTROLVM_RESP_ERROR_ALREADY_DONE;
563                         }
564                         read_unlock(&BusListLock);
565                         /* the msg is bound for virtpci; send
566                          * guest_msgs struct to callback
567                          */
568                         if (!uuid_le_cmp(dev->channelTypeGuid,
569                                         UltraVhbaChannelProtocolGuid)) {
570                                 cmd.msgtype = GUEST_PAUSE_VHBA;
571                                 cmd.pause_vhba.chanptr = dev->chanptr;
572                         } else
573                             if (!uuid_le_cmp(dev->channelTypeGuid,
574                                             UltraVnicChannelProtocolGuid)) {
575                                 cmd.msgtype = GUEST_PAUSE_VNIC;
576                                 cmd.pause_vnic.chanptr = dev->chanptr;
577                         } else {
578                                 LOGERR("CONTROLVM_DEVICE_CHANGESTATE:pause Failed: unknown channelTypeGuid.\n");
579                                 return
580                                     CONTROLVM_RESP_ERROR_CHANNEL_TYPE_UNKNOWN;
581                         }
582
583                         if (!VirtControlChanFunc) {
584                                 LOGERR("CONTROLVM_DEVICE_CHANGESTATE Failed: virtpci callback not registered.");
585                                 return
586                                     CONTROLVM_RESP_ERROR_VIRTPCI_DRIVER_FAILURE;
587                         }
588
589                         if (!VirtControlChanFunc(&cmd)) {
590                                 LOGERR("CONTROLVM_DEVICE_CHANGESTATE:pause Failed: virtpci GUEST_PAUSE_[VHBA||VNIC] returned error.");
591                                 return CONTROLVM_RESP_ERROR_VIRTPCI_DRIVER_CALLBACK_ERROR;
592                         }
593                         break;
594                 }
595         }
596
597         if (!bus) {
598                 LOGERR("CONTROLVM_DEVICE_CHANGESTATE:pause Failed: bus %d does not exist",
599                      busNo);
600                 read_unlock(&BusListLock);
601                 return CONTROLVM_RESP_ERROR_BUS_INVALID;
602         }
603
604         return CONTROLVM_RESP_SUCCESS;
605 }
606
607 static int
608 resume_device(CONTROLVM_MESSAGE *msg)
609 {
610         u32 busNo, devNo;
611         struct bus_info *bus;
612         struct device_info *dev;
613         struct guest_msgs cmd;
614
615         busNo = msg->cmd.deviceChangeState.busNo;
616         devNo = msg->cmd.deviceChangeState.devNo;
617
618         read_lock(&BusListLock);
619         for (bus = BusListHead; bus; bus = bus->next) {
620                 if (bus->busNo == busNo) {
621                         /* make sure the device number is valid */
622                         if (devNo >= bus->deviceCount) {
623                                 LOGERR("CONTROLVM_DEVICE_CHANGESTATE:resume Failed: device(%d) >= deviceCount(%d).",
624                                      devNo, bus->deviceCount);
625                                 read_unlock(&BusListLock);
626                                 return CONTROLVM_RESP_ERROR_DEVICE_INVALID;
627                         }
628                         /* make sure this device exists */
629                         dev = bus->device[devNo];
630                         if (!dev) {
631                                 LOGERR("CONTROLVM_DEVICE_CHANGESTATE:resume Failed: device %d does not exist.",
632                                      devNo);
633                                 read_unlock(&BusListLock);
634                                 return CONTROLVM_RESP_ERROR_ALREADY_DONE;
635                         }
636                         read_unlock(&BusListLock);
637                         /* the msg is bound for virtpci; send
638                          * guest_msgs struct to callback
639                          */
640                         if (!uuid_le_cmp(dev->channelTypeGuid,
641                                         UltraVhbaChannelProtocolGuid)) {
642                                 cmd.msgtype = GUEST_RESUME_VHBA;
643                                 cmd.resume_vhba.chanptr = dev->chanptr;
644                         } else
645                             if (!uuid_le_cmp(dev->channelTypeGuid,
646                                             UltraVnicChannelProtocolGuid)) {
647                                 cmd.msgtype = GUEST_RESUME_VNIC;
648                                 cmd.resume_vnic.chanptr = dev->chanptr;
649                         } else {
650                                 LOGERR("CONTROLVM_DEVICE_CHANGESTATE:resume Failed: unknown channelTypeGuid.\n");
651                                 return
652                                     CONTROLVM_RESP_ERROR_CHANNEL_TYPE_UNKNOWN;
653                         }
654
655                         if (!VirtControlChanFunc) {
656                                 LOGERR("CONTROLVM_DEVICE_CHANGESTATE Failed: virtpci callback not registered.");
657                                 return
658                                     CONTROLVM_RESP_ERROR_VIRTPCI_DRIVER_FAILURE;
659                         }
660
661                         if (!VirtControlChanFunc(&cmd)) {
662                                 LOGERR("CONTROLVM_DEVICE_CHANGESTATE:resume Failed: virtpci GUEST_RESUME_[VHBA||VNIC] returned error.");
663                                 return CONTROLVM_RESP_ERROR_VIRTPCI_DRIVER_CALLBACK_ERROR;
664                         }
665                         break;
666                 }
667         }
668
669         if (!bus) {
670                 LOGERR("CONTROLVM_DEVICE_CHANGESTATE:resume Failed: bus %d does not exist",
671                      busNo);
672                 read_unlock(&BusListLock);
673                 return CONTROLVM_RESP_ERROR_BUS_INVALID;
674         }
675
676         return CONTROLVM_RESP_SUCCESS;
677 }
678
679 static int
680 destroy_device(CONTROLVM_MESSAGE *msg, char *buf)
681 {
682         u32 busNo, devNo;
683         struct bus_info *bus;
684         struct device_info *dev;
685         struct guest_msgs cmd;
686
687         busNo = msg->cmd.destroyDevice.busNo;
688         devNo = msg->cmd.destroyDevice.devNo;
689
690         read_lock(&BusListLock);
691         LOGINF("destroy_device called for busNo=%u, devNo=%u", busNo, devNo);
692         for (bus = BusListHead; bus; bus = bus->next) {
693                 if (bus->busNo == busNo) {
694                         /* make sure the device number is valid */
695                         if (devNo >= bus->deviceCount) {
696                                 LOGERR("CONTROLVM_DEVICE_DESTORY Failed: device(%d) >= deviceCount(%d).",
697                                      devNo, bus->deviceCount);
698                                 read_unlock(&BusListLock);
699                                 return CONTROLVM_RESP_ERROR_DEVICE_INVALID;
700                         }
701                         /* make sure this device exists */
702                         dev = bus->device[devNo];
703                         if (!dev) {
704                                 LOGERR("CONTROLVM_DEVICE_DESTROY Failed: device %d does not exist.",
705                                      devNo);
706                                 read_unlock(&BusListLock);
707                                 return CONTROLVM_RESP_ERROR_ALREADY_DONE;
708                         }
709                         read_unlock(&BusListLock);
710                         /* the msg is bound for virtpci; send
711                          * guest_msgs struct to callback
712                          */
713                         if (!uuid_le_cmp(dev->channelTypeGuid,
714                                         UltraVhbaChannelProtocolGuid)) {
715                                 cmd.msgtype = GUEST_DEL_VHBA;
716                                 cmd.del_vhba.chanptr = dev->chanptr;
717                         } else
718                             if (!uuid_le_cmp(dev->channelTypeGuid,
719                                             UltraVnicChannelProtocolGuid)) {
720                                 cmd.msgtype = GUEST_DEL_VNIC;
721                                 cmd.del_vnic.chanptr = dev->chanptr;
722                         } else {
723                                 LOGERR("CONTROLVM_DEVICE_DESTROY Failed: unknown channelTypeGuid.\n");
724                                 return
725                                     CONTROLVM_RESP_ERROR_CHANNEL_TYPE_UNKNOWN;
726                         }
727
728                         if (!VirtControlChanFunc) {
729                                 LOGERR("CONTROLVM_DEVICE_DESTORY Failed: virtpci callback not registered.");
730                                 return
731                                     CONTROLVM_RESP_ERROR_VIRTPCI_DRIVER_FAILURE;
732                         }
733
734                         if (!VirtControlChanFunc(&cmd)) {
735                                 LOGERR("CONTROLVM_DEVICE_DESTROY Failed: virtpci GUEST_DEL_[VHBA||VNIC] returned error.");
736                                 return CONTROLVM_RESP_ERROR_VIRTPCI_DRIVER_CALLBACK_ERROR;
737                         }
738 /* you must disable channel interrupts BEFORE you unmap the channel,
739  * because if you unmap first, there may still be some activity going
740  * on which accesses the channel and you will get a "unable to handle
741  * kernel paging request"
742  */
743                         if (dev->polling) {
744                                 LOGINF("calling uislib_disable_channel_interrupts");
745                                 uislib_disable_channel_interrupts(busNo, devNo);
746                         }
747                         /* unmap the channel memory for the device. */
748                         if (!msg->hdr.Flags.testMessage) {
749                                 LOGINF("destroy_device, doing iounmap");
750                                 uislib_iounmap(dev->chanptr);
751                         }
752                         kfree(dev);
753                         bus->device[devNo] = NULL;
754                         break;
755                 }
756         }
757
758         if (!bus) {
759                 LOGERR("CONTROLVM_DEVICE_DESTROY Failed: bus %d does not exist",
760                        busNo);
761                 read_unlock(&BusListLock);
762                 return CONTROLVM_RESP_ERROR_BUS_INVALID;
763         }
764
765         return CONTROLVM_RESP_SUCCESS;
766 }
767
768 static int
769 init_chipset(CONTROLVM_MESSAGE *msg, char *buf)
770 {
771         POSTCODE_LINUX_2(CHIPSET_INIT_ENTRY_PC, POSTCODE_SEVERITY_INFO);
772
773         MaxBusCount = msg->cmd.initChipset.busCount;
774         PlatformNumber = msg->cmd.initChipset.platformNumber;
775         PhysicalDataChan = 0;
776
777         /* We need to make sure we have our functions registered
778         * before processing messages.  If we are a test vehicle the
779         * testMessage for init_chipset will be set.  We can ignore the
780         * waits for the callbacks, since this will be manually entered
781         * from a user.  If no testMessage is set, we will wait for the
782         * functions.
783         */
784         if (!msg->hdr.Flags.testMessage)
785                 WAIT_ON_CALLBACK(VirtControlChanFunc);
786
787         chipset_inited = 1;
788         POSTCODE_LINUX_2(CHIPSET_INIT_EXIT_PC, POSTCODE_SEVERITY_INFO);
789
790         return CONTROLVM_RESP_SUCCESS;
791 }
792
793 static int
794 delete_bus_glue(u32 busNo)
795 {
796         CONTROLVM_MESSAGE msg;
797
798         init_msg_header(&msg, CONTROLVM_BUS_DESTROY, 0, 0);
799         msg.cmd.destroyBus.busNo = busNo;
800         if (destroy_bus(&msg, NULL) != CONTROLVM_RESP_SUCCESS) {
801                 LOGERR("destroy_bus failed. busNo=0x%x\n", busNo);
802                 return 0;
803         }
804         return 1;
805 }
806
807 static int
808 delete_device_glue(u32 busNo, u32 devNo)
809 {
810         CONTROLVM_MESSAGE msg;
811
812         init_msg_header(&msg, CONTROLVM_DEVICE_DESTROY, 0, 0);
813         msg.cmd.destroyDevice.busNo = busNo;
814         msg.cmd.destroyDevice.devNo = devNo;
815         if (destroy_device(&msg, NULL) != CONTROLVM_RESP_SUCCESS) {
816                 LOGERR("destroy_device failed. busNo=0x%x devNo=0x%x\n", busNo,
817                        devNo);
818                 return 0;
819         }
820         return 1;
821 }
822
823 int
824 uislib_client_inject_add_bus(u32 busNo, uuid_le instGuid,
825                              u64 channelAddr, ulong nChannelBytes)
826 {
827         CONTROLVM_MESSAGE msg;
828
829         LOGINF("enter busNo=0x%x\n", busNo);
830         /* step 0: init the chipset */
831         POSTCODE_LINUX_3(CHIPSET_INIT_ENTRY_PC, busNo, POSTCODE_SEVERITY_INFO);
832
833         if (!chipset_inited) {
834                 /* step: initialize the chipset */
835                 init_msg_header(&msg, CONTROLVM_CHIPSET_INIT, 0, 0);
836                 /* this change is needed so that console will come up
837                 * OK even when the bus 0 create comes in late.  If the
838                 * bus 0 create is the first create, then the add_vnic
839                 * will work fine, but if the bus 0 create arrives
840                 * after number 4, then the add_vnic will fail, and the
841                 * ultraboot will fail.
842                 */
843                 msg.cmd.initChipset.busCount = 23;
844                 msg.cmd.initChipset.switchCount = 0;
845                 if (init_chipset(&msg, NULL) != CONTROLVM_RESP_SUCCESS) {
846                         LOGERR("init_chipset failed.\n");
847                         return 0;
848                 }
849                 LOGINF("chipset initialized\n");
850                 POSTCODE_LINUX_3(CHIPSET_INIT_EXIT_PC, busNo,
851                                  POSTCODE_SEVERITY_INFO);
852         }
853
854         /* step 1: create a bus */
855         POSTCODE_LINUX_3(BUS_CREATE_ENTRY_PC, busNo, POSTCODE_SEVERITY_WARNING);
856         init_msg_header(&msg, CONTROLVM_BUS_CREATE, 0, 0);
857         msg.cmd.createBus.busNo = busNo;
858         msg.cmd.createBus.deviceCount = 23;     /* devNo+1; */
859         msg.cmd.createBus.channelAddr = channelAddr;
860         msg.cmd.createBus.channelBytes = nChannelBytes;
861         if (create_bus(&msg, NULL) != CONTROLVM_RESP_SUCCESS) {
862                 LOGERR("create_bus failed.\n");
863                 POSTCODE_LINUX_3(BUS_CREATE_FAILURE_PC, busNo,
864                                  POSTCODE_SEVERITY_ERR);
865                 return 0;
866         }
867         POSTCODE_LINUX_3(BUS_CREATE_EXIT_PC, busNo, POSTCODE_SEVERITY_INFO);
868
869         return 1;
870 }
871 EXPORT_SYMBOL_GPL(uislib_client_inject_add_bus);
872
873
874 int
875 uislib_client_inject_del_bus(u32 busNo)
876 {
877         return delete_bus_glue(busNo);
878 }
879 EXPORT_SYMBOL_GPL(uislib_client_inject_del_bus);
880
881 int
882 uislib_client_inject_pause_vhba(u32 busNo, u32 devNo)
883 {
884         CONTROLVM_MESSAGE msg;
885         int rc;
886
887         init_msg_header(&msg, CONTROLVM_DEVICE_CHANGESTATE, 0, 0);
888         msg.cmd.deviceChangeState.busNo = busNo;
889         msg.cmd.deviceChangeState.devNo = devNo;
890         msg.cmd.deviceChangeState.state = SegmentStateStandby;
891         rc = pause_device(&msg);
892         if (rc != CONTROLVM_RESP_SUCCESS) {
893                 LOGERR("VHBA pause_device failed. busNo=0x%x devNo=0x%x\n",
894                        busNo, devNo);
895                 return rc;
896         }
897         return 0;
898 }
899 EXPORT_SYMBOL_GPL(uislib_client_inject_pause_vhba);
900
901 int
902 uislib_client_inject_resume_vhba(u32 busNo, u32 devNo)
903 {
904         CONTROLVM_MESSAGE msg;
905         int rc;
906
907         init_msg_header(&msg, CONTROLVM_DEVICE_CHANGESTATE, 0, 0);
908         msg.cmd.deviceChangeState.busNo = busNo;
909         msg.cmd.deviceChangeState.devNo = devNo;
910         msg.cmd.deviceChangeState.state = SegmentStateRunning;
911         rc = resume_device(&msg);
912         if (rc != CONTROLVM_RESP_SUCCESS) {
913                 LOGERR("VHBA resume_device failed. busNo=0x%x devNo=0x%x\n",
914                        busNo, devNo);
915                 return rc;
916         }
917         return 0;
918
919 }
920 EXPORT_SYMBOL_GPL(uislib_client_inject_resume_vhba);
921
922 int
923 uislib_client_inject_add_vhba(u32 busNo, u32 devNo,
924                               u64 phys_chan_addr, u32 chan_bytes,
925                               int is_test_addr, uuid_le instGuid,
926                               struct InterruptInfo *intr)
927 {
928         CONTROLVM_MESSAGE msg;
929
930         LOGINF(" enter busNo=0x%x devNo=0x%x\n", busNo, devNo);
931         /* chipset init'ed with bus bus has been previously created -
932         * Verify it still exists step 2: create the VHBA device on the
933         * bus
934         */
935         POSTCODE_LINUX_4(VHBA_CREATE_ENTRY_PC, devNo, busNo,
936                          POSTCODE_SEVERITY_INFO);
937
938         init_msg_header(&msg, CONTROLVM_DEVICE_CREATE, 0, 0);
939         if (is_test_addr)
940                 /* signify that the physical channel address does NOT
941                  * need to be ioremap()ed
942                  */
943                 msg.hdr.Flags.testMessage = 1;
944         msg.cmd.createDevice.busNo = busNo;
945         msg.cmd.createDevice.devNo = devNo;
946         msg.cmd.createDevice.devInstGuid = instGuid;
947         if (intr)
948                 msg.cmd.createDevice.intr = *intr;
949         else
950                 memset(&msg.cmd.createDevice.intr, 0,
951                        sizeof(struct InterruptInfo));
952         msg.cmd.createDevice.channelAddr = phys_chan_addr;
953         if (chan_bytes < MIN_IO_CHANNEL_SIZE) {
954                 LOGERR("wrong channel size.chan_bytes = 0x%x IO_CHANNEL_SIZE= 0x%x\n",
955                      chan_bytes, (unsigned int) MIN_IO_CHANNEL_SIZE);
956                 POSTCODE_LINUX_4(VHBA_CREATE_FAILURE_PC, chan_bytes,
957                                  MIN_IO_CHANNEL_SIZE, POSTCODE_SEVERITY_ERR);
958                 return 0;
959         }
960         msg.cmd.createDevice.channelBytes = chan_bytes;
961         msg.cmd.createDevice.dataTypeGuid = UltraVhbaChannelProtocolGuid;
962         if (create_device(&msg, NULL) != CONTROLVM_RESP_SUCCESS) {
963                 LOGERR("VHBA create_device failed.\n");
964                 POSTCODE_LINUX_4(VHBA_CREATE_FAILURE_PC, devNo, busNo,
965                                  POSTCODE_SEVERITY_ERR);
966                 return 0;
967         }
968         POSTCODE_LINUX_4(VHBA_CREATE_SUCCESS_PC, devNo, busNo,
969                          POSTCODE_SEVERITY_INFO);
970         return 1;
971 }
972 EXPORT_SYMBOL_GPL(uislib_client_inject_add_vhba);
973
974 int
975 uislib_client_inject_del_vhba(u32 busNo, u32 devNo)
976 {
977         return delete_device_glue(busNo, devNo);
978 }
979 EXPORT_SYMBOL_GPL(uislib_client_inject_del_vhba);
980
981 int
982 uislib_client_inject_add_vnic(u32 busNo, u32 devNo,
983                               u64 phys_chan_addr, u32 chan_bytes,
984                               int is_test_addr, uuid_le instGuid,
985                               struct InterruptInfo *intr)
986 {
987         CONTROLVM_MESSAGE msg;
988
989         LOGINF(" enter busNo=0x%x devNo=0x%x\n", busNo, devNo);
990         /* chipset init'ed with bus bus has been previously created -
991         * Verify it still exists step 2: create the VNIC device on the
992         * bus
993         */
994         POSTCODE_LINUX_4(VNIC_CREATE_ENTRY_PC, devNo, busNo,
995                          POSTCODE_SEVERITY_INFO);
996
997         init_msg_header(&msg, CONTROLVM_DEVICE_CREATE, 0, 0);
998         if (is_test_addr)
999                 /* signify that the physical channel address does NOT
1000                  * need to be ioremap()ed
1001                  */
1002                 msg.hdr.Flags.testMessage = 1;
1003         msg.cmd.createDevice.busNo = busNo;
1004         msg.cmd.createDevice.devNo = devNo;
1005         msg.cmd.createDevice.devInstGuid = instGuid;
1006         if (intr)
1007                 msg.cmd.createDevice.intr = *intr;
1008         else
1009                 memset(&msg.cmd.createDevice.intr, 0,
1010                        sizeof(struct InterruptInfo));
1011         msg.cmd.createDevice.channelAddr = phys_chan_addr;
1012         if (chan_bytes < MIN_IO_CHANNEL_SIZE) {
1013                 LOGERR("wrong channel size.chan_bytes = 0x%x IO_CHANNEL_SIZE= 0x%x\n",
1014                      chan_bytes, (unsigned int) MIN_IO_CHANNEL_SIZE);
1015                 POSTCODE_LINUX_4(VNIC_CREATE_FAILURE_PC, chan_bytes,
1016                                  MIN_IO_CHANNEL_SIZE, POSTCODE_SEVERITY_ERR);
1017                 return 0;
1018         }
1019         msg.cmd.createDevice.channelBytes = chan_bytes;
1020         msg.cmd.createDevice.dataTypeGuid = UltraVnicChannelProtocolGuid;
1021         if (create_device(&msg, NULL) != CONTROLVM_RESP_SUCCESS) {
1022                 LOGERR("VNIC create_device failed.\n");
1023                 POSTCODE_LINUX_4(VNIC_CREATE_FAILURE_PC, devNo, busNo,
1024                                  POSTCODE_SEVERITY_ERR);
1025                 return 0;
1026         }
1027
1028         POSTCODE_LINUX_4(VNIC_CREATE_SUCCESS_PC, devNo, busNo,
1029                          POSTCODE_SEVERITY_INFO);
1030         return 1;
1031 }
1032 EXPORT_SYMBOL_GPL(uislib_client_inject_add_vnic);
1033
1034 int
1035 uislib_client_inject_pause_vnic(u32 busNo, u32 devNo)
1036 {
1037         CONTROLVM_MESSAGE msg;
1038         int rc;
1039
1040         init_msg_header(&msg, CONTROLVM_DEVICE_CHANGESTATE, 0, 0);
1041         msg.cmd.deviceChangeState.busNo = busNo;
1042         msg.cmd.deviceChangeState.devNo = devNo;
1043         msg.cmd.deviceChangeState.state = SegmentStateStandby;
1044         rc = pause_device(&msg);
1045         if (rc != CONTROLVM_RESP_SUCCESS) {
1046                 LOGERR("VNIC pause_device failed. busNo=0x%x devNo=0x%x\n",
1047                        busNo, devNo);
1048                 return -1;
1049         }
1050         return 0;
1051 }
1052 EXPORT_SYMBOL_GPL(uislib_client_inject_pause_vnic);
1053
1054 int
1055 uislib_client_inject_resume_vnic(u32 busNo, u32 devNo)
1056 {
1057         CONTROLVM_MESSAGE msg;
1058         int rc;
1059
1060         init_msg_header(&msg, CONTROLVM_DEVICE_CHANGESTATE, 0, 0);
1061         msg.cmd.deviceChangeState.busNo = busNo;
1062         msg.cmd.deviceChangeState.devNo = devNo;
1063         msg.cmd.deviceChangeState.state = SegmentStateRunning;
1064         rc = resume_device(&msg);
1065         if (rc != CONTROLVM_RESP_SUCCESS) {
1066                 LOGERR("VNIC resume_device failed. busNo=0x%x devNo=0x%x\n",
1067                        busNo, devNo);
1068                 return -1;
1069         }
1070         return 0;
1071
1072 }
1073 EXPORT_SYMBOL_GPL(uislib_client_inject_resume_vnic);
1074
1075 int
1076 uislib_client_inject_del_vnic(u32 busNo, u32 devNo)
1077 {
1078         return delete_device_glue(busNo, devNo);
1079 }
1080 EXPORT_SYMBOL_GPL(uislib_client_inject_del_vnic);
1081
1082 static int
1083 uislib_client_add_vnic(u32 busNo)
1084 {
1085         BOOL busCreated = FALSE;
1086         int devNo = 0;          /* Default to 0, since only one device
1087                                  * will be created for this bus... */
1088         CONTROLVM_MESSAGE msg;
1089
1090         init_msg_header(&msg, CONTROLVM_BUS_CREATE, 0, 0);
1091         msg.hdr.Flags.testMessage = 1;
1092         msg.cmd.createBus.busNo = busNo;
1093         msg.cmd.createBus.deviceCount = 4;
1094         msg.cmd.createBus.channelAddr = 0;
1095         msg.cmd.createBus.channelBytes = 0;
1096         if (create_bus(&msg, NULL) != CONTROLVM_RESP_SUCCESS) {
1097                 LOGERR("client create_bus failed");
1098                 return 0;
1099         }
1100         busCreated = TRUE;
1101
1102         init_msg_header(&msg, CONTROLVM_DEVICE_CREATE, 0, 0);
1103         msg.hdr.Flags.testMessage = 1;
1104         msg.cmd.createDevice.busNo = busNo;
1105         msg.cmd.createDevice.devNo = devNo;
1106         msg.cmd.createDevice.devInstGuid = NULL_UUID_LE;
1107         memset(&msg.cmd.createDevice.intr, 0, sizeof(struct InterruptInfo));
1108         msg.cmd.createDevice.channelAddr = PhysicalDataChan;
1109         msg.cmd.createDevice.channelBytes = MIN_IO_CHANNEL_SIZE;
1110         msg.cmd.createDevice.dataTypeGuid = UltraVnicChannelProtocolGuid;
1111         if (create_device(&msg, NULL) != CONTROLVM_RESP_SUCCESS) {
1112                 LOGERR("client create_device failed");
1113                 goto AwayCleanup;
1114         }
1115
1116         return 1;
1117
1118 AwayCleanup:
1119         if (busCreated) {
1120                 init_msg_header(&msg, CONTROLVM_BUS_DESTROY, 0, 0);
1121                 msg.hdr.Flags.testMessage = 1;
1122                 msg.cmd.destroyBus.busNo = busNo;
1123                 if (destroy_bus(&msg, NULL) != CONTROLVM_RESP_SUCCESS)
1124                         LOGERR("client destroy_bus failed.\n");
1125         }
1126
1127         return 0;
1128 }                               /* end uislib_client_add_vnic */
1129 EXPORT_SYMBOL_GPL(uislib_client_add_vnic);
1130
1131 static int
1132 uislib_client_delete_vnic(u32 busNo)
1133 {
1134         int devNo = 0;          /* Default to 0, since only one device
1135                                  * will be created for this bus... */
1136         CONTROLVM_MESSAGE msg;
1137
1138         init_msg_header(&msg, CONTROLVM_DEVICE_DESTROY, 0, 0);
1139         msg.hdr.Flags.testMessage = 1;
1140         msg.cmd.destroyDevice.busNo = busNo;
1141         msg.cmd.destroyDevice.devNo = devNo;
1142         if (destroy_device(&msg, NULL) != CONTROLVM_RESP_SUCCESS) {
1143                 /* Don't error exit - try to see if bus can be destroyed... */
1144                 LOGERR("client destroy_device failed.\n");
1145         }
1146
1147         init_msg_header(&msg, CONTROLVM_BUS_DESTROY, 0, 0);
1148         msg.hdr.Flags.testMessage = 1;
1149         msg.cmd.destroyBus.busNo = busNo;
1150         if (destroy_bus(&msg, NULL) != CONTROLVM_RESP_SUCCESS)
1151                 LOGERR("client destroy_bus failed.\n");
1152
1153         return 1;
1154 }
1155 EXPORT_SYMBOL_GPL(uislib_client_delete_vnic);
1156 /* end client_delete_vnic */
1157
1158 void *
1159 uislib_cache_alloc(struct kmem_cache *cur_pool, char *fn, int ln)
1160 {
1161         /* __GFP_NORETRY means "ok to fail", meaning kmalloc() can
1162         * return NULL.  If you do NOT specify __GFP_NORETRY, Linux
1163         * will go to extreme measures to get memory for you (like,
1164         * invoke oom killer), which will probably cripple the system.
1165         */
1166         void *p = kmem_cache_alloc(cur_pool, GFP_ATOMIC | __GFP_NORETRY);
1167         if (p == NULL) {
1168                 LOGERR("uislib_malloc failed to alloc uiscmdrsp @%s:%d",
1169                        fn, ln);
1170                 return NULL;
1171         }
1172         return p;
1173 }
1174 EXPORT_SYMBOL_GPL(uislib_cache_alloc);
1175
1176 void
1177 uislib_cache_free(struct kmem_cache *cur_pool, void *p, char *fn, int ln)
1178 {
1179         if (p == NULL) {
1180                 LOGERR("uislib_free NULL pointer @%s:%d", fn, ln);
1181                 return;
1182         }
1183         kmem_cache_free(cur_pool, p);
1184 }
1185 EXPORT_SYMBOL_GPL(uislib_cache_free);
1186
1187 /*****************************************************/
1188 /* proc filesystem callback functions                */
1189 /*****************************************************/
1190
1191 #define PLINE(...) uisutil_add_proc_line_ex(&tot, buff, \
1192                                                buff_len, __VA_ARGS__)
1193
1194 static int
1195 info_debugfs_read_helper(char **buff, int *buff_len)
1196 {
1197         int i, tot = 0;
1198         struct bus_info *bus;
1199
1200         if (PLINE("\nBuses:\n") < 0)
1201                 goto err_done;
1202
1203         read_lock(&BusListLock);
1204         for (bus = BusListHead; bus; bus = bus->next) {
1205
1206                 if (PLINE("    bus=0x%p, busNo=%d, deviceCount=%d\n",
1207                           bus, bus->busNo, bus->deviceCount) < 0)
1208                         goto err_done_unlock;
1209
1210
1211                 if (PLINE("        Devices:\n") < 0)
1212                         goto err_done_unlock;
1213
1214                 for (i = 0; i < bus->deviceCount; i++) {
1215                         if (bus->device[i]) {
1216                                 if (PLINE("            busNo %d, device[%i]: 0x%p, chanptr=0x%p, swtch=0x%p\n",
1217                                           bus->busNo, i, bus->device[i],
1218                                           bus->device[i]->chanptr,
1219                                           bus->device[i]->swtch) < 0)
1220                                         goto err_done_unlock;
1221
1222                                 if (PLINE("            first_busy_cnt=%llu, moved_to_tail_cnt=%llu, last_on_list_cnt=%llu\n",
1223                                           bus->device[i]->first_busy_cnt,
1224                                           bus->device[i]->moved_to_tail_cnt,
1225                                           bus->device[i]->last_on_list_cnt) < 0)
1226                                         goto err_done_unlock;
1227                         }
1228                 }
1229         }
1230         read_unlock(&BusListLock);
1231
1232         if (PLINE("UisUtils_Registered_Services: %d\n",
1233                   atomic_read(&UisUtils_Registered_Services)) < 0)
1234                 goto err_done;
1235         if (PLINE("cycles_before_wait %llu wait_cycles:%llu\n",
1236                   cycles_before_wait, wait_cycles) < 0)
1237                         goto err_done;
1238         if (PLINE("tot_wakeup_cnt %llu:tot_wait_cnt %llu:tot_schedule_cnt %llu\n",
1239                   tot_wakeup_cnt, tot_wait_cnt, tot_schedule_cnt) < 0)
1240                         goto err_done;
1241         if (PLINE("en_smart_wakeup %d\n", en_smart_wakeup) < 0)
1242                         goto err_done;
1243         if (PLINE("tot_moved_to_tail_cnt %llu\n", tot_moved_to_tail_cnt) < 0)
1244                         goto err_done;
1245
1246         return tot;
1247
1248 err_done_unlock:
1249         read_unlock(&BusListLock);
1250 err_done:
1251         return -1;
1252 }
1253
1254 static ssize_t
1255 info_debugfs_read(struct file *file, char __user *buf,
1256                 size_t len, loff_t *offset)
1257 {
1258         char *temp;
1259         int totalBytes = 0;
1260         int remaining_bytes = PROC_READ_BUFFER_SIZE;
1261
1262 /* *start = buf; */
1263         if (ProcReadBuffer == NULL) {
1264                 DBGINF("ProcReadBuffer == NULL; allocating buffer.\n.");
1265                 ProcReadBuffer = vmalloc(PROC_READ_BUFFER_SIZE);
1266
1267                 if (ProcReadBuffer == NULL) {
1268                         LOGERR("failed to allocate buffer to provide proc data.\n");
1269                         return -ENOMEM;
1270                 }
1271         }
1272
1273         temp = ProcReadBuffer;
1274
1275         if ((*offset == 0) || (!ProcReadBufferValid)) {
1276                 DBGINF("calling info_debugfs_read_helper.\n");
1277                 /* if the read fails, then -1 will be returned */
1278                 totalBytes = info_debugfs_read_helper(&temp, &remaining_bytes);
1279                 ProcReadBufferValid = 1;
1280         } else
1281                 totalBytes = strlen(ProcReadBuffer);
1282
1283         return simple_read_from_buffer(buf, len, offset,
1284                                        ProcReadBuffer, totalBytes);
1285 }
1286
1287 static struct device_info *
1288 find_dev(u32 busNo, u32 devNo)
1289 {
1290         struct bus_info *bus;
1291         struct device_info *dev = NULL;
1292
1293         read_lock(&BusListLock);
1294         for (bus = BusListHead; bus; bus = bus->next) {
1295                 if (bus->busNo == busNo) {
1296                         /* make sure the device number is valid */
1297                         if (devNo >= bus->deviceCount) {
1298                                 LOGERR("%s bad busNo, devNo=%d,%d",
1299                                        __func__,
1300                                        (int) (busNo), (int) (devNo));
1301                                 goto Away;
1302                         }
1303                         dev = bus->device[devNo];
1304                         if (!dev)
1305                                 LOGERR("%s bad busNo, devNo=%d,%d",
1306                                        __func__,
1307                                        (int) (busNo), (int) (devNo));
1308                         goto Away;
1309                 }
1310         }
1311 Away:
1312         read_unlock(&BusListLock);
1313         return dev;
1314 }
1315
1316 /*  This thread calls the "interrupt" function for each device that has
1317  *  enabled such using uislib_enable_channel_interrupts().  The "interrupt"
1318  *  function typically reads and processes the devices's channel input
1319  *  queue.  This thread repeatedly does this, until the thread is told to stop
1320  *  (via uisthread_stop()).  Sleeping rules:
1321  *  - If we have called the "interrupt" function for all devices, and all of
1322  *    them have reported "nothing processed" (returned 0), then we will go to
1323  *    sleep for a maximum of POLLJIFFIES_NORMAL jiffies.
1324  *  - If anyone calls uislib_force_channel_interrupt(), the above jiffy
1325  *    sleep will be interrupted, and we will resume calling the "interrupt"
1326  *    function for all devices.
1327  *  - The list of devices is dynamically re-ordered in order to
1328  *    attempt to preserve fairness.  Whenever we spin thru the list of
1329  *    devices and call the dev->interrupt() function, if we find
1330  *    devices which report that there is still more work to do, the
1331  *    the first such device we find is moved to the end of the device
1332  *    list.  This ensures that extremely busy devices don't starve out
1333  *    less-busy ones.
1334  *
1335  */
1336 static int
1337 Process_Incoming(void *v)
1338 {
1339         unsigned long long cur_cycles, old_cycles, idle_cycles, delta_cycles;
1340         struct list_head *new_tail = NULL;
1341         int i;
1342         UIS_DAEMONIZE("dev_incoming");
1343         for (i = 0; i < 16; i++) {
1344                 old_cycles = get_cycles();
1345                 wait_event_timeout(Wakeup_Polling_Device_Channels,
1346                                    0, POLLJIFFIES_NORMAL);
1347                 cur_cycles = get_cycles();
1348                 if (wait_cycles == 0) {
1349                         wait_cycles = (cur_cycles - old_cycles);
1350                 } else {
1351                         if (wait_cycles < (cur_cycles - old_cycles))
1352                                 wait_cycles = (cur_cycles - old_cycles);
1353                 }
1354         }
1355         LOGINF("wait_cycles=%llu", wait_cycles);
1356         cycles_before_wait = wait_cycles;
1357         idle_cycles = 0;
1358         Go_Polling_Device_Channels = 0;
1359         while (1) {
1360                 struct list_head *lelt, *tmp;
1361                 struct device_info *dev = NULL;
1362
1363                 /* poll each channel for input */
1364                 LOCKSEM_UNINTERRUPTIBLE(&Lock_Polling_Device_Channels);
1365                 new_tail = NULL;
1366                 list_for_each_safe(lelt, tmp, &List_Polling_Device_Channels) {
1367                         int rc = 0;
1368                         dev = list_entry(lelt, struct device_info,
1369                                          list_polling_device_channels);
1370                         LOCKSEM_UNINTERRUPTIBLE(&dev->interrupt_callback_lock);
1371                         if (dev->interrupt)
1372                                 rc = dev->interrupt(dev->interrupt_context);
1373                         else
1374                                 continue;
1375                         UNLOCKSEM(&dev->interrupt_callback_lock);
1376                         if (rc) {
1377                                 /* dev->interrupt returned, but there
1378                                 * is still more work to do.
1379                                 * Reschedule work to occur as soon as
1380                                 * possible. */
1381                                 idle_cycles = 0;
1382                                 if (new_tail == NULL) {
1383                                         dev->first_busy_cnt++;
1384                                         if (!
1385                                             (list_is_last
1386                                              (lelt,
1387                                               &List_Polling_Device_Channels))) {
1388                                                 new_tail = lelt;
1389                                                 dev->moved_to_tail_cnt++;
1390                                         } else
1391                                                 dev->last_on_list_cnt++;
1392                                 }
1393
1394                         }
1395                         if (Incoming_ThreadInfo.should_stop)
1396                                 break;
1397                 }
1398                 if (new_tail != NULL) {
1399                         tot_moved_to_tail_cnt++;
1400                         list_move_tail(new_tail, &List_Polling_Device_Channels);
1401                 }
1402                 UNLOCKSEM(&Lock_Polling_Device_Channels);
1403                 cur_cycles = get_cycles();
1404                 delta_cycles = cur_cycles - old_cycles;
1405                 old_cycles = cur_cycles;
1406
1407                 /* At this point, we have scanned thru all of the
1408                 * channels, and at least one of the following is true:
1409                 * - there is no input waiting on any of the channels
1410                 * - we have received a signal to stop this thread
1411                 */
1412                 if (Incoming_ThreadInfo.should_stop)
1413                         break;
1414                 if (en_smart_wakeup == 0xFF) {
1415                         LOGINF("en_smart_wakeup set to 0xff, to force exiting process_incoming");
1416                         break;
1417                 }
1418                 /* wait for POLLJIFFIES_NORMAL jiffies, or until
1419                 * someone wakes up Wakeup_Polling_Device_Channels,
1420                 * whichever comes first only do a wait when we have
1421                 * been idle for cycles_before_wait cycles.
1422                 */
1423                 if (idle_cycles > cycles_before_wait) {
1424                         Go_Polling_Device_Channels = 0;
1425                         tot_wait_cnt++;
1426                         wait_event_timeout(Wakeup_Polling_Device_Channels,
1427                                            Go_Polling_Device_Channels,
1428                                            POLLJIFFIES_NORMAL);
1429                         Go_Polling_Device_Channels = 1;
1430                 } else {
1431                         tot_schedule_cnt++;
1432                         schedule();
1433                         idle_cycles = idle_cycles + delta_cycles;
1434                 }
1435         }
1436         DBGINF("exiting.\n");
1437         complete_and_exit(&Incoming_ThreadInfo.has_stopped, 0);
1438 }
1439
1440 static BOOL
1441 Initialize_incoming_thread(void)
1442 {
1443         if (Incoming_Thread_Started)
1444                 return TRUE;
1445         if (!uisthread_start(&Incoming_ThreadInfo,
1446                              &Process_Incoming, NULL, "dev_incoming")) {
1447                 LOGERR("uisthread_start Initialize_incoming_thread ****FAILED");
1448                 return FALSE;
1449         }
1450         Incoming_Thread_Started = TRUE;
1451         return TRUE;
1452 }
1453
1454 /*  Add a new device/channel to the list being processed by
1455  *  Process_Incoming().
1456  *  <interrupt> - indicates the function to call periodically.
1457  *  <interrupt_context> - indicates the data to pass to the <interrupt>
1458  *                        function.
1459  */
1460 void
1461 uislib_enable_channel_interrupts(u32 busNo, u32 devNo,
1462                                  int (*interrupt)(void *),
1463                                  void *interrupt_context)
1464 {
1465         struct device_info *dev;
1466         dev = find_dev(busNo, devNo);
1467         if (!dev) {
1468                 LOGERR("%s busNo=%d, devNo=%d", __func__, (int) (busNo),
1469                        (int) (devNo));
1470                 return;
1471         }
1472         LOCKSEM_UNINTERRUPTIBLE(&Lock_Polling_Device_Channels);
1473         Initialize_incoming_thread();
1474         dev->interrupt = interrupt;
1475         dev->interrupt_context = interrupt_context;
1476         dev->polling = TRUE;
1477         list_add_tail(&(dev->list_polling_device_channels),
1478                       &List_Polling_Device_Channels);
1479         UNLOCKSEM(&Lock_Polling_Device_Channels);
1480 }
1481 EXPORT_SYMBOL_GPL(uislib_enable_channel_interrupts);
1482
1483 /*  Remove a device/channel from the list being processed by
1484  *  Process_Incoming().
1485  */
1486 void
1487 uislib_disable_channel_interrupts(u32 busNo, u32 devNo)
1488 {
1489         struct device_info *dev;
1490         dev = find_dev(busNo, devNo);
1491         if (!dev) {
1492                 LOGERR("%s busNo=%d, devNo=%d", __func__, (int) (busNo),
1493                        (int) (devNo));
1494                 return;
1495         }
1496         LOCKSEM_UNINTERRUPTIBLE(&Lock_Polling_Device_Channels);
1497         list_del(&dev->list_polling_device_channels);
1498         dev->polling = FALSE;
1499         dev->interrupt = NULL;
1500         UNLOCKSEM(&Lock_Polling_Device_Channels);
1501 }
1502 EXPORT_SYMBOL_GPL(uislib_disable_channel_interrupts);
1503
1504 static void
1505 do_wakeup_polling_device_channels(struct work_struct *dummy)
1506 {
1507         if (!Go_Polling_Device_Channels) {
1508                 Go_Polling_Device_Channels = 1;
1509                 wake_up(&Wakeup_Polling_Device_Channels);
1510         }
1511 }
1512
1513 static DECLARE_WORK(Work_wakeup_polling_device_channels,
1514                     do_wakeup_polling_device_channels);
1515
1516 /*  Call this function when you want to send a hint to Process_Incoming() that
1517  *  your device might have more requests.
1518  */
1519 void
1520 uislib_force_channel_interrupt(u32 busNo, u32 devNo)
1521 {
1522         if (en_smart_wakeup == 0)
1523                 return;
1524         if (Go_Polling_Device_Channels)
1525                 return;
1526         /* The point of using schedule_work() instead of just doing
1527          * the work inline is to force a slight delay before waking up
1528          * the Process_Incoming() thread.
1529          */
1530         tot_wakeup_cnt++;
1531         schedule_work(&Work_wakeup_polling_device_channels);
1532 }
1533 EXPORT_SYMBOL_GPL(uislib_force_channel_interrupt);
1534
1535 /*****************************************************/
1536 /* Module Init & Exit functions                      */
1537 /*****************************************************/
1538
1539 static int __init
1540 uislib_mod_init(void)
1541 {
1542
1543         if (!unisys_spar_platform)
1544                 return -ENODEV;
1545
1546         LOGINF("MONITORAPIS");
1547
1548         LOGINF("sizeof(struct uiscmdrsp):%lu bytes\n",
1549                (ulong) sizeof(struct uiscmdrsp));
1550         LOGINF("sizeof(struct phys_info):%lu\n",
1551                (ulong) sizeof(struct phys_info));
1552         LOGINF("sizeof(uiscmdrsp_scsi):%lu\n",
1553                (ulong) sizeof(struct uiscmdrsp_scsi));
1554         LOGINF("sizeof(uiscmdrsp_net):%lu\n",
1555                (ulong) sizeof(struct uiscmdrsp_net));
1556         LOGINF("sizeof(CONTROLVM_MESSAGE):%lu bytes\n",
1557                (ulong) sizeof(CONTROLVM_MESSAGE));
1558         LOGINF("sizeof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL):%lu bytes\n",
1559                (ulong) sizeof(ULTRA_CONTROLVM_CHANNEL_PROTOCOL));
1560         LOGINF("sizeof(CHANNEL_HEADER):%lu bytes\n",
1561                (ulong) sizeof(CHANNEL_HEADER));
1562         LOGINF("sizeof(ULTRA_IO_CHANNEL_PROTOCOL):%lu bytes\n",
1563                (ulong) sizeof(ULTRA_IO_CHANNEL_PROTOCOL));
1564         LOGINF("SIZEOF_CMDRSP:%lu bytes\n", SIZEOF_CMDRSP);
1565         LOGINF("SIZEOF_PROTOCOL:%lu bytes\n", SIZEOF_PROTOCOL);
1566
1567         /* initialize global pointers to NULL */
1568         BusListHead = NULL;
1569         BusListCount = MaxBusCount = 0;
1570         rwlock_init(&BusListLock);
1571         VirtControlChanFunc = NULL;
1572
1573         /* Issue VMCALL_GET_CONTROLVM_ADDR to get CtrlChanPhysAddr and
1574          * then map this physical address to a virtual address. */
1575         POSTCODE_LINUX_2(DRIVER_ENTRY_PC, POSTCODE_SEVERITY_INFO);
1576
1577         dir_debugfs = debugfs_create_dir(DIR_DEBUGFS_ENTRY, NULL);
1578         if (dir_debugfs) {
1579                 info_debugfs_entry = debugfs_create_file(
1580                         INFO_DEBUGFS_ENTRY_FN, 0444, dir_debugfs, NULL,
1581                         &debugfs_info_fops);
1582
1583                 platformnumber_debugfs_read = debugfs_create_u32(
1584                         PLATFORMNUMBER_DEBUGFS_ENTRY_FN, 0444, dir_debugfs,
1585                         &PlatformNumber);
1586
1587                 cycles_before_wait_debugfs_read = debugfs_create_u64(
1588                         CYCLES_BEFORE_WAIT_DEBUGFS_ENTRY_FN, 0666, dir_debugfs,
1589                         &cycles_before_wait);
1590
1591                 smart_wakeup_debugfs_entry = debugfs_create_bool(
1592                         SMART_WAKEUP_DEBUGFS_ENTRY_FN, 0666, dir_debugfs,
1593                         &en_smart_wakeup);
1594         }
1595
1596         POSTCODE_LINUX_3(DRIVER_EXIT_PC, 0, POSTCODE_SEVERITY_INFO);
1597         return 0;
1598 }
1599
1600 static void __exit
1601 uislib_mod_exit(void)
1602 {
1603         if (ProcReadBuffer) {
1604                 vfree(ProcReadBuffer);
1605                 ProcReadBuffer = NULL;
1606         }
1607
1608         debugfs_remove(info_debugfs_entry);
1609         debugfs_remove(smart_wakeup_debugfs_entry);
1610         debugfs_remove(cycles_before_wait_debugfs_read);
1611         debugfs_remove(platformnumber_debugfs_read);
1612         debugfs_remove(dir_debugfs);
1613
1614         DBGINF("goodbye.\n");
1615         return;
1616 }
1617
1618 module_init(uislib_mod_init);
1619 module_exit(uislib_mod_exit);
1620
1621 MODULE_LICENSE("GPL");
1622 MODULE_AUTHOR("Usha Srinivasan");
1623 MODULE_ALIAS("uislib");
1624   /* this is extracted during depmod and kept in modules.dep */