summaryrefslogtreecommitdiff
path: root/drivers/staging/hv/storvsc.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/staging/hv/storvsc.c')
-rw-r--r--drivers/staging/hv/storvsc.c152
1 files changed, 84 insertions, 68 deletions
diff --git a/drivers/staging/hv/storvsc.c b/drivers/staging/hv/storvsc.c
index 9295113e09b9..e2ad72924184 100644
--- a/drivers/staging/hv/storvsc.c
+++ b/drivers/staging/hv/storvsc.c
@@ -19,11 +19,13 @@
* Hank Janssen <hjanssen@microsoft.com>
*/
#include <linux/kernel.h>
+#include <linux/sched.h>
+#include <linux/wait.h>
#include <linux/string.h>
#include <linux/slab.h>
#include <linux/mm.h>
#include <linux/delay.h>
-#include "osd.h"
+#include "hv_api.h"
#include "logging.h"
#include "storvsc_api.h"
#include "vmbus_packet_format.h"
@@ -38,7 +40,8 @@ struct storvsc_request_extension {
struct hv_device *device;
/* Synchronize the request/response if needed */
- struct osd_waitevent *wait_event;
+ int wait_condition;
+ wait_queue_head_t wait_event;
struct vstor_packet vstor_packet;
};
@@ -94,7 +97,7 @@ static inline struct storvsc_device *alloc_stor_device(struct hv_device *device)
atomic_cmpxchg(&stor_device->ref_count, 0, 2);
stor_device->device = device;
- device->Extension = stor_device;
+ device->ext = stor_device;
return stor_device;
}
@@ -110,7 +113,7 @@ static inline struct storvsc_device *get_stor_device(struct hv_device *device)
{
struct storvsc_device *stor_device;
- stor_device = (struct storvsc_device *)device->Extension;
+ stor_device = (struct storvsc_device *)device->ext;
if (stor_device && atomic_read(&stor_device->ref_count) > 1)
atomic_inc(&stor_device->ref_count);
else
@@ -125,7 +128,7 @@ static inline struct storvsc_device *must_get_stor_device(
{
struct storvsc_device *stor_device;
- stor_device = (struct storvsc_device *)device->Extension;
+ stor_device = (struct storvsc_device *)device->ext;
if (stor_device && atomic_read(&stor_device->ref_count))
atomic_inc(&stor_device->ref_count);
else
@@ -138,7 +141,7 @@ static inline void put_stor_device(struct hv_device *device)
{
struct storvsc_device *stor_device;
- stor_device = (struct storvsc_device *)device->Extension;
+ stor_device = (struct storvsc_device *)device->ext;
/* ASSERT(stor_device); */
atomic_dec(&stor_device->ref_count);
@@ -151,7 +154,7 @@ static inline struct storvsc_device *release_stor_device(
{
struct storvsc_device *stor_device;
- stor_device = (struct storvsc_device *)device->Extension;
+ stor_device = (struct storvsc_device *)device->ext;
/* ASSERT(stor_device); */
/* Busy wait until the ref drop to 2, then set it to 1 */
@@ -167,14 +170,14 @@ static inline struct storvsc_device *final_release_stor_device(
{
struct storvsc_device *stor_device;
- stor_device = (struct storvsc_device *)device->Extension;
+ stor_device = (struct storvsc_device *)device->ext;
/* ASSERT(stor_device); */
/* Busy wait until the ref drop to 1, then set it to 0 */
while (atomic_cmpxchg(&stor_device->ref_count, 1, 0) != 1)
udelay(100);
- device->Extension = NULL;
+ device->ext = NULL;
return stor_device;
}
@@ -200,40 +203,38 @@ static int stor_vsc_channel_init(struct hv_device *device)
* channel
*/
memset(request, 0, sizeof(struct storvsc_request_extension));
- request->wait_event = osd_waitevent_create();
- if (!request->wait_event) {
- ret = -ENOMEM;
- goto nomem;
- }
-
+ init_waitqueue_head(&request->wait_event);
vstor_packet->operation = VSTOR_OPERATION_BEGIN_INITIALIZATION;
vstor_packet->flags = REQUEST_COMPLETION_FLAG;
- /*SpinlockAcquire(gDriverExt.packetListLock);
- INSERT_TAIL_LIST(&gDriverExt.packetList, &packet->listEntry.entry);
- SpinlockRelease(gDriverExt.packetListLock);*/
-
DPRINT_INFO(STORVSC, "BEGIN_INITIALIZATION_OPERATION...");
+ request->wait_condition = 0;
ret = vmbus_sendpacket(device->channel, vstor_packet,
sizeof(struct vstor_packet),
(unsigned long)request,
- VmbusPacketTypeDataInBand,
+ VM_PKT_DATA_INBAND,
VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
if (ret != 0) {
DPRINT_ERR(STORVSC,
"unable to send BEGIN_INITIALIZATION_OPERATION");
- goto Cleanup;
+ goto cleanup;
+ }
+
+ wait_event_timeout(request->wait_event, request->wait_condition,
+ msecs_to_jiffies(1000));
+ if (request->wait_condition == 0) {
+ ret = -ETIMEDOUT;
+ goto cleanup;
}
- osd_waitevent_wait(request->wait_event);
if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO ||
vstor_packet->status != 0) {
DPRINT_ERR(STORVSC, "BEGIN_INITIALIZATION_OPERATION failed "
"(op %d status 0x%x)",
vstor_packet->operation, vstor_packet->status);
- goto Cleanup;
+ goto cleanup;
}
DPRINT_INFO(STORVSC, "QUERY_PROTOCOL_VERSION_OPERATION...");
@@ -246,18 +247,24 @@ static int stor_vsc_channel_init(struct hv_device *device)
vstor_packet->version.major_minor = VMSTOR_PROTOCOL_VERSION_CURRENT;
FILL_VMSTOR_REVISION(vstor_packet->version.revision);
+ request->wait_condition = 0;
ret = vmbus_sendpacket(device->channel, vstor_packet,
sizeof(struct vstor_packet),
(unsigned long)request,
- VmbusPacketTypeDataInBand,
+ VM_PKT_DATA_INBAND,
VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
if (ret != 0) {
DPRINT_ERR(STORVSC,
"unable to send BEGIN_INITIALIZATION_OPERATION");
- goto Cleanup;
+ goto cleanup;
}
- osd_waitevent_wait(request->wait_event);
+ wait_event_timeout(request->wait_event, request->wait_condition,
+ msecs_to_jiffies(1000));
+ if (request->wait_condition == 0) {
+ ret = -ETIMEDOUT;
+ goto cleanup;
+ }
/* TODO: Check returned version */
if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO ||
@@ -265,7 +272,7 @@ static int stor_vsc_channel_init(struct hv_device *device)
DPRINT_ERR(STORVSC, "QUERY_PROTOCOL_VERSION_OPERATION failed "
"(op %d status 0x%x)",
vstor_packet->operation, vstor_packet->status);
- goto Cleanup;
+ goto cleanup;
}
/* Query channel properties */
@@ -277,19 +284,25 @@ static int stor_vsc_channel_init(struct hv_device *device)
vstor_packet->storage_channel_properties.port_number =
stor_device->port_number;
+ request->wait_condition = 0;
ret = vmbus_sendpacket(device->channel, vstor_packet,
sizeof(struct vstor_packet),
(unsigned long)request,
- VmbusPacketTypeDataInBand,
+ VM_PKT_DATA_INBAND,
VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
if (ret != 0) {
DPRINT_ERR(STORVSC,
"unable to send QUERY_PROPERTIES_OPERATION");
- goto Cleanup;
+ goto cleanup;
}
- osd_waitevent_wait(request->wait_event);
+ wait_event_timeout(request->wait_event, request->wait_condition,
+ msecs_to_jiffies(1000));
+ if (request->wait_condition == 0) {
+ ret = -ETIMEDOUT;
+ goto cleanup;
+ }
/* TODO: Check returned version */
if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO ||
@@ -297,7 +310,7 @@ static int stor_vsc_channel_init(struct hv_device *device)
DPRINT_ERR(STORVSC, "QUERY_PROPERTIES_OPERATION failed "
"(op %d status 0x%x)",
vstor_packet->operation, vstor_packet->status);
- goto Cleanup;
+ goto cleanup;
}
stor_device->path_id = vstor_packet->storage_channel_properties.path_id;
@@ -314,34 +327,37 @@ static int stor_vsc_channel_init(struct hv_device *device)
vstor_packet->operation = VSTOR_OPERATION_END_INITIALIZATION;
vstor_packet->flags = REQUEST_COMPLETION_FLAG;
+ request->wait_condition = 0;
ret = vmbus_sendpacket(device->channel, vstor_packet,
sizeof(struct vstor_packet),
(unsigned long)request,
- VmbusPacketTypeDataInBand,
+ VM_PKT_DATA_INBAND,
VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
if (ret != 0) {
DPRINT_ERR(STORVSC,
"unable to send END_INITIALIZATION_OPERATION");
- goto Cleanup;
+ goto cleanup;
}
- osd_waitevent_wait(request->wait_event);
+ wait_event_timeout(request->wait_event, request->wait_condition,
+ msecs_to_jiffies(1000));
+ if (request->wait_condition == 0) {
+ ret = -ETIMEDOUT;
+ goto cleanup;
+ }
if (vstor_packet->operation != VSTOR_OPERATION_COMPLETE_IO ||
vstor_packet->status != 0) {
DPRINT_ERR(STORVSC, "END_INITIALIZATION_OPERATION failed "
"(op %d status 0x%x)",
vstor_packet->operation, vstor_packet->status);
- goto Cleanup;
+ goto cleanup;
}
DPRINT_INFO(STORVSC, "**** storage channel up and running!! ****");
-Cleanup:
- kfree(request->wait_event);
- request->wait_event = NULL;
-nomem:
+cleanup:
put_stor_device(device);
return ret;
}
@@ -437,7 +453,7 @@ static void stor_vsc_on_channel_callback(void *context)
struct storvsc_device *stor_device;
u32 bytes_recvd;
u64 request_id;
- unsigned char packet[ALIGN_UP(sizeof(struct vstor_packet), 8)];
+ unsigned char packet[ALIGN(sizeof(struct vstor_packet), 8)];
struct storvsc_request_extension *request;
int ret;
@@ -452,7 +468,7 @@ static void stor_vsc_on_channel_callback(void *context)
do {
ret = vmbus_recvpacket(device->channel, packet,
- ALIGN_UP(sizeof(struct vstor_packet), 8),
+ ALIGN(sizeof(struct vstor_packet), 8),
&bytes_recvd, &request_id);
if (ret == 0 && bytes_recvd > 0) {
DPRINT_DBG(STORVSC, "receive %d bytes - tid %llx",
@@ -476,8 +492,8 @@ static void stor_vsc_on_channel_callback(void *context)
memcpy(&request->vstor_packet, packet,
sizeof(struct vstor_packet));
-
- osd_waitevent_set(request->wait_event);
+ request->wait_condition = 1;
+ wake_up(&request->wait_event);
} else {
stor_vsc_on_receive(device,
(struct vstor_packet *)packet,
@@ -499,7 +515,7 @@ static int stor_vsc_connect_to_vsp(struct hv_device *device)
struct storvsc_driver_object *stor_driver;
int ret;
- stor_driver = (struct storvsc_driver_object *)device->Driver;
+ stor_driver = (struct storvsc_driver_object *)device->drv;
memset(&props, 0, sizeof(struct vmstorage_channel_properties));
/* Open the channel */
@@ -539,7 +555,7 @@ static int stor_vsc_on_device_add(struct hv_device *device,
stor_device = alloc_stor_device(device);
if (!stor_device) {
ret = -1;
- goto Cleanup;
+ goto cleanup;
}
/* Save the channel properties to our storvsc channel */
@@ -569,7 +585,7 @@ static int stor_vsc_on_device_add(struct hv_device *device,
stor_device->port_number, stor_device->path_id,
stor_device->target_id);
-Cleanup:
+cleanup:
return ret;
}
@@ -581,7 +597,7 @@ static int stor_vsc_on_device_remove(struct hv_device *device)
struct storvsc_device *stor_device;
DPRINT_INFO(STORVSC, "disabling storage device (%p)...",
- device->Extension);
+ device->ext);
stor_device = release_stor_device(device);
@@ -597,7 +613,7 @@ static int stor_vsc_on_device_remove(struct hv_device *device)
}
DPRINT_INFO(STORVSC, "removing storage device (%p)...",
- device->Extension);
+ device->ext);
stor_device = final_release_stor_device(device);
@@ -629,31 +645,31 @@ int stor_vsc_on_host_reset(struct hv_device *device)
request = &stor_device->reset_request;
vstor_packet = &request->vstor_packet;
- request->wait_event = osd_waitevent_create();
- if (!request->wait_event) {
- ret = -ENOMEM;
- goto Cleanup;
- }
+ init_waitqueue_head(&request->wait_event);
vstor_packet->operation = VSTOR_OPERATION_RESET_BUS;
vstor_packet->flags = REQUEST_COMPLETION_FLAG;
vstor_packet->vm_srb.path_id = stor_device->path_id;
+ request->wait_condition = 0;
ret = vmbus_sendpacket(device->channel, vstor_packet,
sizeof(struct vstor_packet),
(unsigned long)&stor_device->reset_request,
- VmbusPacketTypeDataInBand,
+ VM_PKT_DATA_INBAND,
VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
if (ret != 0) {
DPRINT_ERR(STORVSC, "Unable to send reset packet %p ret %d",
vstor_packet, ret);
- goto Cleanup;
+ goto cleanup;
}
- /* FIXME: Add a timeout */
- osd_waitevent_wait(request->wait_event);
+ wait_event_timeout(request->wait_event, request->wait_condition,
+ msecs_to_jiffies(1000));
+ if (request->wait_condition == 0) {
+ ret = -ETIMEDOUT;
+ goto cleanup;
+ }
- kfree(request->wait_event);
DPRINT_INFO(STORVSC, "host adapter reset completed");
/*
@@ -661,7 +677,7 @@ int stor_vsc_on_host_reset(struct hv_device *device)
* should have been flushed out and return to us
*/
-Cleanup:
+cleanup:
put_stor_device(device);
return ret;
}
@@ -687,7 +703,7 @@ static int stor_vsc_on_io_request(struct hv_device *device,
request_extension);
DPRINT_DBG(STORVSC, "req %p len %d bus %d, target %d, lun %d cdblen %d",
- request, request->data_buffer.Length, request->bus,
+ request, request->data_buffer.len, request->bus,
request->target_id, request->lun_id, request->cdb_len);
if (!stor_device) {
@@ -720,7 +736,7 @@ static int stor_vsc_on_io_request(struct hv_device *device,
memcpy(&vstor_packet->vm_srb.cdb, request->cdb, request->cdb_len);
vstor_packet->vm_srb.data_in = request->type;
- vstor_packet->vm_srb.data_transfer_length = request->data_buffer.Length;
+ vstor_packet->vm_srb.data_transfer_length = request->data_buffer.len;
vstor_packet->operation = VSTOR_OPERATION_EXECUTE_SRB;
@@ -734,7 +750,7 @@ static int stor_vsc_on_io_request(struct hv_device *device,
vstor_packet->vm_srb.sense_info_length,
vstor_packet->vm_srb.cdb_length);
- if (request_extension->request->data_buffer.Length) {
+ if (request_extension->request->data_buffer.len) {
ret = vmbus_sendpacket_multipagebuffer(device->channel,
&request_extension->request->data_buffer,
vstor_packet,
@@ -744,7 +760,7 @@ static int stor_vsc_on_io_request(struct hv_device *device,
ret = vmbus_sendpacket(device->channel, vstor_packet,
sizeof(struct vstor_packet),
(unsigned long)request_extension,
- VmbusPacketTypeDataInBand,
+ VM_PKT_DATA_INBAND,
VMBUS_DATA_PACKET_FLAG_COMPLETION_REQUESTED);
}
@@ -788,7 +804,7 @@ int stor_vsc_initialize(struct hv_driver *driver)
/* ASSERT(stor_driver->RingBufferSize >= (PAGE_SIZE << 1)); */
driver->name = g_driver_name;
- memcpy(&driver->deviceType, &gStorVscDeviceType,
+ memcpy(&driver->dev_type, &gStorVscDeviceType,
sizeof(struct hv_guid));
stor_driver->request_ext_size =
@@ -802,7 +818,7 @@ int stor_vsc_initialize(struct hv_driver *driver)
*/
stor_driver->max_outstanding_req_per_channel =
((stor_driver->ring_buffer_size - PAGE_SIZE) /
- ALIGN_UP(MAX_MULTIPAGE_BUFFER_PACKET +
+ ALIGN(MAX_MULTIPAGE_BUFFER_PACKET +
sizeof(struct vstor_packet) + sizeof(u64),
sizeof(u64)));
@@ -811,9 +827,9 @@ int stor_vsc_initialize(struct hv_driver *driver)
STORVSC_MAX_IO_REQUESTS);
/* Setup the dispatch table */
- stor_driver->base.OnDeviceAdd = stor_vsc_on_device_add;
- stor_driver->base.OnDeviceRemove = stor_vsc_on_device_remove;
- stor_driver->base.OnCleanup = stor_vsc_on_cleanup;
+ stor_driver->base.dev_add = stor_vsc_on_device_add;
+ stor_driver->base.dev_rm = stor_vsc_on_device_remove;
+ stor_driver->base.cleanup = stor_vsc_on_cleanup;
stor_driver->on_io_request = stor_vsc_on_io_request;