aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/s390
diff options
context:
space:
mode:
authorStefan Haberland <stefan.haberland@de.ibm.com>2012-01-18 12:03:41 -0500
committerMartin Schwidefsky <schwidefsky@de.ibm.com>2012-01-18 12:03:42 -0500
commitf16330316321d1c388d13096f6858f5d2dac29dc (patch)
tree0dda4b86553b3e5881c8a53391f24210b17a2eb6 /drivers/s390
parentf9f8d02fae0dc47d8868fd069bb88d12f8d1d71f (diff)
[S390] dasd: revalidate server for new pathgroup
If a pathgroup is established we get an event and have to revalidate the server to propagate supported features like PAV and enable them. Signed-off-by: Stefan Haberland <stefan.haberland@de.ibm.com> Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
Diffstat (limited to 'drivers/s390')
-rw-r--r--drivers/s390/block/dasd.c6
-rw-r--r--drivers/s390/block/dasd_eckd.c22
-rw-r--r--drivers/s390/block/dasd_int.h2
3 files changed, 30 insertions, 0 deletions
diff --git a/drivers/s390/block/dasd.c b/drivers/s390/block/dasd.c
index eef27a197c00..110137e7ec81 100644
--- a/drivers/s390/block/dasd.c
+++ b/drivers/s390/block/dasd.c
@@ -3261,6 +3261,12 @@ void dasd_generic_path_event(struct ccw_device *cdev, int *path_event)
3261 device->path_data.tbvpm |= eventlpm; 3261 device->path_data.tbvpm |= eventlpm;
3262 dasd_schedule_device_bh(device); 3262 dasd_schedule_device_bh(device);
3263 } 3263 }
3264 if (path_event[chp] & PE_PATHGROUP_ESTABLISHED) {
3265 DBF_DEV_EVENT(DBF_WARNING, device, "%s",
3266 "Pathgroup re-established\n");
3267 if (device->discipline->kick_validate)
3268 device->discipline->kick_validate(device);
3269 }
3264 } 3270 }
3265 dasd_put_device(device); 3271 dasd_put_device(device);
3266} 3272}
diff --git a/drivers/s390/block/dasd_eckd.c b/drivers/s390/block/dasd_eckd.c
index 1b6e7ea9347f..70880be26015 100644
--- a/drivers/s390/block/dasd_eckd.c
+++ b/drivers/s390/block/dasd_eckd.c
@@ -1550,6 +1550,24 @@ static void dasd_eckd_validate_server(struct dasd_device *device)
1550 "returned rc=%d", private->uid.ssid, rc); 1550 "returned rc=%d", private->uid.ssid, rc);
1551} 1551}
1552 1552
1553/*
1554 * worker to do a validate server in case of a lost pathgroup
1555 */
1556static void dasd_eckd_do_validate_server(struct work_struct *work)
1557{
1558 struct dasd_device *device = container_of(work, struct dasd_device,
1559 kick_validate);
1560 dasd_eckd_validate_server(device);
1561 dasd_put_device(device);
1562}
1563
1564static void dasd_eckd_kick_validate_server(struct dasd_device *device)
1565{
1566 dasd_get_device(device);
1567 /* queue call to do_validate_server to the kernel event daemon. */
1568 schedule_work(&device->kick_validate);
1569}
1570
1553static u32 get_fcx_max_data(struct dasd_device *device) 1571static u32 get_fcx_max_data(struct dasd_device *device)
1554{ 1572{
1555#if defined(CONFIG_64BIT) 1573#if defined(CONFIG_64BIT)
@@ -1595,6 +1613,9 @@ dasd_eckd_check_characteristics(struct dasd_device *device)
1595 int readonly; 1613 int readonly;
1596 unsigned long value; 1614 unsigned long value;
1597 1615
1616 /* setup work queue for validate server*/
1617 INIT_WORK(&device->kick_validate, dasd_eckd_do_validate_server);
1618
1598 if (!ccw_device_is_pathgroup(device->cdev)) { 1619 if (!ccw_device_is_pathgroup(device->cdev)) {
1599 dev_warn(&device->cdev->dev, 1620 dev_warn(&device->cdev->dev,
1600 "A channel path group could not be established\n"); 1621 "A channel path group could not be established\n");
@@ -4259,6 +4280,7 @@ static struct dasd_discipline dasd_eckd_discipline = {
4259 .restore = dasd_eckd_restore_device, 4280 .restore = dasd_eckd_restore_device,
4260 .reload = dasd_eckd_reload_device, 4281 .reload = dasd_eckd_reload_device,
4261 .get_uid = dasd_eckd_get_uid, 4282 .get_uid = dasd_eckd_get_uid,
4283 .kick_validate = dasd_eckd_kick_validate_server,
4262}; 4284};
4263 4285
4264static int __init 4286static int __init
diff --git a/drivers/s390/block/dasd_int.h b/drivers/s390/block/dasd_int.h
index afe8c33422ed..33a6743ddc55 100644
--- a/drivers/s390/block/dasd_int.h
+++ b/drivers/s390/block/dasd_int.h
@@ -355,6 +355,7 @@ struct dasd_discipline {
355 int (*reload) (struct dasd_device *); 355 int (*reload) (struct dasd_device *);
356 356
357 int (*get_uid) (struct dasd_device *, struct dasd_uid *); 357 int (*get_uid) (struct dasd_device *, struct dasd_uid *);
358 void (*kick_validate) (struct dasd_device *);
358}; 359};
359 360
360extern struct dasd_discipline *dasd_diag_discipline_pointer; 361extern struct dasd_discipline *dasd_diag_discipline_pointer;
@@ -455,6 +456,7 @@ struct dasd_device {
455 struct work_struct kick_work; 456 struct work_struct kick_work;
456 struct work_struct restore_device; 457 struct work_struct restore_device;
457 struct work_struct reload_device; 458 struct work_struct reload_device;
459 struct work_struct kick_validate;
458 struct timer_list timer; 460 struct timer_list timer;
459 461
460 debug_info_t *debug_area; 462 debug_info_t *debug_area;