* [PATCH 10/20] Staging: hv: storvsc: Get rid of alloc_stor_device() by inlining the code
From: K. Y. Srinivasan @ 2011-09-13 17:59 UTC (permalink / raw)
To: gregkh, linux-kernel, devel, virtualization
Cc: K. Y. Srinivasan, Haiyang Zhang
In-Reply-To: <1315936796-20662-1-git-send-email-kys@microsoft.com>
Get rid of alloc_stor_device() by inlining the code.
Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
---
drivers/staging/hv/storvsc_drv.c | 24 ++++++------------------
1 files changed, 6 insertions(+), 18 deletions(-)
diff --git a/drivers/staging/hv/storvsc_drv.c b/drivers/staging/hv/storvsc_drv.c
index 2210c8c..ce8652e 100644
--- a/drivers/staging/hv/storvsc_drv.c
+++ b/drivers/staging/hv/storvsc_drv.c
@@ -332,23 +332,6 @@ static inline void storvsc_wait_to_drain(struct storvsc_device *dev)
dev->drain_notify = false;
}
-static inline struct storvsc_device *alloc_stor_device(struct hv_device *device)
-{
- struct storvsc_device *stor_device;
-
- stor_device = kzalloc(sizeof(struct storvsc_device), GFP_KERNEL);
- if (!stor_device)
- return NULL;
-
- stor_device->destroy = false;
- init_waitqueue_head(&stor_device->waiting_to_drain);
- stor_device->device = device;
- device->ext = stor_device;
-
- return stor_device;
-}
-
-
static inline struct storvsc_device *get_in_stor_device(
struct hv_device *device)
{
@@ -1382,13 +1365,18 @@ static int storvsc_probe(struct hv_device *device,
return -ENOMEM;
}
- stor_device = alloc_stor_device(device);
+ stor_device = kzalloc(sizeof(struct storvsc_device), GFP_KERNEL);
if (!stor_device) {
kmem_cache_destroy(host_dev->request_pool);
scsi_host_put(host);
return -ENOMEM;
}
+ stor_device->destroy = false;
+ init_waitqueue_head(&stor_device->waiting_to_drain);
+ stor_device->device = device;
+ device->ext = stor_device;
+
stor_device->port_number = host->host_no;
ret = storvsc_connect_to_vsp(device, storvsc_ringbuffer_size);
if (ret) {
--
1.7.4.1
^ permalink raw reply related
* [PATCH 09/20] Staging: hv: storvsc: Get rid of storvsc_dev_add() by inlining the code
From: K. Y. Srinivasan @ 2011-09-13 17:59 UTC (permalink / raw)
To: gregkh, linux-kernel, devel, virtualization; +Cc: Haiyang Zhang
In-Reply-To: <1315936796-20662-1-git-send-email-kys@microsoft.com>
Get rid of storvsc_dev_add() by inlining the code.
Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
---
drivers/staging/hv/storvsc_drv.c | 58 +++++++++----------------------------
1 files changed, 14 insertions(+), 44 deletions(-)
diff --git a/drivers/staging/hv/storvsc_drv.c b/drivers/staging/hv/storvsc_drv.c
index b996293..2210c8c 100644
--- a/drivers/staging/hv/storvsc_drv.c
+++ b/drivers/staging/hv/storvsc_drv.c
@@ -651,41 +651,6 @@ static int storvsc_connect_to_vsp(struct hv_device *device, u32 ring_size)
return ret;
}
-static int storvsc_dev_add(struct hv_device *device,
- void *additional_info)
-{
- struct storvsc_device *stor_device;
- struct storvsc_device_info *device_info;
- int ret = 0;
-
- device_info = (struct storvsc_device_info *)additional_info;
- stor_device = alloc_stor_device(device);
- if (!stor_device)
- return -ENOMEM;
-
- /* Save the channel properties to our storvsc channel */
-
- /*
- * If we support more than 1 scsi channel, we need to set the
- * port number here to the scsi channel but how do we get the
- * scsi channel prior to the bus scan.
- *
- * The host does not support this.
- */
-
- stor_device->port_number = device_info->port_number;
- /* Send it back up */
- ret = storvsc_connect_to_vsp(device, device_info->ring_buffer_size);
- if (ret) {
- kfree(stor_device);
- return ret;
- }
- device_info->path_id = stor_device->path_id;
- device_info->target_id = stor_device->target_id;
-
- return ret;
-}
-
static int storvsc_dev_remove(struct hv_device *device)
{
struct storvsc_device *stor_device;
@@ -1389,10 +1354,10 @@ static int storvsc_probe(struct hv_device *device,
int ret;
struct Scsi_Host *host;
struct hv_host_device *host_dev;
- struct storvsc_device_info device_info;
bool dev_is_ide = ((dev_id->driver_data == IDE_GUID) ? true : false);
int path = 0;
int target = 0;
+ struct storvsc_device *stor_device;
host = scsi_host_alloc(&scsi_driver,
sizeof(struct hv_host_device));
@@ -1417,22 +1382,27 @@ static int storvsc_probe(struct hv_device *device,
return -ENOMEM;
}
- device_info.port_number = host->host_no;
- device_info.ring_buffer_size = storvsc_ringbuffer_size;
- /* Call to the vsc driver to add the device */
- ret = storvsc_dev_add(device, (void *)&device_info);
+ stor_device = alloc_stor_device(device);
+ if (!stor_device) {
+ kmem_cache_destroy(host_dev->request_pool);
+ scsi_host_put(host);
+ return -ENOMEM;
+ }
- if (ret != 0) {
+ stor_device->port_number = host->host_no;
+ ret = storvsc_connect_to_vsp(device, storvsc_ringbuffer_size);
+ if (ret) {
kmem_cache_destroy(host_dev->request_pool);
scsi_host_put(host);
- return -ENODEV;
+ kfree(stor_device);
+ return ret;
}
if (dev_is_ide)
storvsc_get_ide_info(device, &target, &path);
- host_dev->path = device_info.path_id;
- host_dev->target = device_info.target_id;
+ host_dev->path = stor_device->path_id;
+ host_dev->target = stor_device->target_id;
/* max # of devices per target */
host->max_lun = STORVSC_MAX_LUNS_PER_TARGET;
--
1.7.4.1
^ permalink raw reply related
* [PATCH 08/20] Staging: hv: vmbus: Cleanup vmbus_remove()
From: K. Y. Srinivasan @ 2011-09-13 17:59 UTC (permalink / raw)
To: gregkh, linux-kernel, devel, virtualization; +Cc: Haiyang Zhang
In-Reply-To: <1315936796-20662-1-git-send-email-kys@microsoft.com>
vmbus_remove() cannot fail; clean it up accordingly.
Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
---
drivers/staging/hv/vmbus_drv.c | 20 ++++++--------------
1 files changed, 6 insertions(+), 14 deletions(-)
diff --git a/drivers/staging/hv/vmbus_drv.c b/drivers/staging/hv/vmbus_drv.c
index 2fccb1f..466425a 100644
--- a/drivers/staging/hv/vmbus_drv.c
+++ b/drivers/staging/hv/vmbus_drv.c
@@ -334,22 +334,14 @@ static int vmbus_probe(struct device *child_device)
*/
static int vmbus_remove(struct device *child_device)
{
- int ret;
- struct hv_driver *drv;
-
+ struct hv_driver *drv = drv_to_hv_drv(child_device->driver);
struct hv_device *dev = device_to_hv_device(child_device);
- if (child_device->driver) {
- drv = drv_to_hv_drv(child_device->driver);
-
- if (drv->remove) {
- ret = drv->remove(dev);
- } else {
- pr_err("remove not set for driver %s\n",
- dev_name(child_device));
- ret = -ENODEV;
- }
- }
+ if (drv->remove)
+ drv->remove(dev);
+ else
+ pr_err("remove not set for driver %s\n",
+ dev_name(child_device));
return 0;
}
--
1.7.4.1
^ permalink raw reply related
* [PATCH 07/20] Staging: hv: vmbus: Get rid of hv_cb_utils[] and other unneeded code
From: K. Y. Srinivasan @ 2011-09-13 17:59 UTC (permalink / raw)
To: gregkh, linux-kernel, devel, virtualization
Cc: K. Y. Srinivasan, Haiyang Zhang
In-Reply-To: <1315936796-20662-1-git-send-email-kys@microsoft.com>
Now that the transformation of the util driver is complete,
get rid of hv_cb_utils[] and other unneeded code.
Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
---
drivers/staging/hv/channel_mgmt.c | 94 -------------------------------------
drivers/staging/hv/hyperv.h | 13 -----
2 files changed, 0 insertions(+), 107 deletions(-)
diff --git a/drivers/staging/hv/channel_mgmt.c b/drivers/staging/hv/channel_mgmt.c
index 3c67e4c..f20cd84 100644
--- a/drivers/staging/hv/channel_mgmt.c
+++ b/drivers/staging/hv/channel_mgmt.c
@@ -158,100 +158,6 @@ void prep_negotiate_resp(struct icmsg_hdr *icmsghdrp,
}
EXPORT_SYMBOL(prep_negotiate_resp);
-/**
- * chn_cb_negotiate() - Default handler for non IDE/SCSI/NETWORK
- * Hyper-V requests
- * @context: Pointer to argument structure.
- *
- * Set up the default handler for non device driver specific requests
- * from Hyper-V. This stub responds to the default negotiate messages
- * that come in for every non IDE/SCSI/Network request.
- * This behavior is normally overwritten in the hv_utils driver. That
- * driver handles requests like graceful shutdown, heartbeats etc.
- *
- * Mainly used by Hyper-V drivers.
- */
-void chn_cb_negotiate(void *context)
-{
- struct vmbus_channel *channel = context;
- u8 *buf;
- u32 buflen, recvlen;
- u64 requestid;
-
- struct icmsg_hdr *icmsghdrp;
- struct icmsg_negotiate *negop = NULL;
-
- buflen = PAGE_SIZE;
- buf = kmalloc(buflen, GFP_ATOMIC);
-
- vmbus_recvpacket(channel, buf, buflen, &recvlen, &requestid);
-
- if (recvlen > 0) {
- icmsghdrp = (struct icmsg_hdr *)&buf[
- sizeof(struct vmbuspipe_hdr)];
-
- prep_negotiate_resp(icmsghdrp, negop, buf);
-
- icmsghdrp->icflags = ICMSGHDRFLAG_TRANSACTION
- | ICMSGHDRFLAG_RESPONSE;
-
- vmbus_sendpacket(channel, buf,
- recvlen, requestid,
- VM_PKT_DATA_INBAND, 0);
- }
-
- kfree(buf);
-}
-EXPORT_SYMBOL(chn_cb_negotiate);
-
-/*
- * Function table used for message responses for non IDE/SCSI/Network type
- * messages. (Such as KVP/Shutdown etc)
- */
-struct hyperv_service_callback hv_cb_utils[MAX_MSG_TYPES] = {
- /* 0E0B6031-5213-4934-818B-38D90CED39DB */
- /* Shutdown */
- {
- .msg_type = HV_SHUTDOWN_MSG,
- .data.b = {
- 0x31, 0x60, 0x0B, 0X0E, 0x13, 0x52, 0x34, 0x49,
- 0x81, 0x8B, 0x38, 0XD9, 0x0C, 0xED, 0x39, 0xDB
- },
- .log_msg = "Shutdown channel functionality initialized"
- },
-
- /* {9527E630-D0AE-497b-ADCE-E80AB0175CAF} */
- /* TimeSync */
- {
- .msg_type = HV_TIMESYNC_MSG,
- .data.b = {
- 0x30, 0xe6, 0x27, 0x95, 0xae, 0xd0, 0x7b, 0x49,
- 0xad, 0xce, 0xe8, 0x0a, 0xb0, 0x17, 0x5c, 0xaf
- },
- .log_msg = "Timesync channel functionality initialized"
- },
- /* {57164f39-9115-4e78-ab55-382f3bd5422d} */
- /* Heartbeat */
- {
- .msg_type = HV_HEARTBEAT_MSG,
- .data.b = {
- 0x39, 0x4f, 0x16, 0x57, 0x15, 0x91, 0x78, 0x4e,
- 0xab, 0x55, 0x38, 0x2f, 0x3b, 0xd5, 0x42, 0x2d
- },
- .log_msg = "Heartbeat channel functionality initialized"
- },
- /* {A9A0F4E7-5A45-4d96-B827-8A841E8C03E6} */
- /* KVP */
- {
- .data.b = {
- 0xe7, 0xf4, 0xa0, 0xa9, 0x45, 0x5a, 0x96, 0x4d,
- 0xb8, 0x27, 0x8a, 0x84, 0x1e, 0x8c, 0x3, 0xe6
- },
- .log_msg = "KVP channel functionality initialized"
- },
-};
-EXPORT_SYMBOL(hv_cb_utils);
-
/*
* alloc_channel - Allocate and initialize a vmbus channel object
*/
diff --git a/drivers/staging/hv/hyperv.h b/drivers/staging/hv/hyperv.h
index b0d7711..e51341f 100644
--- a/drivers/staging/hv/hyperv.h
+++ b/drivers/staging/hv/hyperv.h
@@ -581,11 +581,6 @@ struct vmbus_channel {
struct work_struct work;
enum vmbus_channel_state state;
- /*
- * For util channels, stash the
- * the service index for easy access.
- */
- s8 util_index;
struct vmbus_channel_offer_channel offermsg;
/*
@@ -964,12 +959,6 @@ struct ictimesync_data {
u8 flags;
} __packed;
-/* Index for each IC struct in array hv_cb_utils[] */
-#define HV_SHUTDOWN_MSG 0
-#define HV_TIMESYNC_MSG 1
-#define HV_HEARTBEAT_MSG 2
-#define HV_KVP_MSG 3
-
struct hyperv_service_callback {
u8 msg_type;
char *log_msg;
@@ -980,7 +969,5 @@ struct hyperv_service_callback {
extern void prep_negotiate_resp(struct icmsg_hdr *,
struct icmsg_negotiate *, u8 *);
-extern void chn_cb_negotiate(void *);
-extern struct hyperv_service_callback hv_cb_utils[];
#endif /* _HYPERV_H */
--
1.7.4.1
^ permalink raw reply related
* [PATCH 06/20] Staging: hv: util: Properly handle util services in the util driver
From: K. Y. Srinivasan @ 2011-09-13 17:59 UTC (permalink / raw)
To: gregkh, linux-kernel, devel, virtualization; +Cc: Haiyang Zhang
In-Reply-To: <1315936796-20662-1-git-send-email-kys@microsoft.com>
Now, properly handle util services in the util driver and eliminate code
that will not be necessary. In the current code, util services were
all handled not as other vmbus devices (net, block) but rather through
special handling (channel setup etc.). In this patch we handle all
services using the standard Linux Driver Model.
Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
---
drivers/staging/hv/channel_mgmt.c | 39 +-------------------------
drivers/staging/hv/hv_kvp.c | 7 ++++
drivers/staging/hv/hv_util.c | 56 +++++++++++-------------------------
3 files changed, 25 insertions(+), 77 deletions(-)
diff --git a/drivers/staging/hv/channel_mgmt.c b/drivers/staging/hv/channel_mgmt.c
index c68e5fa..3c67e4c 100644
--- a/drivers/staging/hv/channel_mgmt.c
+++ b/drivers/staging/hv/channel_mgmt.c
@@ -181,24 +181,6 @@ void chn_cb_negotiate(void *context)
struct icmsg_hdr *icmsghdrp;
struct icmsg_negotiate *negop = NULL;
- if (channel->util_index >= 0) {
- /*
- * This is a properly initialized util channel.
- * Route this callback appropriately and setup state
- * so that we don't need to reroute again.
- */
- if (hv_cb_utils[channel->util_index].callback != NULL) {
- /*
- * The util driver has established a handler for
- * this service; do the magic.
- */
- channel->onchannel_callback =
- hv_cb_utils[channel->util_index].callback;
- (hv_cb_utils[channel->util_index].callback)(channel);
- return;
- }
- }
-
buflen = PAGE_SIZE;
buf = kmalloc(buflen, GFP_ATOMIC);
@@ -348,7 +330,6 @@ static void vmbus_process_offer(struct work_struct *work)
struct vmbus_channel *channel;
bool fnew = true;
int ret;
- int cnt;
unsigned long flags;
/* The next possible work is rescind handling */
@@ -403,31 +384,13 @@ static void vmbus_process_offer(struct work_struct *work)
spin_unlock_irqrestore(&vmbus_connection.channel_lock, flags);
free_channel(newchannel);
- } else {
+ } else
/*
* This state is used to indicate a successful open
* so that when we do close the channel normally, we
* can cleanup properly
*/
newchannel->state = CHANNEL_OPEN_STATE;
- newchannel->util_index = -1; /* Invalid index */
-
- /* Open IC channels */
- for (cnt = 0; cnt < MAX_MSG_TYPES; cnt++) {
- if (!uuid_le_cmp(newchannel->offermsg.offer.if_type,
- hv_cb_utils[cnt].data) &&
- vmbus_open(newchannel, 2 * PAGE_SIZE,
- 2 * PAGE_SIZE, NULL, 0,
- chn_cb_negotiate,
- newchannel) == 0) {
- hv_cb_utils[cnt].channel = newchannel;
- newchannel->util_index = cnt;
-
- pr_info("%s\n", hv_cb_utils[cnt].log_msg);
-
- }
- }
- }
}
/*
diff --git a/drivers/staging/hv/hv_kvp.c b/drivers/staging/hv/hv_kvp.c
index ff0d9ab..9aa9ede 100644
--- a/drivers/staging/hv/hv_kvp.c
+++ b/drivers/staging/hv/hv_kvp.c
@@ -177,6 +177,13 @@ kvp_respond_to_host(char *key, char *value, int error)
channel = kvp_transaction.recv_channel;
req_id = kvp_transaction.recv_req_id;
+ if (channel->onchannel_callback == NULL)
+ /*
+ * We have raced with util driver being unloaded;
+ * silently return.
+ */
+ return;
+
icmsghdrp = (struct icmsg_hdr *)
&recv_buffer[sizeof(struct vmbuspipe_hdr)];
kvp_msg = (struct hv_kvp_msg *)
diff --git a/drivers/staging/hv/hv_util.c b/drivers/staging/hv/hv_util.c
index f082e5a..31abe9e 100644
--- a/drivers/staging/hv/hv_util.c
+++ b/drivers/staging/hv/hv_util.c
@@ -273,19 +273,33 @@ static int util_probe(struct hv_device *dev,
if (srv->util_init) {
ret = srv->util_init(srv);
if (ret) {
- kfree(srv->recv_buffer);
- return -ENODEV;
+ ret = -ENODEV;
+ goto error1;
}
}
+ ret = vmbus_open(dev->channel, 2 * PAGE_SIZE, 2 * PAGE_SIZE, NULL, 0,
+ srv->util_cb, dev->channel);
+ if (ret)
+ goto error;
+
+ pr_info("%s", srv->service_name);
hv_set_drvdata(dev, srv);
return 0;
+
+error:
+ if (srv->util_deinit)
+ srv->util_deinit();
+error1:
+ kfree(srv->recv_buffer);
+ return ret;
}
static int util_remove(struct hv_device *dev)
{
struct hv_util_service *srv = hv_get_drvdata(dev);
+ vmbus_close(dev->channel);
if (srv->util_deinit)
srv->util_deinit();
kfree(srv->recv_buffer);
@@ -325,51 +339,15 @@ static struct hv_driver util_drv = {
static int __init init_hyperv_utils(void)
{
- int ret;
pr_info("Registering HyperV Utility Driver\n");
-
- ret = vmbus_driver_register(&util_drv);
-
- if (ret != 0)
- return ret;
-
- hv_cb_utils[HV_SHUTDOWN_MSG].callback = &shutdown_onchannelcallback;
-
- hv_cb_utils[HV_TIMESYNC_MSG].callback = ×ync_onchannelcallback;
-
- hv_cb_utils[HV_HEARTBEAT_MSG].callback = &heartbeat_onchannelcallback;
-
- hv_cb_utils[HV_KVP_MSG].callback = &hv_kvp_onchannelcallback;
-
- return 0;
-
+ return vmbus_driver_register(&util_drv);
}
static void exit_hyperv_utils(void)
{
pr_info("De-Registered HyperV Utility Driver\n");
- if (hv_cb_utils[HV_SHUTDOWN_MSG].channel != NULL)
- hv_cb_utils[HV_SHUTDOWN_MSG].channel->onchannel_callback =
- &chn_cb_negotiate;
- hv_cb_utils[HV_SHUTDOWN_MSG].callback = NULL;
-
- if (hv_cb_utils[HV_TIMESYNC_MSG].channel != NULL)
- hv_cb_utils[HV_TIMESYNC_MSG].channel->onchannel_callback =
- &chn_cb_negotiate;
- hv_cb_utils[HV_TIMESYNC_MSG].callback = NULL;
-
- if (hv_cb_utils[HV_HEARTBEAT_MSG].channel != NULL)
- hv_cb_utils[HV_HEARTBEAT_MSG].channel->onchannel_callback =
- &chn_cb_negotiate;
- hv_cb_utils[HV_HEARTBEAT_MSG].callback = NULL;
-
- if (hv_cb_utils[HV_KVP_MSG].channel != NULL)
- hv_cb_utils[HV_KVP_MSG].channel->onchannel_callback =
- &chn_cb_negotiate;
- hv_cb_utils[HV_KVP_MSG].callback = NULL;
-
vmbus_driver_unregister(&util_drv);
}
--
1.7.4.1
^ permalink raw reply related
* [PATCH 05/20] Staging: hv: util: Perform some service specific init/deinit in probe/remove
From: K. Y. Srinivasan @ 2011-09-13 17:59 UTC (permalink / raw)
To: gregkh, linux-kernel, devel, virtualization
Cc: K. Y. Srinivasan, Haiyang Zhang
In-Reply-To: <1315936796-20662-1-git-send-email-kys@microsoft.com>
In preparation for modifying the util driver to fully conform to the
Linux Driver Model, perform some service specific init and de-init
operations in util_probe()/util_remove() as opposed to in
init_hyperv_utils()/exit_hyperv_utils() as is currently done.
Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
---
drivers/staging/hv/hv_kvp.c | 7 +--
drivers/staging/hv/hv_kvp.h | 2 +-
drivers/staging/hv/hv_util.c | 95 ++++++++++++++++++++++++++----------------
drivers/staging/hv/hyperv.h | 14 ++++++
4 files changed, 76 insertions(+), 42 deletions(-)
diff --git a/drivers/staging/hv/hv_kvp.c b/drivers/staging/hv/hv_kvp.c
index 13b0ecf..ff0d9ab 100644
--- a/drivers/staging/hv/hv_kvp.c
+++ b/drivers/staging/hv/hv_kvp.c
@@ -312,16 +312,14 @@ callback_done:
}
int
-hv_kvp_init(void)
+hv_kvp_init(struct hv_util_service *srv)
{
int err;
err = cn_add_callback(&kvp_id, kvp_name, kvp_cn_callback);
if (err)
return err;
- recv_buffer = kmalloc(PAGE_SIZE, GFP_KERNEL);
- if (!recv_buffer)
- return -ENOMEM;
+ recv_buffer = srv->recv_buffer;
return 0;
}
@@ -330,5 +328,4 @@ void hv_kvp_deinit(void)
{
cn_del_callback(&kvp_id);
cancel_delayed_work_sync(&kvp_work);
- kfree(recv_buffer);
}
diff --git a/drivers/staging/hv/hv_kvp.h b/drivers/staging/hv/hv_kvp.h
index 8c402f3..9b765d7 100644
--- a/drivers/staging/hv/hv_kvp.h
+++ b/drivers/staging/hv/hv_kvp.h
@@ -175,7 +175,7 @@ struct hv_kvp_msg {
struct hv_kvp_msg_enumerate kvp_data;
};
-int hv_kvp_init(void);
+int hv_kvp_init(struct hv_util_service *);
void hv_kvp_deinit(void);
void hv_kvp_onchannelcallback(void *);
diff --git a/drivers/staging/hv/hv_util.c b/drivers/staging/hv/hv_util.c
index d9460fdd..f082e5a 100644
--- a/drivers/staging/hv/hv_util.c
+++ b/drivers/staging/hv/hv_util.c
@@ -30,9 +30,31 @@
#include "hyperv.h"
#include "hv_kvp.h"
-static u8 *shut_txf_buf;
-static u8 *time_txf_buf;
-static u8 *hbeat_txf_buf;
+
+static void shutdown_onchannelcallback(void *context);
+static struct hv_util_service util_shutdown = {
+ .service_name = "Shutdown channel functionality initialized\n",
+ .util_cb = shutdown_onchannelcallback,
+};
+
+static void timesync_onchannelcallback(void *context);
+static struct hv_util_service util_timesynch = {
+ .service_name = "Timesync channel functionality initialized\n",
+ .util_cb = timesync_onchannelcallback,
+};
+
+static void heartbeat_onchannelcallback(void *context);
+static struct hv_util_service util_heartbeat = {
+ .service_name = "Heartbeat channel functionality initialized\n",
+ .util_cb = heartbeat_onchannelcallback,
+};
+
+static struct hv_util_service util_kvp = {
+ .service_name = "KVP channel functionality initialized\n",
+ .util_cb = hv_kvp_onchannelcallback,
+ .util_init = hv_kvp_init,
+ .util_deinit = hv_kvp_deinit,
+};
static void shutdown_onchannelcallback(void *context)
{
@@ -40,6 +62,7 @@ static void shutdown_onchannelcallback(void *context)
u32 recvlen;
u64 requestid;
u8 execute_shutdown = false;
+ u8 *shut_txf_buf = util_shutdown.recv_buffer;
struct shutdown_msg_data *shutdown_msg;
@@ -169,6 +192,7 @@ static void timesync_onchannelcallback(void *context)
u64 requestid;
struct icmsg_hdr *icmsghdrp;
struct ictimesync_data *timedatap;
+ u8 *time_txf_buf = util_timesynch.recv_buffer;
vmbus_recvpacket(channel, time_txf_buf,
PAGE_SIZE, &recvlen, &requestid);
@@ -207,6 +231,7 @@ static void heartbeat_onchannelcallback(void *context)
u64 requestid;
struct icmsg_hdr *icmsghdrp;
struct heartbeat_msg_data *heartbeat_msg;
+ u8 *hbeat_txf_buf = util_heartbeat.recv_buffer;
vmbus_recvpacket(channel, hbeat_txf_buf,
PAGE_SIZE, &recvlen, &requestid);
@@ -235,34 +260,56 @@ static void heartbeat_onchannelcallback(void *context)
}
}
-/*
- * The devices managed by the util driver don't need any additional
- * setup.
- */
static int util_probe(struct hv_device *dev,
const struct hv_vmbus_device_id *dev_id)
{
+ struct hv_util_service *srv =
+ (struct hv_util_service *)dev_id->driver_data;
+ int ret;
+
+ srv->recv_buffer = kmalloc(PAGE_SIZE, GFP_KERNEL);
+ if (!srv->recv_buffer)
+ return -ENOMEM;
+ if (srv->util_init) {
+ ret = srv->util_init(srv);
+ if (ret) {
+ kfree(srv->recv_buffer);
+ return -ENODEV;
+ }
+ }
+
+ hv_set_drvdata(dev, srv);
return 0;
}
static int util_remove(struct hv_device *dev)
{
+ struct hv_util_service *srv = hv_get_drvdata(dev);
+
+ if (srv->util_deinit)
+ srv->util_deinit();
+ kfree(srv->recv_buffer);
+
return 0;
}
static const struct hv_vmbus_device_id id_table[] = {
/* Shutdown guid */
{ VMBUS_DEVICE(0x31, 0x60, 0x0B, 0X0E, 0x13, 0x52, 0x34, 0x49,
- 0x81, 0x8B, 0x38, 0XD9, 0x0C, 0xED, 0x39, 0xDB) },
+ 0x81, 0x8B, 0x38, 0XD9, 0x0C, 0xED, 0x39, 0xDB)
+ .driver_data = (unsigned long)&util_shutdown },
/* Time synch guid */
{ VMBUS_DEVICE(0x30, 0xe6, 0x27, 0x95, 0xae, 0xd0, 0x7b, 0x49,
- 0xad, 0xce, 0xe8, 0x0a, 0xb0, 0x17, 0x5c, 0xaf) },
+ 0xad, 0xce, 0xe8, 0x0a, 0xb0, 0x17, 0x5c, 0xaf)
+ .driver_data = (unsigned long)&util_timesynch },
/* Heartbeat guid */
{ VMBUS_DEVICE(0x39, 0x4f, 0x16, 0x57, 0x15, 0x91, 0x78, 0x4e,
- 0xab, 0x55, 0x38, 0x2f, 0x3b, 0xd5, 0x42, 0x2d) },
+ 0xab, 0x55, 0x38, 0x2f, 0x3b, 0xd5, 0x42, 0x2d)
+ .driver_data = (unsigned long)&util_heartbeat },
/* KVP guid */
{ VMBUS_DEVICE(0xe7, 0xf4, 0xa0, 0xa9, 0x45, 0x5a, 0x96, 0x4d,
- 0xb8, 0x27, 0x8a, 0x84, 0x1e, 0x8c, 0x3, 0xe6) },
+ 0xb8, 0x27, 0x8a, 0x84, 0x1e, 0x8c, 0x3, 0xe6)
+ .driver_data = (unsigned long)&util_kvp },
{ },
};
@@ -281,24 +328,11 @@ static int __init init_hyperv_utils(void)
int ret;
pr_info("Registering HyperV Utility Driver\n");
- if (hv_kvp_init())
- return -ENODEV;
-
-
- shut_txf_buf = kmalloc(PAGE_SIZE, GFP_KERNEL);
- time_txf_buf = kmalloc(PAGE_SIZE, GFP_KERNEL);
- hbeat_txf_buf = kmalloc(PAGE_SIZE, GFP_KERNEL);
-
- if (!shut_txf_buf || !time_txf_buf || !hbeat_txf_buf) {
- pr_info("Unable to allocate memory for receive buffer\n");
- ret = -ENOMEM;
- goto err;
- }
ret = vmbus_driver_register(&util_drv);
if (ret != 0)
- goto err;
+ return ret;
hv_cb_utils[HV_SHUTDOWN_MSG].callback = &shutdown_onchannelcallback;
@@ -310,12 +344,6 @@ static int __init init_hyperv_utils(void)
return 0;
-err:
- kfree(shut_txf_buf);
- kfree(time_txf_buf);
- kfree(hbeat_txf_buf);
-
- return ret;
}
static void exit_hyperv_utils(void)
@@ -342,11 +370,6 @@ static void exit_hyperv_utils(void)
&chn_cb_negotiate;
hv_cb_utils[HV_KVP_MSG].callback = NULL;
- hv_kvp_deinit();
-
- kfree(shut_txf_buf);
- kfree(time_txf_buf);
- kfree(hbeat_txf_buf);
vmbus_driver_unregister(&util_drv);
}
diff --git a/drivers/staging/hv/hyperv.h b/drivers/staging/hv/hyperv.h
index 91e557b..b0d7711 100644
--- a/drivers/staging/hv/hyperv.h
+++ b/drivers/staging/hv/hyperv.h
@@ -892,6 +892,20 @@ void vmbus_driver_unregister(struct hv_driver *hv_driver);
#define HV_ERROR_NOT_SUPPORTED 0x80070032
#define HV_ERROR_MACHINE_LOCKED 0x800704F7
+/*
+ * While we want to handle util services as regular devices,
+ * there is only one instance of each of these services; so
+ * we statically allocate the service specific state.
+ */
+
+struct hv_util_service {
+ u8 *recv_buffer;
+ char *service_name;
+ void (*util_cb)(void *);
+ int (*util_init)(struct hv_util_service *);
+ void (*util_deinit)(void);
+};
+
struct vmbuspipe_hdr {
u32 flags;
u32 msgsize;
--
1.7.4.1
^ permalink raw reply related
* [PATCH 04/20] Staging: hv: vmbus: Introduce functions for setting and getting driver data
From: K. Y. Srinivasan @ 2011-09-13 17:59 UTC (permalink / raw)
To: gregkh, linux-kernel, devel, virtualization
Cc: K. Y. Srinivasan, Haiyang Zhang
In-Reply-To: <1315936796-20662-1-git-send-email-kys@microsoft.com>
Introduce vmbus specific wrapper functions to set/get driver specific data.
Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
---
drivers/staging/hv/hyperv.h | 9 +++++++++
1 files changed, 9 insertions(+), 0 deletions(-)
diff --git a/drivers/staging/hv/hyperv.h b/drivers/staging/hv/hyperv.h
index caa3a7b..91e557b 100644
--- a/drivers/staging/hv/hyperv.h
+++ b/drivers/staging/hv/hyperv.h
@@ -843,6 +843,15 @@ static inline struct hv_driver *drv_to_hv_drv(struct device_driver *d)
return container_of(d, struct hv_driver, driver);
}
+static inline void hv_set_drvdata(struct hv_device *dev, void *data)
+{
+ dev_set_drvdata(&dev->device, data);
+}
+
+static inline void *hv_get_drvdata(struct hv_device *dev)
+{
+ return dev_get_drvdata(&dev->device);
+}
/* Vmbus interface */
#define vmbus_driver_register(driver) \
--
1.7.4.1
^ permalink raw reply related
* [PATCH 03/20] Staging: hv: storvsc: Use the driver_data to identify ide
From: K. Y. Srinivasan @ 2011-09-13 17:59 UTC (permalink / raw)
To: gregkh, linux-kernel, devel, virtualization
Cc: K. Y. Srinivasan, Haiyang Zhang
In-Reply-To: <1315936796-20662-1-git-send-email-kys@microsoft.com>
Use the driver_data to identify ide devices in storvsc_probe().
Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
---
drivers/staging/hv/storvsc_drv.c | 22 ++++++++++------------
1 files changed, 10 insertions(+), 12 deletions(-)
diff --git a/drivers/staging/hv/storvsc_drv.c b/drivers/staging/hv/storvsc_drv.c
index fff1e5b..b996293 100644
--- a/drivers/staging/hv/storvsc_drv.c
+++ b/drivers/staging/hv/storvsc_drv.c
@@ -1359,17 +1359,20 @@ static struct scsi_host_template scsi_driver = {
.dma_boundary = PAGE_SIZE-1,
};
-/*
- * The storvsc_probe function assumes that the IDE guid
- * is the second entry.
- */
+enum {
+ SCSI_GUID,
+ IDE_GUID,
+};
+
static const struct hv_vmbus_device_id id_table[] = {
/* SCSI guid */
{ VMBUS_DEVICE(0xd9, 0x63, 0x61, 0xba, 0xa1, 0x04, 0x29, 0x4d,
- 0xb6, 0x05, 0x72, 0xe2, 0xff, 0xb1, 0xdc, 0x7f) },
+ 0xb6, 0x05, 0x72, 0xe2, 0xff, 0xb1, 0xdc, 0x7f)
+ .driver_data = SCSI_GUID },
/* IDE guid */
{ VMBUS_DEVICE(0x32, 0x26, 0x41, 0x32, 0xcb, 0x86, 0xa2, 0x44,
- 0x9b, 0x5c, 0x50, 0xd1, 0x41, 0x73, 0x54, 0xf5) },
+ 0x9b, 0x5c, 0x50, 0xd1, 0x41, 0x73, 0x54, 0xf5)
+ .driver_data = IDE_GUID },
{ },
};
@@ -1387,15 +1390,10 @@ static int storvsc_probe(struct hv_device *device,
struct Scsi_Host *host;
struct hv_host_device *host_dev;
struct storvsc_device_info device_info;
- bool dev_is_ide;
+ bool dev_is_ide = ((dev_id->driver_data == IDE_GUID) ? true : false);
int path = 0;
int target = 0;
- if (!memcmp(&device->dev_type.b, id_table[1].guid, sizeof(uuid_le)))
- dev_is_ide = true;
- else
- dev_is_ide = false;
-
host = scsi_host_alloc(&scsi_driver,
sizeof(struct hv_host_device));
if (!host)
--
1.7.4.1
^ permalink raw reply related
* [PATCH 02/20] Staging: hv: vmbus: Change the signature of struct hv_driver probe function
From: K. Y. Srinivasan @ 2011-09-13 17:59 UTC (permalink / raw)
To: gregkh, linux-kernel, devel, virtualization; +Cc: Haiyang Zhang
In-Reply-To: <1315936796-20662-1-git-send-email-kys@microsoft.com>
In preparation to leveraging the driver_data field in struct
hv_vmbus_device_id, change the signature of struct hv_driver probe function.
Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
---
drivers/staging/hv/hv_mouse.c | 3 ++-
drivers/staging/hv/hv_util.c | 3 ++-
drivers/staging/hv/hyperv.h | 2 +-
drivers/staging/hv/netvsc_drv.c | 3 ++-
drivers/staging/hv/storvsc_drv.c | 3 ++-
drivers/staging/hv/vmbus_drv.c | 4 +++-
6 files changed, 12 insertions(+), 6 deletions(-)
diff --git a/drivers/staging/hv/hv_mouse.c b/drivers/staging/hv/hv_mouse.c
index dbb04ee..5ff8a03 100644
--- a/drivers/staging/hv/hv_mouse.c
+++ b/drivers/staging/hv/hv_mouse.c
@@ -823,7 +823,8 @@ static int mousevsc_on_device_remove(struct hv_device *device)
}
-static int mousevsc_probe(struct hv_device *dev)
+static int mousevsc_probe(struct hv_device *dev,
+ const struct hv_vmbus_device_id *dev_id)
{
int ret = 0;
diff --git a/drivers/staging/hv/hv_util.c b/drivers/staging/hv/hv_util.c
index 6039217..d9460fdd 100644
--- a/drivers/staging/hv/hv_util.c
+++ b/drivers/staging/hv/hv_util.c
@@ -239,7 +239,8 @@ static void heartbeat_onchannelcallback(void *context)
* The devices managed by the util driver don't need any additional
* setup.
*/
-static int util_probe(struct hv_device *dev)
+static int util_probe(struct hv_device *dev,
+ const struct hv_vmbus_device_id *dev_id)
{
return 0;
}
diff --git a/drivers/staging/hv/hyperv.h b/drivers/staging/hv/hyperv.h
index c249811..caa3a7b 100644
--- a/drivers/staging/hv/hyperv.h
+++ b/drivers/staging/hv/hyperv.h
@@ -810,7 +810,7 @@ struct hv_driver {
struct device_driver driver;
- int (*probe)(struct hv_device *);
+ int (*probe)(struct hv_device *, const struct hv_vmbus_device_id *);
int (*remove)(struct hv_device *);
void (*shutdown)(struct hv_device *);
diff --git a/drivers/staging/hv/netvsc_drv.c b/drivers/staging/hv/netvsc_drv.c
index 30b9c80..d06cde2 100644
--- a/drivers/staging/hv/netvsc_drv.c
+++ b/drivers/staging/hv/netvsc_drv.c
@@ -329,7 +329,8 @@ static void netvsc_send_garp(struct work_struct *w)
}
-static int netvsc_probe(struct hv_device *dev)
+static int netvsc_probe(struct hv_device *dev,
+ const struct hv_vmbus_device_id *dev_id)
{
struct net_device *net = NULL;
struct net_device_context *net_device_ctx;
diff --git a/drivers/staging/hv/storvsc_drv.c b/drivers/staging/hv/storvsc_drv.c
index b0c4e56..fff1e5b 100644
--- a/drivers/staging/hv/storvsc_drv.c
+++ b/drivers/staging/hv/storvsc_drv.c
@@ -1380,7 +1380,8 @@ MODULE_DEVICE_TABLE(vmbus, id_table);
* storvsc_probe - Add a new device for this driver
*/
-static int storvsc_probe(struct hv_device *device)
+static int storvsc_probe(struct hv_device *device,
+ const struct hv_vmbus_device_id *dev_id)
{
int ret;
struct Scsi_Host *host;
diff --git a/drivers/staging/hv/vmbus_drv.c b/drivers/staging/hv/vmbus_drv.c
index 77f4373..2fccb1f 100644
--- a/drivers/staging/hv/vmbus_drv.c
+++ b/drivers/staging/hv/vmbus_drv.c
@@ -312,9 +312,11 @@ static int vmbus_probe(struct device *child_device)
struct hv_driver *drv =
drv_to_hv_drv(child_device->driver);
struct hv_device *dev = device_to_hv_device(child_device);
+ const struct hv_vmbus_device_id *dev_id;
+ dev_id = hv_vmbus_get_id(drv->id_table, dev->dev_type.b);
if (drv->probe) {
- ret = drv->probe(dev);
+ ret = drv->probe(dev, dev_id);
if (ret != 0)
pr_err("probe failed for device %s (%d)\n",
dev_name(child_device), ret);
--
1.7.4.1
^ permalink raw reply related
* [PATCH 01/20] Staging: hv: vmbus: Introduce a utility function to match hv_vmbus_device_id
From: K. Y. Srinivasan @ 2011-09-13 17:59 UTC (permalink / raw)
To: gregkh, linux-kernel, devel, virtualization
Cc: K. Y. Srinivasan, Haiyang Zhang
In-Reply-To: <1315936759-20623-1-git-send-email-kys@microsoft.com>
Introduce a utility function to match hv_vmbus_device_id.
Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
---
drivers/staging/hv/vmbus_drv.c | 23 ++++++++++++++++++-----
1 files changed, 18 insertions(+), 5 deletions(-)
diff --git a/drivers/staging/hv/vmbus_drv.c b/drivers/staging/hv/vmbus_drv.c
index 375e451..77f4373 100644
--- a/drivers/staging/hv/vmbus_drv.c
+++ b/drivers/staging/hv/vmbus_drv.c
@@ -272,6 +272,22 @@ static inline bool is_null_guid(const __u8 *guid)
return true;
}
+/*
+ * Return a matching hv_vmbus_device_id pointer.
+ * If there is no match, return NULL.
+ */
+static const struct hv_vmbus_device_id *hv_vmbus_get_id(
+ const struct hv_vmbus_device_id *id,
+ __u8 *guid)
+{
+ for (; !is_null_guid(id->guid); id++)
+ if (!memcmp(&id->guid, guid, sizeof(uuid_le)))
+ return id;
+
+ return NULL;
+}
+
+
/*
* vmbus_match - Attempt to match the specified device to the specified driver
@@ -280,12 +296,9 @@ static int vmbus_match(struct device *device, struct device_driver *driver)
{
struct hv_driver *drv = drv_to_hv_drv(driver);
struct hv_device *hv_dev = device_to_hv_device(device);
- const struct hv_vmbus_device_id *id_array = drv->id_table;
- for (; !is_null_guid(id_array->guid); id_array++)
- if (!memcmp(&id_array->guid, &hv_dev->dev_type.b,
- sizeof(uuid_le)))
- return 1;
+ if (hv_vmbus_get_id(drv->id_table, hv_dev->dev_type.b))
+ return 1;
return 0;
}
--
1.7.4.1
^ permalink raw reply related
* [PATCH 0000/0020] Staging: hv: Driver cleanup
From: K. Y. Srinivasan @ 2011-09-13 17:59 UTC (permalink / raw)
To: gregkh, linux-kernel, devel, virtualization; +Cc: K. Y. Srinivasan
Address Greg's VmBus audit comments:
1) Leverage driver_data field in struct hv_vmbus_device_id to
simplify driver code.
2) Make the util driver conform to the Linux Driver Model.
3) Get rid of the ext field in struct hv_device by using the
driver specific data functionality.
4) Implement vmbus specific wrapper functions for setting and getting
driver specific data..
5) Other general cleanup.
Regards,
K. Y
^ permalink raw reply
* RE: [PATCH 10/25] Staging: hv: vmbus: Return proper error code in vmbus_remove()
From: KY Srinivasan @ 2011-09-10 20:33 UTC (permalink / raw)
To: Greg KH
Cc: Greg KH, linux-kernel@vger.kernel.org,
devel@linuxdriverproject.org, virtualization@lists.osdl.org,
Haiyang Zhang
In-Reply-To: <20110910183336.GB30865@suse.de>
> -----Original Message-----
> From: Greg KH [mailto:gregkh@suse.de]
> Sent: Saturday, September 10, 2011 2:34 PM
> To: KY Srinivasan
> Cc: Greg KH; linux-kernel@vger.kernel.org; devel@linuxdriverproject.org;
> virtualization@lists.osdl.org; Haiyang Zhang
> Subject: Re: [PATCH 10/25] Staging: hv: vmbus: Return proper error code in
> vmbus_remove()
>
> On Sat, Sep 10, 2011 at 02:22:22PM +0000, KY Srinivasan wrote:
> >
> >
> > > -----Original Message-----
> > > From: Greg KH [mailto:greg@kroah.com]
> > > Sent: Friday, September 09, 2011 4:43 PM
> > > To: KY Srinivasan
> > > Cc: gregkh@suse.de; linux-kernel@vger.kernel.org;
> > > devel@linuxdriverproject.org; virtualization@lists.osdl.org; Haiyang Zhang
> > > Subject: Re: [PATCH 10/25] Staging: hv: vmbus: Return proper error code in
> > > vmbus_remove()
> > >
> > > On Thu, Sep 08, 2011 at 07:24:21AM -0700, K. Y. Srinivasan wrote:
> > > > Return proper error code in vmbus_remove().
> > > >
> > > > Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
> > > > Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
> > > > ---
> > > > drivers/staging/hv/vmbus_drv.c | 4 ++--
> > > > 1 files changed, 2 insertions(+), 2 deletions(-)
> > > >
> > > > diff --git a/drivers/staging/hv/vmbus_drv.c
> b/drivers/staging/hv/vmbus_drv.c
> > > > index b9aeb76..95d33a4 100644
> > > > --- a/drivers/staging/hv/vmbus_drv.c
> > > > +++ b/drivers/staging/hv/vmbus_drv.c
> > > > @@ -325,7 +325,7 @@ static int vmbus_probe(struct device *child_device)
> > > > */
> > > > static int vmbus_remove(struct device *child_device)
> > > > {
> > > > - int ret;
> > > > + int ret = 0;
> > >
> > > As remove functions can't fail, why return anything at all?
> > >
> > > Doesn't make sense, please fix.
> >
> > Greg,
> >
> > Looking at the struct bus_type, the remove function is not a void function.
>
> Yeah, but it's never checked, and most bus types just use a void
> function as the function can not fail (or, it's not allowed to at
> least.)
>
> > I was just fixing something that was broken in this function.
>
> That's fine, then you can add it to the list of things to change :)
Ok; I will do what is done in pci_device_remove().
Regards,
K. Y
^ permalink raw reply
* Re: [PATCH 09/25] Staging: hv: util: Perform some service specific de-initialization in util_remove()
From: Greg KH @ 2011-09-10 18:35 UTC (permalink / raw)
To: KY Srinivasan
Cc: virtualization@lists.osdl.org, Haiyang Zhang,
linux-kernel@vger.kernel.org, devel@linuxdriverproject.org
In-Reply-To: <6E21E5352C11B742B20C142EB499E048081DC4C7@TK5EX14MBXC128.redmond.corp.microsoft.com>
On Sat, Sep 10, 2011 at 02:31:15PM +0000, KY Srinivasan wrote:
> I will rework this to be more on the lines of what you had suggested; and yes,
> I remember my original promise! I want to re-spin these patches and send it to
> you as soon as possible. Which tree can I clone to get your latest check-ins; kernel.org
> still seems to have issues this morning. Have you checked in Olaf's patches.
I checked in one of Olaf's patches, but the others I told him needed to
be reworked to use KBUILD_MODNAME.
As for a public tree, no, sorry, my tree is not public until kernel.org
is back up and running, and I don't have any idea when that will be.
I'm out of the country all this week so responses from me is going to be
very delayed anyway. Hopefully when I return kernel.org will be up and
running and everyone can sync up properly at that time.
greg k-h
^ permalink raw reply
* Re: [PATCH 10/25] Staging: hv: vmbus: Return proper error code in vmbus_remove()
From: Greg KH @ 2011-09-10 18:33 UTC (permalink / raw)
To: KY Srinivasan
Cc: Greg KH, linux-kernel@vger.kernel.org,
devel@linuxdriverproject.org, virtualization@lists.osdl.org,
Haiyang Zhang
In-Reply-To: <6E21E5352C11B742B20C142EB499E048081DC4B3@TK5EX14MBXC128.redmond.corp.microsoft.com>
On Sat, Sep 10, 2011 at 02:22:22PM +0000, KY Srinivasan wrote:
>
>
> > -----Original Message-----
> > From: Greg KH [mailto:greg@kroah.com]
> > Sent: Friday, September 09, 2011 4:43 PM
> > To: KY Srinivasan
> > Cc: gregkh@suse.de; linux-kernel@vger.kernel.org;
> > devel@linuxdriverproject.org; virtualization@lists.osdl.org; Haiyang Zhang
> > Subject: Re: [PATCH 10/25] Staging: hv: vmbus: Return proper error code in
> > vmbus_remove()
> >
> > On Thu, Sep 08, 2011 at 07:24:21AM -0700, K. Y. Srinivasan wrote:
> > > Return proper error code in vmbus_remove().
> > >
> > > Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
> > > Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
> > > ---
> > > drivers/staging/hv/vmbus_drv.c | 4 ++--
> > > 1 files changed, 2 insertions(+), 2 deletions(-)
> > >
> > > diff --git a/drivers/staging/hv/vmbus_drv.c b/drivers/staging/hv/vmbus_drv.c
> > > index b9aeb76..95d33a4 100644
> > > --- a/drivers/staging/hv/vmbus_drv.c
> > > +++ b/drivers/staging/hv/vmbus_drv.c
> > > @@ -325,7 +325,7 @@ static int vmbus_probe(struct device *child_device)
> > > */
> > > static int vmbus_remove(struct device *child_device)
> > > {
> > > - int ret;
> > > + int ret = 0;
> >
> > As remove functions can't fail, why return anything at all?
> >
> > Doesn't make sense, please fix.
>
> Greg,
>
> Looking at the struct bus_type, the remove function is not a void function.
Yeah, but it's never checked, and most bus types just use a void
function as the function can not fail (or, it's not allowed to at
least.)
> I was just fixing something that was broken in this function.
That's fine, then you can add it to the list of things to change :)
greg k-h
^ permalink raw reply
* Re: [PATCH 18/25] Staging: hv: storvsc: Eliminate the usage of ext field in struct hv_device
From: Greg KH @ 2011-09-10 18:28 UTC (permalink / raw)
To: KY Srinivasan
Cc: Greg KH, linux-kernel@vger.kernel.org,
devel@linuxdriverproject.org, virtualization@lists.osdl.org,
Haiyang Zhang
In-Reply-To: <6E21E5352C11B742B20C142EB499E048081DC4A1@TK5EX14MBXC128.redmond.corp.microsoft.com>
On Sat, Sep 10, 2011 at 02:16:14PM +0000, KY Srinivasan wrote:
>
>
> > -----Original Message-----
> > From: Greg KH [mailto:greg@kroah.com]
> > Sent: Friday, September 09, 2011 4:45 PM
> > To: KY Srinivasan
> > Cc: gregkh@suse.de; linux-kernel@vger.kernel.org;
> > devel@linuxdriverproject.org; virtualization@lists.osdl.org; Haiyang Zhang
> > Subject: Re: [PATCH 18/25] Staging: hv: storvsc: Eliminate the usage of ext field in
> > struct hv_device
> >
> > On Thu, Sep 08, 2011 at 07:24:29AM -0700, K. Y. Srinivasan wrote:
> > > Now, eliminate the usage of ext field in struct hv_device for storvsc driver.
> > > We do this by registering pointer to struct storvsc_device as the driver
> > > specific data and eliminating the current usage of driver specific data to
> > > save and retrieve the pointer to struct Scsi_Host.
> > > Additionally, all access to the driver specific data is through
> > > the vmbus wrapper functions.
> > >
> > > Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
> > > Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
> > > ---
> > > drivers/staging/hv/storvsc_drv.c | 24 +++++++++++++++---------
> > > 1 files changed, 15 insertions(+), 9 deletions(-)
> > >
> > > diff --git a/drivers/staging/hv/storvsc_drv.c b/drivers/staging/hv/storvsc_drv.c
> > > index 57c1035..98d47cd 100644
> > > --- a/drivers/staging/hv/storvsc_drv.c
> > > +++ b/drivers/staging/hv/storvsc_drv.c
> > > @@ -266,6 +266,7 @@ struct storvsc_device {
> > > bool destroy;
> > > bool drain_notify;
> > > atomic_t num_outstanding_req;
> > > + struct Scsi_Host *host;
> >
> > You are properly reference counting this pointer, right?
>
> The scsi_host_alloc() which we use to allocate the host structure, gives us
> the needed reference.
Ok, thanks, I missed that. The casting though should be taken out,
otherwise the janitor project will just come along and clean it up
again...
greg k-h
^ permalink raw reply
* RE: [PATCH 09/25] Staging: hv: util: Perform some service specific de-initialization in util_remove()
From: KY Srinivasan @ 2011-09-10 14:31 UTC (permalink / raw)
To: Greg KH
Cc: devel@linuxdriverproject.org, Haiyang Zhang, gregkh@suse.de,
linux-kernel@vger.kernel.org, virtualization@lists.osdl.org
In-Reply-To: <20110909204240.GF19127@kroah.com>
> -----Original Message-----
> From: Greg KH [mailto:greg@kroah.com]
> Sent: Friday, September 09, 2011 4:43 PM
> To: KY Srinivasan
> Cc: gregkh@suse.de; linux-kernel@vger.kernel.org;
> devel@linuxdriverproject.org; virtualization@lists.osdl.org; Haiyang Zhang
> Subject: Re: [PATCH 09/25] Staging: hv: util: Perform some service specific de-
> initialization in util_remove()
>
> On Thu, Sep 08, 2011 at 07:24:20AM -0700, K. Y. Srinivasan wrote:
> > In preparation for modifying the util driver to fully conform to the
> > Linux Driver Model, perform some service specific de-initialization in
> > util_remove() as opposed to in exit_hyperv_utils() as is currently done.
> >
> >
> > Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
> > Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
> > ---
> > drivers/staging/hv/hv_util.c | 29 ++++++++++++++++++++++++-----
> > 1 files changed, 24 insertions(+), 5 deletions(-)
> >
> > diff --git a/drivers/staging/hv/hv_util.c b/drivers/staging/hv/hv_util.c
> > index b86128a..2475ab2 100644
> > --- a/drivers/staging/hv/hv_util.c
> > +++ b/drivers/staging/hv/hv_util.c
> > @@ -291,6 +291,30 @@ error:
> > static int util_remove(struct hv_device *dev,
> > const struct hv_vmbus_device_id *dev_id)
> > {
> > + int service = dev_id->driver_data;
> > +
> > + switch (service) {
> > + case HV_SHUTDOWN:
> > + kfree(shut_txf_buf);
> > + break;
>
> This switch and "static" pointers you need to free aren't needed at all
> if you do this code logic correctly (i.e. a per-device buffer.)
>
> {sigh}
>
> I'm stopping reviewing now, this is making me grumpy, someone owes me a
> bunch of beer...
Greg,
I will rework this to be more on the lines of what you had suggested; and yes,
I remember my original promise! I want to re-spin these patches and send it to
you as soon as possible. Which tree can I clone to get your latest check-ins; kernel.org
still seems to have issues this morning. Have you checked in Olaf's patches.
Thanks,
K. Y
^ permalink raw reply
* RE: [PATCH 10/25] Staging: hv: vmbus: Return proper error code in vmbus_remove()
From: KY Srinivasan @ 2011-09-10 14:22 UTC (permalink / raw)
To: Greg KH
Cc: devel@linuxdriverproject.org, Haiyang Zhang, gregkh@suse.de,
linux-kernel@vger.kernel.org, virtualization@lists.osdl.org
In-Reply-To: <20110909204309.GG19127@kroah.com>
> -----Original Message-----
> From: Greg KH [mailto:greg@kroah.com]
> Sent: Friday, September 09, 2011 4:43 PM
> To: KY Srinivasan
> Cc: gregkh@suse.de; linux-kernel@vger.kernel.org;
> devel@linuxdriverproject.org; virtualization@lists.osdl.org; Haiyang Zhang
> Subject: Re: [PATCH 10/25] Staging: hv: vmbus: Return proper error code in
> vmbus_remove()
>
> On Thu, Sep 08, 2011 at 07:24:21AM -0700, K. Y. Srinivasan wrote:
> > Return proper error code in vmbus_remove().
> >
> > Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
> > Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
> > ---
> > drivers/staging/hv/vmbus_drv.c | 4 ++--
> > 1 files changed, 2 insertions(+), 2 deletions(-)
> >
> > diff --git a/drivers/staging/hv/vmbus_drv.c b/drivers/staging/hv/vmbus_drv.c
> > index b9aeb76..95d33a4 100644
> > --- a/drivers/staging/hv/vmbus_drv.c
> > +++ b/drivers/staging/hv/vmbus_drv.c
> > @@ -325,7 +325,7 @@ static int vmbus_probe(struct device *child_device)
> > */
> > static int vmbus_remove(struct device *child_device)
> > {
> > - int ret;
> > + int ret = 0;
>
> As remove functions can't fail, why return anything at all?
>
> Doesn't make sense, please fix.
Greg,
Looking at the struct bus_type, the remove function is not a void function.
I was just fixing something that was broken in this function.
Regards,
K. Y
^ permalink raw reply
* RE: [PATCH 18/25] Staging: hv: storvsc: Eliminate the usage of ext field in struct hv_device
From: KY Srinivasan @ 2011-09-10 14:16 UTC (permalink / raw)
To: Greg KH
Cc: gregkh@suse.de, linux-kernel@vger.kernel.org,
devel@linuxdriverproject.org, virtualization@lists.osdl.org,
Haiyang Zhang
In-Reply-To: <20110909204451.GH19127@kroah.com>
> -----Original Message-----
> From: Greg KH [mailto:greg@kroah.com]
> Sent: Friday, September 09, 2011 4:45 PM
> To: KY Srinivasan
> Cc: gregkh@suse.de; linux-kernel@vger.kernel.org;
> devel@linuxdriverproject.org; virtualization@lists.osdl.org; Haiyang Zhang
> Subject: Re: [PATCH 18/25] Staging: hv: storvsc: Eliminate the usage of ext field in
> struct hv_device
>
> On Thu, Sep 08, 2011 at 07:24:29AM -0700, K. Y. Srinivasan wrote:
> > Now, eliminate the usage of ext field in struct hv_device for storvsc driver.
> > We do this by registering pointer to struct storvsc_device as the driver
> > specific data and eliminating the current usage of driver specific data to
> > save and retrieve the pointer to struct Scsi_Host.
> > Additionally, all access to the driver specific data is through
> > the vmbus wrapper functions.
> >
> > Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
> > Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
> > ---
> > drivers/staging/hv/storvsc_drv.c | 24 +++++++++++++++---------
> > 1 files changed, 15 insertions(+), 9 deletions(-)
> >
> > diff --git a/drivers/staging/hv/storvsc_drv.c b/drivers/staging/hv/storvsc_drv.c
> > index 57c1035..98d47cd 100644
> > --- a/drivers/staging/hv/storvsc_drv.c
> > +++ b/drivers/staging/hv/storvsc_drv.c
> > @@ -266,6 +266,7 @@ struct storvsc_device {
> > bool destroy;
> > bool drain_notify;
> > atomic_t num_outstanding_req;
> > + struct Scsi_Host *host;
>
> You are properly reference counting this pointer, right?
The scsi_host_alloc() which we use to allocate the host structure, gives us
the needed reference.
>
> > @@ -306,7 +307,8 @@ static inline struct storvsc_device
> *get_out_stor_device(
> > {
> > struct storvsc_device *stor_device;
> >
> > - stor_device = (struct storvsc_device *)device->ext;
> > + stor_device =
> > + (struct storvsc_device *)hv_get_drvdata(device);
>
> Casting is not needed at all.
>
> > @@ -1366,7 +1371,8 @@ static int storvsc_probe(struct hv_device *device,
> > stor_device->destroy = false;
> > init_waitqueue_head(&stor_device->waiting_to_drain);
> > stor_device->device = device;
> > - device->ext = stor_device;
> > + stor_device->host = host;
> > + hv_set_drvdata(device, stor_device);
>
> Lookie there, no reference count incremented, right? Or did I miss it
> somewhere else?
We are stashing the pointer to a structure on which we already have a reference
(that was established at the point of allocating the host).
Regards,
K. Y
^ permalink raw reply
* Re: [PATCH 18/25] Staging: hv: storvsc: Eliminate the usage of ext field in struct hv_device
From: Greg KH @ 2011-09-09 20:44 UTC (permalink / raw)
To: K. Y. Srinivasan
Cc: devel, Haiyang Zhang, gregkh, linux-kernel, virtualization
In-Reply-To: <1315491876-9554-18-git-send-email-kys@microsoft.com>
On Thu, Sep 08, 2011 at 07:24:29AM -0700, K. Y. Srinivasan wrote:
> Now, eliminate the usage of ext field in struct hv_device for storvsc driver.
> We do this by registering pointer to struct storvsc_device as the driver
> specific data and eliminating the current usage of driver specific data to
> save and retrieve the pointer to struct Scsi_Host.
> Additionally, all access to the driver specific data is through
> the vmbus wrapper functions.
>
> Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
> Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
> ---
> drivers/staging/hv/storvsc_drv.c | 24 +++++++++++++++---------
> 1 files changed, 15 insertions(+), 9 deletions(-)
>
> diff --git a/drivers/staging/hv/storvsc_drv.c b/drivers/staging/hv/storvsc_drv.c
> index 57c1035..98d47cd 100644
> --- a/drivers/staging/hv/storvsc_drv.c
> +++ b/drivers/staging/hv/storvsc_drv.c
> @@ -266,6 +266,7 @@ struct storvsc_device {
> bool destroy;
> bool drain_notify;
> atomic_t num_outstanding_req;
> + struct Scsi_Host *host;
You are properly reference counting this pointer, right?
> @@ -306,7 +307,8 @@ static inline struct storvsc_device *get_out_stor_device(
> {
> struct storvsc_device *stor_device;
>
> - stor_device = (struct storvsc_device *)device->ext;
> + stor_device =
> + (struct storvsc_device *)hv_get_drvdata(device);
Casting is not needed at all.
> @@ -1366,7 +1371,8 @@ static int storvsc_probe(struct hv_device *device,
> stor_device->destroy = false;
> init_waitqueue_head(&stor_device->waiting_to_drain);
> stor_device->device = device;
> - device->ext = stor_device;
> + stor_device->host = host;
> + hv_set_drvdata(device, stor_device);
Lookie there, no reference count incremented, right? Or did I miss it
somewhere else?
gotta love dynamic pointer lifetime rules...
greg k-h
^ permalink raw reply
* Re: [PATCH 10/25] Staging: hv: vmbus: Return proper error code in vmbus_remove()
From: Greg KH @ 2011-09-09 20:43 UTC (permalink / raw)
To: K. Y. Srinivasan
Cc: devel, Haiyang Zhang, gregkh, linux-kernel, virtualization
In-Reply-To: <1315491876-9554-10-git-send-email-kys@microsoft.com>
On Thu, Sep 08, 2011 at 07:24:21AM -0700, K. Y. Srinivasan wrote:
> Return proper error code in vmbus_remove().
>
> Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
> Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
> ---
> drivers/staging/hv/vmbus_drv.c | 4 ++--
> 1 files changed, 2 insertions(+), 2 deletions(-)
>
> diff --git a/drivers/staging/hv/vmbus_drv.c b/drivers/staging/hv/vmbus_drv.c
> index b9aeb76..95d33a4 100644
> --- a/drivers/staging/hv/vmbus_drv.c
> +++ b/drivers/staging/hv/vmbus_drv.c
> @@ -325,7 +325,7 @@ static int vmbus_probe(struct device *child_device)
> */
> static int vmbus_remove(struct device *child_device)
> {
> - int ret;
> + int ret = 0;
As remove functions can't fail, why return anything at all?
Doesn't make sense, please fix.
greg k-h
^ permalink raw reply
* Re: [PATCH 09/25] Staging: hv: util: Perform some service specific de-initialization in util_remove()
From: Greg KH @ 2011-09-09 20:42 UTC (permalink / raw)
To: K. Y. Srinivasan
Cc: devel, Haiyang Zhang, gregkh, linux-kernel, virtualization
In-Reply-To: <1315491876-9554-9-git-send-email-kys@microsoft.com>
On Thu, Sep 08, 2011 at 07:24:20AM -0700, K. Y. Srinivasan wrote:
> In preparation for modifying the util driver to fully conform to the
> Linux Driver Model, perform some service specific de-initialization in
> util_remove() as opposed to in exit_hyperv_utils() as is currently done.
>
>
> Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
> Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
> ---
> drivers/staging/hv/hv_util.c | 29 ++++++++++++++++++++++++-----
> 1 files changed, 24 insertions(+), 5 deletions(-)
>
> diff --git a/drivers/staging/hv/hv_util.c b/drivers/staging/hv/hv_util.c
> index b86128a..2475ab2 100644
> --- a/drivers/staging/hv/hv_util.c
> +++ b/drivers/staging/hv/hv_util.c
> @@ -291,6 +291,30 @@ error:
> static int util_remove(struct hv_device *dev,
> const struct hv_vmbus_device_id *dev_id)
> {
> + int service = dev_id->driver_data;
> +
> + switch (service) {
> + case HV_SHUTDOWN:
> + kfree(shut_txf_buf);
> + break;
This switch and "static" pointers you need to free aren't needed at all
if you do this code logic correctly (i.e. a per-device buffer.)
{sigh}
I'm stopping reviewing now, this is making me grumpy, someone owes me a
bunch of beer...
greg k-h
^ permalink raw reply
* Re: [PATCH 06/25] Staging: hv: storvsc: Use the driver_data to identify ide
From: Greg KH @ 2011-09-09 20:41 UTC (permalink / raw)
To: K. Y. Srinivasan
Cc: gregkh, linux-kernel, devel, virtualization, Haiyang Zhang
In-Reply-To: <1315491876-9554-6-git-send-email-kys@microsoft.com>
On Thu, Sep 08, 2011 at 07:24:17AM -0700, K. Y. Srinivasan wrote:
> Use the driver_data to identify ide devices in storvsc_probe().
>
> Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
> Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
> ---
> drivers/staging/hv/storvsc_drv.c | 13 +++++--------
> 1 files changed, 5 insertions(+), 8 deletions(-)
>
> diff --git a/drivers/staging/hv/storvsc_drv.c b/drivers/staging/hv/storvsc_drv.c
> index fff1e5b..e2c63e5 100644
> --- a/drivers/staging/hv/storvsc_drv.c
> +++ b/drivers/staging/hv/storvsc_drv.c
> @@ -1366,10 +1366,12 @@ static struct scsi_host_template scsi_driver = {
> static const struct hv_vmbus_device_id id_table[] = {
> /* SCSI guid */
> { VMBUS_DEVICE(0xd9, 0x63, 0x61, 0xba, 0xa1, 0x04, 0x29, 0x4d,
> - 0xb6, 0x05, 0x72, 0xe2, 0xff, 0xb1, 0xdc, 0x7f) },
> + 0xb6, 0x05, 0x72, 0xe2, 0xff, 0xb1, 0xdc, 0x7f)
> + .driver_data = 0 },
What does 0 mean? That's the "default" here, right?
> /* IDE guid */
> { VMBUS_DEVICE(0x32, 0x26, 0x41, 0x32, 0xcb, 0x86, 0xa2, 0x44,
> - 0x9b, 0x5c, 0x50, 0xd1, 0x41, 0x73, 0x54, 0xf5) },
> + 0x9b, 0x5c, 0x50, 0xd1, 0x41, 0x73, 0x54, 0xf5)
> + .driver_data = 1 },
What does 1 mean?
And yes, I can guess, but please, will you really remember this in 2
years?
enums are your friend...
PLEASE make your code easier to maintain for the person who has to come
clean it up after you, which is usually yourself so you are only making
your own life easier.
greg k-h
^ permalink raw reply
* Re: [PATCH 07/25] Staging: hv: vmbus: Change the signature of struct hv_driver remove() function
From: Greg KH @ 2011-09-09 20:40 UTC (permalink / raw)
To: K. Y. Srinivasan
Cc: gregkh, linux-kernel, devel, virtualization, Haiyang Zhang
In-Reply-To: <1315491876-9554-7-git-send-email-kys@microsoft.com>
On Thu, Sep 08, 2011 at 07:24:18AM -0700, K. Y. Srinivasan wrote:
> In preparation for leveraging the driver_data in struct
> hv_vmbus_device_id, change the signature of struct hv_driver remove() function.
Why? This shouldn't be needed at remove() time as the driver already
has saved off the needed id information in its probe function, if it
needed it.
> --- a/drivers/staging/hv/vmbus_drv.c
> +++ b/drivers/staging/hv/vmbus_drv.c
> @@ -329,12 +329,19 @@ static int vmbus_remove(struct device *child_device)
> struct hv_driver *drv;
>
> struct hv_device *dev = device_to_hv_device(child_device);
> + const struct hv_vmbus_device_id *dev_id;
>
> if (child_device->driver) {
> drv = drv_to_hv_drv(child_device->driver);
> + dev_id = drv->id_table;
> +
> + for (; !is_null_guid(dev_id->guid); dev_id++)
> + if (!memcmp(&dev_id->guid, &dev->dev_type.b,
> + sizeof(uuid_le)))
> + break;
Even though it is wrong, look you duplicated the matching logic again!
ick.
greg k-h
^ permalink raw reply
* Re: [PATCH 05/25] Staging: hv: vmbus: Change the signature of struct hv_driver probe function
From: Greg KH @ 2011-09-09 20:38 UTC (permalink / raw)
To: K. Y. Srinivasan
Cc: devel, Haiyang Zhang, gregkh, linux-kernel, virtualization
In-Reply-To: <1315491876-9554-5-git-send-email-kys@microsoft.com>
On Thu, Sep 08, 2011 at 07:24:16AM -0700, K. Y. Srinivasan wrote:
> --- a/drivers/staging/hv/vmbus_drv.c
> +++ b/drivers/staging/hv/vmbus_drv.c
> @@ -299,9 +299,15 @@ static int vmbus_probe(struct device *child_device)
> struct hv_driver *drv =
> drv_to_hv_drv(child_device->driver);
> struct hv_device *dev = device_to_hv_device(child_device);
> + const struct hv_vmbus_device_id *dev_id = drv->id_table;
> +
> + for (; !is_null_guid(dev_id->guid); dev_id++)
> + if (!memcmp(&dev_id->guid, &dev->dev_type.b,
> + sizeof(uuid_le)))
> + break;
Don't duplicate this section of code twice (at least) in the driver.
Make it a "vmbus_match_device()" function that returns the proper
hv_vmbus_device_id * to do something with.
thanks,
greg k-h
^ permalink raw reply
* Re: [PATCH 1/1] Staging: hv: Integrate the time source driver with Hyper-V detection code
From: Greg KH @ 2011-09-09 20:32 UTC (permalink / raw)
To: K. Y. Srinivasan
Cc: devel, Haiyang Zhang, gregkh, linux-kernel, virtualization
In-Reply-To: <1315434310-4827-1-git-send-email-kys@microsoft.com>
On Wed, Sep 07, 2011 at 03:25:10PM -0700, K. Y. Srinivasan wrote:
> The Hyper-V timesource driver is best integrated with Hyper-V detection code
> since: (a) Linux guests running on Hyper-V need this timesource and (b)
> by integrating with Hyper-V detection, we could significantly minimize the
> code in the timesource driver.
>
> Signed-off-by: K. Y. Srinivasan <kys@microsoft.com>
> Signed-off-by: Haiyang Zhang <haiyangz@microsoft.com>
Acked-by: Greg Kroah-Hartman <gregkh@suse.de>
^ permalink raw reply
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox