summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--drivers/s390/net/lcs.c74
1 files changed, 65 insertions, 9 deletions
diff --git a/drivers/s390/net/lcs.c b/drivers/s390/net/lcs.c
index a45bc24eb5f9..07a25c3f94b6 100644
--- a/drivers/s390/net/lcs.c
+++ b/drivers/s390/net/lcs.c
@@ -1,15 +1,12 @@
/*
- * linux/drivers/s390/net/lcs.c
- *
* Linux for S/390 Lan Channel Station Network Driver
*
- * Copyright (C) 1999-2001 IBM Deutschland Entwicklung GmbH,
- * IBM Corporation
- * Author(s): Original Code written by
- * DJ Barrow (djbarrow@de.ibm.com,barrow_dj@yahoo.com)
- * Rewritten by
- * Frank Pavlic (fpavlic@de.ibm.com) and
- * Martin Schwidefsky <schwidefsky@de.ibm.com>
+ * Copyright IBM Corp. 1999, 2009
+ * Author(s): Original Code written by
+ * DJ Barrow <djbarrow@de.ibm.com,barrow_dj@yahoo.com>
+ * Rewritten by
+ * Frank Pavlic <fpavlic@de.ibm.com> and
+ * Martin Schwidefsky <schwidefsky@de.ibm.com>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -2313,6 +2310,60 @@ lcs_remove_device(struct ccwgroup_device *ccwgdev)
put_device(&ccwgdev->dev);
}
+static int lcs_pm_suspend(struct lcs_card *card)
+{
+ if (card->dev)
+ netif_device_detach(card->dev);
+ lcs_set_allowed_threads(card, 0);
+ lcs_wait_for_threads(card, 0xffffffff);
+ if (card->state != DEV_STATE_DOWN)
+ __lcs_shutdown_device(card->gdev, 1);
+ return 0;
+}
+
+static int lcs_pm_resume(struct lcs_card *card)
+{
+ int rc = 0;
+
+ if (card->state == DEV_STATE_RECOVER)
+ rc = lcs_new_device(card->gdev);
+ if (card->dev)
+ netif_device_attach(card->dev);
+ if (rc) {
+ dev_warn(&card->gdev->dev, "The lcs device driver "
+ "failed to recover the device\n");
+ }
+ return rc;
+}
+
+static int lcs_prepare(struct ccwgroup_device *gdev)
+{
+ return 0;
+}
+
+static void lcs_complete(struct ccwgroup_device *gdev)
+{
+ return;
+}
+
+static int lcs_freeze(struct ccwgroup_device *gdev)
+{
+ struct lcs_card *card = dev_get_drvdata(&gdev->dev);
+ return lcs_pm_suspend(card);
+}
+
+static int lcs_thaw(struct ccwgroup_device *gdev)
+{
+ struct lcs_card *card = dev_get_drvdata(&gdev->dev);
+ return lcs_pm_resume(card);
+}
+
+static int lcs_restore(struct ccwgroup_device *gdev)
+{
+ struct lcs_card *card = dev_get_drvdata(&gdev->dev);
+ return lcs_pm_resume(card);
+}
+
/**
* LCS ccwgroup driver registration
*/
@@ -2325,6 +2376,11 @@ static struct ccwgroup_driver lcs_group_driver = {
.remove = lcs_remove_device,
.set_online = lcs_new_device,
.set_offline = lcs_shutdown_device,
+ .prepare = lcs_prepare,
+ .complete = lcs_complete,
+ .freeze = lcs_freeze,
+ .thaw = lcs_thaw,
+ .restore = lcs_restore,
};
/**