blob: 152fd29f04f295509b3317f899e0fc7675e4e527 [file] [log] [blame]
Greg Kroah-Hartmanb79c0f42017-11-07 14:58:47 +01001// SPDX-License-Identifier: GPL-2.0
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -04002/*
Benjamin Romer6f14cc12015-07-16 12:40:48 -04003 * Copyright � 2010 - 2015 UNISYS CORPORATION
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04004 * All rights reserved.
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04005 */
6
David Kershnerb71d87b2017-09-27 13:14:31 -04007#include <linux/ctype.h>
Tim Sell8217bec2016-11-03 11:44:16 -04008#include <linux/debugfs.h>
David Kershnereb6eb1e2017-09-27 13:14:29 -04009#include <linux/module.h>
10#include <linux/slab.h>
David Kershner93d3ad92017-12-07 12:11:07 -050011#include <linux/visorbus.h>
Erik Arfvidson3703987cd2015-05-05 18:36:00 -040012#include <linux/uuid.h>
13
Prarit Bhargavac79b28f2015-05-05 18:36:15 -040014#include "visorbus_private.h"
Prarit Bhargava4b780002015-05-05 18:36:10 -040015
Andy Shevchenkob32c5cb2017-08-22 13:26:54 -040016static const guid_t visor_vbus_channel_guid = VISOR_VBUS_CHANNEL_GUID;
17
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -040018/* Display string that is guaranteed to be no longer the 99 characters */
Erik Arfvidson38d56c22016-04-13 12:07:07 -040019#define LINESIZE 99
David Binderffcdb102017-03-17 11:27:18 -040020#define POLLJIFFIES_NORMALCHANNEL 10
Erik Arfvidson3703987cd2015-05-05 18:36:00 -040021
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -040022/* stores whether bus_registration was successful */
23static bool initialized;
Tim Sell8217bec2016-11-03 11:44:16 -040024static struct dentry *visorbus_debugfs_dir;
Benjamin Romer6155a3c2015-09-04 12:01:32 -040025
David Binder3fd1b3b2016-06-10 21:48:16 -040026/*
Prarit Bhargava59fd2c82015-07-24 12:06:53 -040027 * DEVICE type attributes
28 *
29 * The modalias file will contain the guid of the device.
30 */
31static ssize_t modalias_show(struct device *dev, struct device_attribute *attr,
32 char *buf)
33{
34 struct visor_device *vdev;
Andy Shevchenkob32c5cb2017-08-22 13:26:54 -040035 const guid_t *guid;
Prarit Bhargava59fd2c82015-07-24 12:06:53 -040036
37 vdev = to_visor_device(dev);
Andy Shevchenkob32c5cb2017-08-22 13:26:54 -040038 guid = visorchannel_get_guid(vdev->visorchannel);
39 return sprintf(buf, "visorbus:%pUl\n", guid);
Prarit Bhargava59fd2c82015-07-24 12:06:53 -040040}
41static DEVICE_ATTR_RO(modalias);
42
43static struct attribute *visorbus_dev_attrs[] = {
44 &dev_attr_modalias.attr,
45 NULL,
46};
47
David Kershneraa5ebde2017-08-22 13:27:36 -040048ATTRIBUTE_GROUPS(visorbus_dev);
Prarit Bhargava59fd2c82015-07-24 12:06:53 -040049
Erik Arfvidson3703987cd2015-05-05 18:36:00 -040050/* filled in with info about parent chipset driver when we register with it */
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -040051static struct visor_vbus_deviceinfo chipset_driverinfo;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -040052/* filled in with info about this driver, wrt it servicing client busses */
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -040053static struct visor_vbus_deviceinfo clientbus_driverinfo;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -040054
David Binder3fd1b3b2016-06-10 21:48:16 -040055/* list of visor_device structs, linked via .list_all */
Erik Arfvidson3703987cd2015-05-05 18:36:00 -040056static LIST_HEAD(list_all_bus_instances);
David Binder3fd1b3b2016-06-10 21:48:16 -040057/* list of visor_device structs, linked via .list_all */
Erik Arfvidson3703987cd2015-05-05 18:36:00 -040058static LIST_HEAD(list_all_device_instances);
59
Sameer Wadgaonkar403043c2017-07-17 16:17:02 -040060/*
61 * Generic function useful for validating any type of channel when it is
62 * received by the client that will be accessing the channel.
63 * Note that <logCtx> is only needed for callers in the EFI environment, and
64 * is used to pass the EFI_DIAG_CAPTURE_PROTOCOL needed to log messages.
65 */
David Kershner5f50a342017-09-27 13:14:22 -040066int visor_check_channel(struct channel_header *ch, struct device *dev,
67 const guid_t *expected_guid, char *chname,
68 u64 expected_min_bytes, u32 expected_version,
Sameer Wadgaonkar403043c2017-07-17 16:17:02 -040069 u64 expected_signature)
70{
Andy Shevchenkob32c5cb2017-08-22 13:26:54 -040071 if (!guid_is_null(expected_guid)) {
Sameer Wadgaonkar403043c2017-07-17 16:17:02 -040072 /* caller wants us to verify type GUID */
Andy Shevchenkob32c5cb2017-08-22 13:26:54 -040073 if (!guid_equal(&ch->chtype, expected_guid)) {
Sameer Wadgaonkare25201d2017-08-30 13:36:35 -040074 dev_err(dev, "Channel mismatch on channel=%s(%pUL) field=type expected=%pUL actual=%pUL\n",
75 chname, expected_guid, expected_guid,
76 &ch->chtype);
Sameer Wadgaonkar403043c2017-07-17 16:17:02 -040077 return 0;
78 }
79 }
80 /* verify channel size */
81 if (expected_min_bytes > 0) {
82 if (ch->size < expected_min_bytes) {
Sameer Wadgaonkare25201d2017-08-30 13:36:35 -040083 dev_err(dev, "Channel mismatch on channel=%s(%pUL) field=size expected=0x%-8.8Lx actual=0x%-8.8Lx\n",
84 chname, expected_guid,
85 (unsigned long long)expected_min_bytes,
86 ch->size);
Sameer Wadgaonkar403043c2017-07-17 16:17:02 -040087 return 0;
88 }
89 }
90 /* verify channel version */
91 if (expected_version > 0) {
92 if (ch->version_id != expected_version) {
Sameer Wadgaonkare25201d2017-08-30 13:36:35 -040093 dev_err(dev, "Channel mismatch on channel=%s(%pUL) field=version expected=0x%-8.8lx actual=0x%-8.8x\n",
94 chname, expected_guid,
95 (unsigned long)expected_version,
96 ch->version_id);
Sameer Wadgaonkar403043c2017-07-17 16:17:02 -040097 return 0;
98 }
99 }
100 /* verify channel signature */
101 if (expected_signature > 0) {
102 if (ch->signature != expected_signature) {
Sameer Wadgaonkare25201d2017-08-30 13:36:35 -0400103 dev_err(dev, "Channel mismatch on channel=%s(%pUL) field=signature expected=0x%-8.8Lx actual=0x%-8.8Lx\n",
104 chname, expected_guid, expected_signature,
105 ch->signature);
Sameer Wadgaonkar403043c2017-07-17 16:17:02 -0400106 return 0;
107 }
108 }
109 return 1;
110}
Sameer Wadgaonkar403043c2017-07-17 16:17:02 -0400111
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400112static int visorbus_uevent(struct device *xdev, struct kobj_uevent_env *env)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400113{
Prarit Bhargava59fd2c82015-07-24 12:06:53 -0400114 struct visor_device *dev;
Andy Shevchenkob32c5cb2017-08-22 13:26:54 -0400115 const guid_t *guid;
Prarit Bhargava59fd2c82015-07-24 12:06:53 -0400116
117 dev = to_visor_device(xdev);
Andy Shevchenkob32c5cb2017-08-22 13:26:54 -0400118 guid = visorchannel_get_guid(dev->visorchannel);
Andy Shevchenkob32c5cb2017-08-22 13:26:54 -0400119 return add_uevent_var(env, "MODALIAS=visorbus:%pUl", guid);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400120}
121
David Binderb84be592017-02-21 12:53:24 -0500122/*
David Binder3fd1b3b2016-06-10 21:48:16 -0400123 * visorbus_match() - called automatically upon adding a visor_device
124 * (device_add), or adding a visor_driver
125 * (visorbus_register_visor_driver)
126 * @xdev: struct device for the device being matched
127 * @xdrv: struct device_driver for driver to match device against
128 *
129 * Return: 1 iff the provided driver can control the specified device
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400130 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400131static int visorbus_match(struct device *xdev, struct device_driver *xdrv)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400132{
Andy Shevchenkob32c5cb2017-08-22 13:26:54 -0400133 const guid_t *channel_type;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400134 int i;
135 struct visor_device *dev;
136 struct visor_driver *drv;
Sameer Wadgaonkarcb3b5dc2017-09-27 13:14:43 -0400137 struct visorchannel *chan;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400138
139 dev = to_visor_device(xdev);
Andy Shevchenkob32c5cb2017-08-22 13:26:54 -0400140 channel_type = visorchannel_get_guid(dev->visorchannel);
David Binderd4e8a222017-07-17 16:16:43 -0400141 drv = to_visor_driver(xdrv);
Sameer Wadgaonkarcb3b5dc2017-09-27 13:14:43 -0400142 chan = dev->visorchannel;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400143 if (!drv->channel_types)
David Kershner8e33f482016-03-12 21:27:11 -0500144 return 0;
David Kershner425eaf42017-08-30 13:36:32 -0400145 for (i = 0; !guid_is_null(&drv->channel_types[i].guid); i++)
Sameer Wadgaonkarcb3b5dc2017-09-27 13:14:43 -0400146 if (guid_equal(&drv->channel_types[i].guid, channel_type) &&
147 visor_check_channel(visorchannel_get_header(chan),
148 xdev,
149 &drv->channel_types[i].guid,
150 (char *)drv->channel_types[i].name,
151 drv->channel_types[i].min_bytes,
152 drv->channel_types[i].version,
153 VISOR_CHANNEL_SIGNATURE))
David Kershner8e33f482016-03-12 21:27:11 -0500154 return i + 1;
David Kershner8e33f482016-03-12 21:27:11 -0500155 return 0;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400156}
157
David Kershner7993b402016-09-19 17:09:35 -0400158/*
159 * This describes the TYPE of bus.
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -0400160 * (Don't confuse this with an INSTANCE of the bus.)
David Kershner7993b402016-09-19 17:09:35 -0400161 */
David Kershner69a4d1e2017-09-27 13:14:36 -0400162static struct bus_type visorbus_type = {
David Kershner7993b402016-09-19 17:09:35 -0400163 .name = "visorbus",
164 .match = visorbus_match,
165 .uevent = visorbus_uevent,
166 .dev_groups = visorbus_dev_groups,
David Kershner7993b402016-09-19 17:09:35 -0400167};
168
David Kershner69a4d1e2017-09-27 13:14:36 -0400169struct visor_busdev {
170 u32 bus_no;
171 u32 dev_no;
172};
173
Suzuki K Poulose418e3ea2019-06-14 18:53:59 +0100174static int match_visorbus_dev_by_id(struct device *dev, const void *data)
David Kershner69a4d1e2017-09-27 13:14:36 -0400175{
176 struct visor_device *vdev = to_visor_device(dev);
Suzuki K Poulose418e3ea2019-06-14 18:53:59 +0100177 const struct visor_busdev *id = data;
David Kershner69a4d1e2017-09-27 13:14:36 -0400178
David Kershner614b0832017-09-27 13:14:48 -0400179 if (vdev->chipset_bus_no == id->bus_no &&
180 vdev->chipset_dev_no == id->dev_no)
David Kershner69a4d1e2017-09-27 13:14:36 -0400181 return 1;
182 return 0;
183}
184
185struct visor_device *visorbus_get_device_by_id(u32 bus_no, u32 dev_no,
186 struct visor_device *from)
187{
188 struct device *dev;
189 struct device *dev_start = NULL;
190 struct visor_busdev id = {
191 .bus_no = bus_no,
192 .dev_no = dev_no
193 };
194
195 if (from)
196 dev_start = &from->device;
197 dev = bus_find_device(&visorbus_type, dev_start, (void *)&id,
198 match_visorbus_dev_by_id);
199 if (!dev)
200 return NULL;
201 return to_visor_device(dev);
202}
203
David Binderb84be592017-02-21 12:53:24 -0500204/*
David Binderce4617e2017-02-21 12:53:21 -0500205 * visorbus_release_busdevice() - called when device_unregister() is called for
206 * the bus device instance, after all other tasks
207 * involved with destroying the dev are complete
David Binder3fd1b3b2016-06-10 21:48:16 -0400208 * @xdev: struct device for the bus being released
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400209 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400210static void visorbus_release_busdevice(struct device *xdev)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400211{
Don Zickus343506b2015-06-04 09:22:37 -0400212 struct visor_device *dev = dev_get_drvdata(xdev);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400213
David Kershner1c218002017-09-27 13:14:21 -0400214 debugfs_remove(dev->debugfs_bus_info);
Tim Sell8217bec2016-11-03 11:44:16 -0400215 debugfs_remove_recursive(dev->debugfs_dir);
David Kershnerae54a282017-09-27 13:14:17 -0400216 visorchannel_destroy(dev->visorchannel);
Don Zickus343506b2015-06-04 09:22:37 -0400217 kfree(dev);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400218}
219
David Binderb84be592017-02-21 12:53:24 -0500220/*
David Binder3fd1b3b2016-06-10 21:48:16 -0400221 * visorbus_release_device() - called when device_unregister() is called for
222 * each child device instance
223 * @xdev: struct device for the visor device being released
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400224 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400225static void visorbus_release_device(struct device *xdev)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400226{
227 struct visor_device *dev = to_visor_device(xdev);
228
Sameer Wadgaonkard72e1a12017-07-17 16:16:56 -0400229 visorchannel_destroy(dev->visorchannel);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400230 kfree(dev);
231}
232
David Binder3fd1b3b2016-06-10 21:48:16 -0400233/*
David Kershner7915a3c2017-09-27 13:14:13 -0400234 * BUS specific channel attributes to appear under
David Binder3fd1b3b2016-06-10 21:48:16 -0400235 * /sys/bus/visorbus<x>/dev<y>/channel
236 */
237
Don Zickus79573162015-05-13 13:22:17 -0400238static ssize_t physaddr_show(struct device *dev, struct device_attribute *attr,
239 char *buf)
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400240{
Don Zickus79573162015-05-13 13:22:17 -0400241 struct visor_device *vdev = to_visor_device(dev);
242
David Binder7a413852017-01-03 16:01:16 -0500243 return sprintf(buf, "0x%llx\n",
244 visorchannel_get_physaddr(vdev->visorchannel));
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400245}
Tim Sella25280b2016-11-03 11:44:15 -0400246static DEVICE_ATTR_RO(physaddr);
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400247
Don Zickus79573162015-05-13 13:22:17 -0400248static ssize_t nbytes_show(struct device *dev, struct device_attribute *attr,
249 char *buf)
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400250{
Don Zickus79573162015-05-13 13:22:17 -0400251 struct visor_device *vdev = to_visor_device(dev);
252
David Binder7a413852017-01-03 16:01:16 -0500253 return sprintf(buf, "0x%lx\n",
David Kershnerda56cb02017-09-27 13:14:39 -0400254 visorchannel_get_nbytes(vdev->visorchannel));
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400255}
Tim Sella25280b2016-11-03 11:44:15 -0400256static DEVICE_ATTR_RO(nbytes);
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400257
Don Zickus79573162015-05-13 13:22:17 -0400258static ssize_t clientpartition_show(struct device *dev,
259 struct device_attribute *attr, char *buf)
260{
261 struct visor_device *vdev = to_visor_device(dev);
262
David Binder7a413852017-01-03 16:01:16 -0500263 return sprintf(buf, "0x%llx\n",
264 visorchannel_get_clientpartition(vdev->visorchannel));
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400265}
Tim Sella25280b2016-11-03 11:44:15 -0400266static DEVICE_ATTR_RO(clientpartition);
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400267
Don Zickus79573162015-05-13 13:22:17 -0400268static ssize_t typeguid_show(struct device *dev, struct device_attribute *attr,
269 char *buf)
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400270{
Don Zickus79573162015-05-13 13:22:17 -0400271 struct visor_device *vdev = to_visor_device(dev);
Erik Arfvidson38d56c22016-04-13 12:07:07 -0400272 char typeid[LINESIZE];
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400273
David Binder7a413852017-01-03 16:01:16 -0500274 return sprintf(buf, "%s\n",
275 visorchannel_id(vdev->visorchannel, typeid));
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400276}
Tim Sella25280b2016-11-03 11:44:15 -0400277static DEVICE_ATTR_RO(typeguid);
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400278
Don Zickus79573162015-05-13 13:22:17 -0400279static ssize_t zoneguid_show(struct device *dev, struct device_attribute *attr,
280 char *buf)
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400281{
Don Zickus79573162015-05-13 13:22:17 -0400282 struct visor_device *vdev = to_visor_device(dev);
Erik Arfvidson38d56c22016-04-13 12:07:07 -0400283 char zoneid[LINESIZE];
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400284
David Binder7a413852017-01-03 16:01:16 -0500285 return sprintf(buf, "%s\n",
286 visorchannel_zoneid(vdev->visorchannel, zoneid));
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400287}
Tim Sella25280b2016-11-03 11:44:15 -0400288static DEVICE_ATTR_RO(zoneguid);
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400289
Don Zickus79573162015-05-13 13:22:17 -0400290static ssize_t typename_show(struct device *dev, struct device_attribute *attr,
291 char *buf)
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400292{
293 int i = 0;
Don Zickus79573162015-05-13 13:22:17 -0400294 struct bus_type *xbus = dev->bus;
295 struct device_driver *xdrv = dev->driver;
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400296 struct visor_driver *drv = NULL;
297
Sameer Wadgaonkara3276bf2017-07-17 16:16:58 -0400298 if (!xdrv)
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400299 return 0;
Don Zickus79573162015-05-13 13:22:17 -0400300 i = xbus->match(dev, xdrv);
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400301 if (!i)
302 return 0;
303 drv = to_visor_driver(xdrv);
David Binder7a413852017-01-03 16:01:16 -0500304 return sprintf(buf, "%s\n", drv->channel_types[i - 1].name);
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400305}
Don Zickus79573162015-05-13 13:22:17 -0400306static DEVICE_ATTR_RO(typename);
Don Zickus79573162015-05-13 13:22:17 -0400307
308static struct attribute *channel_attrs[] = {
Zachary Dremannb372fee2017-06-30 15:43:24 -0400309 &dev_attr_physaddr.attr,
310 &dev_attr_nbytes.attr,
311 &dev_attr_clientpartition.attr,
312 &dev_attr_typeguid.attr,
313 &dev_attr_zoneguid.attr,
314 &dev_attr_typename.attr,
315 NULL
Don Zickus79573162015-05-13 13:22:17 -0400316};
317
David Kershneraa5ebde2017-08-22 13:27:36 -0400318ATTRIBUTE_GROUPS(channel);
Prarit Bhargava826b6a02015-05-05 18:36:06 -0400319
David Binder3fd1b3b2016-06-10 21:48:16 -0400320/*
321 * BUS instance attributes
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400322 *
323 * define & implement display of bus attributes under
David Binder3fd1b3b2016-06-10 21:48:16 -0400324 * /sys/bus/visorbus/devices/visorbus<n>.
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400325 */
Don Zickusd181dd02015-05-13 13:22:13 -0400326static ssize_t partition_handle_show(struct device *dev,
David Kershner5f50a342017-09-27 13:14:22 -0400327 struct device_attribute *attr, char *buf)
Erik Arfvidson7b9de712017-06-30 15:43:26 -0400328{
Don Zickus5ecbd5d2015-05-13 13:22:23 -0400329 struct visor_device *vdev = to_visor_device(dev);
330 u64 handle = visorchannel_get_clientpartition(vdev->visorchannel);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400331
David Binder7a413852017-01-03 16:01:16 -0500332 return sprintf(buf, "0x%llx\n", handle);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400333}
Tim Sella25280b2016-11-03 11:44:15 -0400334static DEVICE_ATTR_RO(partition_handle);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400335
Don Zickusd181dd02015-05-13 13:22:13 -0400336static ssize_t partition_guid_show(struct device *dev,
David Kershner5f50a342017-09-27 13:14:22 -0400337 struct device_attribute *attr, char *buf)
Erik Arfvidson7b9de712017-06-30 15:43:26 -0400338{
Don Zickus5ecbd5d2015-05-13 13:22:23 -0400339 struct visor_device *vdev = to_visor_device(dev);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400340
Andy Shevchenkob32c5cb2017-08-22 13:26:54 -0400341 return sprintf(buf, "{%pUb}\n", &vdev->partition_guid);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400342}
Tim Sella25280b2016-11-03 11:44:15 -0400343static DEVICE_ATTR_RO(partition_guid);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400344
Don Zickusd181dd02015-05-13 13:22:13 -0400345static ssize_t partition_name_show(struct device *dev,
David Kershner5f50a342017-09-27 13:14:22 -0400346 struct device_attribute *attr, char *buf)
Erik Arfvidson7b9de712017-06-30 15:43:26 -0400347{
Don Zickus5ecbd5d2015-05-13 13:22:23 -0400348 struct visor_device *vdev = to_visor_device(dev);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400349
David Binder7a413852017-01-03 16:01:16 -0500350 return sprintf(buf, "%s\n", vdev->name);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400351}
Tim Sella25280b2016-11-03 11:44:15 -0400352static DEVICE_ATTR_RO(partition_name);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400353
Don Zickusd181dd02015-05-13 13:22:13 -0400354static ssize_t channel_addr_show(struct device *dev,
David Kershner5f50a342017-09-27 13:14:22 -0400355 struct device_attribute *attr, char *buf)
Erik Arfvidson7b9de712017-06-30 15:43:26 -0400356{
Don Zickus5ecbd5d2015-05-13 13:22:23 -0400357 struct visor_device *vdev = to_visor_device(dev);
358 u64 addr = visorchannel_get_physaddr(vdev->visorchannel);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400359
David Binder7a413852017-01-03 16:01:16 -0500360 return sprintf(buf, "0x%llx\n", addr);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400361}
Tim Sella25280b2016-11-03 11:44:15 -0400362static DEVICE_ATTR_RO(channel_addr);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400363
Don Zickusd181dd02015-05-13 13:22:13 -0400364static ssize_t channel_bytes_show(struct device *dev,
David Kershner5f50a342017-09-27 13:14:22 -0400365 struct device_attribute *attr, char *buf)
Erik Arfvidson7b9de712017-06-30 15:43:26 -0400366{
Don Zickus5ecbd5d2015-05-13 13:22:23 -0400367 struct visor_device *vdev = to_visor_device(dev);
368 u64 nbytes = visorchannel_get_nbytes(vdev->visorchannel);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400369
David Binder7a413852017-01-03 16:01:16 -0500370 return sprintf(buf, "0x%llx\n", nbytes);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400371}
Tim Sella25280b2016-11-03 11:44:15 -0400372static DEVICE_ATTR_RO(channel_bytes);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400373
Don Zickusd181dd02015-05-13 13:22:13 -0400374static ssize_t channel_id_show(struct device *dev,
David Kershner5f50a342017-09-27 13:14:22 -0400375 struct device_attribute *attr, char *buf)
Erik Arfvidson7b9de712017-06-30 15:43:26 -0400376{
Don Zickus5ecbd5d2015-05-13 13:22:23 -0400377 struct visor_device *vdev = to_visor_device(dev);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400378 int len = 0;
379
David Binderbf8d0e92017-03-17 11:27:03 -0400380 visorchannel_id(vdev->visorchannel, buf);
381 len = strlen(buf);
382 buf[len++] = '\n';
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400383 return len;
384}
Tim Sella25280b2016-11-03 11:44:15 -0400385static DEVICE_ATTR_RO(channel_id);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400386
David Kershneraa5ebde2017-08-22 13:27:36 -0400387static struct attribute *visorbus_attrs[] = {
Zachary Dremannb372fee2017-06-30 15:43:24 -0400388 &dev_attr_partition_handle.attr,
389 &dev_attr_partition_guid.attr,
390 &dev_attr_partition_name.attr,
391 &dev_attr_channel_addr.attr,
392 &dev_attr_channel_bytes.attr,
393 &dev_attr_channel_id.attr,
394 NULL
Don Zickusd181dd02015-05-13 13:22:13 -0400395};
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400396
David Kershneraa5ebde2017-08-22 13:27:36 -0400397ATTRIBUTE_GROUPS(visorbus);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400398
Tim Sell8217bec2016-11-03 11:44:16 -0400399/*
400 * BUS debugfs entries
401 *
402 * define & implement display of debugfs attributes under
403 * /sys/kernel/debug/visorbus/visorbus<n>.
404 */
David Binderd4e8a222017-07-17 16:16:43 -0400405
David Kershner738561a2017-03-28 09:34:40 -0400406/*
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400407 * vbuschannel_print_devinfo() - format a struct visor_vbus_deviceinfo
David Kershner738561a2017-03-28 09:34:40 -0400408 * and write it to a seq_file
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400409 * @devinfo: the struct visor_vbus_deviceinfo to format
David Kershner738561a2017-03-28 09:34:40 -0400410 * @seq: seq_file to write to
411 * @devix: the device index to be included in the output data, or -1 if no
412 * device index is to be included
413 *
414 * Reads @devInfo, and writes it in human-readable notation to @seq.
415 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400416static void vbuschannel_print_devinfo(struct visor_vbus_deviceinfo *devinfo,
417 struct seq_file *seq, int devix)
David Kershner738561a2017-03-28 09:34:40 -0400418{
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -0400419 /* uninitialized vbus device entry */
David Kershner738561a2017-03-28 09:34:40 -0400420 if (!isprint(devinfo->devtype[0]))
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -0400421 return;
David Kershner738561a2017-03-28 09:34:40 -0400422 if (devix >= 0)
423 seq_printf(seq, "[%d]", devix);
424 else
425 /* vbus device entry is for bus or chipset */
426 seq_puts(seq, " ");
David Kershner738561a2017-03-28 09:34:40 -0400427 /*
428 * Note: because the s-Par back-end is free to scribble in this area,
429 * we never assume '\0'-termination.
430 */
431 seq_printf(seq, "%-*.*s ", (int)sizeof(devinfo->devtype),
432 (int)sizeof(devinfo->devtype), devinfo->devtype);
433 seq_printf(seq, "%-*.*s ", (int)sizeof(devinfo->drvname),
434 (int)sizeof(devinfo->drvname), devinfo->drvname);
435 seq_printf(seq, "%.*s\n", (int)sizeof(devinfo->infostrs),
436 devinfo->infostrs);
437}
Tim Sell8217bec2016-11-03 11:44:16 -0400438
David Kershner1c218002017-09-27 13:14:21 -0400439static int bus_info_debugfs_show(struct seq_file *seq, void *v)
Tim Sell8217bec2016-11-03 11:44:16 -0400440{
David Binderd4e8a222017-07-17 16:16:43 -0400441 int i = 0;
Tim Sell8217bec2016-11-03 11:44:16 -0400442 unsigned long off;
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400443 struct visor_vbus_deviceinfo dev_info;
David Binderd4e8a222017-07-17 16:16:43 -0400444 struct visor_device *vdev = seq->private;
445 struct visorchannel *channel = vdev->visorchannel;
Tim Sell8217bec2016-11-03 11:44:16 -0400446
447 if (!channel)
448 return 0;
449
450 seq_printf(seq,
David Kershner453ca1932017-09-27 13:14:23 -0400451 "Client device/driver info for %s partition (vbus #%u):\n",
Tim Sell8217bec2016-11-03 11:44:16 -0400452 ((vdev->name) ? (char *)(vdev->name) : ""),
453 vdev->chipset_bus_no);
454 if (visorchannel_read(channel,
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400455 offsetof(struct visor_vbus_channel, chp_info),
Tim Sell8217bec2016-11-03 11:44:16 -0400456 &dev_info, sizeof(dev_info)) >= 0)
457 vbuschannel_print_devinfo(&dev_info, seq, -1);
458 if (visorchannel_read(channel,
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400459 offsetof(struct visor_vbus_channel, bus_info),
Tim Sell8217bec2016-11-03 11:44:16 -0400460 &dev_info, sizeof(dev_info)) >= 0)
461 vbuschannel_print_devinfo(&dev_info, seq, -1);
David Binderd4e8a222017-07-17 16:16:43 -0400462
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400463 off = offsetof(struct visor_vbus_channel, dev_info);
Tim Sell8217bec2016-11-03 11:44:16 -0400464 while (off + sizeof(dev_info) <= visorchannel_get_nbytes(channel)) {
465 if (visorchannel_read(channel, off, &dev_info,
466 sizeof(dev_info)) >= 0)
467 vbuschannel_print_devinfo(&dev_info, seq, i);
468 off += sizeof(dev_info);
469 i++;
470 }
Tim Sell8217bec2016-11-03 11:44:16 -0400471 return 0;
472}
473
David Kershner1c218002017-09-27 13:14:21 -0400474static int bus_info_debugfs_open(struct inode *inode, struct file *file)
Tim Sell8217bec2016-11-03 11:44:16 -0400475{
David Kershner1c218002017-09-27 13:14:21 -0400476 return single_open(file, bus_info_debugfs_show, inode->i_private);
Tim Sell8217bec2016-11-03 11:44:16 -0400477}
478
David Kershner1c218002017-09-27 13:14:21 -0400479static const struct file_operations bus_info_debugfs_fops = {
Tim Sell8217bec2016-11-03 11:44:16 -0400480 .owner = THIS_MODULE,
David Kershner1c218002017-09-27 13:14:21 -0400481 .open = bus_info_debugfs_open,
Tim Sell8217bec2016-11-03 11:44:16 -0400482 .read = seq_read,
483 .llseek = seq_lseek,
484 .release = single_release,
485};
486
Kees Cooke99e88a2017-10-16 14:43:17 -0700487static void dev_periodic_work(struct timer_list *t)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400488{
Kees Cooke99e88a2017-10-16 14:43:17 -0700489 struct visor_device *dev = from_timer(dev, t, timer);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400490 struct visor_driver *drv = to_visor_driver(dev->device.driver);
491
Tim Sell396e36c2017-01-09 13:02:22 -0500492 drv->channel_interrupt(dev);
Tim Sell9ebab642016-06-10 21:48:08 -0400493 mod_timer(&dev->timer, jiffies + POLLJIFFIES_NORMALCHANNEL);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400494}
495
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400496static int dev_start_periodic_work(struct visor_device *dev)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400497{
Tim Sell9ebab642016-06-10 21:48:08 -0400498 if (dev->being_removed || dev->timer_active)
David Kershnerb90194d2017-03-28 09:34:43 -0400499 return -EINVAL;
David Kershner4e953472017-09-27 13:14:27 -0400500
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400501 /* now up by at least 2 */
502 get_device(&dev->device);
Tim Sell9ebab642016-06-10 21:48:08 -0400503 dev->timer.expires = jiffies + POLLJIFFIES_NORMALCHANNEL;
504 add_timer(&dev->timer);
505 dev->timer_active = true;
David Kershnerb90194d2017-03-28 09:34:43 -0400506 return 0;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400507}
508
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400509static void dev_stop_periodic_work(struct visor_device *dev)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400510{
Tim Sell9ebab642016-06-10 21:48:08 -0400511 if (!dev->timer_active)
512 return;
David Kershner4e953472017-09-27 13:14:27 -0400513
Tim Sell9ebab642016-06-10 21:48:08 -0400514 del_timer_sync(&dev->timer);
515 dev->timer_active = false;
516 put_device(&dev->device);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400517}
518
David Binderb84be592017-02-21 12:53:24 -0500519/*
David Binder3fd1b3b2016-06-10 21:48:16 -0400520 * visordriver_remove_device() - handle visor device going away
521 * @xdev: struct device for the visor device being removed
522 *
523 * This is called when device_unregister() is called for each child device
524 * instance, to notify the appropriate visorbus function driver that the device
525 * is going away, and to decrease the reference count of the device.
526 *
527 * Return: 0 iff successful
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400528 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400529static int visordriver_remove_device(struct device *xdev)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400530{
David Kershner7f912282017-09-27 13:14:28 -0400531 struct visor_device *dev = to_visor_device(xdev);
532 struct visor_driver *drv = to_visor_driver(xdev->driver);
David Binderd4e8a222017-07-17 16:16:43 -0400533
Bryan Thompsond5058552016-06-10 21:48:10 -0400534 mutex_lock(&dev->visordriver_callback_lock);
Prarit Bhargava779d0752015-05-05 18:37:01 -0400535 dev->being_removed = true;
Sameer Wadgaonkarc2d00b22017-07-17 16:16:59 -0400536 drv->remove(dev);
Bryan Thompsond5058552016-06-10 21:48:10 -0400537 mutex_unlock(&dev->visordriver_callback_lock);
David Binderd4e8a222017-07-17 16:16:43 -0400538 dev_stop_periodic_work(dev);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400539 put_device(&dev->device);
Abdul Hussaindf7f46e2015-06-11 10:03:49 +0000540 return 0;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400541}
542
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -0400543/*
David Binder3fd1b3b2016-06-10 21:48:16 -0400544 * visorbus_unregister_visor_driver() - unregisters the provided driver
545 * @drv: the driver to unregister
546 *
547 * A visor function driver calls this function to unregister the driver,
548 * i.e., within its module_exit function.
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400549 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400550void visorbus_unregister_visor_driver(struct visor_driver *drv)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400551{
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400552 driver_unregister(&drv->driver);
553}
554EXPORT_SYMBOL_GPL(visorbus_unregister_visor_driver);
555
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -0400556/*
David Binder3fd1b3b2016-06-10 21:48:16 -0400557 * visorbus_read_channel() - reads from the designated channel into
558 * the provided buffer
559 * @dev: the device whose channel is read from
560 * @offset: the offset into the channel at which reading starts
561 * @dest: the destination buffer that is written into from the channel
562 * @nbytes: the number of bytes to read from the channel
563 *
David Kershner7915a3c2017-09-27 13:14:13 -0400564 * If receiving a message, use the visorchannel_signalremove() function instead.
David Binder3fd1b3b2016-06-10 21:48:16 -0400565 *
566 * Return: integer indicating success (zero) or failure (non-zero)
567 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400568int visorbus_read_channel(struct visor_device *dev, unsigned long offset,
569 void *dest, unsigned long nbytes)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400570{
571 return visorchannel_read(dev->visorchannel, offset, dest, nbytes);
572}
573EXPORT_SYMBOL_GPL(visorbus_read_channel);
574
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -0400575/*
David Binder3fd1b3b2016-06-10 21:48:16 -0400576 * visorbus_write_channel() - writes the provided buffer into the designated
577 * channel
578 * @dev: the device whose channel is written to
579 * @offset: the offset into the channel at which writing starts
580 * @src: the source buffer that is written into the channel
581 * @nbytes: the number of bytes to write into the channel
582 *
David Kershner7915a3c2017-09-27 13:14:13 -0400583 * If sending a message, use the visorchannel_signalinsert() function instead.
David Binder3fd1b3b2016-06-10 21:48:16 -0400584 *
585 * Return: integer indicating success (zero) or failure (non-zero)
586 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400587int visorbus_write_channel(struct visor_device *dev, unsigned long offset,
588 void *src, unsigned long nbytes)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400589{
590 return visorchannel_write(dev->visorchannel, offset, src, nbytes);
591}
592EXPORT_SYMBOL_GPL(visorbus_write_channel);
593
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -0400594/*
David Binder3fd1b3b2016-06-10 21:48:16 -0400595 * visorbus_enable_channel_interrupts() - enables interrupts on the
596 * designated device
597 * @dev: the device on which to enable interrupts
598 *
599 * Currently we don't yet have a real interrupt, so for now we just call the
600 * interrupt function periodically via a timer.
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400601 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400602int visorbus_enable_channel_interrupts(struct visor_device *dev)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400603{
Tim Sell396e36c2017-01-09 13:02:22 -0500604 struct visor_driver *drv = to_visor_driver(dev->device.driver);
605
606 if (!drv->channel_interrupt) {
607 dev_err(&dev->device, "%s no interrupt function!\n", __func__);
David Kershner5dca9b22017-03-28 09:34:44 -0400608 return -ENOENT;
Tim Sell396e36c2017-01-09 13:02:22 -0500609 }
610
David Kershner5dca9b22017-03-28 09:34:44 -0400611 return dev_start_periodic_work(dev);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400612}
613EXPORT_SYMBOL_GPL(visorbus_enable_channel_interrupts);
614
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -0400615/*
David Binder3fd1b3b2016-06-10 21:48:16 -0400616 * visorbus_disable_channel_interrupts() - disables interrupts on the
617 * designated device
618 * @dev: the device on which to disable interrupts
619 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400620void visorbus_disable_channel_interrupts(struct visor_device *dev)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400621{
622 dev_stop_periodic_work(dev);
623}
624EXPORT_SYMBOL_GPL(visorbus_disable_channel_interrupts);
625
David Binderb84be592017-02-21 12:53:24 -0500626/*
David Binder3fd1b3b2016-06-10 21:48:16 -0400627 * create_visor_device() - create visor device as a result of receiving the
628 * controlvm device_create message for a new device
629 * @dev: a freshly-zeroed struct visor_device, containing only filled-in values
630 * for chipset_bus_no and chipset_dev_no, that will be initialized
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400631 *
David Binder3fd1b3b2016-06-10 21:48:16 -0400632 * This is how everything starts from the device end.
633 * This function is called when a channel first appears via a ControlVM
David Kershner7915a3c2017-09-27 13:14:13 -0400634 * message. In response, this function allocates a visor_device to correspond
635 * to the new channel, and attempts to connect it the appropriate * driver. If
636 * the appropriate driver is found, the visor_driver.probe() function for that
637 * driver will be called, and will be passed the new * visor_device that we
638 * just created.
David Binder3fd1b3b2016-06-10 21:48:16 -0400639 *
640 * It's ok if the appropriate driver is not yet loaded, because in that case
641 * the new device struct will just stick around in the bus' list of devices.
642 * When the appropriate driver calls visorbus_register_visor_driver(), the
David Kershner7915a3c2017-09-27 13:14:13 -0400643 * visor_driver.probe() for the new driver will be called with the new device.
David Binder3fd1b3b2016-06-10 21:48:16 -0400644 *
645 * Return: 0 if successful, otherwise the negative value returned by
646 * device_add() indicating the reason for failure
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400647 */
Sameer Wadgaonkar51c0f812017-08-22 13:27:34 -0400648int create_visor_device(struct visor_device *dev)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400649{
David Kershner0b2acf32016-03-12 21:27:12 -0500650 int err;
Don Zickusa298bc02015-06-04 09:22:42 -0400651 u32 chipset_bus_no = dev->chipset_bus_no;
652 u32 chipset_dev_no = dev->chipset_dev_no;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400653
Bryan Thompsond5058552016-06-10 21:48:10 -0400654 mutex_init(&dev->visordriver_callback_lock);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400655 dev->device.bus = &visorbus_type;
David Kershneraa5ebde2017-08-22 13:27:36 -0400656 dev->device.groups = channel_groups;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400657 device_initialize(&dev->device);
658 dev->device.release = visorbus_release_device;
659 /* keep a reference just for us (now 2) */
660 get_device(&dev->device);
Kees Cooke99e88a2017-10-16 14:43:17 -0700661 timer_setup(&dev->timer, dev_periodic_work, 0);
David Binder3fd1b3b2016-06-10 21:48:16 -0400662 /*
David Kershner7915a3c2017-09-27 13:14:13 -0400663 * bus_id must be a unique name with respect to this bus TYPE (NOT bus
664 * instance). That's why we need to include the bus number within the
665 * name.
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400666 */
David Kershnere0d210a2017-03-28 09:34:50 -0400667 err = dev_set_name(&dev->device, "vbus%u:dev%u",
668 chipset_bus_no, chipset_dev_no);
669 if (err)
670 goto err_put;
David Binder3fd1b3b2016-06-10 21:48:16 -0400671 /*
672 * device_add does this:
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400673 * bus_add_device(dev)
674 * ->device_attach(dev)
675 * ->for each driver drv registered on the bus that dev is on
676 * if (dev.drv) ** device already has a driver **
677 * ** not sure we could ever get here... **
678 * else
679 * if (bus.match(dev,drv)) [visorbus_match]
680 * dev.drv = drv
681 * if (!drv.probe(dev)) [visordriver_probe_device]
682 * dev.drv = NULL
683 *
David Kershner7915a3c2017-09-27 13:14:13 -0400684 * Note that device_add does NOT fail if no driver failed to claim the
685 * device. The device will be linked onto bus_type.klist_devices
686 * regardless (use bus_for_each_dev).
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400687 */
David Kershner0b2acf32016-03-12 21:27:12 -0500688 err = device_add(&dev->device);
David Kershnerebdc1b82017-04-18 16:55:09 -0400689 if (err < 0)
David Kershner0b2acf32016-03-12 21:27:12 -0500690 goto err_put;
Don Zickusa298bc02015-06-04 09:22:42 -0400691 list_add_tail(&dev->list_all, &list_all_device_instances);
Sameer Wadgaonkar51c0f812017-08-22 13:27:34 -0400692 dev->state.created = 1;
693 visorbus_response(dev, err, CONTROLVM_DEVICE_CREATE);
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -0400694 /* success: reference kept via unmatched get_device() */
695 return 0;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400696
David Kershner0b2acf32016-03-12 21:27:12 -0500697err_put:
Don Zickusa298bc02015-06-04 09:22:42 -0400698 put_device(&dev->device);
David Kershnerebdc1b82017-04-18 16:55:09 -0400699 dev_err(&dev->device, "Creating visor device failed. %d\n", err);
David Kershner0b2acf32016-03-12 21:27:12 -0500700 return err;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400701}
702
Sameer Wadgaonkarb74856b2017-08-22 13:27:35 -0400703void remove_visor_device(struct visor_device *dev)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400704{
705 list_del(&dev->list_all);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400706 put_device(&dev->device);
David Kershnerfd9e4502017-09-27 13:14:16 -0400707 if (dev->pending_msg_hdr)
708 visorbus_response(dev, 0, CONTROLVM_DEVICE_DESTROY);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400709 device_unregister(&dev->device);
710}
711
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400712static int get_vbus_header_info(struct visorchannel *chan,
Sameer Wadgaonkare25201d2017-08-30 13:36:35 -0400713 struct device *dev,
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400714 struct visor_vbus_headerinfo *hdr_info)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400715{
David Kershner711c67f2017-03-28 09:34:51 -0400716 int err;
717
Sameer Wadgaonkar315dfc82017-05-19 16:17:54 -0400718 if (!visor_check_channel(visorchannel_get_header(chan),
Sameer Wadgaonkare25201d2017-08-30 13:36:35 -0400719 dev,
Andy Shevchenkob32c5cb2017-08-22 13:26:54 -0400720 &visor_vbus_channel_guid,
Sameer Wadgaonkar315dfc82017-05-19 16:17:54 -0400721 "vbus",
722 sizeof(struct visor_vbus_channel),
723 VISOR_VBUS_CHANNEL_VERSIONID,
Alex Curtine9b92752017-07-17 16:16:51 -0400724 VISOR_CHANNEL_SIGNATURE))
Benjamin Romerf748f642016-02-23 10:01:50 -0500725 return -EINVAL;
726
David Kershner711c67f2017-03-28 09:34:51 -0400727 err = visorchannel_read(chan, sizeof(struct channel_header), hdr_info,
728 sizeof(*hdr_info));
729 if (err < 0)
730 return err;
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400731 if (hdr_info->struct_bytes < sizeof(struct visor_vbus_headerinfo))
Benjamin Romerf748f642016-02-23 10:01:50 -0500732 return -EINVAL;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400733 if (hdr_info->device_info_struct_bytes <
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400734 sizeof(struct visor_vbus_deviceinfo))
Benjamin Romerf748f642016-02-23 10:01:50 -0500735 return -EINVAL;
Benjamin Romerf748f642016-02-23 10:01:50 -0500736 return 0;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400737}
738
David Binderb84be592017-02-21 12:53:24 -0500739/*
David Binder3fd1b3b2016-06-10 21:48:16 -0400740 * write_vbus_chp_info() - write the contents of <info> to the struct
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400741 * visor_vbus_channel.chp_info
David Binder3fd1b3b2016-06-10 21:48:16 -0400742 * @chan: indentifies the s-Par channel that will be updated
743 * @hdr_info: used to find appropriate channel offset to write data
744 * @info: contains the information to write
Erik Arfvidsonff13cf32016-06-10 21:47:59 -0400745 *
David Binder3fd1b3b2016-06-10 21:48:16 -0400746 * Writes chipset info into the channel memory to be used for diagnostic
747 * purposes.
748 *
749 * Returns no value since this is debug information and not needed for
Erik Arfvidsonff13cf32016-06-10 21:47:59 -0400750 * device functionality.
Gavin O'Leary48117892015-11-09 20:12:00 -0800751 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400752static void write_vbus_chp_info(struct visorchannel *chan,
753 struct visor_vbus_headerinfo *hdr_info,
754 struct visor_vbus_deviceinfo *info)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400755{
David Kershner5d1a7fd2017-09-27 13:14:19 -0400756 int off;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400757
758 if (hdr_info->chp_info_offset == 0)
Erik Arfvidsonff13cf32016-06-10 21:47:59 -0400759 return;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400760
David Kershner5d1a7fd2017-09-27 13:14:19 -0400761 off = sizeof(struct channel_header) + hdr_info->chp_info_offset;
Erik Arfvidsonff13cf32016-06-10 21:47:59 -0400762 visorchannel_write(chan, off, info, sizeof(*info));
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400763}
764
David Binderb84be592017-02-21 12:53:24 -0500765/*
David Binder3fd1b3b2016-06-10 21:48:16 -0400766 * write_vbus_bus_info() - write the contents of <info> to the struct
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400767 * visor_vbus_channel.bus_info
David Binder3fd1b3b2016-06-10 21:48:16 -0400768 * @chan: indentifies the s-Par channel that will be updated
769 * @hdr_info: used to find appropriate channel offset to write data
770 * @info: contains the information to write
Erik Arfvidsonff13cf32016-06-10 21:47:59 -0400771 *
David Binder3fd1b3b2016-06-10 21:48:16 -0400772 * Writes bus info into the channel memory to be used for diagnostic
773 * purposes.
774 *
775 * Returns no value since this is debug information and not needed for
Erik Arfvidsonff13cf32016-06-10 21:47:59 -0400776 * device functionality.
Gavin O'Leary48117892015-11-09 20:12:00 -0800777 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400778static void write_vbus_bus_info(struct visorchannel *chan,
779 struct visor_vbus_headerinfo *hdr_info,
780 struct visor_vbus_deviceinfo *info)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400781{
David Kershner5d1a7fd2017-09-27 13:14:19 -0400782 int off;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400783
784 if (hdr_info->bus_info_offset == 0)
Erik Arfvidsonff13cf32016-06-10 21:47:59 -0400785 return;
David Kershner4e953472017-09-27 13:14:27 -0400786
David Kershner5d1a7fd2017-09-27 13:14:19 -0400787 off = sizeof(struct channel_header) + hdr_info->bus_info_offset;
Erik Arfvidsonff13cf32016-06-10 21:47:59 -0400788 visorchannel_write(chan, off, info, sizeof(*info));
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400789}
790
David Binderb84be592017-02-21 12:53:24 -0500791/*
David Binder3fd1b3b2016-06-10 21:48:16 -0400792 * write_vbus_dev_info() - write the contents of <info> to the struct
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400793 * visor_vbus_channel.dev_info[<devix>]
David Binder3fd1b3b2016-06-10 21:48:16 -0400794 * @chan: indentifies the s-Par channel that will be updated
795 * @hdr_info: used to find appropriate channel offset to write data
796 * @info: contains the information to write
797 * @devix: the relative device number (0..n-1) of the device on the bus
Erik Arfvidsonff13cf32016-06-10 21:47:59 -0400798 *
David Binder3fd1b3b2016-06-10 21:48:16 -0400799 * Writes device info into the channel memory to be used for diagnostic
800 * purposes.
801 *
802 * Returns no value since this is debug information and not needed for
Erik Arfvidsonff13cf32016-06-10 21:47:59 -0400803 * device functionality.
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400804 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400805static void write_vbus_dev_info(struct visorchannel *chan,
806 struct visor_vbus_headerinfo *hdr_info,
807 struct visor_vbus_deviceinfo *info,
808 unsigned int devix)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400809{
David Kershner5d1a7fd2017-09-27 13:14:19 -0400810 int off;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400811
812 if (hdr_info->dev_info_offset == 0)
Erik Arfvidsonff13cf32016-06-10 21:47:59 -0400813 return;
David Kershner5d1a7fd2017-09-27 13:14:19 -0400814 off = (sizeof(struct channel_header) + hdr_info->dev_info_offset) +
815 (hdr_info->device_info_struct_bytes * devix);
Erik Arfvidsonff13cf32016-06-10 21:47:59 -0400816 visorchannel_write(chan, off, info, sizeof(*info));
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400817}
818
David Kershnerb5577d72017-03-28 09:34:28 -0400819static void bus_device_info_init(
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400820 struct visor_vbus_deviceinfo *bus_device_info_ptr,
David Kershnerb5577d72017-03-28 09:34:28 -0400821 const char *dev_type, const char *drv_name)
822{
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400823 memset(bus_device_info_ptr, 0, sizeof(struct visor_vbus_deviceinfo));
David Kershnerb5577d72017-03-28 09:34:28 -0400824 snprintf(bus_device_info_ptr->devtype,
825 sizeof(bus_device_info_ptr->devtype),
826 "%s", (dev_type) ? dev_type : "unknownType");
827 snprintf(bus_device_info_ptr->drvname,
828 sizeof(bus_device_info_ptr->drvname),
829 "%s", (drv_name) ? drv_name : "unknownDriver");
830 snprintf(bus_device_info_ptr->infostrs,
831 sizeof(bus_device_info_ptr->infostrs), "kernel ver. %s",
832 utsname()->release);
833}
834
David Binderb84be592017-02-21 12:53:24 -0500835/*
Erik Arfvidsone3b2ed62017-07-17 16:17:07 -0400836 * publish_vbus_dev_info() - for a child device just created on a client bus,
837 * fill in information about the driver that is
838 * controlling this device into the appropriate slot
839 * within the vbus channel of the bus instance
David Binder3fd1b3b2016-06-10 21:48:16 -0400840 * @visordev: struct visor_device for the desired device
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400841 */
Erik Arfvidsone3b2ed62017-07-17 16:17:07 -0400842static void publish_vbus_dev_info(struct visor_device *visordev)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400843{
844 int i;
Don Zickusd32517e2015-06-04 09:22:41 -0400845 struct visor_device *bdev;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400846 struct visor_driver *visordrv;
Tim Sellf7a34ff2016-09-27 14:42:21 -0400847 u32 bus_no = visordev->chipset_bus_no;
848 u32 dev_no = visordev->chipset_dev_no;
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400849 struct visor_vbus_deviceinfo dev_info;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400850 const char *chan_type_name = NULL;
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400851 struct visor_vbus_headerinfo *hdr_info;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400852
853 if (!visordev->device.driver)
Christophe JAILLET216c3e22015-07-13 20:52:26 +0200854 return;
Don Zickusd32517e2015-06-04 09:22:41 -0400855 bdev = visorbus_get_device_by_id(bus_no, BUS_ROOT_DEVICE, NULL);
856 if (!bdev)
857 return;
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -0400858 hdr_info = (struct visor_vbus_headerinfo *)bdev->vbus_hdr_info;
Tim Sell5990b392016-09-27 14:42:22 -0400859 if (!hdr_info)
860 return;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400861 visordrv = to_visor_driver(visordev->device.driver);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400862
David Binder3fd1b3b2016-06-10 21:48:16 -0400863 /*
864 * Within the list of device types (by GUID) that the driver
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400865 * says it supports, find out which one of those types matches
866 * the type of this device, so that we can include the device
867 * type name
868 */
869 for (i = 0; visordrv->channel_types[i].name; i++) {
David Kershner5d489422017-09-27 13:14:14 -0400870 if (guid_equal(&visordrv->channel_types[i].guid,
871 &visordev->channel_type_guid)) {
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400872 chan_type_name = visordrv->channel_types[i].name;
873 break;
874 }
875 }
Jon Frische82ed632016-09-26 11:03:41 -0400876 bus_device_info_init(&dev_info, chan_type_name, visordrv->name);
Don Zickusd32517e2015-06-04 09:22:41 -0400877 write_vbus_dev_info(bdev->visorchannel, hdr_info, &dev_info, dev_no);
Don Zickusd32517e2015-06-04 09:22:41 -0400878 write_vbus_chp_info(bdev->visorchannel, hdr_info, &chipset_driverinfo);
879 write_vbus_bus_info(bdev->visorchannel, hdr_info,
880 &clientbus_driverinfo);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -0400881}
882
David Binderb84be592017-02-21 12:53:24 -0500883/*
David Kershner7a0ee692016-09-19 17:09:36 -0400884 * visordriver_probe_device() - handle new visor device coming online
885 * @xdev: struct device for the visor device being probed
886 *
887 * This is called automatically upon adding a visor_device (device_add), or
888 * adding a visor_driver (visorbus_register_visor_driver), but only after
889 * visorbus_match() has returned 1 to indicate a successful match between
890 * driver and device.
891 *
892 * If successful, a reference to the device will be held onto via get_device().
893 *
894 * Return: 0 if successful, meaning the function driver's probe() function
895 * was successful with this device, otherwise a negative errno
896 * value indicating failure reason
897 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -0400898static int visordriver_probe_device(struct device *xdev)
David Kershner7a0ee692016-09-19 17:09:36 -0400899{
David Kershner61f38f92017-09-27 13:14:20 -0400900 int err;
David Kershner7f912282017-09-27 13:14:28 -0400901 struct visor_driver *drv = to_visor_driver(xdev->driver);
902 struct visor_device *dev = to_visor_device(xdev);
David Kershner7a0ee692016-09-19 17:09:36 -0400903
904 mutex_lock(&dev->visordriver_callback_lock);
905 dev->being_removed = false;
David Kershner61f38f92017-09-27 13:14:20 -0400906 err = drv->probe(dev);
907 if (err) {
908 mutex_unlock(&dev->visordriver_callback_lock);
909 return err;
David Kershner7a0ee692016-09-19 17:09:36 -0400910 }
David Kershner61f38f92017-09-27 13:14:20 -0400911 /* success: reference kept via unmatched get_device() */
912 get_device(&dev->device);
913 publish_vbus_dev_info(dev);
David Kershner7a0ee692016-09-19 17:09:36 -0400914 mutex_unlock(&dev->visordriver_callback_lock);
David Kershner61f38f92017-09-27 13:14:20 -0400915 return 0;
David Kershner7a0ee692016-09-19 17:09:36 -0400916}
917
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -0400918/*
David Kershner7915a3c2017-09-27 13:14:13 -0400919 * visorbus_register_visor_driver() - registers the provided visor driver for
920 * handling one or more visor device
David Kershner7a0ee692016-09-19 17:09:36 -0400921 * types (channel_types)
922 * @drv: the driver to register
923 *
David Kershner7915a3c2017-09-27 13:14:13 -0400924 * A visor function driver calls this function to register the driver. The
925 * caller MUST fill in the following fields within the #drv structure:
David Kershner7a0ee692016-09-19 17:09:36 -0400926 * name, version, owner, channel_types, probe, remove
927 *
928 * Here's how the whole Linux bus / driver / device model works.
929 *
930 * At system start-up, the visorbus kernel module is loaded, which registers
931 * visorbus_type as a bus type, using bus_register().
932 *
933 * All kernel modules that support particular device types on a
934 * visorbus bus are loaded. Each of these kernel modules calls
935 * visorbus_register_visor_driver() in their init functions, passing a
936 * visor_driver struct. visorbus_register_visor_driver() in turn calls
937 * register_driver(&visor_driver.driver). This .driver member is
938 * initialized with generic methods (like probe), whose sole responsibility
939 * is to act as a broker for the real methods, which are within the
940 * visor_driver struct. (This is the way the subclass behavior is
941 * implemented, since visor_driver is essentially a subclass of the
942 * generic driver.) Whenever a driver_register() happens, core bus code in
943 * the kernel does (see device_attach() in drivers/base/dd.c):
944 *
945 * for each dev associated with the bus (the bus that driver is on) that
946 * does not yet have a driver
947 * if bus.match(dev,newdriver) == yes_matched ** .match specified
948 * ** during bus_register().
949 * newdriver.probe(dev) ** for visor drivers, this will call
950 * ** the generic driver.probe implemented in visorbus.c,
951 * ** which in turn calls the probe specified within the
952 * ** struct visor_driver (which was specified by the
953 * ** actual device driver as part of
954 * ** visorbus_register_visor_driver()).
955 *
956 * The above dance also happens when a new device appears.
957 * So the question is, how are devices created within the system?
958 * Basically, just call device_add(dev). See pci_bus_add_devices().
959 * pci_scan_device() shows an example of how to build a device struct. It
960 * returns the newly-created struct to pci_scan_single_device(), who adds it
961 * to the list of devices at PCIBUS.devices. That list of devices is what
962 * is traversed by pci_bus_add_devices().
963 *
964 * Return: integer indicating success (zero) or failure (non-zero)
965 */
966int visorbus_register_visor_driver(struct visor_driver *drv)
967{
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -0400968 /* can't register on a nonexistent bus */
David Kershnerb0512fa2017-03-31 14:20:12 -0400969 if (!initialized)
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -0400970 return -ENODEV;
Sameer Wadgaonkarc2d00b22017-07-17 16:16:59 -0400971 if (!drv->probe)
Sameer Wadgaonkar3459e832017-08-30 13:36:10 -0400972 return -EINVAL;
Sameer Wadgaonkarc2d00b22017-07-17 16:16:59 -0400973 if (!drv->remove)
Sameer Wadgaonkar3459e832017-08-30 13:36:10 -0400974 return -EINVAL;
Sameer Wadgaonkarc2d00b22017-07-17 16:16:59 -0400975 if (!drv->pause)
Sameer Wadgaonkar3459e832017-08-30 13:36:10 -0400976 return -EINVAL;
Sameer Wadgaonkarc2d00b22017-07-17 16:16:59 -0400977 if (!drv->resume)
Sameer Wadgaonkar3459e832017-08-30 13:36:10 -0400978 return -EINVAL;
Sameer Wadgaonkarc2d00b22017-07-17 16:16:59 -0400979
David Kershner7a0ee692016-09-19 17:09:36 -0400980 drv->driver.name = drv->name;
981 drv->driver.bus = &visorbus_type;
982 drv->driver.probe = visordriver_probe_device;
983 drv->driver.remove = visordriver_remove_device;
984 drv->driver.owner = drv->owner;
David Kershner7a0ee692016-09-19 17:09:36 -0400985 /*
986 * driver_register does this:
987 * bus_add_driver(drv)
988 * ->if (drv.bus) ** (bus_type) **
989 * driver_attach(drv)
990 * for each dev with bus type of drv.bus
991 * if (!dev.drv) ** no driver assigned yet **
992 * if (bus.match(dev,drv)) [visorbus_match]
993 * dev.drv = drv
994 * if (!drv.probe(dev)) [visordriver_probe_device]
995 * dev.drv = NULL
996 */
David Kershner293deb22017-03-28 09:34:52 -0400997 return driver_register(&drv->driver);
David Kershner7a0ee692016-09-19 17:09:36 -0400998}
999EXPORT_SYMBOL_GPL(visorbus_register_visor_driver);
1000
David Binderb84be592017-02-21 12:53:24 -05001001/*
Sameer Wadgaonkar9e78fd32017-05-19 16:17:39 -04001002 * visorbus_create_instance() - create a device instance for the visorbus itself
David Binder3fd1b3b2016-06-10 21:48:16 -04001003 * @dev: struct visor_device indicating the bus instance
1004 *
1005 * Return: 0 for success, otherwise negative errno value indicating reason for
1006 * failure
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001007 */
David Kershnerfdf5b9a2017-08-22 13:27:24 -04001008int visorbus_create_instance(struct visor_device *dev)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001009{
Don Zickusd32517e2015-06-04 09:22:41 -04001010 int id = dev->chipset_bus_no;
Tim Sell8217bec2016-11-03 11:44:16 -04001011 int err;
Sameer Wadgaonkar55c71eb2017-05-19 16:17:45 -04001012 struct visor_vbus_headerinfo *hdr_info;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001013
Don Zickus7726f812015-06-01 13:00:28 -04001014 hdr_info = kzalloc(sizeof(*hdr_info), GFP_KERNEL);
Benjamin Romerc2c667d2016-02-23 10:01:52 -05001015 if (!hdr_info)
1016 return -ENOMEM;
Don Zickus343506b2015-06-04 09:22:37 -04001017 dev_set_name(&dev->device, "visorbus%d", id);
1018 dev->device.bus = &visorbus_type;
1019 dev->device.groups = visorbus_groups;
1020 dev->device.release = visorbus_release_busdevice;
Tim Sell8217bec2016-11-03 11:44:16 -04001021 dev->debugfs_dir = debugfs_create_dir(dev_name(&dev->device),
1022 visorbus_debugfs_dir);
David Kershner1c218002017-09-27 13:14:21 -04001023 dev->debugfs_bus_info = debugfs_create_file("client_bus_info", 0440,
1024 dev->debugfs_dir, dev,
1025 &bus_info_debugfs_fops);
David Kershner362f87f2017-03-28 09:34:45 -04001026 dev_set_drvdata(&dev->device, dev);
Sameer Wadgaonkare25201d2017-08-30 13:36:35 -04001027 err = get_vbus_header_info(dev->visorchannel, &dev->device, hdr_info);
David Kershner362f87f2017-03-28 09:34:45 -04001028 if (err < 0)
1029 goto err_debugfs_dir;
David Kershner362f87f2017-03-28 09:34:45 -04001030 err = device_register(&dev->device);
David Kershner450333f2017-04-18 16:55:11 -04001031 if (err < 0)
Tim Sell8217bec2016-11-03 11:44:16 -04001032 goto err_debugfs_dir;
Don Zickus343506b2015-06-04 09:22:37 -04001033 list_add_tail(&dev->list_all, &list_all_bus_instances);
David Kershnerfdf5b9a2017-08-22 13:27:24 -04001034 dev->state.created = 1;
David Kershner362f87f2017-03-28 09:34:45 -04001035 dev->vbus_hdr_info = (void *)hdr_info;
David Kershner9f1d28f2017-09-27 13:14:18 -04001036 write_vbus_chp_info(dev->visorchannel, hdr_info, &chipset_driverinfo);
1037 write_vbus_bus_info(dev->visorchannel, hdr_info, &clientbus_driverinfo);
David Kershnerfdf5b9a2017-08-22 13:27:24 -04001038 visorbus_response(dev, err, CONTROLVM_BUS_CREATE);
David Kershner362f87f2017-03-28 09:34:45 -04001039 return 0;
Tim Sell8217bec2016-11-03 11:44:16 -04001040
1041err_debugfs_dir:
1042 debugfs_remove_recursive(dev->debugfs_dir);
Tim Sell8217bec2016-11-03 11:44:16 -04001043 kfree(hdr_info);
Zachary Dremann23d01c42017-07-17 16:16:41 -04001044 dev_err(&dev->device, "%s failed: %d\n", __func__, err);
Tim Sell8217bec2016-11-03 11:44:16 -04001045 return err;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001046}
1047
David Binderb84be592017-02-21 12:53:24 -05001048/*
Sameer Wadgaonkar9e78fd32017-05-19 16:17:39 -04001049 * visorbus_remove_instance() - remove a device instance for the visorbus itself
David Binder3fd1b3b2016-06-10 21:48:16 -04001050 * @dev: struct visor_device indentifying the bus to remove
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001051 */
Sameer Wadgaonkara7093ba2017-08-22 13:27:33 -04001052void visorbus_remove_instance(struct visor_device *dev)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001053{
David Binder3fd1b3b2016-06-10 21:48:16 -04001054 /*
1055 * Note that this will result in the release method for
Don Zickus343506b2015-06-04 09:22:37 -04001056 * dev->dev being called, which will call
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001057 * visorbus_release_busdevice(). This has something to do with
1058 * the put_device() done in device_unregister(), but I have never
1059 * successfully been able to trace thru the code to see where/how
1060 * release() gets called. But I know it does.
1061 */
Don Zickus343506b2015-06-04 09:22:37 -04001062 kfree(dev->vbus_hdr_info);
1063 list_del(&dev->list_all);
David Kershnerae54a282017-09-27 13:14:17 -04001064 if (dev->pending_msg_hdr)
1065 visorbus_response(dev, 0, CONTROLVM_BUS_DESTROY);
Don Zickus343506b2015-06-04 09:22:37 -04001066 device_unregister(&dev->device);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001067}
1068
David Binderb84be592017-02-21 12:53:24 -05001069/*
Sameer Wadgaonkar9e78fd32017-05-19 16:17:39 -04001070 * remove_all_visor_devices() - remove all child visorbus device instances
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001071 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -04001072static void remove_all_visor_devices(void)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001073{
1074 struct list_head *listentry, *listtmp;
1075
1076 list_for_each_safe(listentry, listtmp, &list_all_device_instances) {
David Kershner17e4bdd2017-09-27 13:14:15 -04001077 struct visor_device *dev;
1078
1079 dev = list_entry(listentry, struct visor_device, list_all);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001080 remove_visor_device(dev);
1081 }
1082}
1083
David Binderb84be592017-02-21 12:53:24 -05001084/*
David Binder3fd1b3b2016-06-10 21:48:16 -04001085 * pause_state_change_complete() - the callback function to be called by a
1086 * visorbus function driver when a
1087 * pending "pause device" operation has
1088 * completed
1089 * @dev: struct visor_device identifying the paused device
1090 * @status: 0 iff the pause state change completed successfully, otherwise
1091 * a negative errno value indicating the reason for failure
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001092 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -04001093static void pause_state_change_complete(struct visor_device *dev, int status)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001094{
1095 if (!dev->pausing)
Christophe JAILLET216c3e22015-07-13 20:52:26 +02001096 return;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001097
Prarit Bhargava779d0752015-05-05 18:37:01 -04001098 dev->pausing = false;
Sameer Wadgaonkar722e73d2017-08-22 13:27:04 -04001099 visorbus_device_changestate_response(dev, status,
1100 segment_state_standby);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001101}
1102
David Binderb84be592017-02-21 12:53:24 -05001103/*
David Binder3fd1b3b2016-06-10 21:48:16 -04001104 * resume_state_change_complete() - the callback function to be called by a
1105 * visorbus function driver when a
1106 * pending "resume device" operation has
1107 * completed
1108 * @dev: struct visor_device identifying the resumed device
1109 * @status: 0 iff the resume state change completed successfully, otherwise
1110 * a negative errno value indicating the reason for failure
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001111 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -04001112static void resume_state_change_complete(struct visor_device *dev, int status)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001113{
1114 if (!dev->resuming)
Christophe JAILLET216c3e22015-07-13 20:52:26 +02001115 return;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001116
Prarit Bhargava779d0752015-05-05 18:37:01 -04001117 dev->resuming = false;
David Binder3fd1b3b2016-06-10 21:48:16 -04001118 /*
1119 * Notify the chipset driver that the resume is complete,
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001120 * which will presumably want to send some sort of response to
Gavin O'Leary48117892015-11-09 20:12:00 -08001121 * the initiator.
1122 */
Sameer Wadgaonkar722e73d2017-08-22 13:27:04 -04001123 visorbus_device_changestate_response(dev, status,
1124 segment_state_running);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001125}
1126
David Binderb84be592017-02-21 12:53:24 -05001127/*
Sameer Wadgaonkar451072e2017-05-19 16:17:42 -04001128 * visorchipset_initiate_device_pause_resume() - start a pause or resume
1129 * operation for a visor device
David Binder3fd1b3b2016-06-10 21:48:16 -04001130 * @dev: struct visor_device identifying the device being paused or resumed
1131 * @is_pause: true to indicate pause operation, false to indicate resume
1132 *
1133 * Tell the subordinate function driver for a specific device to pause
1134 * or resume that device. Success/failure result is returned asynchronously
1135 * via a callback function; see pause_state_change_complete() and
1136 * resume_state_change_complete().
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001137 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -04001138static int visorchipset_initiate_device_pause_resume(struct visor_device *dev,
1139 bool is_pause)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001140{
David Kershner15d9ce92017-03-28 09:34:53 -04001141 int err;
David Kershner473659d2017-09-27 13:14:24 -04001142 struct visor_driver *drv;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001143
David Kershner68f4f762017-08-30 13:36:17 -04001144 /* If no driver associated with the device nothing to pause/resume */
1145 if (!dev->device.driver)
1146 return 0;
David Kershner15d9ce92017-03-28 09:34:53 -04001147 if (dev->pausing || dev->resuming)
1148 return -EBUSY;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001149
David Kershner68f4f762017-08-30 13:36:17 -04001150 drv = to_visor_driver(dev->device.driver);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001151 if (is_pause) {
Prarit Bhargava779d0752015-05-05 18:37:01 -04001152 dev->pausing = true;
David Kershner15d9ce92017-03-28 09:34:53 -04001153 err = drv->pause(dev, pause_state_change_complete);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001154 } else {
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -04001155 /*
1156 * The vbus_dev_info structure in the channel was been cleared,
1157 * make sure it is valid.
Gavin O'Leary48117892015-11-09 20:12:00 -08001158 */
Erik Arfvidsone3b2ed62017-07-17 16:17:07 -04001159 publish_vbus_dev_info(dev);
Prarit Bhargava779d0752015-05-05 18:37:01 -04001160 dev->resuming = true;
David Kershner15d9ce92017-03-28 09:34:53 -04001161 err = drv->resume(dev, resume_state_change_complete);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001162 }
David Kershner15d9ce92017-03-28 09:34:53 -04001163 return err;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001164}
1165
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -04001166/*
Sameer Wadgaonkarc0b44132017-05-19 16:17:41 -04001167 * visorchipset_device_pause() - start a pause operation for a visor device
David Binder3fd1b3b2016-06-10 21:48:16 -04001168 * @dev_info: struct visor_device identifying the device being paused
1169 *
1170 * Tell the subordinate function driver for a specific device to pause
1171 * that device. Success/failure result is returned asynchronously
1172 * via a callback function; see pause_state_change_complete().
1173 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -04001174int visorchipset_device_pause(struct visor_device *dev_info)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001175{
David Kershner15d9ce92017-03-28 09:34:53 -04001176 int err;
1177
Sameer Wadgaonkar451072e2017-05-19 16:17:42 -04001178 err = visorchipset_initiate_device_pause_resume(dev_info, true);
David Kershner15d9ce92017-03-28 09:34:53 -04001179 if (err < 0) {
1180 dev_info->pausing = false;
David Kershnerb4a8e6a2017-03-28 09:34:54 -04001181 return err;
David Kershner15d9ce92017-03-28 09:34:53 -04001182 }
David Kershnerb4a8e6a2017-03-28 09:34:54 -04001183 return 0;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001184}
1185
Sameer Wadgaonkar060b2932017-06-30 15:43:05 -04001186/*
Sameer Wadgaonkarc0b44132017-05-19 16:17:41 -04001187 * visorchipset_device_resume() - start a resume operation for a visor device
David Binder3fd1b3b2016-06-10 21:48:16 -04001188 * @dev_info: struct visor_device identifying the device being resumed
1189 *
1190 * Tell the subordinate function driver for a specific device to resume
1191 * that device. Success/failure result is returned asynchronously
1192 * via a callback function; see resume_state_change_complete().
1193 */
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -04001194int visorchipset_device_resume(struct visor_device *dev_info)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001195{
David Kershner15d9ce92017-03-28 09:34:53 -04001196 int err;
1197
Sameer Wadgaonkar451072e2017-05-19 16:17:42 -04001198 err = visorchipset_initiate_device_pause_resume(dev_info, false);
David Kershner15d9ce92017-03-28 09:34:53 -04001199 if (err < 0) {
David Kershner15d9ce92017-03-28 09:34:53 -04001200 dev_info->resuming = false;
David Kershnerb4a8e6a2017-03-28 09:34:54 -04001201 return err;
David Kershner15d9ce92017-03-28 09:34:53 -04001202 }
David Kershnerb4a8e6a2017-03-28 09:34:54 -04001203 return 0;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001204}
1205
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -04001206int visorbus_init(void)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001207{
David Kershner78af1ae2016-03-12 21:27:10 -05001208 int err;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001209
Tim Sell8217bec2016-11-03 11:44:16 -04001210 visorbus_debugfs_dir = debugfs_create_dir("visorbus", NULL);
Jon Frische82ed632016-09-26 11:03:41 -04001211 bus_device_info_init(&clientbus_driverinfo, "clientbus", "visorbus");
David Kershner5b6f9b92017-03-28 09:34:46 -04001212 err = bus_register(&visorbus_type);
David Kershner804aab32017-04-18 16:55:15 -04001213 if (err < 0)
1214 return err;
David Kershnerb0512fa2017-03-31 14:20:12 -04001215 initialized = true;
Jon Frische82ed632016-09-26 11:03:41 -04001216 bus_device_info_init(&chipset_driverinfo, "chipset", "visorchipset");
David Kershner78af1ae2016-03-12 21:27:10 -05001217 return 0;
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001218}
1219
Sameer Wadgaonkarbaf9b702017-07-17 16:16:57 -04001220void visorbus_exit(void)
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001221{
1222 struct list_head *listentry, *listtmp;
1223
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001224 remove_all_visor_devices();
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001225 list_for_each_safe(listentry, listtmp, &list_all_bus_instances) {
David Kershner17e4bdd2017-09-27 13:14:15 -04001226 struct visor_device *dev;
1227
1228 dev = list_entry(listentry, struct visor_device, list_all);
Sameer Wadgaonkar9e78fd32017-05-19 16:17:39 -04001229 visorbus_remove_instance(dev);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001230 }
David Kershner5b6f9b92017-03-28 09:34:46 -04001231 bus_unregister(&visorbus_type);
David Kershnerb0512fa2017-03-31 14:20:12 -04001232 initialized = false;
Tim Sell8217bec2016-11-03 11:44:16 -04001233 debugfs_remove_recursive(visorbus_debugfs_dir);
Erik Arfvidson3703987cd2015-05-05 18:36:00 -04001234}