V4L/DVB (12380): uvcvideo: Avoid flooding the kernel log with "unknown event type...
[pandora-kernel.git] / drivers / scsi / libfc / fc_rport.c
1 /*
2  * Copyright(c) 2007 - 2008 Intel Corporation. All rights reserved.
3  *
4  * This program is free software; you can redistribute it and/or modify it
5  * under the terms and conditions of the GNU General Public License,
6  * version 2, as published by the Free Software Foundation.
7  *
8  * This program is distributed in the hope it will be useful, but WITHOUT
9  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
11  * more details.
12  *
13  * You should have received a copy of the GNU General Public License along with
14  * this program; if not, write to the Free Software Foundation, Inc.,
15  * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
16  *
17  * Maintained at www.Open-FCoE.org
18  */
19
20 /*
21  * RPORT GENERAL INFO
22  *
23  * This file contains all processing regarding fc_rports. It contains the
24  * rport state machine and does all rport interaction with the transport class.
25  * There should be no other places in libfc that interact directly with the
26  * transport class in regards to adding and deleting rports.
27  *
28  * fc_rport's represent N_Port's within the fabric.
29  */
30
31 /*
32  * RPORT LOCKING
33  *
34  * The rport should never hold the rport mutex and then attempt to acquire
35  * either the lport or disc mutexes. The rport's mutex is considered lesser
36  * than both the lport's mutex and the disc mutex. Refer to fc_lport.c for
37  * more comments on the heirarchy.
38  *
39  * The locking strategy is similar to the lport's strategy. The lock protects
40  * the rport's states and is held and released by the entry points to the rport
41  * block. All _enter_* functions correspond to rport states and expect the rport
42  * mutex to be locked before calling them. This means that rports only handle
43  * one request or response at a time, since they're not critical for the I/O
44  * path this potential over-use of the mutex is acceptable.
45  */
46
47 #include <linux/kernel.h>
48 #include <linux/spinlock.h>
49 #include <linux/interrupt.h>
50 #include <linux/rcupdate.h>
51 #include <linux/timer.h>
52 #include <linux/workqueue.h>
53 #include <asm/unaligned.h>
54
55 #include <scsi/libfc.h>
56 #include <scsi/fc_encode.h>
57
58 struct workqueue_struct *rport_event_queue;
59
60 static void fc_rport_enter_plogi(struct fc_rport *);
61 static void fc_rport_enter_prli(struct fc_rport *);
62 static void fc_rport_enter_rtv(struct fc_rport *);
63 static void fc_rport_enter_ready(struct fc_rport *);
64 static void fc_rport_enter_logo(struct fc_rport *);
65
66 static void fc_rport_recv_plogi_req(struct fc_rport *,
67                                     struct fc_seq *, struct fc_frame *);
68 static void fc_rport_recv_prli_req(struct fc_rport *,
69                                    struct fc_seq *, struct fc_frame *);
70 static void fc_rport_recv_prlo_req(struct fc_rport *,
71                                    struct fc_seq *, struct fc_frame *);
72 static void fc_rport_recv_logo_req(struct fc_rport *,
73                                    struct fc_seq *, struct fc_frame *);
74 static void fc_rport_timeout(struct work_struct *);
75 static void fc_rport_error(struct fc_rport *, struct fc_frame *);
76 static void fc_rport_error_retry(struct fc_rport *, struct fc_frame *);
77 static void fc_rport_work(struct work_struct *);
78
79 static const char *fc_rport_state_names[] = {
80         [RPORT_ST_NONE] = "None",
81         [RPORT_ST_INIT] = "Init",
82         [RPORT_ST_PLOGI] = "PLOGI",
83         [RPORT_ST_PRLI] = "PRLI",
84         [RPORT_ST_RTV] = "RTV",
85         [RPORT_ST_READY] = "Ready",
86         [RPORT_ST_LOGO] = "LOGO",
87 };
88
89 static void fc_rport_rogue_destroy(struct device *dev)
90 {
91         struct fc_rport *rport = dev_to_rport(dev);
92         FC_RPORT_DBG(rport, "Destroying rogue rport\n");
93         kfree(rport);
94 }
95
96 struct fc_rport *fc_rport_rogue_create(struct fc_disc_port *dp)
97 {
98         struct fc_rport *rport;
99         struct fc_rport_libfc_priv *rdata;
100         rport = kzalloc(sizeof(*rport) + sizeof(*rdata), GFP_KERNEL);
101
102         if (!rport)
103                 return NULL;
104
105         rdata = RPORT_TO_PRIV(rport);
106
107         rport->dd_data = rdata;
108         rport->port_id = dp->ids.port_id;
109         rport->port_name = dp->ids.port_name;
110         rport->node_name = dp->ids.node_name;
111         rport->roles = dp->ids.roles;
112         rport->maxframe_size = FC_MIN_MAX_PAYLOAD;
113         /*
114          * Note: all this libfc rogue rport code will be removed for
115          * upstream so it fine that this is really ugly and hacky right now.
116          */
117         device_initialize(&rport->dev);
118         rport->dev.release = fc_rport_rogue_destroy;
119
120         mutex_init(&rdata->rp_mutex);
121         rdata->local_port = dp->lp;
122         rdata->trans_state = FC_PORTSTATE_ROGUE;
123         rdata->rp_state = RPORT_ST_INIT;
124         rdata->event = RPORT_EV_NONE;
125         rdata->flags = FC_RP_FLAGS_REC_SUPPORTED;
126         rdata->ops = NULL;
127         rdata->e_d_tov = dp->lp->e_d_tov;
128         rdata->r_a_tov = dp->lp->r_a_tov;
129         INIT_DELAYED_WORK(&rdata->retry_work, fc_rport_timeout);
130         INIT_WORK(&rdata->event_work, fc_rport_work);
131         /*
132          * For good measure, but not necessary as we should only
133          * add REAL rport to the lport list.
134          */
135         INIT_LIST_HEAD(&rdata->peers);
136
137         return rport;
138 }
139
140 /**
141  * fc_rport_state() - return a string for the state the rport is in
142  * @rport: The rport whose state we want to get a string for
143  */
144 static const char *fc_rport_state(struct fc_rport *rport)
145 {
146         const char *cp;
147         struct fc_rport_libfc_priv *rdata = rport->dd_data;
148
149         cp = fc_rport_state_names[rdata->rp_state];
150         if (!cp)
151                 cp = "Unknown";
152         return cp;
153 }
154
155 /**
156  * fc_set_rport_loss_tmo() - Set the remote port loss timeout in seconds.
157  * @rport: Pointer to Fibre Channel remote port structure
158  * @timeout: timeout in seconds
159  */
160 void fc_set_rport_loss_tmo(struct fc_rport *rport, u32 timeout)
161 {
162         if (timeout)
163                 rport->dev_loss_tmo = timeout + 5;
164         else
165                 rport->dev_loss_tmo = 30;
166 }
167 EXPORT_SYMBOL(fc_set_rport_loss_tmo);
168
169 /**
170  * fc_plogi_get_maxframe() - Get max payload from the common service parameters
171  * @flp: FLOGI payload structure
172  * @maxval: upper limit, may be less than what is in the service parameters
173  */
174 static unsigned int fc_plogi_get_maxframe(struct fc_els_flogi *flp,
175                                           unsigned int maxval)
176 {
177         unsigned int mfs;
178
179         /*
180          * Get max payload from the common service parameters and the
181          * class 3 receive data field size.
182          */
183         mfs = ntohs(flp->fl_csp.sp_bb_data) & FC_SP_BB_DATA_MASK;
184         if (mfs >= FC_SP_MIN_MAX_PAYLOAD && mfs < maxval)
185                 maxval = mfs;
186         mfs = ntohs(flp->fl_cssp[3 - 1].cp_rdfs);
187         if (mfs >= FC_SP_MIN_MAX_PAYLOAD && mfs < maxval)
188                 maxval = mfs;
189         return maxval;
190 }
191
192 /**
193  * fc_rport_state_enter() - Change the rport's state
194  * @rport: The rport whose state should change
195  * @new: The new state of the rport
196  *
197  * Locking Note: Called with the rport lock held
198  */
199 static void fc_rport_state_enter(struct fc_rport *rport,
200                                  enum fc_rport_state new)
201 {
202         struct fc_rport_libfc_priv *rdata = rport->dd_data;
203         if (rdata->rp_state != new)
204                 rdata->retries = 0;
205         rdata->rp_state = new;
206 }
207
208 static void fc_rport_work(struct work_struct *work)
209 {
210         u32 port_id;
211         struct fc_rport_libfc_priv *rdata =
212                 container_of(work, struct fc_rport_libfc_priv, event_work);
213         enum fc_rport_event event;
214         enum fc_rport_trans_state trans_state;
215         struct fc_lport *lport = rdata->local_port;
216         struct fc_rport_operations *rport_ops;
217         struct fc_rport *rport = PRIV_TO_RPORT(rdata);
218
219         mutex_lock(&rdata->rp_mutex);
220         event = rdata->event;
221         rport_ops = rdata->ops;
222
223         if (event == RPORT_EV_CREATED) {
224                 struct fc_rport *new_rport;
225                 struct fc_rport_libfc_priv *new_rdata;
226                 struct fc_rport_identifiers ids;
227
228                 ids.port_id = rport->port_id;
229                 ids.roles = rport->roles;
230                 ids.port_name = rport->port_name;
231                 ids.node_name = rport->node_name;
232
233                 mutex_unlock(&rdata->rp_mutex);
234
235                 new_rport = fc_remote_port_add(lport->host, 0, &ids);
236                 if (new_rport) {
237                         /*
238                          * Switch from the rogue rport to the rport
239                          * returned by the FC class.
240                          */
241                         new_rport->maxframe_size = rport->maxframe_size;
242
243                         new_rdata = new_rport->dd_data;
244                         new_rdata->e_d_tov = rdata->e_d_tov;
245                         new_rdata->r_a_tov = rdata->r_a_tov;
246                         new_rdata->ops = rdata->ops;
247                         new_rdata->local_port = rdata->local_port;
248                         new_rdata->flags = FC_RP_FLAGS_REC_SUPPORTED;
249                         new_rdata->trans_state = FC_PORTSTATE_REAL;
250                         mutex_init(&new_rdata->rp_mutex);
251                         INIT_DELAYED_WORK(&new_rdata->retry_work,
252                                           fc_rport_timeout);
253                         INIT_LIST_HEAD(&new_rdata->peers);
254                         INIT_WORK(&new_rdata->event_work, fc_rport_work);
255
256                         fc_rport_state_enter(new_rport, RPORT_ST_READY);
257                 } else {
258                         printk(KERN_WARNING "libfc: Failed to allocate "
259                                " memory for rport (%6x)\n", ids.port_id);
260                         event = RPORT_EV_FAILED;
261                 }
262                 if (rport->port_id != FC_FID_DIR_SERV)
263                         if (rport_ops->event_callback)
264                                 rport_ops->event_callback(lport, rport,
265                                                           RPORT_EV_FAILED);
266                 put_device(&rport->dev);
267                 rport = new_rport;
268                 rdata = new_rport->dd_data;
269                 if (rport_ops->event_callback)
270                         rport_ops->event_callback(lport, rport, event);
271         } else if ((event == RPORT_EV_FAILED) ||
272                    (event == RPORT_EV_LOGO) ||
273                    (event == RPORT_EV_STOP)) {
274                 trans_state = rdata->trans_state;
275                 mutex_unlock(&rdata->rp_mutex);
276                 if (rport_ops->event_callback)
277                         rport_ops->event_callback(lport, rport, event);
278                 if (trans_state == FC_PORTSTATE_ROGUE)
279                         put_device(&rport->dev);
280                 else {
281                         port_id = rport->port_id;
282                         fc_remote_port_delete(rport);
283                         lport->tt.exch_mgr_reset(lport, 0, port_id);
284                         lport->tt.exch_mgr_reset(lport, port_id, 0);
285                 }
286         } else
287                 mutex_unlock(&rdata->rp_mutex);
288 }
289
290 /**
291  * fc_rport_login() - Start the remote port login state machine
292  * @rport: Fibre Channel remote port
293  *
294  * Locking Note: Called without the rport lock held. This
295  * function will hold the rport lock, call an _enter_*
296  * function and then unlock the rport.
297  */
298 int fc_rport_login(struct fc_rport *rport)
299 {
300         struct fc_rport_libfc_priv *rdata = rport->dd_data;
301
302         mutex_lock(&rdata->rp_mutex);
303
304         FC_RPORT_DBG(rport, "Login to port\n");
305
306         fc_rport_enter_plogi(rport);
307
308         mutex_unlock(&rdata->rp_mutex);
309
310         return 0;
311 }
312
313 /**
314  * fc_rport_logoff() - Logoff and remove an rport
315  * @rport: Fibre Channel remote port to be removed
316  *
317  * Locking Note: Called without the rport lock held. This
318  * function will hold the rport lock, call an _enter_*
319  * function and then unlock the rport.
320  */
321 int fc_rport_logoff(struct fc_rport *rport)
322 {
323         struct fc_rport_libfc_priv *rdata = rport->dd_data;
324
325         mutex_lock(&rdata->rp_mutex);
326
327         FC_RPORT_DBG(rport, "Remove port\n");
328
329         if (rdata->rp_state == RPORT_ST_NONE) {
330                 FC_RPORT_DBG(rport, "Port in NONE state, not removing\n");
331                 mutex_unlock(&rdata->rp_mutex);
332                 goto out;
333         }
334
335         fc_rport_enter_logo(rport);
336
337         /*
338          * Change the state to NONE so that we discard
339          * the response.
340          */
341         fc_rport_state_enter(rport, RPORT_ST_NONE);
342
343         mutex_unlock(&rdata->rp_mutex);
344
345         cancel_delayed_work_sync(&rdata->retry_work);
346
347         mutex_lock(&rdata->rp_mutex);
348
349         rdata->event = RPORT_EV_STOP;
350         queue_work(rport_event_queue, &rdata->event_work);
351
352         mutex_unlock(&rdata->rp_mutex);
353
354 out:
355         return 0;
356 }
357
358 /**
359  * fc_rport_enter_ready() - The rport is ready
360  * @rport: Fibre Channel remote port that is ready
361  *
362  * Locking Note: The rport lock is expected to be held before calling
363  * this routine.
364  */
365 static void fc_rport_enter_ready(struct fc_rport *rport)
366 {
367         struct fc_rport_libfc_priv *rdata = rport->dd_data;
368
369         fc_rport_state_enter(rport, RPORT_ST_READY);
370
371         FC_RPORT_DBG(rport, "Port is Ready\n");
372
373         rdata->event = RPORT_EV_CREATED;
374         queue_work(rport_event_queue, &rdata->event_work);
375 }
376
377 /**
378  * fc_rport_timeout() - Handler for the retry_work timer.
379  * @work: The work struct of the fc_rport_libfc_priv
380  *
381  * Locking Note: Called without the rport lock held. This
382  * function will hold the rport lock, call an _enter_*
383  * function and then unlock the rport.
384  */
385 static void fc_rport_timeout(struct work_struct *work)
386 {
387         struct fc_rport_libfc_priv *rdata =
388                 container_of(work, struct fc_rport_libfc_priv, retry_work.work);
389         struct fc_rport *rport = PRIV_TO_RPORT(rdata);
390
391         mutex_lock(&rdata->rp_mutex);
392
393         switch (rdata->rp_state) {
394         case RPORT_ST_PLOGI:
395                 fc_rport_enter_plogi(rport);
396                 break;
397         case RPORT_ST_PRLI:
398                 fc_rport_enter_prli(rport);
399                 break;
400         case RPORT_ST_RTV:
401                 fc_rport_enter_rtv(rport);
402                 break;
403         case RPORT_ST_LOGO:
404                 fc_rport_enter_logo(rport);
405                 break;
406         case RPORT_ST_READY:
407         case RPORT_ST_INIT:
408         case RPORT_ST_NONE:
409                 break;
410         }
411
412         mutex_unlock(&rdata->rp_mutex);
413         put_device(&rport->dev);
414 }
415
416 /**
417  * fc_rport_error() - Error handler, called once retries have been exhausted
418  * @rport: The fc_rport object
419  * @fp: The frame pointer
420  *
421  * Locking Note: The rport lock is expected to be held before
422  * calling this routine
423  */
424 static void fc_rport_error(struct fc_rport *rport, struct fc_frame *fp)
425 {
426         struct fc_rport_libfc_priv *rdata = rport->dd_data;
427
428         FC_RPORT_DBG(rport, "Error %ld in state %s, retries %d\n",
429                      PTR_ERR(fp), fc_rport_state(rport), rdata->retries);
430
431         switch (rdata->rp_state) {
432         case RPORT_ST_PLOGI:
433         case RPORT_ST_PRLI:
434         case RPORT_ST_LOGO:
435                 rdata->event = RPORT_EV_FAILED;
436                 fc_rport_state_enter(rport, RPORT_ST_NONE);
437                 queue_work(rport_event_queue,
438                            &rdata->event_work);
439                 break;
440         case RPORT_ST_RTV:
441                 fc_rport_enter_ready(rport);
442                 break;
443         case RPORT_ST_NONE:
444         case RPORT_ST_READY:
445         case RPORT_ST_INIT:
446                 break;
447         }
448 }
449
450 /**
451  * fc_rport_error_retry() - Error handler when retries are desired
452  * @rport: The fc_rport object
453  * @fp: The frame pointer
454  *
455  * If the error was an exchange timeout retry immediately,
456  * otherwise wait for E_D_TOV.
457  *
458  * Locking Note: The rport lock is expected to be held before
459  * calling this routine
460  */
461 static void fc_rport_error_retry(struct fc_rport *rport, struct fc_frame *fp)
462 {
463         struct fc_rport_libfc_priv *rdata = rport->dd_data;
464         unsigned long delay = FC_DEF_E_D_TOV;
465
466         /* make sure this isn't an FC_EX_CLOSED error, never retry those */
467         if (PTR_ERR(fp) == -FC_EX_CLOSED)
468                 return fc_rport_error(rport, fp);
469
470         if (rdata->retries < rdata->local_port->max_rport_retry_count) {
471                 FC_RPORT_DBG(rport, "Error %ld in state %s, retrying\n",
472                              PTR_ERR(fp), fc_rport_state(rport));
473                 rdata->retries++;
474                 /* no additional delay on exchange timeouts */
475                 if (PTR_ERR(fp) == -FC_EX_TIMEOUT)
476                         delay = 0;
477                 get_device(&rport->dev);
478                 schedule_delayed_work(&rdata->retry_work, delay);
479                 return;
480         }
481
482         return fc_rport_error(rport, fp);
483 }
484
485 /**
486  * fc_rport_plogi_recv_resp() - Handle incoming ELS PLOGI response
487  * @sp: current sequence in the PLOGI exchange
488  * @fp: response frame
489  * @rp_arg: Fibre Channel remote port
490  *
491  * Locking Note: This function will be called without the rport lock
492  * held, but it will lock, call an _enter_* function or fc_rport_error
493  * and then unlock the rport.
494  */
495 static void fc_rport_plogi_resp(struct fc_seq *sp, struct fc_frame *fp,
496                                 void *rp_arg)
497 {
498         struct fc_rport *rport = rp_arg;
499         struct fc_rport_libfc_priv *rdata = rport->dd_data;
500         struct fc_lport *lport = rdata->local_port;
501         struct fc_els_flogi *plp = NULL;
502         unsigned int tov;
503         u16 csp_seq;
504         u16 cssp_seq;
505         u8 op;
506
507         mutex_lock(&rdata->rp_mutex);
508
509         FC_RPORT_DBG(rport, "Received a PLOGI response\n");
510
511         if (rdata->rp_state != RPORT_ST_PLOGI) {
512                 FC_RPORT_DBG(rport, "Received a PLOGI response, but in state "
513                              "%s\n", fc_rport_state(rport));
514                 if (IS_ERR(fp))
515                         goto err;
516                 goto out;
517         }
518
519         if (IS_ERR(fp)) {
520                 fc_rport_error_retry(rport, fp);
521                 goto err;
522         }
523
524         op = fc_frame_payload_op(fp);
525         if (op == ELS_LS_ACC &&
526             (plp = fc_frame_payload_get(fp, sizeof(*plp))) != NULL) {
527                 rport->port_name = get_unaligned_be64(&plp->fl_wwpn);
528                 rport->node_name = get_unaligned_be64(&plp->fl_wwnn);
529
530                 tov = ntohl(plp->fl_csp.sp_e_d_tov);
531                 if (ntohs(plp->fl_csp.sp_features) & FC_SP_FT_EDTR)
532                         tov /= 1000;
533                 if (tov > rdata->e_d_tov)
534                         rdata->e_d_tov = tov;
535                 csp_seq = ntohs(plp->fl_csp.sp_tot_seq);
536                 cssp_seq = ntohs(plp->fl_cssp[3 - 1].cp_con_seq);
537                 if (cssp_seq < csp_seq)
538                         csp_seq = cssp_seq;
539                 rdata->max_seq = csp_seq;
540                 rport->maxframe_size =
541                         fc_plogi_get_maxframe(plp, lport->mfs);
542
543                 /*
544                  * If the rport is one of the well known addresses
545                  * we skip PRLI and RTV and go straight to READY.
546                  */
547                 if (rport->port_id >= FC_FID_DOM_MGR)
548                         fc_rport_enter_ready(rport);
549                 else
550                         fc_rport_enter_prli(rport);
551         } else
552                 fc_rport_error_retry(rport, fp);
553
554 out:
555         fc_frame_free(fp);
556 err:
557         mutex_unlock(&rdata->rp_mutex);
558         put_device(&rport->dev);
559 }
560
561 /**
562  * fc_rport_enter_plogi() - Send Port Login (PLOGI) request to peer
563  * @rport: Fibre Channel remote port to send PLOGI to
564  *
565  * Locking Note: The rport lock is expected to be held before calling
566  * this routine.
567  */
568 static void fc_rport_enter_plogi(struct fc_rport *rport)
569 {
570         struct fc_rport_libfc_priv *rdata = rport->dd_data;
571         struct fc_lport *lport = rdata->local_port;
572         struct fc_frame *fp;
573
574         FC_RPORT_DBG(rport, "Port entered PLOGI state from %s state\n",
575                      fc_rport_state(rport));
576
577         fc_rport_state_enter(rport, RPORT_ST_PLOGI);
578
579         rport->maxframe_size = FC_MIN_MAX_PAYLOAD;
580         fp = fc_frame_alloc(lport, sizeof(struct fc_els_flogi));
581         if (!fp) {
582                 fc_rport_error_retry(rport, fp);
583                 return;
584         }
585         rdata->e_d_tov = lport->e_d_tov;
586
587         if (!lport->tt.elsct_send(lport, rport, fp, ELS_PLOGI,
588                                   fc_rport_plogi_resp, rport, lport->e_d_tov))
589                 fc_rport_error_retry(rport, fp);
590         else
591                 get_device(&rport->dev);
592 }
593
594 /**
595  * fc_rport_prli_resp() - Process Login (PRLI) response handler
596  * @sp: current sequence in the PRLI exchange
597  * @fp: response frame
598  * @rp_arg: Fibre Channel remote port
599  *
600  * Locking Note: This function will be called without the rport lock
601  * held, but it will lock, call an _enter_* function or fc_rport_error
602  * and then unlock the rport.
603  */
604 static void fc_rport_prli_resp(struct fc_seq *sp, struct fc_frame *fp,
605                                void *rp_arg)
606 {
607         struct fc_rport *rport = rp_arg;
608         struct fc_rport_libfc_priv *rdata = rport->dd_data;
609         struct {
610                 struct fc_els_prli prli;
611                 struct fc_els_spp spp;
612         } *pp;
613         u32 roles = FC_RPORT_ROLE_UNKNOWN;
614         u32 fcp_parm = 0;
615         u8 op;
616
617         mutex_lock(&rdata->rp_mutex);
618
619         FC_RPORT_DBG(rport, "Received a PRLI response\n");
620
621         if (rdata->rp_state != RPORT_ST_PRLI) {
622                 FC_RPORT_DBG(rport, "Received a PRLI response, but in state "
623                              "%s\n", fc_rport_state(rport));
624                 if (IS_ERR(fp))
625                         goto err;
626                 goto out;
627         }
628
629         if (IS_ERR(fp)) {
630                 fc_rport_error_retry(rport, fp);
631                 goto err;
632         }
633
634         op = fc_frame_payload_op(fp);
635         if (op == ELS_LS_ACC) {
636                 pp = fc_frame_payload_get(fp, sizeof(*pp));
637                 if (pp && pp->prli.prli_spp_len >= sizeof(pp->spp)) {
638                         fcp_parm = ntohl(pp->spp.spp_params);
639                         if (fcp_parm & FCP_SPPF_RETRY)
640                                 rdata->flags |= FC_RP_FLAGS_RETRY;
641                 }
642
643                 rport->supported_classes = FC_COS_CLASS3;
644                 if (fcp_parm & FCP_SPPF_INIT_FCN)
645                         roles |= FC_RPORT_ROLE_FCP_INITIATOR;
646                 if (fcp_parm & FCP_SPPF_TARG_FCN)
647                         roles |= FC_RPORT_ROLE_FCP_TARGET;
648
649                 rport->roles = roles;
650                 fc_rport_enter_rtv(rport);
651
652         } else {
653                 FC_RPORT_DBG(rport, "Bad ELS response for PRLI command\n");
654                 rdata->event = RPORT_EV_FAILED;
655                 fc_rport_state_enter(rport, RPORT_ST_NONE);
656                 queue_work(rport_event_queue, &rdata->event_work);
657         }
658
659 out:
660         fc_frame_free(fp);
661 err:
662         mutex_unlock(&rdata->rp_mutex);
663         put_device(&rport->dev);
664 }
665
666 /**
667  * fc_rport_logo_resp() - Logout (LOGO) response handler
668  * @sp: current sequence in the LOGO exchange
669  * @fp: response frame
670  * @rp_arg: Fibre Channel remote port
671  *
672  * Locking Note: This function will be called without the rport lock
673  * held, but it will lock, call an _enter_* function or fc_rport_error
674  * and then unlock the rport.
675  */
676 static void fc_rport_logo_resp(struct fc_seq *sp, struct fc_frame *fp,
677                                void *rp_arg)
678 {
679         struct fc_rport *rport = rp_arg;
680         struct fc_rport_libfc_priv *rdata = rport->dd_data;
681         u8 op;
682
683         mutex_lock(&rdata->rp_mutex);
684
685         FC_RPORT_DBG(rport, "Received a LOGO response\n");
686
687         if (rdata->rp_state != RPORT_ST_LOGO) {
688                 FC_RPORT_DBG(rport, "Received a LOGO response, but in state "
689                              "%s\n", fc_rport_state(rport));
690                 if (IS_ERR(fp))
691                         goto err;
692                 goto out;
693         }
694
695         if (IS_ERR(fp)) {
696                 fc_rport_error_retry(rport, fp);
697                 goto err;
698         }
699
700         op = fc_frame_payload_op(fp);
701         if (op == ELS_LS_ACC) {
702                 fc_rport_enter_rtv(rport);
703         } else {
704                 FC_RPORT_DBG(rport, "Bad ELS response for LOGO command\n");
705                 rdata->event = RPORT_EV_LOGO;
706                 fc_rport_state_enter(rport, RPORT_ST_NONE);
707                 queue_work(rport_event_queue, &rdata->event_work);
708         }
709
710 out:
711         fc_frame_free(fp);
712 err:
713         mutex_unlock(&rdata->rp_mutex);
714         put_device(&rport->dev);
715 }
716
717 /**
718  * fc_rport_enter_prli() - Send Process Login (PRLI) request to peer
719  * @rport: Fibre Channel remote port to send PRLI to
720  *
721  * Locking Note: The rport lock is expected to be held before calling
722  * this routine.
723  */
724 static void fc_rport_enter_prli(struct fc_rport *rport)
725 {
726         struct fc_rport_libfc_priv *rdata = rport->dd_data;
727         struct fc_lport *lport = rdata->local_port;
728         struct {
729                 struct fc_els_prli prli;
730                 struct fc_els_spp spp;
731         } *pp;
732         struct fc_frame *fp;
733
734         FC_RPORT_DBG(rport, "Port entered PRLI state from %s state\n",
735                      fc_rport_state(rport));
736
737         fc_rport_state_enter(rport, RPORT_ST_PRLI);
738
739         fp = fc_frame_alloc(lport, sizeof(*pp));
740         if (!fp) {
741                 fc_rport_error_retry(rport, fp);
742                 return;
743         }
744
745         if (!lport->tt.elsct_send(lport, rport, fp, ELS_PRLI,
746                                   fc_rport_prli_resp, rport, lport->e_d_tov))
747                 fc_rport_error_retry(rport, fp);
748         else
749                 get_device(&rport->dev);
750 }
751
752 /**
753  * fc_rport_els_rtv_resp() - Request Timeout Value response handler
754  * @sp: current sequence in the RTV exchange
755  * @fp: response frame
756  * @rp_arg: Fibre Channel remote port
757  *
758  * Many targets don't seem to support this.
759  *
760  * Locking Note: This function will be called without the rport lock
761  * held, but it will lock, call an _enter_* function or fc_rport_error
762  * and then unlock the rport.
763  */
764 static void fc_rport_rtv_resp(struct fc_seq *sp, struct fc_frame *fp,
765                               void *rp_arg)
766 {
767         struct fc_rport *rport = rp_arg;
768         struct fc_rport_libfc_priv *rdata = rport->dd_data;
769         u8 op;
770
771         mutex_lock(&rdata->rp_mutex);
772
773         FC_RPORT_DBG(rport, "Received a RTV response\n");
774
775         if (rdata->rp_state != RPORT_ST_RTV) {
776                 FC_RPORT_DBG(rport, "Received a RTV response, but in state "
777                              "%s\n", fc_rport_state(rport));
778                 if (IS_ERR(fp))
779                         goto err;
780                 goto out;
781         }
782
783         if (IS_ERR(fp)) {
784                 fc_rport_error(rport, fp);
785                 goto err;
786         }
787
788         op = fc_frame_payload_op(fp);
789         if (op == ELS_LS_ACC) {
790                 struct fc_els_rtv_acc *rtv;
791                 u32 toq;
792                 u32 tov;
793
794                 rtv = fc_frame_payload_get(fp, sizeof(*rtv));
795                 if (rtv) {
796                         toq = ntohl(rtv->rtv_toq);
797                         tov = ntohl(rtv->rtv_r_a_tov);
798                         if (tov == 0)
799                                 tov = 1;
800                         rdata->r_a_tov = tov;
801                         tov = ntohl(rtv->rtv_e_d_tov);
802                         if (toq & FC_ELS_RTV_EDRES)
803                                 tov /= 1000000;
804                         if (tov == 0)
805                                 tov = 1;
806                         rdata->e_d_tov = tov;
807                 }
808         }
809
810         fc_rport_enter_ready(rport);
811
812 out:
813         fc_frame_free(fp);
814 err:
815         mutex_unlock(&rdata->rp_mutex);
816         put_device(&rport->dev);
817 }
818
819 /**
820  * fc_rport_enter_rtv() - Send Request Timeout Value (RTV) request to peer
821  * @rport: Fibre Channel remote port to send RTV to
822  *
823  * Locking Note: The rport lock is expected to be held before calling
824  * this routine.
825  */
826 static void fc_rport_enter_rtv(struct fc_rport *rport)
827 {
828         struct fc_frame *fp;
829         struct fc_rport_libfc_priv *rdata = rport->dd_data;
830         struct fc_lport *lport = rdata->local_port;
831
832         FC_RPORT_DBG(rport, "Port entered RTV state from %s state\n",
833                      fc_rport_state(rport));
834
835         fc_rport_state_enter(rport, RPORT_ST_RTV);
836
837         fp = fc_frame_alloc(lport, sizeof(struct fc_els_rtv));
838         if (!fp) {
839                 fc_rport_error_retry(rport, fp);
840                 return;
841         }
842
843         if (!lport->tt.elsct_send(lport, rport, fp, ELS_RTV,
844                                      fc_rport_rtv_resp, rport, lport->e_d_tov))
845                 fc_rport_error_retry(rport, fp);
846         else
847                 get_device(&rport->dev);
848 }
849
850 /**
851  * fc_rport_enter_logo() - Send Logout (LOGO) request to peer
852  * @rport: Fibre Channel remote port to send LOGO to
853  *
854  * Locking Note: The rport lock is expected to be held before calling
855  * this routine.
856  */
857 static void fc_rport_enter_logo(struct fc_rport *rport)
858 {
859         struct fc_rport_libfc_priv *rdata = rport->dd_data;
860         struct fc_lport *lport = rdata->local_port;
861         struct fc_frame *fp;
862
863         FC_RPORT_DBG(rport, "Port entered LOGO state from %s state\n",
864                      fc_rport_state(rport));
865
866         fc_rport_state_enter(rport, RPORT_ST_LOGO);
867
868         fp = fc_frame_alloc(lport, sizeof(struct fc_els_logo));
869         if (!fp) {
870                 fc_rport_error_retry(rport, fp);
871                 return;
872         }
873
874         if (!lport->tt.elsct_send(lport, rport, fp, ELS_LOGO,
875                                   fc_rport_logo_resp, rport, lport->e_d_tov))
876                 fc_rport_error_retry(rport, fp);
877         else
878                 get_device(&rport->dev);
879 }
880
881
882 /**
883  * fc_rport_recv_req() - Receive a request from a rport
884  * @sp: current sequence in the PLOGI exchange
885  * @fp: response frame
886  * @rp_arg: Fibre Channel remote port
887  *
888  * Locking Note: Called without the rport lock held. This
889  * function will hold the rport lock, call an _enter_*
890  * function and then unlock the rport.
891  */
892 void fc_rport_recv_req(struct fc_seq *sp, struct fc_frame *fp,
893                        struct fc_rport *rport)
894 {
895         struct fc_rport_libfc_priv *rdata = rport->dd_data;
896         struct fc_lport *lport = rdata->local_port;
897
898         struct fc_frame_header *fh;
899         struct fc_seq_els_data els_data;
900         u8 op;
901
902         mutex_lock(&rdata->rp_mutex);
903
904         els_data.fp = NULL;
905         els_data.explan = ELS_EXPL_NONE;
906         els_data.reason = ELS_RJT_NONE;
907
908         fh = fc_frame_header_get(fp);
909
910         if (fh->fh_r_ctl == FC_RCTL_ELS_REQ && fh->fh_type == FC_TYPE_ELS) {
911                 op = fc_frame_payload_op(fp);
912                 switch (op) {
913                 case ELS_PLOGI:
914                         fc_rport_recv_plogi_req(rport, sp, fp);
915                         break;
916                 case ELS_PRLI:
917                         fc_rport_recv_prli_req(rport, sp, fp);
918                         break;
919                 case ELS_PRLO:
920                         fc_rport_recv_prlo_req(rport, sp, fp);
921                         break;
922                 case ELS_LOGO:
923                         fc_rport_recv_logo_req(rport, sp, fp);
924                         break;
925                 case ELS_RRQ:
926                         els_data.fp = fp;
927                         lport->tt.seq_els_rsp_send(sp, ELS_RRQ, &els_data);
928                         break;
929                 case ELS_REC:
930                         els_data.fp = fp;
931                         lport->tt.seq_els_rsp_send(sp, ELS_REC, &els_data);
932                         break;
933                 default:
934                         els_data.reason = ELS_RJT_UNSUP;
935                         lport->tt.seq_els_rsp_send(sp, ELS_LS_RJT, &els_data);
936                         break;
937                 }
938         }
939
940         mutex_unlock(&rdata->rp_mutex);
941 }
942
943 /**
944  * fc_rport_recv_plogi_req() - Handle incoming Port Login (PLOGI) request
945  * @rport: Fibre Channel remote port that initiated PLOGI
946  * @sp: current sequence in the PLOGI exchange
947  * @fp: PLOGI request frame
948  *
949  * Locking Note: The rport lock is exected to be held before calling
950  * this function.
951  */
952 static void fc_rport_recv_plogi_req(struct fc_rport *rport,
953                                     struct fc_seq *sp, struct fc_frame *rx_fp)
954 {
955         struct fc_rport_libfc_priv *rdata = rport->dd_data;
956         struct fc_lport *lport = rdata->local_port;
957         struct fc_frame *fp = rx_fp;
958         struct fc_exch *ep;
959         struct fc_frame_header *fh;
960         struct fc_els_flogi *pl;
961         struct fc_seq_els_data rjt_data;
962         u32 sid;
963         u64 wwpn;
964         u64 wwnn;
965         enum fc_els_rjt_reason reject = 0;
966         u32 f_ctl;
967         rjt_data.fp = NULL;
968
969         fh = fc_frame_header_get(fp);
970
971         FC_RPORT_DBG(rport, "Received PLOGI request while in state %s\n",
972                      fc_rport_state(rport));
973
974         sid = ntoh24(fh->fh_s_id);
975         pl = fc_frame_payload_get(fp, sizeof(*pl));
976         if (!pl) {
977                 FC_RPORT_DBG(rport, "Received PLOGI too short\n");
978                 WARN_ON(1);
979                 /* XXX TBD: send reject? */
980                 fc_frame_free(fp);
981                 return;
982         }
983         wwpn = get_unaligned_be64(&pl->fl_wwpn);
984         wwnn = get_unaligned_be64(&pl->fl_wwnn);
985
986         /*
987          * If the session was just created, possibly due to the incoming PLOGI,
988          * set the state appropriately and accept the PLOGI.
989          *
990          * If we had also sent a PLOGI, and if the received PLOGI is from a
991          * higher WWPN, we accept it, otherwise an LS_RJT is sent with reason
992          * "command already in progress".
993          *
994          * XXX TBD: If the session was ready before, the PLOGI should result in
995          * all outstanding exchanges being reset.
996          */
997         switch (rdata->rp_state) {
998         case RPORT_ST_INIT:
999                 FC_RPORT_DBG(rport, "Received PLOGI, wwpn %llx state INIT "
1000                              "- reject\n", (unsigned long long)wwpn);
1001                 reject = ELS_RJT_UNSUP;
1002                 break;
1003         case RPORT_ST_PLOGI:
1004                 FC_RPORT_DBG(rport, "Received PLOGI in PLOGI state %d\n",
1005                              rdata->rp_state);
1006                 if (wwpn < lport->wwpn)
1007                         reject = ELS_RJT_INPROG;
1008                 break;
1009         case RPORT_ST_PRLI:
1010         case RPORT_ST_READY:
1011                 FC_RPORT_DBG(rport, "Received PLOGI in logged-in state %d "
1012                              "- ignored for now\n", rdata->rp_state);
1013                 /* XXX TBD - should reset */
1014                 break;
1015         case RPORT_ST_NONE:
1016         default:
1017                 FC_RPORT_DBG(rport, "Received PLOGI in unexpected "
1018                              "state %d\n", rdata->rp_state);
1019                 fc_frame_free(fp);
1020                 return;
1021                 break;
1022         }
1023
1024         if (reject) {
1025                 rjt_data.reason = reject;
1026                 rjt_data.explan = ELS_EXPL_NONE;
1027                 lport->tt.seq_els_rsp_send(sp, ELS_LS_RJT, &rjt_data);
1028                 fc_frame_free(fp);
1029         } else {
1030                 fp = fc_frame_alloc(lport, sizeof(*pl));
1031                 if (fp == NULL) {
1032                         fp = rx_fp;
1033                         rjt_data.reason = ELS_RJT_UNAB;
1034                         rjt_data.explan = ELS_EXPL_NONE;
1035                         lport->tt.seq_els_rsp_send(sp, ELS_LS_RJT, &rjt_data);
1036                         fc_frame_free(fp);
1037                 } else {
1038                         sp = lport->tt.seq_start_next(sp);
1039                         WARN_ON(!sp);
1040                         fc_rport_set_name(rport, wwpn, wwnn);
1041
1042                         /*
1043                          * Get session payload size from incoming PLOGI.
1044                          */
1045                         rport->maxframe_size =
1046                                 fc_plogi_get_maxframe(pl, lport->mfs);
1047                         fc_frame_free(rx_fp);
1048                         fc_plogi_fill(lport, fp, ELS_LS_ACC);
1049
1050                         /*
1051                          * Send LS_ACC.  If this fails,
1052                          * the originator should retry.
1053                          */
1054                         f_ctl = FC_FC_EX_CTX | FC_FC_LAST_SEQ;
1055                         f_ctl |= FC_FC_END_SEQ | FC_FC_SEQ_INIT;
1056                         ep = fc_seq_exch(sp);
1057                         fc_fill_fc_hdr(fp, FC_RCTL_ELS_REP, ep->did, ep->sid,
1058                                        FC_TYPE_ELS, f_ctl, 0);
1059                         lport->tt.seq_send(lport, sp, fp);
1060                         if (rdata->rp_state == RPORT_ST_PLOGI)
1061                                 fc_rport_enter_prli(rport);
1062                 }
1063         }
1064 }
1065
1066 /**
1067  * fc_rport_recv_prli_req() - Handle incoming Process Login (PRLI) request
1068  * @rport: Fibre Channel remote port that initiated PRLI
1069  * @sp: current sequence in the PRLI exchange
1070  * @fp: PRLI request frame
1071  *
1072  * Locking Note: The rport lock is exected to be held before calling
1073  * this function.
1074  */
1075 static void fc_rport_recv_prli_req(struct fc_rport *rport,
1076                                    struct fc_seq *sp, struct fc_frame *rx_fp)
1077 {
1078         struct fc_rport_libfc_priv *rdata = rport->dd_data;
1079         struct fc_lport *lport = rdata->local_port;
1080         struct fc_exch *ep;
1081         struct fc_frame *fp;
1082         struct fc_frame_header *fh;
1083         struct {
1084                 struct fc_els_prli prli;
1085                 struct fc_els_spp spp;
1086         } *pp;
1087         struct fc_els_spp *rspp;        /* request service param page */
1088         struct fc_els_spp *spp; /* response spp */
1089         unsigned int len;
1090         unsigned int plen;
1091         enum fc_els_rjt_reason reason = ELS_RJT_UNAB;
1092         enum fc_els_rjt_explan explan = ELS_EXPL_NONE;
1093         enum fc_els_spp_resp resp;
1094         struct fc_seq_els_data rjt_data;
1095         u32 f_ctl;
1096         u32 fcp_parm;
1097         u32 roles = FC_RPORT_ROLE_UNKNOWN;
1098         rjt_data.fp = NULL;
1099
1100         fh = fc_frame_header_get(rx_fp);
1101
1102         FC_RPORT_DBG(rport, "Received PRLI request while in state %s\n",
1103                      fc_rport_state(rport));
1104
1105         switch (rdata->rp_state) {
1106         case RPORT_ST_PRLI:
1107         case RPORT_ST_READY:
1108                 reason = ELS_RJT_NONE;
1109                 break;
1110         default:
1111                 fc_frame_free(rx_fp);
1112                 return;
1113                 break;
1114         }
1115         len = fr_len(rx_fp) - sizeof(*fh);
1116         pp = fc_frame_payload_get(rx_fp, sizeof(*pp));
1117         if (pp == NULL) {
1118                 reason = ELS_RJT_PROT;
1119                 explan = ELS_EXPL_INV_LEN;
1120         } else {
1121                 plen = ntohs(pp->prli.prli_len);
1122                 if ((plen % 4) != 0 || plen > len) {
1123                         reason = ELS_RJT_PROT;
1124                         explan = ELS_EXPL_INV_LEN;
1125                 } else if (plen < len) {
1126                         len = plen;
1127                 }
1128                 plen = pp->prli.prli_spp_len;
1129                 if ((plen % 4) != 0 || plen < sizeof(*spp) ||
1130                     plen > len || len < sizeof(*pp)) {
1131                         reason = ELS_RJT_PROT;
1132                         explan = ELS_EXPL_INV_LEN;
1133                 }
1134                 rspp = &pp->spp;
1135         }
1136         if (reason != ELS_RJT_NONE ||
1137             (fp = fc_frame_alloc(lport, len)) == NULL) {
1138                 rjt_data.reason = reason;
1139                 rjt_data.explan = explan;
1140                 lport->tt.seq_els_rsp_send(sp, ELS_LS_RJT, &rjt_data);
1141         } else {
1142                 sp = lport->tt.seq_start_next(sp);
1143                 WARN_ON(!sp);
1144                 pp = fc_frame_payload_get(fp, len);
1145                 WARN_ON(!pp);
1146                 memset(pp, 0, len);
1147                 pp->prli.prli_cmd = ELS_LS_ACC;
1148                 pp->prli.prli_spp_len = plen;
1149                 pp->prli.prli_len = htons(len);
1150                 len -= sizeof(struct fc_els_prli);
1151
1152                 /*
1153                  * Go through all the service parameter pages and build
1154                  * response.  If plen indicates longer SPP than standard,
1155                  * use that.  The entire response has been pre-cleared above.
1156                  */
1157                 spp = &pp->spp;
1158                 while (len >= plen) {
1159                         spp->spp_type = rspp->spp_type;
1160                         spp->spp_type_ext = rspp->spp_type_ext;
1161                         spp->spp_flags = rspp->spp_flags & FC_SPP_EST_IMG_PAIR;
1162                         resp = FC_SPP_RESP_ACK;
1163                         if (rspp->spp_flags & FC_SPP_RPA_VAL)
1164                                 resp = FC_SPP_RESP_NO_PA;
1165                         switch (rspp->spp_type) {
1166                         case 0: /* common to all FC-4 types */
1167                                 break;
1168                         case FC_TYPE_FCP:
1169                                 fcp_parm = ntohl(rspp->spp_params);
1170                                 if (fcp_parm * FCP_SPPF_RETRY)
1171                                         rdata->flags |= FC_RP_FLAGS_RETRY;
1172                                 rport->supported_classes = FC_COS_CLASS3;
1173                                 if (fcp_parm & FCP_SPPF_INIT_FCN)
1174                                         roles |= FC_RPORT_ROLE_FCP_INITIATOR;
1175                                 if (fcp_parm & FCP_SPPF_TARG_FCN)
1176                                         roles |= FC_RPORT_ROLE_FCP_TARGET;
1177                                 rport->roles = roles;
1178
1179                                 spp->spp_params =
1180                                         htonl(lport->service_params);
1181                                 break;
1182                         default:
1183                                 resp = FC_SPP_RESP_INVL;
1184                                 break;
1185                         }
1186                         spp->spp_flags |= resp;
1187                         len -= plen;
1188                         rspp = (struct fc_els_spp *)((char *)rspp + plen);
1189                         spp = (struct fc_els_spp *)((char *)spp + plen);
1190                 }
1191
1192                 /*
1193                  * Send LS_ACC.  If this fails, the originator should retry.
1194                  */
1195                 f_ctl = FC_FC_EX_CTX | FC_FC_LAST_SEQ;
1196                 f_ctl |= FC_FC_END_SEQ | FC_FC_SEQ_INIT;
1197                 ep = fc_seq_exch(sp);
1198                 fc_fill_fc_hdr(fp, FC_RCTL_ELS_REP, ep->did, ep->sid,
1199                                FC_TYPE_ELS, f_ctl, 0);
1200                 lport->tt.seq_send(lport, sp, fp);
1201
1202                 /*
1203                  * Get lock and re-check state.
1204                  */
1205                 switch (rdata->rp_state) {
1206                 case RPORT_ST_PRLI:
1207                         fc_rport_enter_ready(rport);
1208                         break;
1209                 case RPORT_ST_READY:
1210                         break;
1211                 default:
1212                         break;
1213                 }
1214         }
1215         fc_frame_free(rx_fp);
1216 }
1217
1218 /**
1219  * fc_rport_recv_prlo_req() - Handle incoming Process Logout (PRLO) request
1220  * @rport: Fibre Channel remote port that initiated PRLO
1221  * @sp: current sequence in the PRLO exchange
1222  * @fp: PRLO request frame
1223  *
1224  * Locking Note: The rport lock is exected to be held before calling
1225  * this function.
1226  */
1227 static void fc_rport_recv_prlo_req(struct fc_rport *rport, struct fc_seq *sp,
1228                                    struct fc_frame *fp)
1229 {
1230         struct fc_rport_libfc_priv *rdata = rport->dd_data;
1231         struct fc_lport *lport = rdata->local_port;
1232
1233         struct fc_frame_header *fh;
1234         struct fc_seq_els_data rjt_data;
1235
1236         fh = fc_frame_header_get(fp);
1237
1238         FC_RPORT_DBG(rport, "Received PRLO request while in state %s\n",
1239                      fc_rport_state(rport));
1240
1241         if (rdata->rp_state == RPORT_ST_NONE) {
1242                 fc_frame_free(fp);
1243                 return;
1244         }
1245
1246         rjt_data.fp = NULL;
1247         rjt_data.reason = ELS_RJT_UNAB;
1248         rjt_data.explan = ELS_EXPL_NONE;
1249         lport->tt.seq_els_rsp_send(sp, ELS_LS_RJT, &rjt_data);
1250         fc_frame_free(fp);
1251 }
1252
1253 /**
1254  * fc_rport_recv_logo_req() - Handle incoming Logout (LOGO) request
1255  * @rport: Fibre Channel remote port that initiated LOGO
1256  * @sp: current sequence in the LOGO exchange
1257  * @fp: LOGO request frame
1258  *
1259  * Locking Note: The rport lock is exected to be held before calling
1260  * this function.
1261  */
1262 static void fc_rport_recv_logo_req(struct fc_rport *rport, struct fc_seq *sp,
1263                                    struct fc_frame *fp)
1264 {
1265         struct fc_frame_header *fh;
1266         struct fc_rport_libfc_priv *rdata = rport->dd_data;
1267         struct fc_lport *lport = rdata->local_port;
1268
1269         fh = fc_frame_header_get(fp);
1270
1271         FC_RPORT_DBG(rport, "Received LOGO request while in state %s\n",
1272                      fc_rport_state(rport));
1273
1274         if (rdata->rp_state == RPORT_ST_NONE) {
1275                 fc_frame_free(fp);
1276                 return;
1277         }
1278
1279         rdata->event = RPORT_EV_LOGO;
1280         fc_rport_state_enter(rport, RPORT_ST_NONE);
1281         queue_work(rport_event_queue, &rdata->event_work);
1282
1283         lport->tt.seq_els_rsp_send(sp, ELS_LS_ACC, NULL);
1284         fc_frame_free(fp);
1285 }
1286
1287 static void fc_rport_flush_queue(void)
1288 {
1289         flush_workqueue(rport_event_queue);
1290 }
1291
1292 int fc_rport_init(struct fc_lport *lport)
1293 {
1294         if (!lport->tt.rport_create)
1295                 lport->tt.rport_create = fc_rport_rogue_create;
1296
1297         if (!lport->tt.rport_login)
1298                 lport->tt.rport_login = fc_rport_login;
1299
1300         if (!lport->tt.rport_logoff)
1301                 lport->tt.rport_logoff = fc_rport_logoff;
1302
1303         if (!lport->tt.rport_recv_req)
1304                 lport->tt.rport_recv_req = fc_rport_recv_req;
1305
1306         if (!lport->tt.rport_flush_queue)
1307                 lport->tt.rport_flush_queue = fc_rport_flush_queue;
1308
1309         return 0;
1310 }
1311 EXPORT_SYMBOL(fc_rport_init);
1312
1313 int fc_setup_rport(void)
1314 {
1315         rport_event_queue = create_singlethread_workqueue("fc_rport_eq");
1316         if (!rport_event_queue)
1317                 return -ENOMEM;
1318         return 0;
1319 }
1320 EXPORT_SYMBOL(fc_setup_rport);
1321
1322 void fc_destroy_rport(void)
1323 {
1324         destroy_workqueue(rport_event_queue);
1325 }
1326 EXPORT_SYMBOL(fc_destroy_rport);
1327
1328 void fc_rport_terminate_io(struct fc_rport *rport)
1329 {
1330         struct fc_rport_libfc_priv *rdata = rport->dd_data;
1331         struct fc_lport *lport = rdata->local_port;
1332
1333         lport->tt.exch_mgr_reset(lport, 0, rport->port_id);
1334         lport->tt.exch_mgr_reset(lport, rport->port_id, 0);
1335 }
1336 EXPORT_SYMBOL(fc_rport_terminate_io);