xref: /openbmc/linux/drivers/s390/scsi/zfcp_ccw.c (revision e23feb16)
1 /*
2  * zfcp device driver
3  *
4  * Registration and callback for the s390 common I/O layer.
5  *
6  * Copyright IBM Corp. 2002, 2010
7  */
8 
9 #define KMSG_COMPONENT "zfcp"
10 #define pr_fmt(fmt) KMSG_COMPONENT ": " fmt
11 
12 #include <linux/module.h>
13 #include "zfcp_ext.h"
14 #include "zfcp_reqlist.h"
15 
16 #define ZFCP_MODEL_PRIV 0x4
17 
18 static DEFINE_SPINLOCK(zfcp_ccw_adapter_ref_lock);
19 
20 struct zfcp_adapter *zfcp_ccw_adapter_by_cdev(struct ccw_device *cdev)
21 {
22 	struct zfcp_adapter *adapter;
23 	unsigned long flags;
24 
25 	spin_lock_irqsave(&zfcp_ccw_adapter_ref_lock, flags);
26 	adapter = dev_get_drvdata(&cdev->dev);
27 	if (adapter)
28 		kref_get(&adapter->ref);
29 	spin_unlock_irqrestore(&zfcp_ccw_adapter_ref_lock, flags);
30 	return adapter;
31 }
32 
33 void zfcp_ccw_adapter_put(struct zfcp_adapter *adapter)
34 {
35 	unsigned long flags;
36 
37 	spin_lock_irqsave(&zfcp_ccw_adapter_ref_lock, flags);
38 	kref_put(&adapter->ref, zfcp_adapter_release);
39 	spin_unlock_irqrestore(&zfcp_ccw_adapter_ref_lock, flags);
40 }
41 
42 /**
43  * zfcp_ccw_activate - activate adapter and wait for it to finish
44  * @cdev: pointer to belonging ccw device
45  * @clear: Status flags to clear.
46  * @tag: s390dbf trace record tag
47  */
48 static int zfcp_ccw_activate(struct ccw_device *cdev, int clear, char *tag)
49 {
50 	struct zfcp_adapter *adapter = zfcp_ccw_adapter_by_cdev(cdev);
51 
52 	if (!adapter)
53 		return 0;
54 
55 	zfcp_erp_clear_adapter_status(adapter, clear);
56 	zfcp_erp_set_adapter_status(adapter, ZFCP_STATUS_COMMON_RUNNING);
57 	zfcp_erp_adapter_reopen(adapter, ZFCP_STATUS_COMMON_ERP_FAILED,
58 				tag);
59 	zfcp_erp_wait(adapter);
60 	flush_work(&adapter->scan_work); /* ok to call even if nothing queued */
61 
62 	zfcp_ccw_adapter_put(adapter);
63 
64 	return 0;
65 }
66 
67 static struct ccw_device_id zfcp_ccw_device_id[] = {
68 	{ CCW_DEVICE_DEVTYPE(0x1731, 0x3, 0x1732, 0x3) },
69 	{ CCW_DEVICE_DEVTYPE(0x1731, 0x3, 0x1732, ZFCP_MODEL_PRIV) },
70 	{},
71 };
72 MODULE_DEVICE_TABLE(ccw, zfcp_ccw_device_id);
73 
74 /**
75  * zfcp_ccw_probe - probe function of zfcp driver
76  * @cdev: pointer to belonging ccw device
77  *
78  * This function gets called by the common i/o layer for each FCP
79  * device found on the current system. This is only a stub to make cio
80  * work: To only allocate adapter resources for devices actually used,
81  * the allocation is deferred to the first call to ccw_set_online.
82  */
83 static int zfcp_ccw_probe(struct ccw_device *cdev)
84 {
85 	return 0;
86 }
87 
88 /**
89  * zfcp_ccw_remove - remove function of zfcp driver
90  * @cdev: pointer to belonging ccw device
91  *
92  * This function gets called by the common i/o layer and removes an adapter
93  * from the system. Task of this function is to get rid of all units and
94  * ports that belong to this adapter. And in addition all resources of this
95  * adapter will be freed too.
96  */
97 static void zfcp_ccw_remove(struct ccw_device *cdev)
98 {
99 	struct zfcp_adapter *adapter;
100 	struct zfcp_port *port, *p;
101 	struct zfcp_unit *unit, *u;
102 	LIST_HEAD(unit_remove_lh);
103 	LIST_HEAD(port_remove_lh);
104 
105 	ccw_device_set_offline(cdev);
106 
107 	adapter = zfcp_ccw_adapter_by_cdev(cdev);
108 	if (!adapter)
109 		return;
110 
111 	write_lock_irq(&adapter->port_list_lock);
112 	list_for_each_entry_safe(port, p, &adapter->port_list, list) {
113 		write_lock(&port->unit_list_lock);
114 		list_for_each_entry_safe(unit, u, &port->unit_list, list)
115 			list_move(&unit->list, &unit_remove_lh);
116 		write_unlock(&port->unit_list_lock);
117 		list_move(&port->list, &port_remove_lh);
118 	}
119 	write_unlock_irq(&adapter->port_list_lock);
120 	zfcp_ccw_adapter_put(adapter); /* put from zfcp_ccw_adapter_by_cdev */
121 
122 	list_for_each_entry_safe(unit, u, &unit_remove_lh, list)
123 		device_unregister(&unit->dev);
124 
125 	list_for_each_entry_safe(port, p, &port_remove_lh, list)
126 		device_unregister(&port->dev);
127 
128 	zfcp_adapter_unregister(adapter);
129 }
130 
131 /**
132  * zfcp_ccw_set_online - set_online function of zfcp driver
133  * @cdev: pointer to belonging ccw device
134  *
135  * This function gets called by the common i/o layer and sets an
136  * adapter into state online.  The first call will allocate all
137  * adapter resources that will be retained until the device is removed
138  * via zfcp_ccw_remove.
139  *
140  * Setting an fcp device online means that it will be registered with
141  * the SCSI stack, that the QDIO queues will be set up and that the
142  * adapter will be opened.
143  */
144 static int zfcp_ccw_set_online(struct ccw_device *cdev)
145 {
146 	struct zfcp_adapter *adapter = zfcp_ccw_adapter_by_cdev(cdev);
147 
148 	if (!adapter) {
149 		adapter = zfcp_adapter_enqueue(cdev);
150 
151 		if (IS_ERR(adapter)) {
152 			dev_err(&cdev->dev,
153 				"Setting up data structures for the "
154 				"FCP adapter failed\n");
155 			return PTR_ERR(adapter);
156 		}
157 		kref_get(&adapter->ref);
158 	}
159 
160 	/* initialize request counter */
161 	BUG_ON(!zfcp_reqlist_isempty(adapter->req_list));
162 	adapter->req_no = 0;
163 
164 	zfcp_ccw_activate(cdev, 0, "ccsonl1");
165 	/* scan for remote ports
166 	   either at the end of any successful adapter recovery
167 	   or only after the adapter recovery for setting a device online */
168 	zfcp_fc_inverse_conditional_port_scan(adapter);
169 	flush_work(&adapter->scan_work); /* ok to call even if nothing queued */
170 	zfcp_ccw_adapter_put(adapter);
171 	return 0;
172 }
173 
174 /**
175  * zfcp_ccw_offline_sync - shut down adapter and wait for it to finish
176  * @cdev: pointer to belonging ccw device
177  * @set: Status flags to set.
178  * @tag: s390dbf trace record tag
179  *
180  * This function gets called by the common i/o layer and sets an adapter
181  * into state offline.
182  */
183 static int zfcp_ccw_offline_sync(struct ccw_device *cdev, int set, char *tag)
184 {
185 	struct zfcp_adapter *adapter = zfcp_ccw_adapter_by_cdev(cdev);
186 
187 	if (!adapter)
188 		return 0;
189 
190 	zfcp_erp_set_adapter_status(adapter, set);
191 	zfcp_erp_adapter_shutdown(adapter, 0, tag);
192 	zfcp_erp_wait(adapter);
193 
194 	zfcp_ccw_adapter_put(adapter);
195 	return 0;
196 }
197 
198 /**
199  * zfcp_ccw_set_offline - set_offline function of zfcp driver
200  * @cdev: pointer to belonging ccw device
201  *
202  * This function gets called by the common i/o layer and sets an adapter
203  * into state offline.
204  */
205 static int zfcp_ccw_set_offline(struct ccw_device *cdev)
206 {
207 	return zfcp_ccw_offline_sync(cdev, 0, "ccsoff1");
208 }
209 
210 /**
211  * zfcp_ccw_notify - ccw notify function
212  * @cdev: pointer to belonging ccw device
213  * @event: indicates if adapter was detached or attached
214  *
215  * This function gets called by the common i/o layer if an adapter has gone
216  * or reappeared.
217  */
218 static int zfcp_ccw_notify(struct ccw_device *cdev, int event)
219 {
220 	struct zfcp_adapter *adapter = zfcp_ccw_adapter_by_cdev(cdev);
221 
222 	if (!adapter)
223 		return 1;
224 
225 	switch (event) {
226 	case CIO_GONE:
227 		if (atomic_read(&adapter->status) &
228 		    ZFCP_STATUS_ADAPTER_SUSPENDED) { /* notification ignore */
229 			zfcp_dbf_hba_basic("ccnigo1", adapter);
230 			break;
231 		}
232 		dev_warn(&cdev->dev, "The FCP device has been detached\n");
233 		zfcp_erp_adapter_shutdown(adapter, 0, "ccnoti1");
234 		break;
235 	case CIO_NO_PATH:
236 		dev_warn(&cdev->dev,
237 			 "The CHPID for the FCP device is offline\n");
238 		zfcp_erp_adapter_shutdown(adapter, 0, "ccnoti2");
239 		break;
240 	case CIO_OPER:
241 		if (atomic_read(&adapter->status) &
242 		    ZFCP_STATUS_ADAPTER_SUSPENDED) { /* notification ignore */
243 			zfcp_dbf_hba_basic("ccniop1", adapter);
244 			break;
245 		}
246 		dev_info(&cdev->dev, "The FCP device is operational again\n");
247 		zfcp_erp_set_adapter_status(adapter,
248 					    ZFCP_STATUS_COMMON_RUNNING);
249 		zfcp_erp_adapter_reopen(adapter, ZFCP_STATUS_COMMON_ERP_FAILED,
250 					"ccnoti4");
251 		break;
252 	case CIO_BOXED:
253 		dev_warn(&cdev->dev, "The FCP device did not respond within "
254 				     "the specified time\n");
255 		zfcp_erp_adapter_shutdown(adapter, 0, "ccnoti5");
256 		break;
257 	}
258 
259 	zfcp_ccw_adapter_put(adapter);
260 	return 1;
261 }
262 
263 /**
264  * zfcp_ccw_shutdown - handle shutdown from cio
265  * @cdev: device for adapter to shutdown.
266  */
267 static void zfcp_ccw_shutdown(struct ccw_device *cdev)
268 {
269 	struct zfcp_adapter *adapter = zfcp_ccw_adapter_by_cdev(cdev);
270 
271 	if (!adapter)
272 		return;
273 
274 	zfcp_erp_adapter_shutdown(adapter, 0, "ccshut1");
275 	zfcp_erp_wait(adapter);
276 	zfcp_erp_thread_kill(adapter);
277 
278 	zfcp_ccw_adapter_put(adapter);
279 }
280 
281 static int zfcp_ccw_suspend(struct ccw_device *cdev)
282 {
283 	zfcp_ccw_offline_sync(cdev, ZFCP_STATUS_ADAPTER_SUSPENDED, "ccsusp1");
284 	return 0;
285 }
286 
287 static int zfcp_ccw_thaw(struct ccw_device *cdev)
288 {
289 	/* trace records for thaw and final shutdown during suspend
290 	   can only be found in system dump until the end of suspend
291 	   but not after resume because it's based on the memory image
292 	   right after the very first suspend (freeze) callback */
293 	zfcp_ccw_activate(cdev, 0, "ccthaw1");
294 	return 0;
295 }
296 
297 static int zfcp_ccw_resume(struct ccw_device *cdev)
298 {
299 	zfcp_ccw_activate(cdev, ZFCP_STATUS_ADAPTER_SUSPENDED, "ccresu1");
300 	return 0;
301 }
302 
303 struct ccw_driver zfcp_ccw_driver = {
304 	.driver = {
305 		.owner	= THIS_MODULE,
306 		.name	= "zfcp",
307 	},
308 	.ids         = zfcp_ccw_device_id,
309 	.probe       = zfcp_ccw_probe,
310 	.remove      = zfcp_ccw_remove,
311 	.set_online  = zfcp_ccw_set_online,
312 	.set_offline = zfcp_ccw_set_offline,
313 	.notify      = zfcp_ccw_notify,
314 	.shutdown    = zfcp_ccw_shutdown,
315 	.freeze      = zfcp_ccw_suspend,
316 	.thaw	     = zfcp_ccw_thaw,
317 	.restore     = zfcp_ccw_resume,
318 };
319