1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23#include <linux/blkdev.h>
24#include <linux/delay.h>
25#include <linux/module.h>
26#include <linux/dma-mapping.h>
27#include <linux/idr.h>
28#include <linux/interrupt.h>
29#include <linux/kthread.h>
30#include <linux/slab.h>
31#include <linux/pci.h>
32#include <linux/spinlock.h>
33#include <linux/ctype.h>
34
35#include <scsi/scsi.h>
36#include <scsi/scsi_device.h>
37#include <scsi/scsi_host.h>
38#include <scsi/scsi_transport_fc.h>
39#include <scsi/fc/fc_fs.h>
40
41#include <linux/nvme-fc-driver.h>
42
43#include "lpfc_hw4.h"
44#include "lpfc_hw.h"
45#include "lpfc_sli.h"
46#include "lpfc_sli4.h"
47#include "lpfc_nl.h"
48#include "lpfc_disc.h"
49#include "lpfc.h"
50#include "lpfc_scsi.h"
51#include "lpfc_nvme.h"
52#include "lpfc_nvmet.h"
53#include "lpfc_logmsg.h"
54#include "lpfc_crtn.h"
55#include "lpfc_vport.h"
56#include "lpfc_version.h"
57#include "lpfc_compat.h"
58#include "lpfc_debugfs.h"
59#include "lpfc_bsg.h"
60
61#ifdef CONFIG_SCSI_LPFC_DEBUG_FS
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93static int lpfc_debugfs_enable = 1;
94module_param(lpfc_debugfs_enable, int, S_IRUGO);
95MODULE_PARM_DESC(lpfc_debugfs_enable, "Enable debugfs services");
96
97
98static int lpfc_debugfs_max_disc_trc;
99module_param(lpfc_debugfs_max_disc_trc, int, S_IRUGO);
100MODULE_PARM_DESC(lpfc_debugfs_max_disc_trc,
101 "Set debugfs discovery trace depth");
102
103
104static int lpfc_debugfs_max_slow_ring_trc;
105module_param(lpfc_debugfs_max_slow_ring_trc, int, S_IRUGO);
106MODULE_PARM_DESC(lpfc_debugfs_max_slow_ring_trc,
107 "Set debugfs slow ring trace depth");
108
109
110static int lpfc_debugfs_max_nvmeio_trc;
111module_param(lpfc_debugfs_max_nvmeio_trc, int, 0444);
112MODULE_PARM_DESC(lpfc_debugfs_max_nvmeio_trc,
113 "Set debugfs NVME IO trace depth");
114
115static int lpfc_debugfs_mask_disc_trc;
116module_param(lpfc_debugfs_mask_disc_trc, int, S_IRUGO);
117MODULE_PARM_DESC(lpfc_debugfs_mask_disc_trc,
118 "Set debugfs discovery trace mask");
119
120#include <linux/debugfs.h>
121
122static atomic_t lpfc_debugfs_seq_trc_cnt = ATOMIC_INIT(0);
123static unsigned long lpfc_debugfs_start_time = 0L;
124
125
126static struct lpfc_idiag idiag;
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147static int
148lpfc_debugfs_disc_trc_data(struct lpfc_vport *vport, char *buf, int size)
149{
150 int i, index, len, enable;
151 uint32_t ms;
152 struct lpfc_debugfs_trc *dtp;
153 char *buffer;
154
155 buffer = kmalloc(LPFC_DEBUG_TRC_ENTRY_SIZE, GFP_KERNEL);
156 if (!buffer)
157 return 0;
158
159 enable = lpfc_debugfs_enable;
160 lpfc_debugfs_enable = 0;
161
162 len = 0;
163 index = (atomic_read(&vport->disc_trc_cnt) + 1) &
164 (lpfc_debugfs_max_disc_trc - 1);
165 for (i = index; i < lpfc_debugfs_max_disc_trc; i++) {
166 dtp = vport->disc_trc + i;
167 if (!dtp->fmt)
168 continue;
169 ms = jiffies_to_msecs(dtp->jif - lpfc_debugfs_start_time);
170 snprintf(buffer,
171 LPFC_DEBUG_TRC_ENTRY_SIZE, "%010d:%010d ms:%s\n",
172 dtp->seq_cnt, ms, dtp->fmt);
173 len += snprintf(buf+len, size-len, buffer,
174 dtp->data1, dtp->data2, dtp->data3);
175 }
176 for (i = 0; i < index; i++) {
177 dtp = vport->disc_trc + i;
178 if (!dtp->fmt)
179 continue;
180 ms = jiffies_to_msecs(dtp->jif - lpfc_debugfs_start_time);
181 snprintf(buffer,
182 LPFC_DEBUG_TRC_ENTRY_SIZE, "%010d:%010d ms:%s\n",
183 dtp->seq_cnt, ms, dtp->fmt);
184 len += snprintf(buf+len, size-len, buffer,
185 dtp->data1, dtp->data2, dtp->data3);
186 }
187
188 lpfc_debugfs_enable = enable;
189 kfree(buffer);
190
191 return len;
192}
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213static int
214lpfc_debugfs_slow_ring_trc_data(struct lpfc_hba *phba, char *buf, int size)
215{
216 int i, index, len, enable;
217 uint32_t ms;
218 struct lpfc_debugfs_trc *dtp;
219 char *buffer;
220
221 buffer = kmalloc(LPFC_DEBUG_TRC_ENTRY_SIZE, GFP_KERNEL);
222 if (!buffer)
223 return 0;
224
225 enable = lpfc_debugfs_enable;
226 lpfc_debugfs_enable = 0;
227
228 len = 0;
229 index = (atomic_read(&phba->slow_ring_trc_cnt) + 1) &
230 (lpfc_debugfs_max_slow_ring_trc - 1);
231 for (i = index; i < lpfc_debugfs_max_slow_ring_trc; i++) {
232 dtp = phba->slow_ring_trc + i;
233 if (!dtp->fmt)
234 continue;
235 ms = jiffies_to_msecs(dtp->jif - lpfc_debugfs_start_time);
236 snprintf(buffer,
237 LPFC_DEBUG_TRC_ENTRY_SIZE, "%010d:%010d ms:%s\n",
238 dtp->seq_cnt, ms, dtp->fmt);
239 len += snprintf(buf+len, size-len, buffer,
240 dtp->data1, dtp->data2, dtp->data3);
241 }
242 for (i = 0; i < index; i++) {
243 dtp = phba->slow_ring_trc + i;
244 if (!dtp->fmt)
245 continue;
246 ms = jiffies_to_msecs(dtp->jif - lpfc_debugfs_start_time);
247 snprintf(buffer,
248 LPFC_DEBUG_TRC_ENTRY_SIZE, "%010d:%010d ms:%s\n",
249 dtp->seq_cnt, ms, dtp->fmt);
250 len += snprintf(buf+len, size-len, buffer,
251 dtp->data1, dtp->data2, dtp->data3);
252 }
253
254 lpfc_debugfs_enable = enable;
255 kfree(buffer);
256
257 return len;
258}
259
260static int lpfc_debugfs_last_hbq = -1;
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281static int
282lpfc_debugfs_hbqinfo_data(struct lpfc_hba *phba, char *buf, int size)
283{
284 int len = 0;
285 int i, j, found, posted, low;
286 uint32_t phys, raw_index, getidx;
287 struct lpfc_hbq_init *hip;
288 struct hbq_s *hbqs;
289 struct lpfc_hbq_entry *hbqe;
290 struct lpfc_dmabuf *d_buf;
291 struct hbq_dmabuf *hbq_buf;
292
293 if (phba->sli_rev != 3)
294 return 0;
295
296 spin_lock_irq(&phba->hbalock);
297
298
299 i = lpfc_sli_hbq_count();
300 if (i > 1) {
301 lpfc_debugfs_last_hbq++;
302 if (lpfc_debugfs_last_hbq >= i)
303 lpfc_debugfs_last_hbq = 0;
304 }
305 else
306 lpfc_debugfs_last_hbq = 0;
307
308 i = lpfc_debugfs_last_hbq;
309
310 len += snprintf(buf+len, size-len, "HBQ %d Info\n", i);
311
312 hbqs = &phba->hbqs[i];
313 posted = 0;
314 list_for_each_entry(d_buf, &hbqs->hbq_buffer_list, list)
315 posted++;
316
317 hip = lpfc_hbq_defs[i];
318 len += snprintf(buf+len, size-len,
319 "idx:%d prof:%d rn:%d bufcnt:%d icnt:%d acnt:%d posted %d\n",
320 hip->hbq_index, hip->profile, hip->rn,
321 hip->buffer_count, hip->init_count, hip->add_count, posted);
322
323 raw_index = phba->hbq_get[i];
324 getidx = le32_to_cpu(raw_index);
325 len += snprintf(buf+len, size-len,
326 "entries:%d bufcnt:%d Put:%d nPut:%d localGet:%d hbaGet:%d\n",
327 hbqs->entry_count, hbqs->buffer_count, hbqs->hbqPutIdx,
328 hbqs->next_hbqPutIdx, hbqs->local_hbqGetIdx, getidx);
329
330 hbqe = (struct lpfc_hbq_entry *) phba->hbqs[i].hbq_virt;
331 for (j=0; j<hbqs->entry_count; j++) {
332 len += snprintf(buf+len, size-len,
333 "%03d: %08x %04x %05x ", j,
334 le32_to_cpu(hbqe->bde.addrLow),
335 le32_to_cpu(hbqe->bde.tus.w),
336 le32_to_cpu(hbqe->buffer_tag));
337 i = 0;
338 found = 0;
339
340
341 low = hbqs->hbqPutIdx - posted;
342 if (low >= 0) {
343 if ((j >= hbqs->hbqPutIdx) || (j < low)) {
344 len += snprintf(buf+len, size-len, "Unused\n");
345 goto skipit;
346 }
347 }
348 else {
349 if ((j >= hbqs->hbqPutIdx) &&
350 (j < (hbqs->entry_count+low))) {
351 len += snprintf(buf+len, size-len, "Unused\n");
352 goto skipit;
353 }
354 }
355
356
357 list_for_each_entry(d_buf, &hbqs->hbq_buffer_list, list) {
358 hbq_buf = container_of(d_buf, struct hbq_dmabuf, dbuf);
359 phys = ((uint64_t)hbq_buf->dbuf.phys & 0xffffffff);
360 if (phys == le32_to_cpu(hbqe->bde.addrLow)) {
361 len += snprintf(buf+len, size-len,
362 "Buf%d: %p %06x\n", i,
363 hbq_buf->dbuf.virt, hbq_buf->tag);
364 found = 1;
365 break;
366 }
367 i++;
368 }
369 if (!found) {
370 len += snprintf(buf+len, size-len, "No DMAinfo?\n");
371 }
372skipit:
373 hbqe++;
374 if (len > LPFC_HBQINFO_SIZE - 54)
375 break;
376 }
377 spin_unlock_irq(&phba->hbalock);
378 return len;
379}
380
381static int lpfc_debugfs_last_hba_slim_off;
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401static int
402lpfc_debugfs_dumpHBASlim_data(struct lpfc_hba *phba, char *buf, int size)
403{
404 int len = 0;
405 int i, off;
406 uint32_t *ptr;
407 char *buffer;
408
409 buffer = kmalloc(1024, GFP_KERNEL);
410 if (!buffer)
411 return 0;
412
413 off = 0;
414 spin_lock_irq(&phba->hbalock);
415
416 len += snprintf(buf+len, size-len, "HBA SLIM\n");
417 lpfc_memcpy_from_slim(buffer,
418 phba->MBslimaddr + lpfc_debugfs_last_hba_slim_off, 1024);
419
420 ptr = (uint32_t *)&buffer[0];
421 off = lpfc_debugfs_last_hba_slim_off;
422
423
424 lpfc_debugfs_last_hba_slim_off += 1024;
425 if (lpfc_debugfs_last_hba_slim_off >= 4096)
426 lpfc_debugfs_last_hba_slim_off = 0;
427
428 i = 1024;
429 while (i > 0) {
430 len += snprintf(buf+len, size-len,
431 "%08x: %08x %08x %08x %08x %08x %08x %08x %08x\n",
432 off, *ptr, *(ptr+1), *(ptr+2), *(ptr+3), *(ptr+4),
433 *(ptr+5), *(ptr+6), *(ptr+7));
434 ptr += 8;
435 i -= (8 * sizeof(uint32_t));
436 off += (8 * sizeof(uint32_t));
437 }
438
439 spin_unlock_irq(&phba->hbalock);
440 kfree(buffer);
441
442 return len;
443}
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460static int
461lpfc_debugfs_dumpHostSlim_data(struct lpfc_hba *phba, char *buf, int size)
462{
463 int len = 0;
464 int i, off;
465 uint32_t word0, word1, word2, word3;
466 uint32_t *ptr;
467 struct lpfc_pgp *pgpp;
468 struct lpfc_sli *psli = &phba->sli;
469 struct lpfc_sli_ring *pring;
470
471 off = 0;
472 spin_lock_irq(&phba->hbalock);
473
474 len += snprintf(buf+len, size-len, "SLIM Mailbox\n");
475 ptr = (uint32_t *)phba->slim2p.virt;
476 i = sizeof(MAILBOX_t);
477 while (i > 0) {
478 len += snprintf(buf+len, size-len,
479 "%08x: %08x %08x %08x %08x %08x %08x %08x %08x\n",
480 off, *ptr, *(ptr+1), *(ptr+2), *(ptr+3), *(ptr+4),
481 *(ptr+5), *(ptr+6), *(ptr+7));
482 ptr += 8;
483 i -= (8 * sizeof(uint32_t));
484 off += (8 * sizeof(uint32_t));
485 }
486
487 len += snprintf(buf+len, size-len, "SLIM PCB\n");
488 ptr = (uint32_t *)phba->pcb;
489 i = sizeof(PCB_t);
490 while (i > 0) {
491 len += snprintf(buf+len, size-len,
492 "%08x: %08x %08x %08x %08x %08x %08x %08x %08x\n",
493 off, *ptr, *(ptr+1), *(ptr+2), *(ptr+3), *(ptr+4),
494 *(ptr+5), *(ptr+6), *(ptr+7));
495 ptr += 8;
496 i -= (8 * sizeof(uint32_t));
497 off += (8 * sizeof(uint32_t));
498 }
499
500 if (phba->sli_rev <= LPFC_SLI_REV3) {
501 for (i = 0; i < 4; i++) {
502 pgpp = &phba->port_gp[i];
503 pring = &psli->sli3_ring[i];
504 len += snprintf(buf+len, size-len,
505 "Ring %d: CMD GetInx:%d "
506 "(Max:%d Next:%d "
507 "Local:%d flg:x%x) "
508 "RSP PutInx:%d Max:%d\n",
509 i, pgpp->cmdGetInx,
510 pring->sli.sli3.numCiocb,
511 pring->sli.sli3.next_cmdidx,
512 pring->sli.sli3.local_getidx,
513 pring->flag, pgpp->rspPutInx,
514 pring->sli.sli3.numRiocb);
515 }
516
517 word0 = readl(phba->HAregaddr);
518 word1 = readl(phba->CAregaddr);
519 word2 = readl(phba->HSregaddr);
520 word3 = readl(phba->HCregaddr);
521 len += snprintf(buf+len, size-len, "HA:%08x CA:%08x HS:%08x "
522 "HC:%08x\n", word0, word1, word2, word3);
523 }
524 spin_unlock_irq(&phba->hbalock);
525 return len;
526}
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543static int
544lpfc_debugfs_nodelist_data(struct lpfc_vport *vport, char *buf, int size)
545{
546 int len = 0;
547 int cnt;
548 struct Scsi_Host *shost = lpfc_shost_from_vport(vport);
549 struct lpfc_hba *phba = vport->phba;
550 struct lpfc_nodelist *ndlp;
551 unsigned char *statep;
552 struct nvme_fc_local_port *localport;
553 struct lpfc_nvmet_tgtport *tgtp;
554 struct nvme_fc_remote_port *nrport;
555
556 cnt = (LPFC_NODELIST_SIZE / LPFC_NODELIST_ENTRY_SIZE);
557
558 len += snprintf(buf+len, size-len, "\nFCP Nodelist Entries ...\n");
559 spin_lock_irq(shost->host_lock);
560 list_for_each_entry(ndlp, &vport->fc_nodes, nlp_listp) {
561 if (!cnt) {
562 len += snprintf(buf+len, size-len,
563 "Missing Nodelist Entries\n");
564 break;
565 }
566 cnt--;
567 switch (ndlp->nlp_state) {
568 case NLP_STE_UNUSED_NODE:
569 statep = "UNUSED";
570 break;
571 case NLP_STE_PLOGI_ISSUE:
572 statep = "PLOGI ";
573 break;
574 case NLP_STE_ADISC_ISSUE:
575 statep = "ADISC ";
576 break;
577 case NLP_STE_REG_LOGIN_ISSUE:
578 statep = "REGLOG";
579 break;
580 case NLP_STE_PRLI_ISSUE:
581 statep = "PRLI ";
582 break;
583 case NLP_STE_LOGO_ISSUE:
584 statep = "LOGO ";
585 break;
586 case NLP_STE_UNMAPPED_NODE:
587 statep = "UNMAP ";
588 break;
589 case NLP_STE_MAPPED_NODE:
590 statep = "MAPPED";
591 break;
592 case NLP_STE_NPR_NODE:
593 statep = "NPR ";
594 break;
595 default:
596 statep = "UNKNOWN";
597 }
598 len += snprintf(buf+len, size-len, "%s DID:x%06x ",
599 statep, ndlp->nlp_DID);
600 len += snprintf(buf+len, size-len,
601 "WWPN x%llx ",
602 wwn_to_u64(ndlp->nlp_portname.u.wwn));
603 len += snprintf(buf+len, size-len,
604 "WWNN x%llx ",
605 wwn_to_u64(ndlp->nlp_nodename.u.wwn));
606 if (ndlp->nlp_flag & NLP_RPI_REGISTERED)
607 len += snprintf(buf+len, size-len, "RPI:%03d ",
608 ndlp->nlp_rpi);
609 else
610 len += snprintf(buf+len, size-len, "RPI:none ");
611 len += snprintf(buf+len, size-len, "flag:x%08x ",
612 ndlp->nlp_flag);
613 if (!ndlp->nlp_type)
614 len += snprintf(buf+len, size-len, "UNKNOWN_TYPE ");
615 if (ndlp->nlp_type & NLP_FC_NODE)
616 len += snprintf(buf+len, size-len, "FC_NODE ");
617 if (ndlp->nlp_type & NLP_FABRIC)
618 len += snprintf(buf+len, size-len, "FABRIC ");
619 if (ndlp->nlp_type & NLP_FCP_TARGET)
620 len += snprintf(buf+len, size-len, "FCP_TGT sid:%d ",
621 ndlp->nlp_sid);
622 if (ndlp->nlp_type & NLP_FCP_INITIATOR)
623 len += snprintf(buf+len, size-len, "FCP_INITIATOR ");
624 if (ndlp->nlp_type & NLP_NVME_TARGET)
625 len += snprintf(buf + len,
626 size - len, "NVME_TGT sid:%d ",
627 NLP_NO_SID);
628 if (ndlp->nlp_type & NLP_NVME_INITIATOR)
629 len += snprintf(buf + len,
630 size - len, "NVME_INITIATOR ");
631 len += snprintf(buf+len, size-len, "usgmap:%x ",
632 ndlp->nlp_usg_map);
633 len += snprintf(buf+len, size-len, "refcnt:%x",
634 kref_read(&ndlp->kref));
635 len += snprintf(buf+len, size-len, "\n");
636 }
637 spin_unlock_irq(shost->host_lock);
638
639 if (phba->nvmet_support && phba->targetport && (vport == phba->pport)) {
640 tgtp = (struct lpfc_nvmet_tgtport *)phba->targetport->private;
641 len += snprintf(buf + len, size - len,
642 "\nNVME Targetport Entry ...\n");
643
644
645 if (phba->targetport->port_id)
646 statep = "REGISTERED";
647 else
648 statep = "INIT";
649 len += snprintf(buf + len, size - len,
650 "TGT WWNN x%llx WWPN x%llx State %s\n",
651 wwn_to_u64(vport->fc_nodename.u.wwn),
652 wwn_to_u64(vport->fc_portname.u.wwn),
653 statep);
654 len += snprintf(buf + len, size - len,
655 " Targetport DID x%06x\n",
656 phba->targetport->port_id);
657 goto out_exit;
658 }
659
660 len += snprintf(buf + len, size - len,
661 "\nNVME Lport/Rport Entries ...\n");
662
663 localport = vport->localport;
664 if (!localport)
665 goto out_exit;
666
667 spin_lock_irq(shost->host_lock);
668
669
670 if (localport->port_id)
671 statep = "ONLINE";
672 else
673 statep = "UNKNOWN ";
674
675 len += snprintf(buf + len, size - len,
676 "Lport DID x%06x PortState %s\n",
677 localport->port_id, statep);
678
679 len += snprintf(buf + len, size - len, "\tRport List:\n");
680 list_for_each_entry(ndlp, &vport->fc_nodes, nlp_listp) {
681
682 if (!ndlp->nrport)
683 continue;
684
685 nrport = ndlp->nrport->remoteport;
686
687
688 switch (nrport->port_state) {
689 case FC_OBJSTATE_ONLINE:
690 statep = "ONLINE";
691 break;
692 case FC_OBJSTATE_UNKNOWN:
693 statep = "UNKNOWN ";
694 break;
695 default:
696 statep = "UNSUPPORTED";
697 break;
698 }
699
700
701 len += snprintf(buf + len, size - len,
702 "\t%s Port ID:x%06x ",
703 statep, nrport->port_id);
704 len += snprintf(buf + len, size - len, "WWPN x%llx ",
705 nrport->port_name);
706 len += snprintf(buf + len, size - len, "WWNN x%llx ",
707 nrport->node_name);
708
709
710 if (nrport->port_role & FC_PORT_ROLE_NVME_INITIATOR)
711 len += snprintf(buf + len, size - len,
712 "INITIATOR ");
713 if (nrport->port_role & FC_PORT_ROLE_NVME_TARGET)
714 len += snprintf(buf + len, size - len,
715 "TARGET ");
716 if (nrport->port_role & FC_PORT_ROLE_NVME_DISCOVERY)
717 len += snprintf(buf + len, size - len,
718 "DISCSRVC ");
719 if (nrport->port_role & ~(FC_PORT_ROLE_NVME_INITIATOR |
720 FC_PORT_ROLE_NVME_TARGET |
721 FC_PORT_ROLE_NVME_DISCOVERY))
722 len += snprintf(buf + len, size - len,
723 "UNKNOWN ROLE x%x",
724 nrport->port_role);
725
726 len += snprintf(buf + len, size - len, "\n");
727 }
728
729 spin_unlock_irq(shost->host_lock);
730 out_exit:
731 return len;
732}
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747static int
748lpfc_debugfs_nvmestat_data(struct lpfc_vport *vport, char *buf, int size)
749{
750 struct lpfc_hba *phba = vport->phba;
751 struct lpfc_nvmet_tgtport *tgtp;
752 struct lpfc_nvmet_rcv_ctx *ctxp, *next_ctxp;
753 struct nvme_fc_local_port *localport;
754 struct lpfc_nvme_lport *lport;
755 uint64_t tot, data1, data2, data3;
756 int len = 0;
757 int cnt;
758
759 if (phba->nvmet_support) {
760 if (!phba->targetport)
761 return len;
762 tgtp = (struct lpfc_nvmet_tgtport *)phba->targetport->private;
763 len += snprintf(buf + len, size - len,
764 "\nNVME Targetport Statistics\n");
765
766 len += snprintf(buf + len, size - len,
767 "LS: Rcv %08x Drop %08x Abort %08x\n",
768 atomic_read(&tgtp->rcv_ls_req_in),
769 atomic_read(&tgtp->rcv_ls_req_drop),
770 atomic_read(&tgtp->xmt_ls_abort));
771 if (atomic_read(&tgtp->rcv_ls_req_in) !=
772 atomic_read(&tgtp->rcv_ls_req_out)) {
773 len += snprintf(buf + len, size - len,
774 "Rcv LS: in %08x != out %08x\n",
775 atomic_read(&tgtp->rcv_ls_req_in),
776 atomic_read(&tgtp->rcv_ls_req_out));
777 }
778
779 len += snprintf(buf + len, size - len,
780 "LS: Xmt %08x Drop %08x Cmpl %08x\n",
781 atomic_read(&tgtp->xmt_ls_rsp),
782 atomic_read(&tgtp->xmt_ls_drop),
783 atomic_read(&tgtp->xmt_ls_rsp_cmpl));
784
785 len += snprintf(buf + len, size - len,
786 "LS: RSP Abort %08x xb %08x Err %08x\n",
787 atomic_read(&tgtp->xmt_ls_rsp_aborted),
788 atomic_read(&tgtp->xmt_ls_rsp_xb_set),
789 atomic_read(&tgtp->xmt_ls_rsp_error));
790
791 len += snprintf(buf + len, size - len,
792 "FCP: Rcv %08x Defer %08x Release %08x "
793 "Drop %08x\n",
794 atomic_read(&tgtp->rcv_fcp_cmd_in),
795 atomic_read(&tgtp->rcv_fcp_cmd_defer),
796 atomic_read(&tgtp->xmt_fcp_release),
797 atomic_read(&tgtp->rcv_fcp_cmd_drop));
798
799 if (atomic_read(&tgtp->rcv_fcp_cmd_in) !=
800 atomic_read(&tgtp->rcv_fcp_cmd_out)) {
801 len += snprintf(buf + len, size - len,
802 "Rcv FCP: in %08x != out %08x\n",
803 atomic_read(&tgtp->rcv_fcp_cmd_in),
804 atomic_read(&tgtp->rcv_fcp_cmd_out));
805 }
806
807 len += snprintf(buf + len, size - len,
808 "FCP Rsp: read %08x readrsp %08x "
809 "write %08x rsp %08x\n",
810 atomic_read(&tgtp->xmt_fcp_read),
811 atomic_read(&tgtp->xmt_fcp_read_rsp),
812 atomic_read(&tgtp->xmt_fcp_write),
813 atomic_read(&tgtp->xmt_fcp_rsp));
814
815 len += snprintf(buf + len, size - len,
816 "FCP Rsp Cmpl: %08x err %08x drop %08x\n",
817 atomic_read(&tgtp->xmt_fcp_rsp_cmpl),
818 atomic_read(&tgtp->xmt_fcp_rsp_error),
819 atomic_read(&tgtp->xmt_fcp_rsp_drop));
820
821 len += snprintf(buf + len, size - len,
822 "FCP Rsp Abort: %08x xb %08x xricqe %08x\n",
823 atomic_read(&tgtp->xmt_fcp_rsp_aborted),
824 atomic_read(&tgtp->xmt_fcp_rsp_xb_set),
825 atomic_read(&tgtp->xmt_fcp_xri_abort_cqe));
826
827 len += snprintf(buf + len, size - len,
828 "ABORT: Xmt %08x Cmpl %08x\n",
829 atomic_read(&tgtp->xmt_fcp_abort),
830 atomic_read(&tgtp->xmt_fcp_abort_cmpl));
831
832 len += snprintf(buf + len, size - len,
833 "ABORT: Sol %08x Usol %08x Err %08x Cmpl %08x",
834 atomic_read(&tgtp->xmt_abort_sol),
835 atomic_read(&tgtp->xmt_abort_unsol),
836 atomic_read(&tgtp->xmt_abort_rsp),
837 atomic_read(&tgtp->xmt_abort_rsp_error));
838
839 len += snprintf(buf + len, size - len, "\n");
840
841 cnt = 0;
842 spin_lock(&phba->sli4_hba.abts_nvme_buf_list_lock);
843 list_for_each_entry_safe(ctxp, next_ctxp,
844 &phba->sli4_hba.lpfc_abts_nvmet_ctx_list,
845 list) {
846 cnt++;
847 }
848 spin_unlock(&phba->sli4_hba.abts_nvme_buf_list_lock);
849 if (cnt) {
850 len += snprintf(buf + len, size - len,
851 "ABORT: %d ctx entries\n", cnt);
852 spin_lock(&phba->sli4_hba.abts_nvme_buf_list_lock);
853 list_for_each_entry_safe(ctxp, next_ctxp,
854 &phba->sli4_hba.lpfc_abts_nvmet_ctx_list,
855 list) {
856 if (len >= (size - LPFC_DEBUG_OUT_LINE_SZ))
857 break;
858 len += snprintf(buf + len, size - len,
859 "Entry: oxid %x state %x "
860 "flag %x\n",
861 ctxp->oxid, ctxp->state,
862 ctxp->flag);
863 }
864 spin_unlock(&phba->sli4_hba.abts_nvme_buf_list_lock);
865 }
866
867
868 tot = atomic_read(&tgtp->rcv_fcp_cmd_drop);
869 tot += atomic_read(&tgtp->xmt_fcp_release);
870 tot = atomic_read(&tgtp->rcv_fcp_cmd_in) - tot;
871
872 len += snprintf(buf + len, size - len,
873 "IO_CTX: %08x WAIT: cur %08x tot %08x\n"
874 "CTX Outstanding %08llx\n",
875 phba->sli4_hba.nvmet_xri_cnt,
876 phba->sli4_hba.nvmet_io_wait_cnt,
877 phba->sli4_hba.nvmet_io_wait_total,
878 tot);
879 } else {
880 if (!(phba->cfg_enable_fc4_type & LPFC_ENABLE_NVME))
881 return len;
882
883 len += snprintf(buf + len, size - len,
884 "\nNVME Lport Statistics\n");
885
886 len += snprintf(buf + len, size - len,
887 "LS: Xmt %016x Cmpl %016x\n",
888 atomic_read(&phba->fc4NvmeLsRequests),
889 atomic_read(&phba->fc4NvmeLsCmpls));
890
891 tot = atomic_read(&phba->fc4NvmeIoCmpls);
892 data1 = atomic_read(&phba->fc4NvmeInputRequests);
893 data2 = atomic_read(&phba->fc4NvmeOutputRequests);
894 data3 = atomic_read(&phba->fc4NvmeControlRequests);
895
896 len += snprintf(buf + len, size - len,
897 "FCP: Rd %016llx Wr %016llx IO %016llx\n",
898 data1, data2, data3);
899
900 len += snprintf(buf + len, size - len,
901 " Cmpl %016llx Outstanding %016llx\n",
902 tot, (data1 + data2 + data3) - tot);
903
904 localport = vport->localport;
905 if (!localport)
906 return len;
907 lport = (struct lpfc_nvme_lport *)localport->private;
908 if (!lport)
909 return len;
910
911 len += snprintf(buf + len, size - len,
912 "LS Xmt Err: Abrt %08x Err %08x "
913 "Cmpl Err: xb %08x Err %08x\n",
914 atomic_read(&lport->xmt_ls_abort),
915 atomic_read(&lport->xmt_ls_err),
916 atomic_read(&lport->cmpl_ls_xb),
917 atomic_read(&lport->cmpl_ls_err));
918
919 len += snprintf(buf + len, size - len,
920 "FCP Xmt Err: noxri %06x nondlp %06x "
921 "qdepth %06x wqerr %06x Abrt %06x\n",
922 atomic_read(&lport->xmt_fcp_noxri),
923 atomic_read(&lport->xmt_fcp_bad_ndlp),
924 atomic_read(&lport->xmt_fcp_qdepth),
925 atomic_read(&lport->xmt_fcp_wqerr),
926 atomic_read(&lport->xmt_fcp_abort));
927
928 len += snprintf(buf + len, size - len,
929 "FCP Cmpl Err: xb %08x Err %08x\n",
930 atomic_read(&lport->cmpl_fcp_xb),
931 atomic_read(&lport->cmpl_fcp_err));
932
933 }
934
935 return len;
936}
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952static int
953lpfc_debugfs_nvmektime_data(struct lpfc_vport *vport, char *buf, int size)
954{
955 struct lpfc_hba *phba = vport->phba;
956 int len = 0;
957
958 if (phba->nvmet_support == 0) {
959
960 len += snprintf(buf + len, PAGE_SIZE - len,
961 "ktime %s: Total Samples: %lld\n",
962 (phba->ktime_on ? "Enabled" : "Disabled"),
963 phba->ktime_data_samples);
964 if (phba->ktime_data_samples == 0)
965 return len;
966
967 len += snprintf(
968 buf + len, PAGE_SIZE - len,
969 "Segment 1: Last NVME Cmd cmpl "
970 "done -to- Start of next NVME cnd (in driver)\n");
971 len += snprintf(
972 buf + len, PAGE_SIZE - len,
973 "avg:%08lld min:%08lld max %08lld\n",
974 div_u64(phba->ktime_seg1_total,
975 phba->ktime_data_samples),
976 phba->ktime_seg1_min,
977 phba->ktime_seg1_max);
978 len += snprintf(
979 buf + len, PAGE_SIZE - len,
980 "Segment 2: Driver start of NVME cmd "
981 "-to- Firmware WQ doorbell\n");
982 len += snprintf(
983 buf + len, PAGE_SIZE - len,
984 "avg:%08lld min:%08lld max %08lld\n",
985 div_u64(phba->ktime_seg2_total,
986 phba->ktime_data_samples),
987 phba->ktime_seg2_min,
988 phba->ktime_seg2_max);
989 len += snprintf(
990 buf + len, PAGE_SIZE - len,
991 "Segment 3: Firmware WQ doorbell -to- "
992 "MSI-X ISR cmpl\n");
993 len += snprintf(
994 buf + len, PAGE_SIZE - len,
995 "avg:%08lld min:%08lld max %08lld\n",
996 div_u64(phba->ktime_seg3_total,
997 phba->ktime_data_samples),
998 phba->ktime_seg3_min,
999 phba->ktime_seg3_max);
1000 len += snprintf(
1001 buf + len, PAGE_SIZE - len,
1002 "Segment 4: MSI-X ISR cmpl -to- "
1003 "NVME cmpl done\n");
1004 len += snprintf(
1005 buf + len, PAGE_SIZE - len,
1006 "avg:%08lld min:%08lld max %08lld\n",
1007 div_u64(phba->ktime_seg4_total,
1008 phba->ktime_data_samples),
1009 phba->ktime_seg4_min,
1010 phba->ktime_seg4_max);
1011 len += snprintf(
1012 buf + len, PAGE_SIZE - len,
1013 "Total IO avg time: %08lld\n",
1014 div_u64(phba->ktime_seg1_total +
1015 phba->ktime_seg2_total +
1016 phba->ktime_seg3_total +
1017 phba->ktime_seg4_total,
1018 phba->ktime_data_samples));
1019 return len;
1020 }
1021
1022
1023 len += snprintf(buf + len, PAGE_SIZE-len,
1024 "ktime %s: Total Samples: %lld %lld\n",
1025 (phba->ktime_on ? "Enabled" : "Disabled"),
1026 phba->ktime_data_samples,
1027 phba->ktime_status_samples);
1028 if (phba->ktime_data_samples == 0)
1029 return len;
1030
1031 len += snprintf(buf + len, PAGE_SIZE-len,
1032 "Segment 1: MSI-X ISR Rcv cmd -to- "
1033 "cmd pass to NVME Layer\n");
1034 len += snprintf(buf + len, PAGE_SIZE-len,
1035 "avg:%08lld min:%08lld max %08lld\n",
1036 div_u64(phba->ktime_seg1_total,
1037 phba->ktime_data_samples),
1038 phba->ktime_seg1_min,
1039 phba->ktime_seg1_max);
1040 len += snprintf(buf + len, PAGE_SIZE-len,
1041 "Segment 2: cmd pass to NVME Layer- "
1042 "-to- Driver rcv cmd OP (action)\n");
1043 len += snprintf(buf + len, PAGE_SIZE-len,
1044 "avg:%08lld min:%08lld max %08lld\n",
1045 div_u64(phba->ktime_seg2_total,
1046 phba->ktime_data_samples),
1047 phba->ktime_seg2_min,
1048 phba->ktime_seg2_max);
1049 len += snprintf(buf + len, PAGE_SIZE-len,
1050 "Segment 3: Driver rcv cmd OP -to- "
1051 "Firmware WQ doorbell: cmd\n");
1052 len += snprintf(buf + len, PAGE_SIZE-len,
1053 "avg:%08lld min:%08lld max %08lld\n",
1054 div_u64(phba->ktime_seg3_total,
1055 phba->ktime_data_samples),
1056 phba->ktime_seg3_min,
1057 phba->ktime_seg3_max);
1058 len += snprintf(buf + len, PAGE_SIZE-len,
1059 "Segment 4: Firmware WQ doorbell: cmd "
1060 "-to- MSI-X ISR for cmd cmpl\n");
1061 len += snprintf(buf + len, PAGE_SIZE-len,
1062 "avg:%08lld min:%08lld max %08lld\n",
1063 div_u64(phba->ktime_seg4_total,
1064 phba->ktime_data_samples),
1065 phba->ktime_seg4_min,
1066 phba->ktime_seg4_max);
1067 len += snprintf(buf + len, PAGE_SIZE-len,
1068 "Segment 5: MSI-X ISR for cmd cmpl "
1069 "-to- NVME layer passed cmd done\n");
1070 len += snprintf(buf + len, PAGE_SIZE-len,
1071 "avg:%08lld min:%08lld max %08lld\n",
1072 div_u64(phba->ktime_seg5_total,
1073 phba->ktime_data_samples),
1074 phba->ktime_seg5_min,
1075 phba->ktime_seg5_max);
1076
1077 if (phba->ktime_status_samples == 0) {
1078 len += snprintf(buf + len, PAGE_SIZE-len,
1079 "Total: cmd received by MSI-X ISR "
1080 "-to- cmd completed on wire\n");
1081 len += snprintf(buf + len, PAGE_SIZE-len,
1082 "avg:%08lld min:%08lld "
1083 "max %08lld\n",
1084 div_u64(phba->ktime_seg10_total,
1085 phba->ktime_data_samples),
1086 phba->ktime_seg10_min,
1087 phba->ktime_seg10_max);
1088 return len;
1089 }
1090
1091 len += snprintf(buf + len, PAGE_SIZE-len,
1092 "Segment 6: NVME layer passed cmd done "
1093 "-to- Driver rcv rsp status OP\n");
1094 len += snprintf(buf + len, PAGE_SIZE-len,
1095 "avg:%08lld min:%08lld max %08lld\n",
1096 div_u64(phba->ktime_seg6_total,
1097 phba->ktime_status_samples),
1098 phba->ktime_seg6_min,
1099 phba->ktime_seg6_max);
1100 len += snprintf(buf + len, PAGE_SIZE-len,
1101 "Segment 7: Driver rcv rsp status OP "
1102 "-to- Firmware WQ doorbell: status\n");
1103 len += snprintf(buf + len, PAGE_SIZE-len,
1104 "avg:%08lld min:%08lld max %08lld\n",
1105 div_u64(phba->ktime_seg7_total,
1106 phba->ktime_status_samples),
1107 phba->ktime_seg7_min,
1108 phba->ktime_seg7_max);
1109 len += snprintf(buf + len, PAGE_SIZE-len,
1110 "Segment 8: Firmware WQ doorbell: status"
1111 " -to- MSI-X ISR for status cmpl\n");
1112 len += snprintf(buf + len, PAGE_SIZE-len,
1113 "avg:%08lld min:%08lld max %08lld\n",
1114 div_u64(phba->ktime_seg8_total,
1115 phba->ktime_status_samples),
1116 phba->ktime_seg8_min,
1117 phba->ktime_seg8_max);
1118 len += snprintf(buf + len, PAGE_SIZE-len,
1119 "Segment 9: MSI-X ISR for status cmpl "
1120 "-to- NVME layer passed status done\n");
1121 len += snprintf(buf + len, PAGE_SIZE-len,
1122 "avg:%08lld min:%08lld max %08lld\n",
1123 div_u64(phba->ktime_seg9_total,
1124 phba->ktime_status_samples),
1125 phba->ktime_seg9_min,
1126 phba->ktime_seg9_max);
1127 len += snprintf(buf + len, PAGE_SIZE-len,
1128 "Total: cmd received by MSI-X ISR -to- "
1129 "cmd completed on wire\n");
1130 len += snprintf(buf + len, PAGE_SIZE-len,
1131 "avg:%08lld min:%08lld max %08lld\n",
1132 div_u64(phba->ktime_seg10_total,
1133 phba->ktime_status_samples),
1134 phba->ktime_seg10_min,
1135 phba->ktime_seg10_max);
1136 return len;
1137}
1138
1139
1140
1141
1142
1143
1144
1145
1146
1147
1148
1149
1150
1151
1152static int
1153lpfc_debugfs_nvmeio_trc_data(struct lpfc_hba *phba, char *buf, int size)
1154{
1155 struct lpfc_debugfs_nvmeio_trc *dtp;
1156 int i, state, index, skip;
1157 int len = 0;
1158
1159 state = phba->nvmeio_trc_on;
1160
1161 index = (atomic_read(&phba->nvmeio_trc_cnt) + 1) &
1162 (phba->nvmeio_trc_size - 1);
1163 skip = phba->nvmeio_trc_output_idx;
1164
1165 len += snprintf(buf + len, size - len,
1166 "%s IO Trace %s: next_idx %d skip %d size %d\n",
1167 (phba->nvmet_support ? "NVME" : "NVMET"),
1168 (state ? "Enabled" : "Disabled"),
1169 index, skip, phba->nvmeio_trc_size);
1170
1171 if (!phba->nvmeio_trc || state)
1172 return len;
1173
1174
1175
1176 for (i = index; i < phba->nvmeio_trc_size; i++) {
1177 if (skip) {
1178 skip--;
1179 continue;
1180 }
1181 dtp = phba->nvmeio_trc + i;
1182 phba->nvmeio_trc_output_idx++;
1183
1184 if (!dtp->fmt)
1185 continue;
1186
1187 len += snprintf(buf + len, size - len, dtp->fmt,
1188 dtp->data1, dtp->data2, dtp->data3);
1189
1190 if (phba->nvmeio_trc_output_idx >= phba->nvmeio_trc_size) {
1191 phba->nvmeio_trc_output_idx = 0;
1192 len += snprintf(buf + len, size - len,
1193 "Trace Complete\n");
1194 goto out;
1195 }
1196
1197 if (len >= (size - LPFC_DEBUG_OUT_LINE_SZ)) {
1198 len += snprintf(buf + len, size - len,
1199 "Trace Continue (%d of %d)\n",
1200 phba->nvmeio_trc_output_idx,
1201 phba->nvmeio_trc_size);
1202 goto out;
1203 }
1204 }
1205 for (i = 0; i < index; i++) {
1206 if (skip) {
1207 skip--;
1208 continue;
1209 }
1210 dtp = phba->nvmeio_trc + i;
1211 phba->nvmeio_trc_output_idx++;
1212
1213 if (!dtp->fmt)
1214 continue;
1215
1216 len += snprintf(buf + len, size - len, dtp->fmt,
1217 dtp->data1, dtp->data2, dtp->data3);
1218
1219 if (phba->nvmeio_trc_output_idx >= phba->nvmeio_trc_size) {
1220 phba->nvmeio_trc_output_idx = 0;
1221 len += snprintf(buf + len, size - len,
1222 "Trace Complete\n");
1223 goto out;
1224 }
1225
1226 if (len >= (size - LPFC_DEBUG_OUT_LINE_SZ)) {
1227 len += snprintf(buf + len, size - len,
1228 "Trace Continue (%d of %d)\n",
1229 phba->nvmeio_trc_output_idx,
1230 phba->nvmeio_trc_size);
1231 goto out;
1232 }
1233 }
1234
1235 len += snprintf(buf + len, size - len,
1236 "Trace Done\n");
1237out:
1238 return len;
1239}
1240
1241
1242
1243
1244
1245
1246
1247
1248
1249
1250
1251
1252
1253
1254static int
1255lpfc_debugfs_cpucheck_data(struct lpfc_vport *vport, char *buf, int size)
1256{
1257 struct lpfc_hba *phba = vport->phba;
1258 int i;
1259 int len = 0;
1260 uint32_t tot_xmt = 0;
1261 uint32_t tot_rcv = 0;
1262 uint32_t tot_cmpl = 0;
1263 uint32_t tot_ccmpl = 0;
1264
1265 if (phba->nvmet_support == 0) {
1266
1267 len += snprintf(buf + len, PAGE_SIZE - len,
1268 "CPUcheck %s\n",
1269 (phba->cpucheck_on & LPFC_CHECK_NVME_IO ?
1270 "Enabled" : "Disabled"));
1271 for (i = 0; i < phba->sli4_hba.num_present_cpu; i++) {
1272 if (i >= LPFC_CHECK_CPU_CNT)
1273 break;
1274 len += snprintf(buf + len, PAGE_SIZE - len,
1275 "%02d: xmit x%08x cmpl x%08x\n",
1276 i, phba->cpucheck_xmt_io[i],
1277 phba->cpucheck_cmpl_io[i]);
1278 tot_xmt += phba->cpucheck_xmt_io[i];
1279 tot_cmpl += phba->cpucheck_cmpl_io[i];
1280 }
1281 len += snprintf(buf + len, PAGE_SIZE - len,
1282 "tot:xmit x%08x cmpl x%08x\n",
1283 tot_xmt, tot_cmpl);
1284 return len;
1285 }
1286
1287
1288 len += snprintf(buf + len, PAGE_SIZE - len,
1289 "CPUcheck %s ",
1290 (phba->cpucheck_on & LPFC_CHECK_NVMET_IO ?
1291 "IO Enabled - " : "IO Disabled - "));
1292 len += snprintf(buf + len, PAGE_SIZE - len,
1293 "%s\n",
1294 (phba->cpucheck_on & LPFC_CHECK_NVMET_RCV ?
1295 "Rcv Enabled\n" : "Rcv Disabled\n"));
1296 for (i = 0; i < phba->sli4_hba.num_present_cpu; i++) {
1297 if (i >= LPFC_CHECK_CPU_CNT)
1298 break;
1299 len += snprintf(buf + len, PAGE_SIZE - len,
1300 "%02d: xmit x%08x ccmpl x%08x "
1301 "cmpl x%08x rcv x%08x\n",
1302 i, phba->cpucheck_xmt_io[i],
1303 phba->cpucheck_ccmpl_io[i],
1304 phba->cpucheck_cmpl_io[i],
1305 phba->cpucheck_rcv_io[i]);
1306 tot_xmt += phba->cpucheck_xmt_io[i];
1307 tot_rcv += phba->cpucheck_rcv_io[i];
1308 tot_cmpl += phba->cpucheck_cmpl_io[i];
1309 tot_ccmpl += phba->cpucheck_ccmpl_io[i];
1310 }
1311 len += snprintf(buf + len, PAGE_SIZE - len,
1312 "tot:xmit x%08x ccmpl x%08x cmpl x%08x rcv x%08x\n",
1313 tot_xmt, tot_ccmpl, tot_cmpl, tot_rcv);
1314 return len;
1315}
1316
1317#endif
1318
1319
1320
1321
1322
1323
1324
1325
1326
1327
1328
1329
1330
1331
1332
1333
1334
1335inline void
1336lpfc_debugfs_disc_trc(struct lpfc_vport *vport, int mask, char *fmt,
1337 uint32_t data1, uint32_t data2, uint32_t data3)
1338{
1339#ifdef CONFIG_SCSI_LPFC_DEBUG_FS
1340 struct lpfc_debugfs_trc *dtp;
1341 int index;
1342
1343 if (!(lpfc_debugfs_mask_disc_trc & mask))
1344 return;
1345
1346 if (!lpfc_debugfs_enable || !lpfc_debugfs_max_disc_trc ||
1347 !vport || !vport->disc_trc)
1348 return;
1349
1350 index = atomic_inc_return(&vport->disc_trc_cnt) &
1351 (lpfc_debugfs_max_disc_trc - 1);
1352 dtp = vport->disc_trc + index;
1353 dtp->fmt = fmt;
1354 dtp->data1 = data1;
1355 dtp->data2 = data2;
1356 dtp->data3 = data3;
1357 dtp->seq_cnt = atomic_inc_return(&lpfc_debugfs_seq_trc_cnt);
1358 dtp->jif = jiffies;
1359#endif
1360 return;
1361}
1362
1363
1364
1365
1366
1367
1368
1369
1370
1371
1372
1373
1374
1375
1376inline void
1377lpfc_debugfs_slow_ring_trc(struct lpfc_hba *phba, char *fmt,
1378 uint32_t data1, uint32_t data2, uint32_t data3)
1379{
1380#ifdef CONFIG_SCSI_LPFC_DEBUG_FS
1381 struct lpfc_debugfs_trc *dtp;
1382 int index;
1383
1384 if (!lpfc_debugfs_enable || !lpfc_debugfs_max_slow_ring_trc ||
1385 !phba || !phba->slow_ring_trc)
1386 return;
1387
1388 index = atomic_inc_return(&phba->slow_ring_trc_cnt) &
1389 (lpfc_debugfs_max_slow_ring_trc - 1);
1390 dtp = phba->slow_ring_trc + index;
1391 dtp->fmt = fmt;
1392 dtp->data1 = data1;
1393 dtp->data2 = data2;
1394 dtp->data3 = data3;
1395 dtp->seq_cnt = atomic_inc_return(&lpfc_debugfs_seq_trc_cnt);
1396 dtp->jif = jiffies;
1397#endif
1398 return;
1399}
1400
1401
1402
1403
1404
1405
1406
1407
1408
1409
1410
1411
1412
1413
1414inline void
1415lpfc_debugfs_nvme_trc(struct lpfc_hba *phba, char *fmt,
1416 uint16_t data1, uint16_t data2, uint32_t data3)
1417{
1418#ifdef CONFIG_SCSI_LPFC_DEBUG_FS
1419 struct lpfc_debugfs_nvmeio_trc *dtp;
1420 int index;
1421
1422 if (!phba->nvmeio_trc_on || !phba->nvmeio_trc)
1423 return;
1424
1425 index = atomic_inc_return(&phba->nvmeio_trc_cnt) &
1426 (phba->nvmeio_trc_size - 1);
1427 dtp = phba->nvmeio_trc + index;
1428 dtp->fmt = fmt;
1429 dtp->data1 = data1;
1430 dtp->data2 = data2;
1431 dtp->data3 = data3;
1432#endif
1433}
1434
1435#ifdef CONFIG_SCSI_LPFC_DEBUG_FS
1436
1437
1438
1439
1440
1441
1442
1443
1444
1445
1446
1447
1448
1449
1450
1451static int
1452lpfc_debugfs_disc_trc_open(struct inode *inode, struct file *file)
1453{
1454 struct lpfc_vport *vport = inode->i_private;
1455 struct lpfc_debug *debug;
1456 int size;
1457 int rc = -ENOMEM;
1458
1459 if (!lpfc_debugfs_max_disc_trc) {
1460 rc = -ENOSPC;
1461 goto out;
1462 }
1463
1464 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
1465 if (!debug)
1466 goto out;
1467
1468
1469 size = (lpfc_debugfs_max_disc_trc * LPFC_DEBUG_TRC_ENTRY_SIZE);
1470 size = PAGE_ALIGN(size);
1471
1472 debug->buffer = kmalloc(size, GFP_KERNEL);
1473 if (!debug->buffer) {
1474 kfree(debug);
1475 goto out;
1476 }
1477
1478 debug->len = lpfc_debugfs_disc_trc_data(vport, debug->buffer, size);
1479 file->private_data = debug;
1480
1481 rc = 0;
1482out:
1483 return rc;
1484}
1485
1486
1487
1488
1489
1490
1491
1492
1493
1494
1495
1496
1497
1498
1499
1500
1501static int
1502lpfc_debugfs_slow_ring_trc_open(struct inode *inode, struct file *file)
1503{
1504 struct lpfc_hba *phba = inode->i_private;
1505 struct lpfc_debug *debug;
1506 int size;
1507 int rc = -ENOMEM;
1508
1509 if (!lpfc_debugfs_max_slow_ring_trc) {
1510 rc = -ENOSPC;
1511 goto out;
1512 }
1513
1514 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
1515 if (!debug)
1516 goto out;
1517
1518
1519 size = (lpfc_debugfs_max_slow_ring_trc * LPFC_DEBUG_TRC_ENTRY_SIZE);
1520 size = PAGE_ALIGN(size);
1521
1522 debug->buffer = kmalloc(size, GFP_KERNEL);
1523 if (!debug->buffer) {
1524 kfree(debug);
1525 goto out;
1526 }
1527
1528 debug->len = lpfc_debugfs_slow_ring_trc_data(phba, debug->buffer, size);
1529 file->private_data = debug;
1530
1531 rc = 0;
1532out:
1533 return rc;
1534}
1535
1536
1537
1538
1539
1540
1541
1542
1543
1544
1545
1546
1547
1548
1549
1550
1551static int
1552lpfc_debugfs_hbqinfo_open(struct inode *inode, struct file *file)
1553{
1554 struct lpfc_hba *phba = inode->i_private;
1555 struct lpfc_debug *debug;
1556 int rc = -ENOMEM;
1557
1558 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
1559 if (!debug)
1560 goto out;
1561
1562
1563 debug->buffer = kmalloc(LPFC_HBQINFO_SIZE, GFP_KERNEL);
1564 if (!debug->buffer) {
1565 kfree(debug);
1566 goto out;
1567 }
1568
1569 debug->len = lpfc_debugfs_hbqinfo_data(phba, debug->buffer,
1570 LPFC_HBQINFO_SIZE);
1571 file->private_data = debug;
1572
1573 rc = 0;
1574out:
1575 return rc;
1576}
1577
1578
1579
1580
1581
1582
1583
1584
1585
1586
1587
1588
1589
1590
1591
1592
1593static int
1594lpfc_debugfs_dumpHBASlim_open(struct inode *inode, struct file *file)
1595{
1596 struct lpfc_hba *phba = inode->i_private;
1597 struct lpfc_debug *debug;
1598 int rc = -ENOMEM;
1599
1600 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
1601 if (!debug)
1602 goto out;
1603
1604
1605 debug->buffer = kmalloc(LPFC_DUMPHBASLIM_SIZE, GFP_KERNEL);
1606 if (!debug->buffer) {
1607 kfree(debug);
1608 goto out;
1609 }
1610
1611 debug->len = lpfc_debugfs_dumpHBASlim_data(phba, debug->buffer,
1612 LPFC_DUMPHBASLIM_SIZE);
1613 file->private_data = debug;
1614
1615 rc = 0;
1616out:
1617 return rc;
1618}
1619
1620
1621
1622
1623
1624
1625
1626
1627
1628
1629
1630
1631
1632
1633
1634
1635static int
1636lpfc_debugfs_dumpHostSlim_open(struct inode *inode, struct file *file)
1637{
1638 struct lpfc_hba *phba = inode->i_private;
1639 struct lpfc_debug *debug;
1640 int rc = -ENOMEM;
1641
1642 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
1643 if (!debug)
1644 goto out;
1645
1646
1647 debug->buffer = kmalloc(LPFC_DUMPHOSTSLIM_SIZE, GFP_KERNEL);
1648 if (!debug->buffer) {
1649 kfree(debug);
1650 goto out;
1651 }
1652
1653 debug->len = lpfc_debugfs_dumpHostSlim_data(phba, debug->buffer,
1654 LPFC_DUMPHOSTSLIM_SIZE);
1655 file->private_data = debug;
1656
1657 rc = 0;
1658out:
1659 return rc;
1660}
1661
1662static int
1663lpfc_debugfs_dumpData_open(struct inode *inode, struct file *file)
1664{
1665 struct lpfc_debug *debug;
1666 int rc = -ENOMEM;
1667
1668 if (!_dump_buf_data)
1669 return -EBUSY;
1670
1671 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
1672 if (!debug)
1673 goto out;
1674
1675
1676 pr_err("9059 BLKGRD: %s: _dump_buf_data=0x%p\n",
1677 __func__, _dump_buf_data);
1678 debug->buffer = _dump_buf_data;
1679 if (!debug->buffer) {
1680 kfree(debug);
1681 goto out;
1682 }
1683
1684 debug->len = (1 << _dump_buf_data_order) << PAGE_SHIFT;
1685 file->private_data = debug;
1686
1687 rc = 0;
1688out:
1689 return rc;
1690}
1691
1692static int
1693lpfc_debugfs_dumpDif_open(struct inode *inode, struct file *file)
1694{
1695 struct lpfc_debug *debug;
1696 int rc = -ENOMEM;
1697
1698 if (!_dump_buf_dif)
1699 return -EBUSY;
1700
1701 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
1702 if (!debug)
1703 goto out;
1704
1705
1706 pr_err("9060 BLKGRD: %s: _dump_buf_dif=0x%p file=%pD\n",
1707 __func__, _dump_buf_dif, file);
1708 debug->buffer = _dump_buf_dif;
1709 if (!debug->buffer) {
1710 kfree(debug);
1711 goto out;
1712 }
1713
1714 debug->len = (1 << _dump_buf_dif_order) << PAGE_SHIFT;
1715 file->private_data = debug;
1716
1717 rc = 0;
1718out:
1719 return rc;
1720}
1721
1722static ssize_t
1723lpfc_debugfs_dumpDataDif_write(struct file *file, const char __user *buf,
1724 size_t nbytes, loff_t *ppos)
1725{
1726
1727
1728
1729
1730
1731 spin_lock(&_dump_buf_lock);
1732
1733 memset((void *)_dump_buf_data, 0,
1734 ((1 << PAGE_SHIFT) << _dump_buf_data_order));
1735 memset((void *)_dump_buf_dif, 0,
1736 ((1 << PAGE_SHIFT) << _dump_buf_dif_order));
1737
1738 _dump_buf_done = 0;
1739
1740 spin_unlock(&_dump_buf_lock);
1741
1742 return nbytes;
1743}
1744
1745static ssize_t
1746lpfc_debugfs_dif_err_read(struct file *file, char __user *buf,
1747 size_t nbytes, loff_t *ppos)
1748{
1749 struct dentry *dent = file->f_path.dentry;
1750 struct lpfc_hba *phba = file->private_data;
1751 char cbuf[32];
1752 uint64_t tmp = 0;
1753 int cnt = 0;
1754
1755 if (dent == phba->debug_writeGuard)
1756 cnt = snprintf(cbuf, 32, "%u\n", phba->lpfc_injerr_wgrd_cnt);
1757 else if (dent == phba->debug_writeApp)
1758 cnt = snprintf(cbuf, 32, "%u\n", phba->lpfc_injerr_wapp_cnt);
1759 else if (dent == phba->debug_writeRef)
1760 cnt = snprintf(cbuf, 32, "%u\n", phba->lpfc_injerr_wref_cnt);
1761 else if (dent == phba->debug_readGuard)
1762 cnt = snprintf(cbuf, 32, "%u\n", phba->lpfc_injerr_rgrd_cnt);
1763 else if (dent == phba->debug_readApp)
1764 cnt = snprintf(cbuf, 32, "%u\n", phba->lpfc_injerr_rapp_cnt);
1765 else if (dent == phba->debug_readRef)
1766 cnt = snprintf(cbuf, 32, "%u\n", phba->lpfc_injerr_rref_cnt);
1767 else if (dent == phba->debug_InjErrNPortID)
1768 cnt = snprintf(cbuf, 32, "0x%06x\n", phba->lpfc_injerr_nportid);
1769 else if (dent == phba->debug_InjErrWWPN) {
1770 memcpy(&tmp, &phba->lpfc_injerr_wwpn, sizeof(struct lpfc_name));
1771 tmp = cpu_to_be64(tmp);
1772 cnt = snprintf(cbuf, 32, "0x%016llx\n", tmp);
1773 } else if (dent == phba->debug_InjErrLBA) {
1774 if (phba->lpfc_injerr_lba == (sector_t)(-1))
1775 cnt = snprintf(cbuf, 32, "off\n");
1776 else
1777 cnt = snprintf(cbuf, 32, "0x%llx\n",
1778 (uint64_t) phba->lpfc_injerr_lba);
1779 } else
1780 lpfc_printf_log(phba, KERN_ERR, LOG_INIT,
1781 "0547 Unknown debugfs error injection entry\n");
1782
1783 return simple_read_from_buffer(buf, nbytes, ppos, &cbuf, cnt);
1784}
1785
1786static ssize_t
1787lpfc_debugfs_dif_err_write(struct file *file, const char __user *buf,
1788 size_t nbytes, loff_t *ppos)
1789{
1790 struct dentry *dent = file->f_path.dentry;
1791 struct lpfc_hba *phba = file->private_data;
1792 char dstbuf[33];
1793 uint64_t tmp = 0;
1794 int size;
1795
1796 memset(dstbuf, 0, 33);
1797 size = (nbytes < 32) ? nbytes : 32;
1798 if (copy_from_user(dstbuf, buf, size))
1799 return 0;
1800
1801 if (dent == phba->debug_InjErrLBA) {
1802 if ((buf[0] == 'o') && (buf[1] == 'f') && (buf[2] == 'f'))
1803 tmp = (uint64_t)(-1);
1804 }
1805
1806 if ((tmp == 0) && (kstrtoull(dstbuf, 0, &tmp)))
1807 return 0;
1808
1809 if (dent == phba->debug_writeGuard)
1810 phba->lpfc_injerr_wgrd_cnt = (uint32_t)tmp;
1811 else if (dent == phba->debug_writeApp)
1812 phba->lpfc_injerr_wapp_cnt = (uint32_t)tmp;
1813 else if (dent == phba->debug_writeRef)
1814 phba->lpfc_injerr_wref_cnt = (uint32_t)tmp;
1815 else if (dent == phba->debug_readGuard)
1816 phba->lpfc_injerr_rgrd_cnt = (uint32_t)tmp;
1817 else if (dent == phba->debug_readApp)
1818 phba->lpfc_injerr_rapp_cnt = (uint32_t)tmp;
1819 else if (dent == phba->debug_readRef)
1820 phba->lpfc_injerr_rref_cnt = (uint32_t)tmp;
1821 else if (dent == phba->debug_InjErrLBA)
1822 phba->lpfc_injerr_lba = (sector_t)tmp;
1823 else if (dent == phba->debug_InjErrNPortID)
1824 phba->lpfc_injerr_nportid = (uint32_t)(tmp & Mask_DID);
1825 else if (dent == phba->debug_InjErrWWPN) {
1826 tmp = cpu_to_be64(tmp);
1827 memcpy(&phba->lpfc_injerr_wwpn, &tmp, sizeof(struct lpfc_name));
1828 } else
1829 lpfc_printf_log(phba, KERN_ERR, LOG_INIT,
1830 "0548 Unknown debugfs error injection entry\n");
1831
1832 return nbytes;
1833}
1834
1835static int
1836lpfc_debugfs_dif_err_release(struct inode *inode, struct file *file)
1837{
1838 return 0;
1839}
1840
1841
1842
1843
1844
1845
1846
1847
1848
1849
1850
1851
1852
1853
1854
1855
1856static int
1857lpfc_debugfs_nodelist_open(struct inode *inode, struct file *file)
1858{
1859 struct lpfc_vport *vport = inode->i_private;
1860 struct lpfc_debug *debug;
1861 int rc = -ENOMEM;
1862
1863 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
1864 if (!debug)
1865 goto out;
1866
1867
1868 debug->buffer = kmalloc(LPFC_NODELIST_SIZE, GFP_KERNEL);
1869 if (!debug->buffer) {
1870 kfree(debug);
1871 goto out;
1872 }
1873
1874 debug->len = lpfc_debugfs_nodelist_data(vport, debug->buffer,
1875 LPFC_NODELIST_SIZE);
1876 file->private_data = debug;
1877
1878 rc = 0;
1879out:
1880 return rc;
1881}
1882
1883
1884
1885
1886
1887
1888
1889
1890
1891
1892
1893
1894
1895
1896
1897
1898
1899
1900static loff_t
1901lpfc_debugfs_lseek(struct file *file, loff_t off, int whence)
1902{
1903 struct lpfc_debug *debug = file->private_data;
1904 return fixed_size_llseek(file, off, whence, debug->len);
1905}
1906
1907
1908
1909
1910
1911
1912
1913
1914
1915
1916
1917
1918
1919
1920
1921
1922
1923static ssize_t
1924lpfc_debugfs_read(struct file *file, char __user *buf,
1925 size_t nbytes, loff_t *ppos)
1926{
1927 struct lpfc_debug *debug = file->private_data;
1928
1929 return simple_read_from_buffer(buf, nbytes, ppos, debug->buffer,
1930 debug->len);
1931}
1932
1933
1934
1935
1936
1937
1938
1939
1940
1941
1942
1943
1944
1945static int
1946lpfc_debugfs_release(struct inode *inode, struct file *file)
1947{
1948 struct lpfc_debug *debug = file->private_data;
1949
1950 kfree(debug->buffer);
1951 kfree(debug);
1952
1953 return 0;
1954}
1955
1956static int
1957lpfc_debugfs_dumpDataDif_release(struct inode *inode, struct file *file)
1958{
1959 struct lpfc_debug *debug = file->private_data;
1960
1961 debug->buffer = NULL;
1962 kfree(debug);
1963
1964 return 0;
1965}
1966
1967
1968static int
1969lpfc_debugfs_nvmestat_open(struct inode *inode, struct file *file)
1970{
1971 struct lpfc_vport *vport = inode->i_private;
1972 struct lpfc_debug *debug;
1973 int rc = -ENOMEM;
1974
1975 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
1976 if (!debug)
1977 goto out;
1978
1979
1980 debug->buffer = kmalloc(LPFC_NVMESTAT_SIZE, GFP_KERNEL);
1981 if (!debug->buffer) {
1982 kfree(debug);
1983 goto out;
1984 }
1985
1986 debug->len = lpfc_debugfs_nvmestat_data(vport, debug->buffer,
1987 LPFC_NVMESTAT_SIZE);
1988
1989 debug->i_private = inode->i_private;
1990 file->private_data = debug;
1991
1992 rc = 0;
1993out:
1994 return rc;
1995}
1996
1997static ssize_t
1998lpfc_debugfs_nvmestat_write(struct file *file, const char __user *buf,
1999 size_t nbytes, loff_t *ppos)
2000{
2001 struct lpfc_debug *debug = file->private_data;
2002 struct lpfc_vport *vport = (struct lpfc_vport *)debug->i_private;
2003 struct lpfc_hba *phba = vport->phba;
2004 struct lpfc_nvmet_tgtport *tgtp;
2005 char mybuf[64];
2006 char *pbuf;
2007
2008 if (!phba->targetport)
2009 return -ENXIO;
2010
2011 if (nbytes > 64)
2012 nbytes = 64;
2013
2014 memset(mybuf, 0, sizeof(mybuf));
2015
2016 if (copy_from_user(mybuf, buf, nbytes))
2017 return -EFAULT;
2018 pbuf = &mybuf[0];
2019
2020 tgtp = (struct lpfc_nvmet_tgtport *)phba->targetport->private;
2021 if ((strncmp(pbuf, "reset", strlen("reset")) == 0) ||
2022 (strncmp(pbuf, "zero", strlen("zero")) == 0)) {
2023 atomic_set(&tgtp->rcv_ls_req_in, 0);
2024 atomic_set(&tgtp->rcv_ls_req_out, 0);
2025 atomic_set(&tgtp->rcv_ls_req_drop, 0);
2026 atomic_set(&tgtp->xmt_ls_abort, 0);
2027 atomic_set(&tgtp->xmt_ls_abort_cmpl, 0);
2028 atomic_set(&tgtp->xmt_ls_rsp, 0);
2029 atomic_set(&tgtp->xmt_ls_drop, 0);
2030 atomic_set(&tgtp->xmt_ls_rsp_error, 0);
2031 atomic_set(&tgtp->xmt_ls_rsp_cmpl, 0);
2032
2033 atomic_set(&tgtp->rcv_fcp_cmd_in, 0);
2034 atomic_set(&tgtp->rcv_fcp_cmd_out, 0);
2035 atomic_set(&tgtp->rcv_fcp_cmd_drop, 0);
2036 atomic_set(&tgtp->xmt_fcp_drop, 0);
2037 atomic_set(&tgtp->xmt_fcp_read_rsp, 0);
2038 atomic_set(&tgtp->xmt_fcp_read, 0);
2039 atomic_set(&tgtp->xmt_fcp_write, 0);
2040 atomic_set(&tgtp->xmt_fcp_rsp, 0);
2041 atomic_set(&tgtp->xmt_fcp_release, 0);
2042 atomic_set(&tgtp->xmt_fcp_rsp_cmpl, 0);
2043 atomic_set(&tgtp->xmt_fcp_rsp_error, 0);
2044 atomic_set(&tgtp->xmt_fcp_rsp_drop, 0);
2045
2046 atomic_set(&tgtp->xmt_fcp_abort, 0);
2047 atomic_set(&tgtp->xmt_fcp_abort_cmpl, 0);
2048 atomic_set(&tgtp->xmt_abort_sol, 0);
2049 atomic_set(&tgtp->xmt_abort_unsol, 0);
2050 atomic_set(&tgtp->xmt_abort_rsp, 0);
2051 atomic_set(&tgtp->xmt_abort_rsp_error, 0);
2052 }
2053 return nbytes;
2054}
2055
2056static int
2057lpfc_debugfs_nvmektime_open(struct inode *inode, struct file *file)
2058{
2059 struct lpfc_vport *vport = inode->i_private;
2060 struct lpfc_debug *debug;
2061 int rc = -ENOMEM;
2062
2063 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
2064 if (!debug)
2065 goto out;
2066
2067
2068 debug->buffer = kmalloc(LPFC_NVMEKTIME_SIZE, GFP_KERNEL);
2069 if (!debug->buffer) {
2070 kfree(debug);
2071 goto out;
2072 }
2073
2074 debug->len = lpfc_debugfs_nvmektime_data(vport, debug->buffer,
2075 LPFC_NVMEKTIME_SIZE);
2076
2077 debug->i_private = inode->i_private;
2078 file->private_data = debug;
2079
2080 rc = 0;
2081out:
2082 return rc;
2083}
2084
2085static ssize_t
2086lpfc_debugfs_nvmektime_write(struct file *file, const char __user *buf,
2087 size_t nbytes, loff_t *ppos)
2088{
2089 struct lpfc_debug *debug = file->private_data;
2090 struct lpfc_vport *vport = (struct lpfc_vport *)debug->i_private;
2091 struct lpfc_hba *phba = vport->phba;
2092 char mybuf[64];
2093 char *pbuf;
2094
2095 if (nbytes > 64)
2096 nbytes = 64;
2097
2098 memset(mybuf, 0, sizeof(mybuf));
2099
2100 if (copy_from_user(mybuf, buf, nbytes))
2101 return -EFAULT;
2102 pbuf = &mybuf[0];
2103
2104 if ((strncmp(pbuf, "on", sizeof("on") - 1) == 0)) {
2105 phba->ktime_data_samples = 0;
2106 phba->ktime_status_samples = 0;
2107 phba->ktime_seg1_total = 0;
2108 phba->ktime_seg1_max = 0;
2109 phba->ktime_seg1_min = 0xffffffff;
2110 phba->ktime_seg2_total = 0;
2111 phba->ktime_seg2_max = 0;
2112 phba->ktime_seg2_min = 0xffffffff;
2113 phba->ktime_seg3_total = 0;
2114 phba->ktime_seg3_max = 0;
2115 phba->ktime_seg3_min = 0xffffffff;
2116 phba->ktime_seg4_total = 0;
2117 phba->ktime_seg4_max = 0;
2118 phba->ktime_seg4_min = 0xffffffff;
2119 phba->ktime_seg5_total = 0;
2120 phba->ktime_seg5_max = 0;
2121 phba->ktime_seg5_min = 0xffffffff;
2122 phba->ktime_seg6_total = 0;
2123 phba->ktime_seg6_max = 0;
2124 phba->ktime_seg6_min = 0xffffffff;
2125 phba->ktime_seg7_total = 0;
2126 phba->ktime_seg7_max = 0;
2127 phba->ktime_seg7_min = 0xffffffff;
2128 phba->ktime_seg8_total = 0;
2129 phba->ktime_seg8_max = 0;
2130 phba->ktime_seg8_min = 0xffffffff;
2131 phba->ktime_seg9_total = 0;
2132 phba->ktime_seg9_max = 0;
2133 phba->ktime_seg9_min = 0xffffffff;
2134 phba->ktime_seg10_total = 0;
2135 phba->ktime_seg10_max = 0;
2136 phba->ktime_seg10_min = 0xffffffff;
2137
2138 phba->ktime_on = 1;
2139 return strlen(pbuf);
2140 } else if ((strncmp(pbuf, "off",
2141 sizeof("off") - 1) == 0)) {
2142 phba->ktime_on = 0;
2143 return strlen(pbuf);
2144 } else if ((strncmp(pbuf, "zero",
2145 sizeof("zero") - 1) == 0)) {
2146 phba->ktime_data_samples = 0;
2147 phba->ktime_status_samples = 0;
2148 phba->ktime_seg1_total = 0;
2149 phba->ktime_seg1_max = 0;
2150 phba->ktime_seg1_min = 0xffffffff;
2151 phba->ktime_seg2_total = 0;
2152 phba->ktime_seg2_max = 0;
2153 phba->ktime_seg2_min = 0xffffffff;
2154 phba->ktime_seg3_total = 0;
2155 phba->ktime_seg3_max = 0;
2156 phba->ktime_seg3_min = 0xffffffff;
2157 phba->ktime_seg4_total = 0;
2158 phba->ktime_seg4_max = 0;
2159 phba->ktime_seg4_min = 0xffffffff;
2160 phba->ktime_seg5_total = 0;
2161 phba->ktime_seg5_max = 0;
2162 phba->ktime_seg5_min = 0xffffffff;
2163 phba->ktime_seg6_total = 0;
2164 phba->ktime_seg6_max = 0;
2165 phba->ktime_seg6_min = 0xffffffff;
2166 phba->ktime_seg7_total = 0;
2167 phba->ktime_seg7_max = 0;
2168 phba->ktime_seg7_min = 0xffffffff;
2169 phba->ktime_seg8_total = 0;
2170 phba->ktime_seg8_max = 0;
2171 phba->ktime_seg8_min = 0xffffffff;
2172 phba->ktime_seg9_total = 0;
2173 phba->ktime_seg9_max = 0;
2174 phba->ktime_seg9_min = 0xffffffff;
2175 phba->ktime_seg10_total = 0;
2176 phba->ktime_seg10_max = 0;
2177 phba->ktime_seg10_min = 0xffffffff;
2178 return strlen(pbuf);
2179 }
2180 return -EINVAL;
2181}
2182
2183static int
2184lpfc_debugfs_nvmeio_trc_open(struct inode *inode, struct file *file)
2185{
2186 struct lpfc_hba *phba = inode->i_private;
2187 struct lpfc_debug *debug;
2188 int rc = -ENOMEM;
2189
2190 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
2191 if (!debug)
2192 goto out;
2193
2194
2195 debug->buffer = kmalloc(LPFC_NVMEIO_TRC_SIZE, GFP_KERNEL);
2196 if (!debug->buffer) {
2197 kfree(debug);
2198 goto out;
2199 }
2200
2201 debug->len = lpfc_debugfs_nvmeio_trc_data(phba, debug->buffer,
2202 LPFC_NVMEIO_TRC_SIZE);
2203
2204 debug->i_private = inode->i_private;
2205 file->private_data = debug;
2206
2207 rc = 0;
2208out:
2209 return rc;
2210}
2211
2212static ssize_t
2213lpfc_debugfs_nvmeio_trc_write(struct file *file, const char __user *buf,
2214 size_t nbytes, loff_t *ppos)
2215{
2216 struct lpfc_debug *debug = file->private_data;
2217 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
2218 int i;
2219 unsigned long sz;
2220 char mybuf[64];
2221 char *pbuf;
2222
2223 if (nbytes > 64)
2224 nbytes = 64;
2225
2226 memset(mybuf, 0, sizeof(mybuf));
2227
2228 if (copy_from_user(mybuf, buf, nbytes))
2229 return -EFAULT;
2230 pbuf = &mybuf[0];
2231
2232 if ((strncmp(pbuf, "off", sizeof("off") - 1) == 0)) {
2233 lpfc_printf_log(phba, KERN_ERR, LOG_INIT,
2234 "0570 nvmeio_trc_off\n");
2235 phba->nvmeio_trc_output_idx = 0;
2236 phba->nvmeio_trc_on = 0;
2237 return strlen(pbuf);
2238 } else if ((strncmp(pbuf, "on", sizeof("on") - 1) == 0)) {
2239 lpfc_printf_log(phba, KERN_ERR, LOG_INIT,
2240 "0571 nvmeio_trc_on\n");
2241 phba->nvmeio_trc_output_idx = 0;
2242 phba->nvmeio_trc_on = 1;
2243 return strlen(pbuf);
2244 }
2245
2246
2247 if (phba->nvmeio_trc_on != 0)
2248 return -EINVAL;
2249
2250
2251 i = kstrtoul(pbuf, 0, &sz);
2252 if (i)
2253 return -EINVAL;
2254 phba->nvmeio_trc_size = (uint32_t)sz;
2255
2256
2257 i = 0;
2258 while (sz > 1) {
2259 sz = sz >> 1;
2260 i++;
2261 }
2262 sz = (1 << i);
2263 if (phba->nvmeio_trc_size != sz)
2264 lpfc_printf_log(phba, KERN_ERR, LOG_INIT,
2265 "0572 nvmeio_trc_size changed to %ld\n",
2266 sz);
2267 phba->nvmeio_trc_size = (uint32_t)sz;
2268
2269
2270 kfree(phba->nvmeio_trc);
2271
2272
2273 phba->nvmeio_trc = kzalloc((sizeof(struct lpfc_debugfs_nvmeio_trc) *
2274 sz), GFP_KERNEL);
2275 if (!phba->nvmeio_trc) {
2276 lpfc_printf_log(phba, KERN_ERR, LOG_INIT,
2277 "0573 Cannot create debugfs "
2278 "nvmeio_trc buffer\n");
2279 return -ENOMEM;
2280 }
2281 atomic_set(&phba->nvmeio_trc_cnt, 0);
2282 phba->nvmeio_trc_on = 0;
2283 phba->nvmeio_trc_output_idx = 0;
2284
2285 return strlen(pbuf);
2286}
2287
2288static int
2289lpfc_debugfs_cpucheck_open(struct inode *inode, struct file *file)
2290{
2291 struct lpfc_vport *vport = inode->i_private;
2292 struct lpfc_debug *debug;
2293 int rc = -ENOMEM;
2294
2295 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
2296 if (!debug)
2297 goto out;
2298
2299
2300 debug->buffer = kmalloc(LPFC_CPUCHECK_SIZE, GFP_KERNEL);
2301 if (!debug->buffer) {
2302 kfree(debug);
2303 goto out;
2304 }
2305
2306 debug->len = lpfc_debugfs_cpucheck_data(vport, debug->buffer,
2307 LPFC_NVMEKTIME_SIZE);
2308
2309 debug->i_private = inode->i_private;
2310 file->private_data = debug;
2311
2312 rc = 0;
2313out:
2314 return rc;
2315}
2316
2317static ssize_t
2318lpfc_debugfs_cpucheck_write(struct file *file, const char __user *buf,
2319 size_t nbytes, loff_t *ppos)
2320{
2321 struct lpfc_debug *debug = file->private_data;
2322 struct lpfc_vport *vport = (struct lpfc_vport *)debug->i_private;
2323 struct lpfc_hba *phba = vport->phba;
2324 char mybuf[64];
2325 char *pbuf;
2326 int i;
2327
2328 if (nbytes > 64)
2329 nbytes = 64;
2330
2331 memset(mybuf, 0, sizeof(mybuf));
2332
2333 if (copy_from_user(mybuf, buf, nbytes))
2334 return -EFAULT;
2335 pbuf = &mybuf[0];
2336
2337 if ((strncmp(pbuf, "on", sizeof("on") - 1) == 0)) {
2338 if (phba->nvmet_support)
2339 phba->cpucheck_on |= LPFC_CHECK_NVMET_IO;
2340 else
2341 phba->cpucheck_on |= LPFC_CHECK_NVME_IO;
2342 return strlen(pbuf);
2343 } else if ((strncmp(pbuf, "rcv",
2344 sizeof("rcv") - 1) == 0)) {
2345 if (phba->nvmet_support)
2346 phba->cpucheck_on |= LPFC_CHECK_NVMET_RCV;
2347 else
2348 return -EINVAL;
2349 return strlen(pbuf);
2350 } else if ((strncmp(pbuf, "off",
2351 sizeof("off") - 1) == 0)) {
2352 phba->cpucheck_on = LPFC_CHECK_OFF;
2353 return strlen(pbuf);
2354 } else if ((strncmp(pbuf, "zero",
2355 sizeof("zero") - 1) == 0)) {
2356 for (i = 0; i < phba->sli4_hba.num_present_cpu; i++) {
2357 if (i >= LPFC_CHECK_CPU_CNT)
2358 break;
2359 phba->cpucheck_rcv_io[i] = 0;
2360 phba->cpucheck_xmt_io[i] = 0;
2361 phba->cpucheck_cmpl_io[i] = 0;
2362 phba->cpucheck_ccmpl_io[i] = 0;
2363 }
2364 return strlen(pbuf);
2365 }
2366 return -EINVAL;
2367}
2368
2369
2370
2371
2372
2373
2374
2375
2376
2377
2378
2379
2380
2381
2382
2383
2384
2385
2386
2387
2388
2389
2390
2391
2392
2393static int lpfc_idiag_cmd_get(const char __user *buf, size_t nbytes,
2394 struct lpfc_idiag_cmd *idiag_cmd)
2395{
2396 char mybuf[64];
2397 char *pbuf, *step_str;
2398 int i;
2399 size_t bsize;
2400
2401 memset(mybuf, 0, sizeof(mybuf));
2402 memset(idiag_cmd, 0, sizeof(*idiag_cmd));
2403 bsize = min(nbytes, (sizeof(mybuf)-1));
2404
2405 if (copy_from_user(mybuf, buf, bsize))
2406 return -EFAULT;
2407 pbuf = &mybuf[0];
2408 step_str = strsep(&pbuf, "\t ");
2409
2410
2411 if (!step_str)
2412 return -EINVAL;
2413
2414 idiag_cmd->opcode = simple_strtol(step_str, NULL, 0);
2415 if (idiag_cmd->opcode == 0)
2416 return -EINVAL;
2417
2418 for (i = 0; i < LPFC_IDIAG_CMD_DATA_SIZE; i++) {
2419 step_str = strsep(&pbuf, "\t ");
2420 if (!step_str)
2421 return i;
2422 idiag_cmd->data[i] = simple_strtol(step_str, NULL, 0);
2423 }
2424 return i;
2425}
2426
2427
2428
2429
2430
2431
2432
2433
2434
2435
2436
2437
2438
2439
2440
2441
2442
2443
2444static int
2445lpfc_idiag_open(struct inode *inode, struct file *file)
2446{
2447 struct lpfc_debug *debug;
2448
2449 debug = kmalloc(sizeof(*debug), GFP_KERNEL);
2450 if (!debug)
2451 return -ENOMEM;
2452
2453 debug->i_private = inode->i_private;
2454 debug->buffer = NULL;
2455 file->private_data = debug;
2456
2457 return 0;
2458}
2459
2460
2461
2462
2463
2464
2465
2466
2467
2468
2469
2470
2471
2472
2473static int
2474lpfc_idiag_release(struct inode *inode, struct file *file)
2475{
2476 struct lpfc_debug *debug = file->private_data;
2477
2478
2479 kfree(debug->buffer);
2480 kfree(debug);
2481
2482 return 0;
2483}
2484
2485
2486
2487
2488
2489
2490
2491
2492
2493
2494
2495
2496
2497
2498static int
2499lpfc_idiag_cmd_release(struct inode *inode, struct file *file)
2500{
2501 struct lpfc_debug *debug = file->private_data;
2502
2503 if (debug->op == LPFC_IDIAG_OP_WR) {
2504 switch (idiag.cmd.opcode) {
2505 case LPFC_IDIAG_CMD_PCICFG_WR:
2506 case LPFC_IDIAG_CMD_PCICFG_ST:
2507 case LPFC_IDIAG_CMD_PCICFG_CL:
2508 case LPFC_IDIAG_CMD_QUEACC_WR:
2509 case LPFC_IDIAG_CMD_QUEACC_ST:
2510 case LPFC_IDIAG_CMD_QUEACC_CL:
2511 memset(&idiag, 0, sizeof(idiag));
2512 break;
2513 default:
2514 break;
2515 }
2516 }
2517
2518
2519 kfree(debug->buffer);
2520 kfree(debug);
2521
2522 return 0;
2523}
2524
2525
2526
2527
2528
2529
2530
2531
2532
2533
2534
2535
2536
2537
2538
2539
2540
2541
2542
2543static ssize_t
2544lpfc_idiag_pcicfg_read(struct file *file, char __user *buf, size_t nbytes,
2545 loff_t *ppos)
2546{
2547 struct lpfc_debug *debug = file->private_data;
2548 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
2549 int offset_label, offset, len = 0, index = LPFC_PCI_CFG_RD_SIZE;
2550 int where, count;
2551 char *pbuffer;
2552 struct pci_dev *pdev;
2553 uint32_t u32val;
2554 uint16_t u16val;
2555 uint8_t u8val;
2556
2557 pdev = phba->pcidev;
2558 if (!pdev)
2559 return 0;
2560
2561
2562 debug->op = LPFC_IDIAG_OP_RD;
2563
2564 if (!debug->buffer)
2565 debug->buffer = kmalloc(LPFC_PCI_CFG_SIZE, GFP_KERNEL);
2566 if (!debug->buffer)
2567 return 0;
2568 pbuffer = debug->buffer;
2569
2570 if (*ppos)
2571 return 0;
2572
2573 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_RD) {
2574 where = idiag.cmd.data[IDIAG_PCICFG_WHERE_INDX];
2575 count = idiag.cmd.data[IDIAG_PCICFG_COUNT_INDX];
2576 } else
2577 return 0;
2578
2579
2580 switch (count) {
2581 case SIZE_U8:
2582 pci_read_config_byte(pdev, where, &u8val);
2583 len += snprintf(pbuffer+len, LPFC_PCI_CFG_SIZE-len,
2584 "%03x: %02x\n", where, u8val);
2585 break;
2586 case SIZE_U16:
2587 pci_read_config_word(pdev, where, &u16val);
2588 len += snprintf(pbuffer+len, LPFC_PCI_CFG_SIZE-len,
2589 "%03x: %04x\n", where, u16val);
2590 break;
2591 case SIZE_U32:
2592 pci_read_config_dword(pdev, where, &u32val);
2593 len += snprintf(pbuffer+len, LPFC_PCI_CFG_SIZE-len,
2594 "%03x: %08x\n", where, u32val);
2595 break;
2596 case LPFC_PCI_CFG_BROWSE:
2597 goto pcicfg_browse;
2598 break;
2599 default:
2600
2601 len = 0;
2602 break;
2603 }
2604 return simple_read_from_buffer(buf, nbytes, ppos, pbuffer, len);
2605
2606pcicfg_browse:
2607
2608
2609 offset_label = idiag.offset.last_rd;
2610 offset = offset_label;
2611
2612
2613 len += snprintf(pbuffer+len, LPFC_PCI_CFG_SIZE-len,
2614 "%03x: ", offset_label);
2615 while (index > 0) {
2616 pci_read_config_dword(pdev, offset, &u32val);
2617 len += snprintf(pbuffer+len, LPFC_PCI_CFG_SIZE-len,
2618 "%08x ", u32val);
2619 offset += sizeof(uint32_t);
2620 if (offset >= LPFC_PCI_CFG_SIZE) {
2621 len += snprintf(pbuffer+len,
2622 LPFC_PCI_CFG_SIZE-len, "\n");
2623 break;
2624 }
2625 index -= sizeof(uint32_t);
2626 if (!index)
2627 len += snprintf(pbuffer+len, LPFC_PCI_CFG_SIZE-len,
2628 "\n");
2629 else if (!(index % (8 * sizeof(uint32_t)))) {
2630 offset_label += (8 * sizeof(uint32_t));
2631 len += snprintf(pbuffer+len, LPFC_PCI_CFG_SIZE-len,
2632 "\n%03x: ", offset_label);
2633 }
2634 }
2635
2636
2637 if (index == 0) {
2638 idiag.offset.last_rd += LPFC_PCI_CFG_RD_SIZE;
2639 if (idiag.offset.last_rd >= LPFC_PCI_CFG_SIZE)
2640 idiag.offset.last_rd = 0;
2641 } else
2642 idiag.offset.last_rd = 0;
2643
2644 return simple_read_from_buffer(buf, nbytes, ppos, pbuffer, len);
2645}
2646
2647
2648
2649
2650
2651
2652
2653
2654
2655
2656
2657
2658
2659
2660
2661
2662
2663
2664
2665static ssize_t
2666lpfc_idiag_pcicfg_write(struct file *file, const char __user *buf,
2667 size_t nbytes, loff_t *ppos)
2668{
2669 struct lpfc_debug *debug = file->private_data;
2670 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
2671 uint32_t where, value, count;
2672 uint32_t u32val;
2673 uint16_t u16val;
2674 uint8_t u8val;
2675 struct pci_dev *pdev;
2676 int rc;
2677
2678 pdev = phba->pcidev;
2679 if (!pdev)
2680 return -EFAULT;
2681
2682
2683 debug->op = LPFC_IDIAG_OP_WR;
2684
2685 rc = lpfc_idiag_cmd_get(buf, nbytes, &idiag.cmd);
2686 if (rc < 0)
2687 return rc;
2688
2689 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_RD) {
2690
2691 if (rc != LPFC_PCI_CFG_RD_CMD_ARG)
2692 goto error_out;
2693
2694 where = idiag.cmd.data[IDIAG_PCICFG_WHERE_INDX];
2695 count = idiag.cmd.data[IDIAG_PCICFG_COUNT_INDX];
2696 if (count == LPFC_PCI_CFG_BROWSE) {
2697 if (where % sizeof(uint32_t))
2698 goto error_out;
2699
2700 idiag.offset.last_rd = where;
2701 } else if ((count != sizeof(uint8_t)) &&
2702 (count != sizeof(uint16_t)) &&
2703 (count != sizeof(uint32_t)))
2704 goto error_out;
2705 if (count == sizeof(uint8_t)) {
2706 if (where > LPFC_PCI_CFG_SIZE - sizeof(uint8_t))
2707 goto error_out;
2708 if (where % sizeof(uint8_t))
2709 goto error_out;
2710 }
2711 if (count == sizeof(uint16_t)) {
2712 if (where > LPFC_PCI_CFG_SIZE - sizeof(uint16_t))
2713 goto error_out;
2714 if (where % sizeof(uint16_t))
2715 goto error_out;
2716 }
2717 if (count == sizeof(uint32_t)) {
2718 if (where > LPFC_PCI_CFG_SIZE - sizeof(uint32_t))
2719 goto error_out;
2720 if (where % sizeof(uint32_t))
2721 goto error_out;
2722 }
2723 } else if (idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_WR ||
2724 idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_ST ||
2725 idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_CL) {
2726
2727 if (rc != LPFC_PCI_CFG_WR_CMD_ARG)
2728 goto error_out;
2729
2730 where = idiag.cmd.data[IDIAG_PCICFG_WHERE_INDX];
2731 count = idiag.cmd.data[IDIAG_PCICFG_COUNT_INDX];
2732 value = idiag.cmd.data[IDIAG_PCICFG_VALUE_INDX];
2733
2734 if ((count != sizeof(uint8_t)) &&
2735 (count != sizeof(uint16_t)) &&
2736 (count != sizeof(uint32_t)))
2737 goto error_out;
2738 if (count == sizeof(uint8_t)) {
2739 if (where > LPFC_PCI_CFG_SIZE - sizeof(uint8_t))
2740 goto error_out;
2741 if (where % sizeof(uint8_t))
2742 goto error_out;
2743 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_WR)
2744 pci_write_config_byte(pdev, where,
2745 (uint8_t)value);
2746 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_ST) {
2747 rc = pci_read_config_byte(pdev, where, &u8val);
2748 if (!rc) {
2749 u8val |= (uint8_t)value;
2750 pci_write_config_byte(pdev, where,
2751 u8val);
2752 }
2753 }
2754 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_CL) {
2755 rc = pci_read_config_byte(pdev, where, &u8val);
2756 if (!rc) {
2757 u8val &= (uint8_t)(~value);
2758 pci_write_config_byte(pdev, where,
2759 u8val);
2760 }
2761 }
2762 }
2763 if (count == sizeof(uint16_t)) {
2764 if (where > LPFC_PCI_CFG_SIZE - sizeof(uint16_t))
2765 goto error_out;
2766 if (where % sizeof(uint16_t))
2767 goto error_out;
2768 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_WR)
2769 pci_write_config_word(pdev, where,
2770 (uint16_t)value);
2771 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_ST) {
2772 rc = pci_read_config_word(pdev, where, &u16val);
2773 if (!rc) {
2774 u16val |= (uint16_t)value;
2775 pci_write_config_word(pdev, where,
2776 u16val);
2777 }
2778 }
2779 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_CL) {
2780 rc = pci_read_config_word(pdev, where, &u16val);
2781 if (!rc) {
2782 u16val &= (uint16_t)(~value);
2783 pci_write_config_word(pdev, where,
2784 u16val);
2785 }
2786 }
2787 }
2788 if (count == sizeof(uint32_t)) {
2789 if (where > LPFC_PCI_CFG_SIZE - sizeof(uint32_t))
2790 goto error_out;
2791 if (where % sizeof(uint32_t))
2792 goto error_out;
2793 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_WR)
2794 pci_write_config_dword(pdev, where, value);
2795 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_ST) {
2796 rc = pci_read_config_dword(pdev, where,
2797 &u32val);
2798 if (!rc) {
2799 u32val |= value;
2800 pci_write_config_dword(pdev, where,
2801 u32val);
2802 }
2803 }
2804 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_PCICFG_CL) {
2805 rc = pci_read_config_dword(pdev, where,
2806 &u32val);
2807 if (!rc) {
2808 u32val &= ~value;
2809 pci_write_config_dword(pdev, where,
2810 u32val);
2811 }
2812 }
2813 }
2814 } else
2815
2816 goto error_out;
2817
2818 return nbytes;
2819error_out:
2820 memset(&idiag, 0, sizeof(idiag));
2821 return -EINVAL;
2822}
2823
2824
2825
2826
2827
2828
2829
2830
2831
2832
2833
2834
2835
2836
2837
2838
2839static ssize_t
2840lpfc_idiag_baracc_read(struct file *file, char __user *buf, size_t nbytes,
2841 loff_t *ppos)
2842{
2843 struct lpfc_debug *debug = file->private_data;
2844 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
2845 int offset_label, offset, offset_run, len = 0, index;
2846 int bar_num, acc_range, bar_size;
2847 char *pbuffer;
2848 void __iomem *mem_mapped_bar;
2849 uint32_t if_type;
2850 struct pci_dev *pdev;
2851 uint32_t u32val;
2852
2853 pdev = phba->pcidev;
2854 if (!pdev)
2855 return 0;
2856
2857
2858 debug->op = LPFC_IDIAG_OP_RD;
2859
2860 if (!debug->buffer)
2861 debug->buffer = kmalloc(LPFC_PCI_BAR_RD_BUF_SIZE, GFP_KERNEL);
2862 if (!debug->buffer)
2863 return 0;
2864 pbuffer = debug->buffer;
2865
2866 if (*ppos)
2867 return 0;
2868
2869 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_BARACC_RD) {
2870 bar_num = idiag.cmd.data[IDIAG_BARACC_BAR_NUM_INDX];
2871 offset = idiag.cmd.data[IDIAG_BARACC_OFF_SET_INDX];
2872 acc_range = idiag.cmd.data[IDIAG_BARACC_ACC_MOD_INDX];
2873 bar_size = idiag.cmd.data[IDIAG_BARACC_BAR_SZE_INDX];
2874 } else
2875 return 0;
2876
2877 if (acc_range == 0)
2878 return 0;
2879
2880 if_type = bf_get(lpfc_sli_intf_if_type, &phba->sli4_hba.sli_intf);
2881 if (if_type == LPFC_SLI_INTF_IF_TYPE_0) {
2882 if (bar_num == IDIAG_BARACC_BAR_0)
2883 mem_mapped_bar = phba->sli4_hba.conf_regs_memmap_p;
2884 else if (bar_num == IDIAG_BARACC_BAR_1)
2885 mem_mapped_bar = phba->sli4_hba.ctrl_regs_memmap_p;
2886 else if (bar_num == IDIAG_BARACC_BAR_2)
2887 mem_mapped_bar = phba->sli4_hba.drbl_regs_memmap_p;
2888 else
2889 return 0;
2890 } else if (if_type == LPFC_SLI_INTF_IF_TYPE_2) {
2891 if (bar_num == IDIAG_BARACC_BAR_0)
2892 mem_mapped_bar = phba->sli4_hba.conf_regs_memmap_p;
2893 else
2894 return 0;
2895 } else
2896 return 0;
2897
2898
2899 if (acc_range == SINGLE_WORD) {
2900 offset_run = offset;
2901 u32val = readl(mem_mapped_bar + offset_run);
2902 len += snprintf(pbuffer+len, LPFC_PCI_BAR_RD_BUF_SIZE-len,
2903 "%05x: %08x\n", offset_run, u32val);
2904 } else
2905 goto baracc_browse;
2906
2907 return simple_read_from_buffer(buf, nbytes, ppos, pbuffer, len);
2908
2909baracc_browse:
2910
2911
2912 offset_label = idiag.offset.last_rd;
2913 offset_run = offset_label;
2914
2915
2916 len += snprintf(pbuffer+len, LPFC_PCI_BAR_RD_BUF_SIZE-len,
2917 "%05x: ", offset_label);
2918 index = LPFC_PCI_BAR_RD_SIZE;
2919 while (index > 0) {
2920 u32val = readl(mem_mapped_bar + offset_run);
2921 len += snprintf(pbuffer+len, LPFC_PCI_BAR_RD_BUF_SIZE-len,
2922 "%08x ", u32val);
2923 offset_run += sizeof(uint32_t);
2924 if (acc_range == LPFC_PCI_BAR_BROWSE) {
2925 if (offset_run >= bar_size) {
2926 len += snprintf(pbuffer+len,
2927 LPFC_PCI_BAR_RD_BUF_SIZE-len, "\n");
2928 break;
2929 }
2930 } else {
2931 if (offset_run >= offset +
2932 (acc_range * sizeof(uint32_t))) {
2933 len += snprintf(pbuffer+len,
2934 LPFC_PCI_BAR_RD_BUF_SIZE-len, "\n");
2935 break;
2936 }
2937 }
2938 index -= sizeof(uint32_t);
2939 if (!index)
2940 len += snprintf(pbuffer+len,
2941 LPFC_PCI_BAR_RD_BUF_SIZE-len, "\n");
2942 else if (!(index % (8 * sizeof(uint32_t)))) {
2943 offset_label += (8 * sizeof(uint32_t));
2944 len += snprintf(pbuffer+len,
2945 LPFC_PCI_BAR_RD_BUF_SIZE-len,
2946 "\n%05x: ", offset_label);
2947 }
2948 }
2949
2950
2951 if (index == 0) {
2952 idiag.offset.last_rd += LPFC_PCI_BAR_RD_SIZE;
2953 if (acc_range == LPFC_PCI_BAR_BROWSE) {
2954 if (idiag.offset.last_rd >= bar_size)
2955 idiag.offset.last_rd = 0;
2956 } else {
2957 if (offset_run >= offset +
2958 (acc_range * sizeof(uint32_t)))
2959 idiag.offset.last_rd = offset;
2960 }
2961 } else {
2962 if (acc_range == LPFC_PCI_BAR_BROWSE)
2963 idiag.offset.last_rd = 0;
2964 else
2965 idiag.offset.last_rd = offset;
2966 }
2967
2968 return simple_read_from_buffer(buf, nbytes, ppos, pbuffer, len);
2969}
2970
2971
2972
2973
2974
2975
2976
2977
2978
2979
2980
2981
2982
2983
2984
2985
2986
2987
2988
2989
2990static ssize_t
2991lpfc_idiag_baracc_write(struct file *file, const char __user *buf,
2992 size_t nbytes, loff_t *ppos)
2993{
2994 struct lpfc_debug *debug = file->private_data;
2995 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
2996 uint32_t bar_num, bar_size, offset, value, acc_range;
2997 struct pci_dev *pdev;
2998 void __iomem *mem_mapped_bar;
2999 uint32_t if_type;
3000 uint32_t u32val;
3001 int rc;
3002
3003 pdev = phba->pcidev;
3004 if (!pdev)
3005 return -EFAULT;
3006
3007
3008 debug->op = LPFC_IDIAG_OP_WR;
3009
3010 rc = lpfc_idiag_cmd_get(buf, nbytes, &idiag.cmd);
3011 if (rc < 0)
3012 return rc;
3013
3014 if_type = bf_get(lpfc_sli_intf_if_type, &phba->sli4_hba.sli_intf);
3015 bar_num = idiag.cmd.data[IDIAG_BARACC_BAR_NUM_INDX];
3016
3017 if (if_type == LPFC_SLI_INTF_IF_TYPE_0) {
3018 if ((bar_num != IDIAG_BARACC_BAR_0) &&
3019 (bar_num != IDIAG_BARACC_BAR_1) &&
3020 (bar_num != IDIAG_BARACC_BAR_2))
3021 goto error_out;
3022 } else if (if_type == LPFC_SLI_INTF_IF_TYPE_2) {
3023 if (bar_num != IDIAG_BARACC_BAR_0)
3024 goto error_out;
3025 } else
3026 goto error_out;
3027
3028 if (if_type == LPFC_SLI_INTF_IF_TYPE_0) {
3029 if (bar_num == IDIAG_BARACC_BAR_0) {
3030 idiag.cmd.data[IDIAG_BARACC_BAR_SZE_INDX] =
3031 LPFC_PCI_IF0_BAR0_SIZE;
3032 mem_mapped_bar = phba->sli4_hba.conf_regs_memmap_p;
3033 } else if (bar_num == IDIAG_BARACC_BAR_1) {
3034 idiag.cmd.data[IDIAG_BARACC_BAR_SZE_INDX] =
3035 LPFC_PCI_IF0_BAR1_SIZE;
3036 mem_mapped_bar = phba->sli4_hba.ctrl_regs_memmap_p;
3037 } else if (bar_num == IDIAG_BARACC_BAR_2) {
3038 idiag.cmd.data[IDIAG_BARACC_BAR_SZE_INDX] =
3039 LPFC_PCI_IF0_BAR2_SIZE;
3040 mem_mapped_bar = phba->sli4_hba.drbl_regs_memmap_p;
3041 } else
3042 goto error_out;
3043 } else if (if_type == LPFC_SLI_INTF_IF_TYPE_2) {
3044 if (bar_num == IDIAG_BARACC_BAR_0) {
3045 idiag.cmd.data[IDIAG_BARACC_BAR_SZE_INDX] =
3046 LPFC_PCI_IF2_BAR0_SIZE;
3047 mem_mapped_bar = phba->sli4_hba.conf_regs_memmap_p;
3048 } else
3049 goto error_out;
3050 } else
3051 goto error_out;
3052
3053 offset = idiag.cmd.data[IDIAG_BARACC_OFF_SET_INDX];
3054 if (offset % sizeof(uint32_t))
3055 goto error_out;
3056
3057 bar_size = idiag.cmd.data[IDIAG_BARACC_BAR_SZE_INDX];
3058 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_BARACC_RD) {
3059
3060 if (rc != LPFC_PCI_BAR_RD_CMD_ARG)
3061 goto error_out;
3062 acc_range = idiag.cmd.data[IDIAG_BARACC_ACC_MOD_INDX];
3063 if (acc_range == LPFC_PCI_BAR_BROWSE) {
3064 if (offset > bar_size - sizeof(uint32_t))
3065 goto error_out;
3066
3067 idiag.offset.last_rd = offset;
3068 } else if (acc_range > SINGLE_WORD) {
3069 if (offset + acc_range * sizeof(uint32_t) > bar_size)
3070 goto error_out;
3071
3072 idiag.offset.last_rd = offset;
3073 } else if (acc_range != SINGLE_WORD)
3074 goto error_out;
3075 } else if (idiag.cmd.opcode == LPFC_IDIAG_CMD_BARACC_WR ||
3076 idiag.cmd.opcode == LPFC_IDIAG_CMD_BARACC_ST ||
3077 idiag.cmd.opcode == LPFC_IDIAG_CMD_BARACC_CL) {
3078
3079 if (rc != LPFC_PCI_BAR_WR_CMD_ARG)
3080 goto error_out;
3081
3082 acc_range = SINGLE_WORD;
3083 value = idiag.cmd.data[IDIAG_BARACC_REG_VAL_INDX];
3084 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_BARACC_WR) {
3085 writel(value, mem_mapped_bar + offset);
3086 readl(mem_mapped_bar + offset);
3087 }
3088 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_BARACC_ST) {
3089 u32val = readl(mem_mapped_bar + offset);
3090 u32val |= value;
3091 writel(u32val, mem_mapped_bar + offset);
3092 readl(mem_mapped_bar + offset);
3093 }
3094 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_BARACC_CL) {
3095 u32val = readl(mem_mapped_bar + offset);
3096 u32val &= ~value;
3097 writel(u32val, mem_mapped_bar + offset);
3098 readl(mem_mapped_bar + offset);
3099 }
3100 } else
3101
3102 goto error_out;
3103
3104 return nbytes;
3105error_out:
3106 memset(&idiag, 0, sizeof(idiag));
3107 return -EINVAL;
3108}
3109
3110static int
3111__lpfc_idiag_print_wq(struct lpfc_queue *qp, char *wqtype,
3112 char *pbuffer, int len)
3113{
3114 if (!qp)
3115 return len;
3116
3117 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3118 "\t\t%s WQ info: ", wqtype);
3119 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3120 "AssocCQID[%04d]: WQ-STAT[oflow:x%x posted:x%llx]\n",
3121 qp->assoc_qid, qp->q_cnt_1,
3122 (unsigned long long)qp->q_cnt_4);
3123 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3124 "\t\tWQID[%02d], QE-CNT[%04d], QE-SZ[%04d], "
3125 "HST-IDX[%04d], PRT-IDX[%04d], PST[%03d]",
3126 qp->queue_id, qp->entry_count,
3127 qp->entry_size, qp->host_index,
3128 qp->hba_index, qp->entry_repost);
3129 len += snprintf(pbuffer + len,
3130 LPFC_QUE_INFO_GET_BUF_SIZE - len, "\n");
3131 return len;
3132}
3133
3134static int
3135lpfc_idiag_wqs_for_cq(struct lpfc_hba *phba, char *wqtype, char *pbuffer,
3136 int *len, int max_cnt, int cq_id)
3137{
3138 struct lpfc_queue *qp;
3139 int qidx;
3140
3141 for (qidx = 0; qidx < phba->cfg_fcp_io_channel; qidx++) {
3142 qp = phba->sli4_hba.fcp_wq[qidx];
3143 if (qp->assoc_qid != cq_id)
3144 continue;
3145 *len = __lpfc_idiag_print_wq(qp, wqtype, pbuffer, *len);
3146 if (*len >= max_cnt)
3147 return 1;
3148 }
3149 for (qidx = 0; qidx < phba->cfg_nvme_io_channel; qidx++) {
3150 qp = phba->sli4_hba.nvme_wq[qidx];
3151 if (qp->assoc_qid != cq_id)
3152 continue;
3153 *len = __lpfc_idiag_print_wq(qp, wqtype, pbuffer, *len);
3154 if (*len >= max_cnt)
3155 return 1;
3156 }
3157 return 0;
3158}
3159
3160static int
3161__lpfc_idiag_print_cq(struct lpfc_queue *qp, char *cqtype,
3162 char *pbuffer, int len)
3163{
3164 if (!qp)
3165 return len;
3166
3167 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3168 "\t%s CQ info: ", cqtype);
3169 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3170 "AssocEQID[%02d]: CQ STAT[max:x%x relw:x%x "
3171 "xabt:x%x wq:x%llx]\n",
3172 qp->assoc_qid, qp->q_cnt_1, qp->q_cnt_2,
3173 qp->q_cnt_3, (unsigned long long)qp->q_cnt_4);
3174 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3175 "\tCQID[%02d], QE-CNT[%04d], QE-SZ[%04d], "
3176 "HST-IDX[%04d], PRT-IDX[%04d], PST[%03d]",
3177 qp->queue_id, qp->entry_count,
3178 qp->entry_size, qp->host_index,
3179 qp->hba_index, qp->entry_repost);
3180
3181 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len, "\n");
3182
3183 return len;
3184}
3185
3186static int
3187__lpfc_idiag_print_rqpair(struct lpfc_queue *qp, struct lpfc_queue *datqp,
3188 char *rqtype, char *pbuffer, int len)
3189{
3190 if (!qp || !datqp)
3191 return len;
3192
3193 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3194 "\t\t%s RQ info: ", rqtype);
3195 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3196 "AssocCQID[%02d]: RQ-STAT[nopost:x%x nobuf:x%x "
3197 "posted:x%x rcv:x%llx]\n",
3198 qp->assoc_qid, qp->q_cnt_1, qp->q_cnt_2,
3199 qp->q_cnt_3, (unsigned long long)qp->q_cnt_4);
3200 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3201 "\t\tHQID[%02d], QE-CNT[%04d], QE-SZ[%04d], "
3202 "HST-IDX[%04d], PRT-IDX[%04d], PST[%03d]\n",
3203 qp->queue_id, qp->entry_count, qp->entry_size,
3204 qp->host_index, qp->hba_index, qp->entry_repost);
3205 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3206 "\t\tDQID[%02d], QE-CNT[%04d], QE-SZ[%04d], "
3207 "HST-IDX[%04d], PRT-IDX[%04d], PST[%03d]\n",
3208 datqp->queue_id, datqp->entry_count,
3209 datqp->entry_size, datqp->host_index,
3210 datqp->hba_index, datqp->entry_repost);
3211 return len;
3212}
3213
3214static int
3215lpfc_idiag_cqs_for_eq(struct lpfc_hba *phba, char *pbuffer,
3216 int *len, int max_cnt, int eqidx, int eq_id)
3217{
3218 struct lpfc_queue *qp;
3219 int qidx, rc;
3220
3221 for (qidx = 0; qidx < phba->cfg_fcp_io_channel; qidx++) {
3222 qp = phba->sli4_hba.fcp_cq[qidx];
3223 if (qp->assoc_qid != eq_id)
3224 continue;
3225
3226 *len = __lpfc_idiag_print_cq(qp, "FCP", pbuffer, *len);
3227
3228
3229 qp->CQ_max_cqe = 0;
3230
3231 if (*len >= max_cnt)
3232 return 1;
3233
3234 rc = lpfc_idiag_wqs_for_cq(phba, "FCP", pbuffer, len,
3235 max_cnt, qp->queue_id);
3236 if (rc)
3237 return 1;
3238 }
3239
3240 for (qidx = 0; qidx < phba->cfg_nvme_io_channel; qidx++) {
3241 qp = phba->sli4_hba.nvme_cq[qidx];
3242 if (qp->assoc_qid != eq_id)
3243 continue;
3244
3245 *len = __lpfc_idiag_print_cq(qp, "NVME", pbuffer, *len);
3246
3247
3248 qp->CQ_max_cqe = 0;
3249
3250 if (*len >= max_cnt)
3251 return 1;
3252
3253 rc = lpfc_idiag_wqs_for_cq(phba, "NVME", pbuffer, len,
3254 max_cnt, qp->queue_id);
3255 if (rc)
3256 return 1;
3257 }
3258
3259 if ((eqidx < phba->cfg_nvmet_mrq) && phba->nvmet_support) {
3260
3261 qp = phba->sli4_hba.nvmet_cqset[eqidx];
3262 *len = __lpfc_idiag_print_cq(qp, "NVMET CQset", pbuffer, *len);
3263
3264
3265 qp->CQ_max_cqe = 0;
3266
3267 if (*len >= max_cnt)
3268 return 1;
3269
3270
3271 qp = phba->sli4_hba.nvmet_mrq_hdr[eqidx];
3272 *len = __lpfc_idiag_print_rqpair(qp,
3273 phba->sli4_hba.nvmet_mrq_data[eqidx],
3274 "NVMET MRQ", pbuffer, *len);
3275
3276 if (*len >= max_cnt)
3277 return 1;
3278 }
3279
3280 return 0;
3281}
3282
3283static int
3284__lpfc_idiag_print_eq(struct lpfc_queue *qp, char *eqtype,
3285 char *pbuffer, int len)
3286{
3287 if (!qp)
3288 return len;
3289
3290 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3291 "\n%s EQ info: EQ-STAT[max:x%x noE:x%x "
3292 "cqe_proc:x%x eqe_proc:x%llx eqd %d]\n",
3293 eqtype, qp->q_cnt_1, qp->q_cnt_2, qp->q_cnt_3,
3294 (unsigned long long)qp->q_cnt_4, qp->q_mode);
3295 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3296 "EQID[%02d], QE-CNT[%04d], QE-SZ[%04d], "
3297 "HST-IDX[%04d], PRT-IDX[%04d], PST[%03d]",
3298 qp->queue_id, qp->entry_count, qp->entry_size,
3299 qp->host_index, qp->hba_index, qp->entry_repost);
3300 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len, "\n");
3301
3302 return len;
3303}
3304
3305
3306
3307
3308
3309
3310
3311
3312
3313
3314
3315
3316
3317
3318
3319
3320
3321
3322
3323static ssize_t
3324lpfc_idiag_queinfo_read(struct file *file, char __user *buf, size_t nbytes,
3325 loff_t *ppos)
3326{
3327 struct lpfc_debug *debug = file->private_data;
3328 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
3329 char *pbuffer;
3330 int max_cnt, rc, x, len = 0;
3331 struct lpfc_queue *qp = NULL;
3332
3333 if (!debug->buffer)
3334 debug->buffer = kmalloc(LPFC_QUE_INFO_GET_BUF_SIZE, GFP_KERNEL);
3335 if (!debug->buffer)
3336 return 0;
3337 pbuffer = debug->buffer;
3338 max_cnt = LPFC_QUE_INFO_GET_BUF_SIZE - 256;
3339
3340 if (*ppos)
3341 return 0;
3342
3343 spin_lock_irq(&phba->hbalock);
3344
3345
3346 if (phba->sli4_hba.hba_eq && phba->io_channel_irqs) {
3347
3348 x = phba->lpfc_idiag_last_eq;
3349 if (phba->cfg_fof && (x >= phba->io_channel_irqs)) {
3350 phba->lpfc_idiag_last_eq = 0;
3351 goto fof;
3352 }
3353 phba->lpfc_idiag_last_eq++;
3354 if (phba->lpfc_idiag_last_eq >= phba->io_channel_irqs)
3355 if (phba->cfg_fof == 0)
3356 phba->lpfc_idiag_last_eq = 0;
3357
3358 len += snprintf(pbuffer + len, LPFC_QUE_INFO_GET_BUF_SIZE - len,
3359 "EQ %d out of %d HBA EQs\n",
3360 x, phba->io_channel_irqs);
3361
3362
3363 qp = phba->sli4_hba.hba_eq[x];
3364 if (!qp)
3365 goto out;
3366
3367 len = __lpfc_idiag_print_eq(qp, "HBA", pbuffer, len);
3368
3369
3370 qp->EQ_max_eqe = 0;
3371
3372 if (len >= max_cnt)
3373 goto too_big;
3374
3375
3376 rc = lpfc_idiag_cqs_for_eq(phba, pbuffer, &len,
3377 max_cnt, x, qp->queue_id);
3378 if (rc)
3379 goto too_big;
3380
3381
3382 if (x)
3383 goto out;
3384
3385
3386 qp = phba->sli4_hba.mbx_cq;
3387 len = __lpfc_idiag_print_cq(qp, "MBX", pbuffer, len);
3388 if (len >= max_cnt)
3389 goto too_big;
3390
3391
3392 qp = phba->sli4_hba.mbx_wq;
3393 len = __lpfc_idiag_print_wq(qp, "MBX", pbuffer, len);
3394 if (len >= max_cnt)
3395 goto too_big;
3396
3397
3398 qp = phba->sli4_hba.els_cq;
3399 len = __lpfc_idiag_print_cq(qp, "ELS", pbuffer, len);
3400
3401 if (qp)
3402 qp->CQ_max_cqe = 0;
3403 if (len >= max_cnt)
3404 goto too_big;
3405
3406
3407 qp = phba->sli4_hba.els_wq;
3408 len = __lpfc_idiag_print_wq(qp, "ELS", pbuffer, len);
3409 if (len >= max_cnt)
3410 goto too_big;
3411
3412 qp = phba->sli4_hba.hdr_rq;
3413 len = __lpfc_idiag_print_rqpair(qp, phba->sli4_hba.dat_rq,
3414 "ELS RQpair", pbuffer, len);
3415 if (len >= max_cnt)
3416 goto too_big;
3417
3418
3419 qp = phba->sli4_hba.nvmels_cq;
3420 len = __lpfc_idiag_print_cq(qp, "NVME LS",
3421 pbuffer, len);
3422
3423 if (qp)
3424 qp->CQ_max_cqe = 0;
3425 if (len >= max_cnt)
3426 goto too_big;
3427
3428
3429 qp = phba->sli4_hba.nvmels_wq;
3430 len = __lpfc_idiag_print_wq(qp, "NVME LS",
3431 pbuffer, len);
3432 if (len >= max_cnt)
3433 goto too_big;
3434
3435 goto out;
3436 }
3437
3438fof:
3439 if (phba->cfg_fof) {
3440
3441 qp = phba->sli4_hba.fof_eq;
3442 len = __lpfc_idiag_print_eq(qp, "FOF", pbuffer, len);
3443
3444
3445 if (qp)
3446 qp->EQ_max_eqe = 0;
3447
3448 if (len >= max_cnt)
3449 goto too_big;
3450
3451
3452 qp = phba->sli4_hba.oas_cq;
3453 len = __lpfc_idiag_print_cq(qp, "OAS", pbuffer, len);
3454
3455 if (qp)
3456 qp->CQ_max_cqe = 0;
3457 if (len >= max_cnt)
3458 goto too_big;
3459
3460
3461 qp = phba->sli4_hba.oas_wq;
3462 len = __lpfc_idiag_print_wq(qp, "OAS", pbuffer, len);
3463 if (len >= max_cnt)
3464 goto too_big;
3465 }
3466
3467 spin_unlock_irq(&phba->hbalock);
3468 return simple_read_from_buffer(buf, nbytes, ppos, pbuffer, len);
3469
3470too_big:
3471 len += snprintf(pbuffer + len,
3472 LPFC_QUE_INFO_GET_BUF_SIZE - len, "Truncated ...\n");
3473out:
3474 spin_unlock_irq(&phba->hbalock);
3475 return simple_read_from_buffer(buf, nbytes, ppos, pbuffer, len);
3476}
3477
3478
3479
3480
3481
3482
3483
3484
3485
3486
3487
3488
3489
3490
3491static int
3492lpfc_idiag_que_param_check(struct lpfc_queue *q, int index, int count)
3493{
3494
3495 if ((count != 1) && (count != LPFC_QUE_ACC_BROWSE))
3496 return -EINVAL;
3497 if (index > q->entry_count - 1)
3498 return -EINVAL;
3499 return 0;
3500}
3501
3502
3503
3504
3505
3506
3507
3508
3509
3510
3511
3512
3513
3514
3515
3516static int
3517lpfc_idiag_queacc_read_qe(char *pbuffer, int len, struct lpfc_queue *pque,
3518 uint32_t index)
3519{
3520 int offset, esize;
3521 uint32_t *pentry;
3522
3523 if (!pbuffer || !pque)
3524 return 0;
3525
3526 esize = pque->entry_size;
3527 len += snprintf(pbuffer+len, LPFC_QUE_ACC_BUF_SIZE-len,
3528 "QE-INDEX[%04d]:\n", index);
3529
3530 offset = 0;
3531 pentry = pque->qe[index].address;
3532 while (esize > 0) {
3533 len += snprintf(pbuffer+len, LPFC_QUE_ACC_BUF_SIZE-len,
3534 "%08x ", *pentry);
3535 pentry++;
3536 offset += sizeof(uint32_t);
3537 esize -= sizeof(uint32_t);
3538 if (esize > 0 && !(offset % (4 * sizeof(uint32_t))))
3539 len += snprintf(pbuffer+len,
3540 LPFC_QUE_ACC_BUF_SIZE-len, "\n");
3541 }
3542 len += snprintf(pbuffer+len, LPFC_QUE_ACC_BUF_SIZE-len, "\n");
3543
3544 return len;
3545}
3546
3547
3548
3549
3550
3551
3552
3553
3554
3555
3556
3557
3558
3559
3560
3561
3562
3563
3564static ssize_t
3565lpfc_idiag_queacc_read(struct file *file, char __user *buf, size_t nbytes,
3566 loff_t *ppos)
3567{
3568 struct lpfc_debug *debug = file->private_data;
3569 uint32_t last_index, index, count;
3570 struct lpfc_queue *pque = NULL;
3571 char *pbuffer;
3572 int len = 0;
3573
3574
3575 debug->op = LPFC_IDIAG_OP_RD;
3576
3577 if (!debug->buffer)
3578 debug->buffer = kmalloc(LPFC_QUE_ACC_BUF_SIZE, GFP_KERNEL);
3579 if (!debug->buffer)
3580 return 0;
3581 pbuffer = debug->buffer;
3582
3583 if (*ppos)
3584 return 0;
3585
3586 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_QUEACC_RD) {
3587 index = idiag.cmd.data[IDIAG_QUEACC_INDEX_INDX];
3588 count = idiag.cmd.data[IDIAG_QUEACC_COUNT_INDX];
3589 pque = (struct lpfc_queue *)idiag.ptr_private;
3590 } else
3591 return 0;
3592
3593
3594 if (count == LPFC_QUE_ACC_BROWSE)
3595 goto que_browse;
3596
3597
3598 len = lpfc_idiag_queacc_read_qe(pbuffer, len, pque, index);
3599
3600 return simple_read_from_buffer(buf, nbytes, ppos, pbuffer, len);
3601
3602que_browse:
3603
3604
3605 last_index = idiag.offset.last_rd;
3606 index = last_index;
3607
3608 while (len < LPFC_QUE_ACC_SIZE - pque->entry_size) {
3609 len = lpfc_idiag_queacc_read_qe(pbuffer, len, pque, index);
3610 index++;
3611 if (index > pque->entry_count - 1)
3612 break;
3613 }
3614
3615
3616 if (index > pque->entry_count - 1)
3617 index = 0;
3618 idiag.offset.last_rd = index;
3619
3620 return simple_read_from_buffer(buf, nbytes, ppos, pbuffer, len);
3621}
3622
3623
3624
3625
3626
3627
3628
3629
3630
3631
3632
3633
3634
3635
3636
3637
3638
3639
3640
3641static ssize_t
3642lpfc_idiag_queacc_write(struct file *file, const char __user *buf,
3643 size_t nbytes, loff_t *ppos)
3644{
3645 struct lpfc_debug *debug = file->private_data;
3646 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
3647 uint32_t qidx, quetp, queid, index, count, offset, value;
3648 uint32_t *pentry;
3649 struct lpfc_queue *pque, *qp;
3650 int rc;
3651
3652
3653 debug->op = LPFC_IDIAG_OP_WR;
3654
3655 rc = lpfc_idiag_cmd_get(buf, nbytes, &idiag.cmd);
3656 if (rc < 0)
3657 return rc;
3658
3659
3660 quetp = idiag.cmd.data[IDIAG_QUEACC_QUETP_INDX];
3661 queid = idiag.cmd.data[IDIAG_QUEACC_QUEID_INDX];
3662 index = idiag.cmd.data[IDIAG_QUEACC_INDEX_INDX];
3663 count = idiag.cmd.data[IDIAG_QUEACC_COUNT_INDX];
3664 offset = idiag.cmd.data[IDIAG_QUEACC_OFFST_INDX];
3665 value = idiag.cmd.data[IDIAG_QUEACC_VALUE_INDX];
3666
3667
3668 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_QUEACC_WR ||
3669 idiag.cmd.opcode == LPFC_IDIAG_CMD_QUEACC_ST ||
3670 idiag.cmd.opcode == LPFC_IDIAG_CMD_QUEACC_CL) {
3671 if (rc != LPFC_QUE_ACC_WR_CMD_ARG)
3672 goto error_out;
3673 if (count != 1)
3674 goto error_out;
3675 } else if (idiag.cmd.opcode == LPFC_IDIAG_CMD_QUEACC_RD) {
3676 if (rc != LPFC_QUE_ACC_RD_CMD_ARG)
3677 goto error_out;
3678 } else
3679 goto error_out;
3680
3681 switch (quetp) {
3682 case LPFC_IDIAG_EQ:
3683
3684 if (phba->sli4_hba.hba_eq) {
3685 for (qidx = 0; qidx < phba->io_channel_irqs; qidx++) {
3686 qp = phba->sli4_hba.hba_eq[qidx];
3687 if (qp && qp->queue_id == queid) {
3688
3689 rc = lpfc_idiag_que_param_check(qp,
3690 index, count);
3691 if (rc)
3692 goto error_out;
3693 idiag.ptr_private = qp;
3694 goto pass_check;
3695 }
3696 }
3697 }
3698 goto error_out;
3699 break;
3700 case LPFC_IDIAG_CQ:
3701
3702 if (phba->sli4_hba.mbx_cq &&
3703 phba->sli4_hba.mbx_cq->queue_id == queid) {
3704
3705 rc = lpfc_idiag_que_param_check(
3706 phba->sli4_hba.mbx_cq, index, count);
3707 if (rc)
3708 goto error_out;
3709 idiag.ptr_private = phba->sli4_hba.mbx_cq;
3710 goto pass_check;
3711 }
3712
3713 if (phba->sli4_hba.els_cq &&
3714 phba->sli4_hba.els_cq->queue_id == queid) {
3715
3716 rc = lpfc_idiag_que_param_check(
3717 phba->sli4_hba.els_cq, index, count);
3718 if (rc)
3719 goto error_out;
3720 idiag.ptr_private = phba->sli4_hba.els_cq;
3721 goto pass_check;
3722 }
3723
3724 if (phba->sli4_hba.nvmels_cq &&
3725 phba->sli4_hba.nvmels_cq->queue_id == queid) {
3726
3727 rc = lpfc_idiag_que_param_check(
3728 phba->sli4_hba.nvmels_cq, index, count);
3729 if (rc)
3730 goto error_out;
3731 idiag.ptr_private = phba->sli4_hba.nvmels_cq;
3732 goto pass_check;
3733 }
3734
3735 if (phba->sli4_hba.fcp_cq) {
3736 for (qidx = 0; qidx < phba->cfg_fcp_io_channel;
3737 qidx++) {
3738 qp = phba->sli4_hba.fcp_cq[qidx];
3739 if (qp && qp->queue_id == queid) {
3740
3741 rc = lpfc_idiag_que_param_check(
3742 qp, index, count);
3743 if (rc)
3744 goto error_out;
3745 idiag.ptr_private = qp;
3746 goto pass_check;
3747 }
3748 }
3749 }
3750
3751 if (phba->sli4_hba.nvme_cq) {
3752 qidx = 0;
3753 do {
3754 if (phba->sli4_hba.nvme_cq[qidx] &&
3755 phba->sli4_hba.nvme_cq[qidx]->queue_id ==
3756 queid) {
3757
3758 rc = lpfc_idiag_que_param_check(
3759 phba->sli4_hba.nvme_cq[qidx],
3760 index, count);
3761 if (rc)
3762 goto error_out;
3763 idiag.ptr_private =
3764 phba->sli4_hba.nvme_cq[qidx];
3765 goto pass_check;
3766 }
3767 } while (++qidx < phba->cfg_nvme_io_channel);
3768 }
3769 goto error_out;
3770 break;
3771 case LPFC_IDIAG_MQ:
3772
3773 if (phba->sli4_hba.mbx_wq &&
3774 phba->sli4_hba.mbx_wq->queue_id == queid) {
3775
3776 rc = lpfc_idiag_que_param_check(
3777 phba->sli4_hba.mbx_wq, index, count);
3778 if (rc)
3779 goto error_out;
3780 idiag.ptr_private = phba->sli4_hba.mbx_wq;
3781 goto pass_check;
3782 }
3783 goto error_out;
3784 break;
3785 case LPFC_IDIAG_WQ:
3786
3787 if (phba->sli4_hba.els_wq &&
3788 phba->sli4_hba.els_wq->queue_id == queid) {
3789
3790 rc = lpfc_idiag_que_param_check(
3791 phba->sli4_hba.els_wq, index, count);
3792 if (rc)
3793 goto error_out;
3794 idiag.ptr_private = phba->sli4_hba.els_wq;
3795 goto pass_check;
3796 }
3797
3798 if (phba->sli4_hba.nvmels_wq &&
3799 phba->sli4_hba.nvmels_wq->queue_id == queid) {
3800
3801 rc = lpfc_idiag_que_param_check(
3802 phba->sli4_hba.nvmels_wq, index, count);
3803 if (rc)
3804 goto error_out;
3805 idiag.ptr_private = phba->sli4_hba.nvmels_wq;
3806 goto pass_check;
3807 }
3808
3809 if (phba->sli4_hba.fcp_wq) {
3810 for (qidx = 0; qidx < phba->cfg_fcp_io_channel;
3811 qidx++) {
3812 qp = phba->sli4_hba.fcp_wq[qidx];
3813 if (qp && qp->queue_id == queid) {
3814
3815 rc = lpfc_idiag_que_param_check(
3816 qp, index, count);
3817 if (rc)
3818 goto error_out;
3819 idiag.ptr_private = qp;
3820 goto pass_check;
3821 }
3822 }
3823 }
3824
3825 if (phba->sli4_hba.nvme_wq) {
3826 for (qidx = 0; qidx < phba->cfg_nvme_io_channel;
3827 qidx++) {
3828 qp = phba->sli4_hba.nvme_wq[qidx];
3829 if (qp && qp->queue_id == queid) {
3830
3831 rc = lpfc_idiag_que_param_check(
3832 qp, index, count);
3833 if (rc)
3834 goto error_out;
3835 idiag.ptr_private = qp;
3836 goto pass_check;
3837 }
3838 }
3839 }
3840
3841
3842 if (phba->sli4_hba.nvme_wq) {
3843 for (qidx = 0; qidx < phba->cfg_nvme_io_channel;
3844 qidx++) {
3845 if (!phba->sli4_hba.nvme_wq[qidx])
3846 continue;
3847 if (phba->sli4_hba.nvme_wq[qidx]->queue_id ==
3848 queid) {
3849
3850 rc = lpfc_idiag_que_param_check(
3851 phba->sli4_hba.nvme_wq[qidx],
3852 index, count);
3853 if (rc)
3854 goto error_out;
3855 idiag.ptr_private =
3856 phba->sli4_hba.nvme_wq[qidx];
3857 goto pass_check;
3858 }
3859 }
3860 }
3861 goto error_out;
3862 break;
3863 case LPFC_IDIAG_RQ:
3864
3865 if (phba->sli4_hba.hdr_rq &&
3866 phba->sli4_hba.hdr_rq->queue_id == queid) {
3867
3868 rc = lpfc_idiag_que_param_check(
3869 phba->sli4_hba.hdr_rq, index, count);
3870 if (rc)
3871 goto error_out;
3872 idiag.ptr_private = phba->sli4_hba.hdr_rq;
3873 goto pass_check;
3874 }
3875
3876 if (phba->sli4_hba.dat_rq &&
3877 phba->sli4_hba.dat_rq->queue_id == queid) {
3878
3879 rc = lpfc_idiag_que_param_check(
3880 phba->sli4_hba.dat_rq, index, count);
3881 if (rc)
3882 goto error_out;
3883 idiag.ptr_private = phba->sli4_hba.dat_rq;
3884 goto pass_check;
3885 }
3886 goto error_out;
3887 break;
3888 default:
3889 goto error_out;
3890 break;
3891 }
3892
3893pass_check:
3894
3895 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_QUEACC_RD) {
3896 if (count == LPFC_QUE_ACC_BROWSE)
3897 idiag.offset.last_rd = index;
3898 }
3899
3900 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_QUEACC_WR ||
3901 idiag.cmd.opcode == LPFC_IDIAG_CMD_QUEACC_ST ||
3902 idiag.cmd.opcode == LPFC_IDIAG_CMD_QUEACC_CL) {
3903
3904 pque = (struct lpfc_queue *)idiag.ptr_private;
3905 if (offset > pque->entry_size/sizeof(uint32_t) - 1)
3906 goto error_out;
3907 pentry = pque->qe[index].address;
3908 pentry += offset;
3909 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_QUEACC_WR)
3910 *pentry = value;
3911 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_QUEACC_ST)
3912 *pentry |= value;
3913 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_QUEACC_CL)
3914 *pentry &= ~value;
3915 }
3916 return nbytes;
3917
3918error_out:
3919
3920 memset(&idiag, 0, sizeof(idiag));
3921 return -EINVAL;
3922}
3923
3924
3925
3926
3927
3928
3929
3930
3931
3932
3933
3934
3935
3936
3937
3938static int
3939lpfc_idiag_drbacc_read_reg(struct lpfc_hba *phba, char *pbuffer,
3940 int len, uint32_t drbregid)
3941{
3942
3943 if (!pbuffer)
3944 return 0;
3945
3946 switch (drbregid) {
3947 case LPFC_DRB_EQ:
3948 len += snprintf(pbuffer + len, LPFC_DRB_ACC_BUF_SIZE-len,
3949 "EQ-DRB-REG: 0x%08x\n",
3950 readl(phba->sli4_hba.EQDBregaddr));
3951 break;
3952 case LPFC_DRB_CQ:
3953 len += snprintf(pbuffer + len, LPFC_DRB_ACC_BUF_SIZE - len,
3954 "CQ-DRB-REG: 0x%08x\n",
3955 readl(phba->sli4_hba.CQDBregaddr));
3956 break;
3957 case LPFC_DRB_MQ:
3958 len += snprintf(pbuffer+len, LPFC_DRB_ACC_BUF_SIZE-len,
3959 "MQ-DRB-REG: 0x%08x\n",
3960 readl(phba->sli4_hba.MQDBregaddr));
3961 break;
3962 case LPFC_DRB_WQ:
3963 len += snprintf(pbuffer+len, LPFC_DRB_ACC_BUF_SIZE-len,
3964 "WQ-DRB-REG: 0x%08x\n",
3965 readl(phba->sli4_hba.WQDBregaddr));
3966 break;
3967 case LPFC_DRB_RQ:
3968 len += snprintf(pbuffer+len, LPFC_DRB_ACC_BUF_SIZE-len,
3969 "RQ-DRB-REG: 0x%08x\n",
3970 readl(phba->sli4_hba.RQDBregaddr));
3971 break;
3972 default:
3973 break;
3974 }
3975
3976 return len;
3977}
3978
3979
3980
3981
3982
3983
3984
3985
3986
3987
3988
3989
3990
3991
3992
3993
3994
3995
3996static ssize_t
3997lpfc_idiag_drbacc_read(struct file *file, char __user *buf, size_t nbytes,
3998 loff_t *ppos)
3999{
4000 struct lpfc_debug *debug = file->private_data;
4001 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
4002 uint32_t drb_reg_id, i;
4003 char *pbuffer;
4004 int len = 0;
4005
4006
4007 debug->op = LPFC_IDIAG_OP_RD;
4008
4009 if (!debug->buffer)
4010 debug->buffer = kmalloc(LPFC_DRB_ACC_BUF_SIZE, GFP_KERNEL);
4011 if (!debug->buffer)
4012 return 0;
4013 pbuffer = debug->buffer;
4014
4015 if (*ppos)
4016 return 0;
4017
4018 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_DRBACC_RD)
4019 drb_reg_id = idiag.cmd.data[IDIAG_DRBACC_REGID_INDX];
4020 else
4021 return 0;
4022
4023 if (drb_reg_id == LPFC_DRB_ACC_ALL)
4024 for (i = 1; i <= LPFC_DRB_MAX; i++)
4025 len = lpfc_idiag_drbacc_read_reg(phba,
4026 pbuffer, len, i);
4027 else
4028 len = lpfc_idiag_drbacc_read_reg(phba,
4029 pbuffer, len, drb_reg_id);
4030
4031 return simple_read_from_buffer(buf, nbytes, ppos, pbuffer, len);
4032}
4033
4034
4035
4036
4037
4038
4039
4040
4041
4042
4043
4044
4045
4046
4047
4048
4049
4050
4051
4052static ssize_t
4053lpfc_idiag_drbacc_write(struct file *file, const char __user *buf,
4054 size_t nbytes, loff_t *ppos)
4055{
4056 struct lpfc_debug *debug = file->private_data;
4057 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
4058 uint32_t drb_reg_id, value, reg_val = 0;
4059 void __iomem *drb_reg;
4060 int rc;
4061
4062
4063 debug->op = LPFC_IDIAG_OP_WR;
4064
4065 rc = lpfc_idiag_cmd_get(buf, nbytes, &idiag.cmd);
4066 if (rc < 0)
4067 return rc;
4068
4069
4070 drb_reg_id = idiag.cmd.data[IDIAG_DRBACC_REGID_INDX];
4071 value = idiag.cmd.data[IDIAG_DRBACC_VALUE_INDX];
4072
4073 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_DRBACC_WR ||
4074 idiag.cmd.opcode == LPFC_IDIAG_CMD_DRBACC_ST ||
4075 idiag.cmd.opcode == LPFC_IDIAG_CMD_DRBACC_CL) {
4076 if (rc != LPFC_DRB_ACC_WR_CMD_ARG)
4077 goto error_out;
4078 if (drb_reg_id > LPFC_DRB_MAX)
4079 goto error_out;
4080 } else if (idiag.cmd.opcode == LPFC_IDIAG_CMD_DRBACC_RD) {
4081 if (rc != LPFC_DRB_ACC_RD_CMD_ARG)
4082 goto error_out;
4083 if ((drb_reg_id > LPFC_DRB_MAX) &&
4084 (drb_reg_id != LPFC_DRB_ACC_ALL))
4085 goto error_out;
4086 } else
4087 goto error_out;
4088
4089
4090 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_DRBACC_WR ||
4091 idiag.cmd.opcode == LPFC_IDIAG_CMD_DRBACC_ST ||
4092 idiag.cmd.opcode == LPFC_IDIAG_CMD_DRBACC_CL) {
4093 switch (drb_reg_id) {
4094 case LPFC_DRB_EQ:
4095 drb_reg = phba->sli4_hba.EQDBregaddr;
4096 break;
4097 case LPFC_DRB_CQ:
4098 drb_reg = phba->sli4_hba.CQDBregaddr;
4099 break;
4100 case LPFC_DRB_MQ:
4101 drb_reg = phba->sli4_hba.MQDBregaddr;
4102 break;
4103 case LPFC_DRB_WQ:
4104 drb_reg = phba->sli4_hba.WQDBregaddr;
4105 break;
4106 case LPFC_DRB_RQ:
4107 drb_reg = phba->sli4_hba.RQDBregaddr;
4108 break;
4109 default:
4110 goto error_out;
4111 }
4112
4113 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_DRBACC_WR)
4114 reg_val = value;
4115 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_DRBACC_ST) {
4116 reg_val = readl(drb_reg);
4117 reg_val |= value;
4118 }
4119 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_DRBACC_CL) {
4120 reg_val = readl(drb_reg);
4121 reg_val &= ~value;
4122 }
4123 writel(reg_val, drb_reg);
4124 readl(drb_reg);
4125 }
4126 return nbytes;
4127
4128error_out:
4129
4130 memset(&idiag, 0, sizeof(idiag));
4131 return -EINVAL;
4132}
4133
4134
4135
4136
4137
4138
4139
4140
4141
4142
4143
4144
4145
4146
4147
4148static int
4149lpfc_idiag_ctlacc_read_reg(struct lpfc_hba *phba, char *pbuffer,
4150 int len, uint32_t ctlregid)
4151{
4152
4153 if (!pbuffer)
4154 return 0;
4155
4156 switch (ctlregid) {
4157 case LPFC_CTL_PORT_SEM:
4158 len += snprintf(pbuffer+len, LPFC_CTL_ACC_BUF_SIZE-len,
4159 "Port SemReg: 0x%08x\n",
4160 readl(phba->sli4_hba.conf_regs_memmap_p +
4161 LPFC_CTL_PORT_SEM_OFFSET));
4162 break;
4163 case LPFC_CTL_PORT_STA:
4164 len += snprintf(pbuffer+len, LPFC_CTL_ACC_BUF_SIZE-len,
4165 "Port StaReg: 0x%08x\n",
4166 readl(phba->sli4_hba.conf_regs_memmap_p +
4167 LPFC_CTL_PORT_STA_OFFSET));
4168 break;
4169 case LPFC_CTL_PORT_CTL:
4170 len += snprintf(pbuffer+len, LPFC_CTL_ACC_BUF_SIZE-len,
4171 "Port CtlReg: 0x%08x\n",
4172 readl(phba->sli4_hba.conf_regs_memmap_p +
4173 LPFC_CTL_PORT_CTL_OFFSET));
4174 break;
4175 case LPFC_CTL_PORT_ER1:
4176 len += snprintf(pbuffer+len, LPFC_CTL_ACC_BUF_SIZE-len,
4177 "Port Er1Reg: 0x%08x\n",
4178 readl(phba->sli4_hba.conf_regs_memmap_p +
4179 LPFC_CTL_PORT_ER1_OFFSET));
4180 break;
4181 case LPFC_CTL_PORT_ER2:
4182 len += snprintf(pbuffer+len, LPFC_CTL_ACC_BUF_SIZE-len,
4183 "Port Er2Reg: 0x%08x\n",
4184 readl(phba->sli4_hba.conf_regs_memmap_p +
4185 LPFC_CTL_PORT_ER2_OFFSET));
4186 break;
4187 case LPFC_CTL_PDEV_CTL:
4188 len += snprintf(pbuffer+len, LPFC_CTL_ACC_BUF_SIZE-len,
4189 "PDev CtlReg: 0x%08x\n",
4190 readl(phba->sli4_hba.conf_regs_memmap_p +
4191 LPFC_CTL_PDEV_CTL_OFFSET));
4192 break;
4193 default:
4194 break;
4195 }
4196 return len;
4197}
4198
4199
4200
4201
4202
4203
4204
4205
4206
4207
4208
4209
4210
4211
4212
4213
4214static ssize_t
4215lpfc_idiag_ctlacc_read(struct file *file, char __user *buf, size_t nbytes,
4216 loff_t *ppos)
4217{
4218 struct lpfc_debug *debug = file->private_data;
4219 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
4220 uint32_t ctl_reg_id, i;
4221 char *pbuffer;
4222 int len = 0;
4223
4224
4225 debug->op = LPFC_IDIAG_OP_RD;
4226
4227 if (!debug->buffer)
4228 debug->buffer = kmalloc(LPFC_CTL_ACC_BUF_SIZE, GFP_KERNEL);
4229 if (!debug->buffer)
4230 return 0;
4231 pbuffer = debug->buffer;
4232
4233 if (*ppos)
4234 return 0;
4235
4236 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_CTLACC_RD)
4237 ctl_reg_id = idiag.cmd.data[IDIAG_CTLACC_REGID_INDX];
4238 else
4239 return 0;
4240
4241 if (ctl_reg_id == LPFC_CTL_ACC_ALL)
4242 for (i = 1; i <= LPFC_CTL_MAX; i++)
4243 len = lpfc_idiag_ctlacc_read_reg(phba,
4244 pbuffer, len, i);
4245 else
4246 len = lpfc_idiag_ctlacc_read_reg(phba,
4247 pbuffer, len, ctl_reg_id);
4248
4249 return simple_read_from_buffer(buf, nbytes, ppos, pbuffer, len);
4250}
4251
4252
4253
4254
4255
4256
4257
4258
4259
4260
4261
4262
4263
4264
4265
4266
4267static ssize_t
4268lpfc_idiag_ctlacc_write(struct file *file, const char __user *buf,
4269 size_t nbytes, loff_t *ppos)
4270{
4271 struct lpfc_debug *debug = file->private_data;
4272 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
4273 uint32_t ctl_reg_id, value, reg_val = 0;
4274 void __iomem *ctl_reg;
4275 int rc;
4276
4277
4278 debug->op = LPFC_IDIAG_OP_WR;
4279
4280 rc = lpfc_idiag_cmd_get(buf, nbytes, &idiag.cmd);
4281 if (rc < 0)
4282 return rc;
4283
4284
4285 ctl_reg_id = idiag.cmd.data[IDIAG_CTLACC_REGID_INDX];
4286 value = idiag.cmd.data[IDIAG_CTLACC_VALUE_INDX];
4287
4288 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_CTLACC_WR ||
4289 idiag.cmd.opcode == LPFC_IDIAG_CMD_CTLACC_ST ||
4290 idiag.cmd.opcode == LPFC_IDIAG_CMD_CTLACC_CL) {
4291 if (rc != LPFC_CTL_ACC_WR_CMD_ARG)
4292 goto error_out;
4293 if (ctl_reg_id > LPFC_CTL_MAX)
4294 goto error_out;
4295 } else if (idiag.cmd.opcode == LPFC_IDIAG_CMD_CTLACC_RD) {
4296 if (rc != LPFC_CTL_ACC_RD_CMD_ARG)
4297 goto error_out;
4298 if ((ctl_reg_id > LPFC_CTL_MAX) &&
4299 (ctl_reg_id != LPFC_CTL_ACC_ALL))
4300 goto error_out;
4301 } else
4302 goto error_out;
4303
4304
4305 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_CTLACC_WR ||
4306 idiag.cmd.opcode == LPFC_IDIAG_CMD_CTLACC_ST ||
4307 idiag.cmd.opcode == LPFC_IDIAG_CMD_CTLACC_CL) {
4308 switch (ctl_reg_id) {
4309 case LPFC_CTL_PORT_SEM:
4310 ctl_reg = phba->sli4_hba.conf_regs_memmap_p +
4311 LPFC_CTL_PORT_SEM_OFFSET;
4312 break;
4313 case LPFC_CTL_PORT_STA:
4314 ctl_reg = phba->sli4_hba.conf_regs_memmap_p +
4315 LPFC_CTL_PORT_STA_OFFSET;
4316 break;
4317 case LPFC_CTL_PORT_CTL:
4318 ctl_reg = phba->sli4_hba.conf_regs_memmap_p +
4319 LPFC_CTL_PORT_CTL_OFFSET;
4320 break;
4321 case LPFC_CTL_PORT_ER1:
4322 ctl_reg = phba->sli4_hba.conf_regs_memmap_p +
4323 LPFC_CTL_PORT_ER1_OFFSET;
4324 break;
4325 case LPFC_CTL_PORT_ER2:
4326 ctl_reg = phba->sli4_hba.conf_regs_memmap_p +
4327 LPFC_CTL_PORT_ER2_OFFSET;
4328 break;
4329 case LPFC_CTL_PDEV_CTL:
4330 ctl_reg = phba->sli4_hba.conf_regs_memmap_p +
4331 LPFC_CTL_PDEV_CTL_OFFSET;
4332 break;
4333 default:
4334 goto error_out;
4335 }
4336
4337 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_CTLACC_WR)
4338 reg_val = value;
4339 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_CTLACC_ST) {
4340 reg_val = readl(ctl_reg);
4341 reg_val |= value;
4342 }
4343 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_CTLACC_CL) {
4344 reg_val = readl(ctl_reg);
4345 reg_val &= ~value;
4346 }
4347 writel(reg_val, ctl_reg);
4348 readl(ctl_reg);
4349 }
4350 return nbytes;
4351
4352error_out:
4353
4354 memset(&idiag, 0, sizeof(idiag));
4355 return -EINVAL;
4356}
4357
4358
4359
4360
4361
4362
4363
4364
4365
4366
4367
4368
4369
4370static int
4371lpfc_idiag_mbxacc_get_setup(struct lpfc_hba *phba, char *pbuffer)
4372{
4373 uint32_t mbx_dump_map, mbx_dump_cnt, mbx_word_cnt, mbx_mbox_cmd;
4374 int len = 0;
4375
4376 mbx_mbox_cmd = idiag.cmd.data[IDIAG_MBXACC_MBCMD_INDX];
4377 mbx_dump_map = idiag.cmd.data[IDIAG_MBXACC_DPMAP_INDX];
4378 mbx_dump_cnt = idiag.cmd.data[IDIAG_MBXACC_DPCNT_INDX];
4379 mbx_word_cnt = idiag.cmd.data[IDIAG_MBXACC_WDCNT_INDX];
4380
4381 len += snprintf(pbuffer+len, LPFC_MBX_ACC_BUF_SIZE-len,
4382 "mbx_dump_map: 0x%08x\n", mbx_dump_map);
4383 len += snprintf(pbuffer+len, LPFC_MBX_ACC_BUF_SIZE-len,
4384 "mbx_dump_cnt: %04d\n", mbx_dump_cnt);
4385 len += snprintf(pbuffer+len, LPFC_MBX_ACC_BUF_SIZE-len,
4386 "mbx_word_cnt: %04d\n", mbx_word_cnt);
4387 len += snprintf(pbuffer+len, LPFC_MBX_ACC_BUF_SIZE-len,
4388 "mbx_mbox_cmd: 0x%02x\n", mbx_mbox_cmd);
4389
4390 return len;
4391}
4392
4393
4394
4395
4396
4397
4398
4399
4400
4401
4402
4403
4404
4405
4406
4407
4408static ssize_t
4409lpfc_idiag_mbxacc_read(struct file *file, char __user *buf, size_t nbytes,
4410 loff_t *ppos)
4411{
4412 struct lpfc_debug *debug = file->private_data;
4413 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
4414 char *pbuffer;
4415 int len = 0;
4416
4417
4418 debug->op = LPFC_IDIAG_OP_RD;
4419
4420 if (!debug->buffer)
4421 debug->buffer = kmalloc(LPFC_MBX_ACC_BUF_SIZE, GFP_KERNEL);
4422 if (!debug->buffer)
4423 return 0;
4424 pbuffer = debug->buffer;
4425
4426 if (*ppos)
4427 return 0;
4428
4429 if ((idiag.cmd.opcode != LPFC_IDIAG_CMD_MBXACC_DP) &&
4430 (idiag.cmd.opcode != LPFC_IDIAG_BSG_MBXACC_DP))
4431 return 0;
4432
4433 len = lpfc_idiag_mbxacc_get_setup(phba, pbuffer);
4434
4435 return simple_read_from_buffer(buf, nbytes, ppos, pbuffer, len);
4436}
4437
4438
4439
4440
4441
4442
4443
4444
4445
4446
4447
4448
4449
4450
4451
4452
4453static ssize_t
4454lpfc_idiag_mbxacc_write(struct file *file, const char __user *buf,
4455 size_t nbytes, loff_t *ppos)
4456{
4457 struct lpfc_debug *debug = file->private_data;
4458 uint32_t mbx_dump_map, mbx_dump_cnt, mbx_word_cnt, mbx_mbox_cmd;
4459 int rc;
4460
4461
4462 debug->op = LPFC_IDIAG_OP_WR;
4463
4464 rc = lpfc_idiag_cmd_get(buf, nbytes, &idiag.cmd);
4465 if (rc < 0)
4466 return rc;
4467
4468
4469 mbx_mbox_cmd = idiag.cmd.data[IDIAG_MBXACC_MBCMD_INDX];
4470 mbx_dump_map = idiag.cmd.data[IDIAG_MBXACC_DPMAP_INDX];
4471 mbx_dump_cnt = idiag.cmd.data[IDIAG_MBXACC_DPCNT_INDX];
4472 mbx_word_cnt = idiag.cmd.data[IDIAG_MBXACC_WDCNT_INDX];
4473
4474 if (idiag.cmd.opcode == LPFC_IDIAG_CMD_MBXACC_DP) {
4475 if (!(mbx_dump_map & LPFC_MBX_DMP_MBX_ALL))
4476 goto error_out;
4477 if ((mbx_dump_map & ~LPFC_MBX_DMP_MBX_ALL) &&
4478 (mbx_dump_map != LPFC_MBX_DMP_ALL))
4479 goto error_out;
4480 if (mbx_word_cnt > sizeof(MAILBOX_t))
4481 goto error_out;
4482 } else if (idiag.cmd.opcode == LPFC_IDIAG_BSG_MBXACC_DP) {
4483 if (!(mbx_dump_map & LPFC_BSG_DMP_MBX_ALL))
4484 goto error_out;
4485 if ((mbx_dump_map & ~LPFC_BSG_DMP_MBX_ALL) &&
4486 (mbx_dump_map != LPFC_MBX_DMP_ALL))
4487 goto error_out;
4488 if (mbx_word_cnt > (BSG_MBOX_SIZE)/4)
4489 goto error_out;
4490 if (mbx_mbox_cmd != 0x9b)
4491 goto error_out;
4492 } else
4493 goto error_out;
4494
4495 if (mbx_word_cnt == 0)
4496 goto error_out;
4497 if (rc != LPFC_MBX_DMP_ARG)
4498 goto error_out;
4499 if (mbx_mbox_cmd & ~0xff)
4500 goto error_out;
4501
4502
4503 if (mbx_dump_cnt == 0)
4504 goto reset_out;
4505
4506 return nbytes;
4507
4508reset_out:
4509
4510 memset(&idiag, 0, sizeof(idiag));
4511 return nbytes;
4512
4513error_out:
4514
4515 memset(&idiag, 0, sizeof(idiag));
4516 return -EINVAL;
4517}
4518
4519
4520
4521
4522
4523
4524
4525
4526
4527
4528
4529
4530
4531static int
4532lpfc_idiag_extacc_avail_get(struct lpfc_hba *phba, char *pbuffer, int len)
4533{
4534 uint16_t ext_cnt, ext_size;
4535
4536 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4537 "\nAvailable Extents Information:\n");
4538
4539 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4540 "\tPort Available VPI extents: ");
4541 lpfc_sli4_get_avail_extnt_rsrc(phba, LPFC_RSC_TYPE_FCOE_VPI,
4542 &ext_cnt, &ext_size);
4543 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4544 "Count %3d, Size %3d\n", ext_cnt, ext_size);
4545
4546 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4547 "\tPort Available VFI extents: ");
4548 lpfc_sli4_get_avail_extnt_rsrc(phba, LPFC_RSC_TYPE_FCOE_VFI,
4549 &ext_cnt, &ext_size);
4550 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4551 "Count %3d, Size %3d\n", ext_cnt, ext_size);
4552
4553 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4554 "\tPort Available RPI extents: ");
4555 lpfc_sli4_get_avail_extnt_rsrc(phba, LPFC_RSC_TYPE_FCOE_RPI,
4556 &ext_cnt, &ext_size);
4557 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4558 "Count %3d, Size %3d\n", ext_cnt, ext_size);
4559
4560 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4561 "\tPort Available XRI extents: ");
4562 lpfc_sli4_get_avail_extnt_rsrc(phba, LPFC_RSC_TYPE_FCOE_XRI,
4563 &ext_cnt, &ext_size);
4564 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4565 "Count %3d, Size %3d\n", ext_cnt, ext_size);
4566
4567 return len;
4568}
4569
4570
4571
4572
4573
4574
4575
4576
4577
4578
4579
4580
4581
4582static int
4583lpfc_idiag_extacc_alloc_get(struct lpfc_hba *phba, char *pbuffer, int len)
4584{
4585 uint16_t ext_cnt, ext_size;
4586 int rc;
4587
4588 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4589 "\nAllocated Extents Information:\n");
4590
4591 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4592 "\tHost Allocated VPI extents: ");
4593 rc = lpfc_sli4_get_allocated_extnts(phba, LPFC_RSC_TYPE_FCOE_VPI,
4594 &ext_cnt, &ext_size);
4595 if (!rc)
4596 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4597 "Port %d Extent %3d, Size %3d\n",
4598 phba->brd_no, ext_cnt, ext_size);
4599 else
4600 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4601 "N/A\n");
4602
4603 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4604 "\tHost Allocated VFI extents: ");
4605 rc = lpfc_sli4_get_allocated_extnts(phba, LPFC_RSC_TYPE_FCOE_VFI,
4606 &ext_cnt, &ext_size);
4607 if (!rc)
4608 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4609 "Port %d Extent %3d, Size %3d\n",
4610 phba->brd_no, ext_cnt, ext_size);
4611 else
4612 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4613 "N/A\n");
4614
4615 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4616 "\tHost Allocated RPI extents: ");
4617 rc = lpfc_sli4_get_allocated_extnts(phba, LPFC_RSC_TYPE_FCOE_RPI,
4618 &ext_cnt, &ext_size);
4619 if (!rc)
4620 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4621 "Port %d Extent %3d, Size %3d\n",
4622 phba->brd_no, ext_cnt, ext_size);
4623 else
4624 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4625 "N/A\n");
4626
4627 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4628 "\tHost Allocated XRI extents: ");
4629 rc = lpfc_sli4_get_allocated_extnts(phba, LPFC_RSC_TYPE_FCOE_XRI,
4630 &ext_cnt, &ext_size);
4631 if (!rc)
4632 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4633 "Port %d Extent %3d, Size %3d\n",
4634 phba->brd_no, ext_cnt, ext_size);
4635 else
4636 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4637 "N/A\n");
4638
4639 return len;
4640}
4641
4642
4643
4644
4645
4646
4647
4648
4649
4650
4651
4652
4653
4654static int
4655lpfc_idiag_extacc_drivr_get(struct lpfc_hba *phba, char *pbuffer, int len)
4656{
4657 struct lpfc_rsrc_blks *rsrc_blks;
4658 int index;
4659
4660 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4661 "\nDriver Extents Information:\n");
4662
4663 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4664 "\tVPI extents:\n");
4665 index = 0;
4666 list_for_each_entry(rsrc_blks, &phba->lpfc_vpi_blk_list, list) {
4667 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4668 "\t\tBlock %3d: Start %4d, Count %4d\n",
4669 index, rsrc_blks->rsrc_start,
4670 rsrc_blks->rsrc_size);
4671 index++;
4672 }
4673 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4674 "\tVFI extents:\n");
4675 index = 0;
4676 list_for_each_entry(rsrc_blks, &phba->sli4_hba.lpfc_vfi_blk_list,
4677 list) {
4678 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4679 "\t\tBlock %3d: Start %4d, Count %4d\n",
4680 index, rsrc_blks->rsrc_start,
4681 rsrc_blks->rsrc_size);
4682 index++;
4683 }
4684
4685 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4686 "\tRPI extents:\n");
4687 index = 0;
4688 list_for_each_entry(rsrc_blks, &phba->sli4_hba.lpfc_rpi_blk_list,
4689 list) {
4690 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4691 "\t\tBlock %3d: Start %4d, Count %4d\n",
4692 index, rsrc_blks->rsrc_start,
4693 rsrc_blks->rsrc_size);
4694 index++;
4695 }
4696
4697 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4698 "\tXRI extents:\n");
4699 index = 0;
4700 list_for_each_entry(rsrc_blks, &phba->sli4_hba.lpfc_xri_blk_list,
4701 list) {
4702 len += snprintf(pbuffer+len, LPFC_EXT_ACC_BUF_SIZE-len,
4703 "\t\tBlock %3d: Start %4d, Count %4d\n",
4704 index, rsrc_blks->rsrc_start,
4705 rsrc_blks->rsrc_size);
4706 index++;
4707 }
4708
4709 return len;
4710}
4711
4712
4713
4714
4715
4716
4717
4718
4719
4720
4721
4722
4723
4724
4725
4726
4727static ssize_t
4728lpfc_idiag_extacc_write(struct file *file, const char __user *buf,
4729 size_t nbytes, loff_t *ppos)
4730{
4731 struct lpfc_debug *debug = file->private_data;
4732 uint32_t ext_map;
4733 int rc;
4734
4735
4736 debug->op = LPFC_IDIAG_OP_WR;
4737
4738 rc = lpfc_idiag_cmd_get(buf, nbytes, &idiag.cmd);
4739 if (rc < 0)
4740 return rc;
4741
4742 ext_map = idiag.cmd.data[IDIAG_EXTACC_EXMAP_INDX];
4743
4744 if (idiag.cmd.opcode != LPFC_IDIAG_CMD_EXTACC_RD)
4745 goto error_out;
4746 if (rc != LPFC_EXT_ACC_CMD_ARG)
4747 goto error_out;
4748 if (!(ext_map & LPFC_EXT_ACC_ALL))
4749 goto error_out;
4750
4751 return nbytes;
4752error_out:
4753
4754 memset(&idiag, 0, sizeof(idiag));
4755 return -EINVAL;
4756}
4757
4758
4759
4760
4761
4762
4763
4764
4765
4766
4767
4768
4769
4770
4771
4772
4773static ssize_t
4774lpfc_idiag_extacc_read(struct file *file, char __user *buf, size_t nbytes,
4775 loff_t *ppos)
4776{
4777 struct lpfc_debug *debug = file->private_data;
4778 struct lpfc_hba *phba = (struct lpfc_hba *)debug->i_private;
4779 char *pbuffer;
4780 uint32_t ext_map;
4781 int len = 0;
4782
4783
4784 debug->op = LPFC_IDIAG_OP_RD;
4785
4786 if (!debug->buffer)
4787 debug->buffer = kmalloc(LPFC_EXT_ACC_BUF_SIZE, GFP_KERNEL);
4788 if (!debug->buffer)
4789 return 0;
4790 pbuffer = debug->buffer;
4791 if (*ppos)
4792 return 0;
4793 if (idiag.cmd.opcode != LPFC_IDIAG_CMD_EXTACC_RD)
4794 return 0;
4795
4796 ext_map = idiag.cmd.data[IDIAG_EXTACC_EXMAP_INDX];
4797 if (ext_map & LPFC_EXT_ACC_AVAIL)
4798 len = lpfc_idiag_extacc_avail_get(phba, pbuffer, len);
4799 if (ext_map & LPFC_EXT_ACC_ALLOC)
4800 len = lpfc_idiag_extacc_alloc_get(phba, pbuffer, len);
4801 if (ext_map & LPFC_EXT_ACC_DRIVR)
4802 len = lpfc_idiag_extacc_drivr_get(phba, pbuffer, len);
4803
4804 return simple_read_from_buffer(buf, nbytes, ppos, pbuffer, len);
4805}
4806
4807#undef lpfc_debugfs_op_disc_trc
4808static const struct file_operations lpfc_debugfs_op_disc_trc = {
4809 .owner = THIS_MODULE,
4810 .open = lpfc_debugfs_disc_trc_open,
4811 .llseek = lpfc_debugfs_lseek,
4812 .read = lpfc_debugfs_read,
4813 .release = lpfc_debugfs_release,
4814};
4815
4816#undef lpfc_debugfs_op_nodelist
4817static const struct file_operations lpfc_debugfs_op_nodelist = {
4818 .owner = THIS_MODULE,
4819 .open = lpfc_debugfs_nodelist_open,
4820 .llseek = lpfc_debugfs_lseek,
4821 .read = lpfc_debugfs_read,
4822 .release = lpfc_debugfs_release,
4823};
4824
4825#undef lpfc_debugfs_op_hbqinfo
4826static const struct file_operations lpfc_debugfs_op_hbqinfo = {
4827 .owner = THIS_MODULE,
4828 .open = lpfc_debugfs_hbqinfo_open,
4829 .llseek = lpfc_debugfs_lseek,
4830 .read = lpfc_debugfs_read,
4831 .release = lpfc_debugfs_release,
4832};
4833
4834#undef lpfc_debugfs_op_dumpHBASlim
4835static const struct file_operations lpfc_debugfs_op_dumpHBASlim = {
4836 .owner = THIS_MODULE,
4837 .open = lpfc_debugfs_dumpHBASlim_open,
4838 .llseek = lpfc_debugfs_lseek,
4839 .read = lpfc_debugfs_read,
4840 .release = lpfc_debugfs_release,
4841};
4842
4843#undef lpfc_debugfs_op_dumpHostSlim
4844static const struct file_operations lpfc_debugfs_op_dumpHostSlim = {
4845 .owner = THIS_MODULE,
4846 .open = lpfc_debugfs_dumpHostSlim_open,
4847 .llseek = lpfc_debugfs_lseek,
4848 .read = lpfc_debugfs_read,
4849 .release = lpfc_debugfs_release,
4850};
4851
4852#undef lpfc_debugfs_op_nvmestat
4853static const struct file_operations lpfc_debugfs_op_nvmestat = {
4854 .owner = THIS_MODULE,
4855 .open = lpfc_debugfs_nvmestat_open,
4856 .llseek = lpfc_debugfs_lseek,
4857 .read = lpfc_debugfs_read,
4858 .write = lpfc_debugfs_nvmestat_write,
4859 .release = lpfc_debugfs_release,
4860};
4861
4862#undef lpfc_debugfs_op_nvmektime
4863static const struct file_operations lpfc_debugfs_op_nvmektime = {
4864 .owner = THIS_MODULE,
4865 .open = lpfc_debugfs_nvmektime_open,
4866 .llseek = lpfc_debugfs_lseek,
4867 .read = lpfc_debugfs_read,
4868 .write = lpfc_debugfs_nvmektime_write,
4869 .release = lpfc_debugfs_release,
4870};
4871
4872#undef lpfc_debugfs_op_nvmeio_trc
4873static const struct file_operations lpfc_debugfs_op_nvmeio_trc = {
4874 .owner = THIS_MODULE,
4875 .open = lpfc_debugfs_nvmeio_trc_open,
4876 .llseek = lpfc_debugfs_lseek,
4877 .read = lpfc_debugfs_read,
4878 .write = lpfc_debugfs_nvmeio_trc_write,
4879 .release = lpfc_debugfs_release,
4880};
4881
4882#undef lpfc_debugfs_op_cpucheck
4883static const struct file_operations lpfc_debugfs_op_cpucheck = {
4884 .owner = THIS_MODULE,
4885 .open = lpfc_debugfs_cpucheck_open,
4886 .llseek = lpfc_debugfs_lseek,
4887 .read = lpfc_debugfs_read,
4888 .write = lpfc_debugfs_cpucheck_write,
4889 .release = lpfc_debugfs_release,
4890};
4891
4892#undef lpfc_debugfs_op_dumpData
4893static const struct file_operations lpfc_debugfs_op_dumpData = {
4894 .owner = THIS_MODULE,
4895 .open = lpfc_debugfs_dumpData_open,
4896 .llseek = lpfc_debugfs_lseek,
4897 .read = lpfc_debugfs_read,
4898 .write = lpfc_debugfs_dumpDataDif_write,
4899 .release = lpfc_debugfs_dumpDataDif_release,
4900};
4901
4902#undef lpfc_debugfs_op_dumpDif
4903static const struct file_operations lpfc_debugfs_op_dumpDif = {
4904 .owner = THIS_MODULE,
4905 .open = lpfc_debugfs_dumpDif_open,
4906 .llseek = lpfc_debugfs_lseek,
4907 .read = lpfc_debugfs_read,
4908 .write = lpfc_debugfs_dumpDataDif_write,
4909 .release = lpfc_debugfs_dumpDataDif_release,
4910};
4911
4912#undef lpfc_debugfs_op_dif_err
4913static const struct file_operations lpfc_debugfs_op_dif_err = {
4914 .owner = THIS_MODULE,
4915 .open = simple_open,
4916 .llseek = lpfc_debugfs_lseek,
4917 .read = lpfc_debugfs_dif_err_read,
4918 .write = lpfc_debugfs_dif_err_write,
4919 .release = lpfc_debugfs_dif_err_release,
4920};
4921
4922#undef lpfc_debugfs_op_slow_ring_trc
4923static const struct file_operations lpfc_debugfs_op_slow_ring_trc = {
4924 .owner = THIS_MODULE,
4925 .open = lpfc_debugfs_slow_ring_trc_open,
4926 .llseek = lpfc_debugfs_lseek,
4927 .read = lpfc_debugfs_read,
4928 .release = lpfc_debugfs_release,
4929};
4930
4931static struct dentry *lpfc_debugfs_root = NULL;
4932static atomic_t lpfc_debugfs_hba_count;
4933
4934
4935
4936
4937#undef lpfc_idiag_op_pciCfg
4938static const struct file_operations lpfc_idiag_op_pciCfg = {
4939 .owner = THIS_MODULE,
4940 .open = lpfc_idiag_open,
4941 .llseek = lpfc_debugfs_lseek,
4942 .read = lpfc_idiag_pcicfg_read,
4943 .write = lpfc_idiag_pcicfg_write,
4944 .release = lpfc_idiag_cmd_release,
4945};
4946
4947#undef lpfc_idiag_op_barAcc
4948static const struct file_operations lpfc_idiag_op_barAcc = {
4949 .owner = THIS_MODULE,
4950 .open = lpfc_idiag_open,
4951 .llseek = lpfc_debugfs_lseek,
4952 .read = lpfc_idiag_baracc_read,
4953 .write = lpfc_idiag_baracc_write,
4954 .release = lpfc_idiag_cmd_release,
4955};
4956
4957#undef lpfc_idiag_op_queInfo
4958static const struct file_operations lpfc_idiag_op_queInfo = {
4959 .owner = THIS_MODULE,
4960 .open = lpfc_idiag_open,
4961 .read = lpfc_idiag_queinfo_read,
4962 .release = lpfc_idiag_release,
4963};
4964
4965#undef lpfc_idiag_op_queAcc
4966static const struct file_operations lpfc_idiag_op_queAcc = {
4967 .owner = THIS_MODULE,
4968 .open = lpfc_idiag_open,
4969 .llseek = lpfc_debugfs_lseek,
4970 .read = lpfc_idiag_queacc_read,
4971 .write = lpfc_idiag_queacc_write,
4972 .release = lpfc_idiag_cmd_release,
4973};
4974
4975#undef lpfc_idiag_op_drbAcc
4976static const struct file_operations lpfc_idiag_op_drbAcc = {
4977 .owner = THIS_MODULE,
4978 .open = lpfc_idiag_open,
4979 .llseek = lpfc_debugfs_lseek,
4980 .read = lpfc_idiag_drbacc_read,
4981 .write = lpfc_idiag_drbacc_write,
4982 .release = lpfc_idiag_cmd_release,
4983};
4984
4985#undef lpfc_idiag_op_ctlAcc
4986static const struct file_operations lpfc_idiag_op_ctlAcc = {
4987 .owner = THIS_MODULE,
4988 .open = lpfc_idiag_open,
4989 .llseek = lpfc_debugfs_lseek,
4990 .read = lpfc_idiag_ctlacc_read,
4991 .write = lpfc_idiag_ctlacc_write,
4992 .release = lpfc_idiag_cmd_release,
4993};
4994
4995#undef lpfc_idiag_op_mbxAcc
4996static const struct file_operations lpfc_idiag_op_mbxAcc = {
4997 .owner = THIS_MODULE,
4998 .open = lpfc_idiag_open,
4999 .llseek = lpfc_debugfs_lseek,
5000 .read = lpfc_idiag_mbxacc_read,
5001 .write = lpfc_idiag_mbxacc_write,
5002 .release = lpfc_idiag_cmd_release,
5003};
5004
5005#undef lpfc_idiag_op_extAcc
5006static const struct file_operations lpfc_idiag_op_extAcc = {
5007 .owner = THIS_MODULE,
5008 .open = lpfc_idiag_open,
5009 .llseek = lpfc_debugfs_lseek,
5010 .read = lpfc_idiag_extacc_read,
5011 .write = lpfc_idiag_extacc_write,
5012 .release = lpfc_idiag_cmd_release,
5013};
5014
5015#endif
5016
5017
5018
5019
5020
5021
5022
5023
5024
5025void
5026lpfc_idiag_mbxacc_dump_bsg_mbox(struct lpfc_hba *phba, enum nemb_type nemb_tp,
5027 enum mbox_type mbox_tp, enum dma_type dma_tp,
5028 enum sta_type sta_tp,
5029 struct lpfc_dmabuf *dmabuf, uint32_t ext_buf)
5030{
5031#ifdef CONFIG_SCSI_LPFC_DEBUG_FS
5032 uint32_t *mbx_mbox_cmd, *mbx_dump_map, *mbx_dump_cnt, *mbx_word_cnt;
5033 char line_buf[LPFC_MBX_ACC_LBUF_SZ];
5034 int len = 0;
5035 uint32_t do_dump = 0;
5036 uint32_t *pword;
5037 uint32_t i;
5038
5039 if (idiag.cmd.opcode != LPFC_IDIAG_BSG_MBXACC_DP)
5040 return;
5041
5042 mbx_mbox_cmd = &idiag.cmd.data[IDIAG_MBXACC_MBCMD_INDX];
5043 mbx_dump_map = &idiag.cmd.data[IDIAG_MBXACC_DPMAP_INDX];
5044 mbx_dump_cnt = &idiag.cmd.data[IDIAG_MBXACC_DPCNT_INDX];
5045 mbx_word_cnt = &idiag.cmd.data[IDIAG_MBXACC_WDCNT_INDX];
5046
5047 if (!(*mbx_dump_map & LPFC_MBX_DMP_ALL) ||
5048 (*mbx_dump_cnt == 0) ||
5049 (*mbx_word_cnt == 0))
5050 return;
5051
5052 if (*mbx_mbox_cmd != 0x9B)
5053 return;
5054
5055 if ((mbox_tp == mbox_rd) && (dma_tp == dma_mbox)) {
5056 if (*mbx_dump_map & LPFC_BSG_DMP_MBX_RD_MBX) {
5057 do_dump |= LPFC_BSG_DMP_MBX_RD_MBX;
5058 pr_err("\nRead mbox command (x%x), "
5059 "nemb:0x%x, extbuf_cnt:%d:\n",
5060 sta_tp, nemb_tp, ext_buf);
5061 }
5062 }
5063 if ((mbox_tp == mbox_rd) && (dma_tp == dma_ebuf)) {
5064 if (*mbx_dump_map & LPFC_BSG_DMP_MBX_RD_BUF) {
5065 do_dump |= LPFC_BSG_DMP_MBX_RD_BUF;
5066 pr_err("\nRead mbox buffer (x%x), "
5067 "nemb:0x%x, extbuf_seq:%d:\n",
5068 sta_tp, nemb_tp, ext_buf);
5069 }
5070 }
5071 if ((mbox_tp == mbox_wr) && (dma_tp == dma_mbox)) {
5072 if (*mbx_dump_map & LPFC_BSG_DMP_MBX_WR_MBX) {
5073 do_dump |= LPFC_BSG_DMP_MBX_WR_MBX;
5074 pr_err("\nWrite mbox command (x%x), "
5075 "nemb:0x%x, extbuf_cnt:%d:\n",
5076 sta_tp, nemb_tp, ext_buf);
5077 }
5078 }
5079 if ((mbox_tp == mbox_wr) && (dma_tp == dma_ebuf)) {
5080 if (*mbx_dump_map & LPFC_BSG_DMP_MBX_WR_BUF) {
5081 do_dump |= LPFC_BSG_DMP_MBX_WR_BUF;
5082 pr_err("\nWrite mbox buffer (x%x), "
5083 "nemb:0x%x, extbuf_seq:%d:\n",
5084 sta_tp, nemb_tp, ext_buf);
5085 }
5086 }
5087
5088
5089 if (do_dump) {
5090 pword = (uint32_t *)dmabuf->virt;
5091 for (i = 0; i < *mbx_word_cnt; i++) {
5092 if (!(i % 8)) {
5093 if (i != 0)
5094 pr_err("%s\n", line_buf);
5095 len = 0;
5096 len += snprintf(line_buf+len,
5097 LPFC_MBX_ACC_LBUF_SZ-len,
5098 "%03d: ", i);
5099 }
5100 len += snprintf(line_buf+len, LPFC_MBX_ACC_LBUF_SZ-len,
5101 "%08x ", (uint32_t)*pword);
5102 pword++;
5103 }
5104 if ((i - 1) % 8)
5105 pr_err("%s\n", line_buf);
5106 (*mbx_dump_cnt)--;
5107 }
5108
5109
5110 if (*mbx_dump_cnt == 0)
5111 memset(&idiag, 0, sizeof(idiag));
5112 return;
5113#endif
5114}
5115
5116
5117
5118
5119
5120
5121
5122
5123
5124void
5125lpfc_idiag_mbxacc_dump_issue_mbox(struct lpfc_hba *phba, MAILBOX_t *pmbox)
5126{
5127#ifdef CONFIG_SCSI_LPFC_DEBUG_FS
5128 uint32_t *mbx_dump_map, *mbx_dump_cnt, *mbx_word_cnt, *mbx_mbox_cmd;
5129 char line_buf[LPFC_MBX_ACC_LBUF_SZ];
5130 int len = 0;
5131 uint32_t *pword;
5132 uint8_t *pbyte;
5133 uint32_t i, j;
5134
5135 if (idiag.cmd.opcode != LPFC_IDIAG_CMD_MBXACC_DP)
5136 return;
5137
5138 mbx_mbox_cmd = &idiag.cmd.data[IDIAG_MBXACC_MBCMD_INDX];
5139 mbx_dump_map = &idiag.cmd.data[IDIAG_MBXACC_DPMAP_INDX];
5140 mbx_dump_cnt = &idiag.cmd.data[IDIAG_MBXACC_DPCNT_INDX];
5141 mbx_word_cnt = &idiag.cmd.data[IDIAG_MBXACC_WDCNT_INDX];
5142
5143 if (!(*mbx_dump_map & LPFC_MBX_DMP_MBX_ALL) ||
5144 (*mbx_dump_cnt == 0) ||
5145 (*mbx_word_cnt == 0))
5146 return;
5147
5148 if ((*mbx_mbox_cmd != LPFC_MBX_ALL_CMD) &&
5149 (*mbx_mbox_cmd != pmbox->mbxCommand))
5150 return;
5151
5152
5153 if (*mbx_dump_map & LPFC_MBX_DMP_MBX_WORD) {
5154 pr_err("Mailbox command:0x%x dump by word:\n",
5155 pmbox->mbxCommand);
5156 pword = (uint32_t *)pmbox;
5157 for (i = 0; i < *mbx_word_cnt; i++) {
5158 if (!(i % 8)) {
5159 if (i != 0)
5160 pr_err("%s\n", line_buf);
5161 len = 0;
5162 memset(line_buf, 0, LPFC_MBX_ACC_LBUF_SZ);
5163 len += snprintf(line_buf+len,
5164 LPFC_MBX_ACC_LBUF_SZ-len,
5165 "%03d: ", i);
5166 }
5167 len += snprintf(line_buf+len, LPFC_MBX_ACC_LBUF_SZ-len,
5168 "%08x ",
5169 ((uint32_t)*pword) & 0xffffffff);
5170 pword++;
5171 }
5172 if ((i - 1) % 8)
5173 pr_err("%s\n", line_buf);
5174 pr_err("\n");
5175 }
5176 if (*mbx_dump_map & LPFC_MBX_DMP_MBX_BYTE) {
5177 pr_err("Mailbox command:0x%x dump by byte:\n",
5178 pmbox->mbxCommand);
5179 pbyte = (uint8_t *)pmbox;
5180 for (i = 0; i < *mbx_word_cnt; i++) {
5181 if (!(i % 8)) {
5182 if (i != 0)
5183 pr_err("%s\n", line_buf);
5184 len = 0;
5185 memset(line_buf, 0, LPFC_MBX_ACC_LBUF_SZ);
5186 len += snprintf(line_buf+len,
5187 LPFC_MBX_ACC_LBUF_SZ-len,
5188 "%03d: ", i);
5189 }
5190 for (j = 0; j < 4; j++) {
5191 len += snprintf(line_buf+len,
5192 LPFC_MBX_ACC_LBUF_SZ-len,
5193 "%02x",
5194 ((uint8_t)*pbyte) & 0xff);
5195 pbyte++;
5196 }
5197 len += snprintf(line_buf+len,
5198 LPFC_MBX_ACC_LBUF_SZ-len, " ");
5199 }
5200 if ((i - 1) % 8)
5201 pr_err("%s\n", line_buf);
5202 pr_err("\n");
5203 }
5204 (*mbx_dump_cnt)--;
5205
5206
5207 if (*mbx_dump_cnt == 0)
5208 memset(&idiag, 0, sizeof(idiag));
5209 return;
5210#endif
5211}
5212
5213
5214
5215
5216
5217
5218
5219
5220
5221
5222
5223inline void
5224lpfc_debugfs_initialize(struct lpfc_vport *vport)
5225{
5226#ifdef CONFIG_SCSI_LPFC_DEBUG_FS
5227 struct lpfc_hba *phba = vport->phba;
5228 char name[64];
5229 uint32_t num, i;
5230 bool pport_setup = false;
5231
5232 if (!lpfc_debugfs_enable)
5233 return;
5234
5235
5236 if (!lpfc_debugfs_root) {
5237 lpfc_debugfs_root = debugfs_create_dir("lpfc", NULL);
5238 atomic_set(&lpfc_debugfs_hba_count, 0);
5239 if (!lpfc_debugfs_root) {
5240 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5241 "0408 Cannot create debugfs root\n");
5242 goto debug_failed;
5243 }
5244 }
5245 if (!lpfc_debugfs_start_time)
5246 lpfc_debugfs_start_time = jiffies;
5247
5248
5249 snprintf(name, sizeof(name), "fn%d", phba->brd_no);
5250 if (!phba->hba_debugfs_root) {
5251 pport_setup = true;
5252 phba->hba_debugfs_root =
5253 debugfs_create_dir(name, lpfc_debugfs_root);
5254 if (!phba->hba_debugfs_root) {
5255 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5256 "0412 Cannot create debugfs hba\n");
5257 goto debug_failed;
5258 }
5259 atomic_inc(&lpfc_debugfs_hba_count);
5260 atomic_set(&phba->debugfs_vport_count, 0);
5261
5262
5263 snprintf(name, sizeof(name), "hbqinfo");
5264 phba->debug_hbqinfo =
5265 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5266 phba->hba_debugfs_root,
5267 phba, &lpfc_debugfs_op_hbqinfo);
5268 if (!phba->debug_hbqinfo) {
5269 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5270 "0411 Cannot create debugfs hbqinfo\n");
5271 goto debug_failed;
5272 }
5273
5274
5275 if (phba->sli_rev < LPFC_SLI_REV4) {
5276 snprintf(name, sizeof(name), "dumpHBASlim");
5277 phba->debug_dumpHBASlim =
5278 debugfs_create_file(name,
5279 S_IFREG|S_IRUGO|S_IWUSR,
5280 phba->hba_debugfs_root,
5281 phba, &lpfc_debugfs_op_dumpHBASlim);
5282 if (!phba->debug_dumpHBASlim) {
5283 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5284 "0413 Cannot create debugfs "
5285 "dumpHBASlim\n");
5286 goto debug_failed;
5287 }
5288 } else
5289 phba->debug_dumpHBASlim = NULL;
5290
5291
5292 if (phba->sli_rev < LPFC_SLI_REV4) {
5293 snprintf(name, sizeof(name), "dumpHostSlim");
5294 phba->debug_dumpHostSlim =
5295 debugfs_create_file(name,
5296 S_IFREG|S_IRUGO|S_IWUSR,
5297 phba->hba_debugfs_root,
5298 phba, &lpfc_debugfs_op_dumpHostSlim);
5299 if (!phba->debug_dumpHostSlim) {
5300 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5301 "0414 Cannot create debugfs "
5302 "dumpHostSlim\n");
5303 goto debug_failed;
5304 }
5305 } else
5306 phba->debug_dumpHostSlim = NULL;
5307
5308
5309 snprintf(name, sizeof(name), "dumpData");
5310 phba->debug_dumpData =
5311 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5312 phba->hba_debugfs_root,
5313 phba, &lpfc_debugfs_op_dumpData);
5314 if (!phba->debug_dumpData) {
5315 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5316 "0800 Cannot create debugfs dumpData\n");
5317 goto debug_failed;
5318 }
5319
5320
5321 snprintf(name, sizeof(name), "dumpDif");
5322 phba->debug_dumpDif =
5323 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5324 phba->hba_debugfs_root,
5325 phba, &lpfc_debugfs_op_dumpDif);
5326 if (!phba->debug_dumpDif) {
5327 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5328 "0801 Cannot create debugfs dumpDif\n");
5329 goto debug_failed;
5330 }
5331
5332
5333 snprintf(name, sizeof(name), "InjErrLBA");
5334 phba->debug_InjErrLBA =
5335 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5336 phba->hba_debugfs_root,
5337 phba, &lpfc_debugfs_op_dif_err);
5338 if (!phba->debug_InjErrLBA) {
5339 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5340 "0807 Cannot create debugfs InjErrLBA\n");
5341 goto debug_failed;
5342 }
5343 phba->lpfc_injerr_lba = LPFC_INJERR_LBA_OFF;
5344
5345 snprintf(name, sizeof(name), "InjErrNPortID");
5346 phba->debug_InjErrNPortID =
5347 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5348 phba->hba_debugfs_root,
5349 phba, &lpfc_debugfs_op_dif_err);
5350 if (!phba->debug_InjErrNPortID) {
5351 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5352 "0809 Cannot create debugfs InjErrNPortID\n");
5353 goto debug_failed;
5354 }
5355
5356 snprintf(name, sizeof(name), "InjErrWWPN");
5357 phba->debug_InjErrWWPN =
5358 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5359 phba->hba_debugfs_root,
5360 phba, &lpfc_debugfs_op_dif_err);
5361 if (!phba->debug_InjErrWWPN) {
5362 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5363 "0810 Cannot create debugfs InjErrWWPN\n");
5364 goto debug_failed;
5365 }
5366
5367 snprintf(name, sizeof(name), "writeGuardInjErr");
5368 phba->debug_writeGuard =
5369 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5370 phba->hba_debugfs_root,
5371 phba, &lpfc_debugfs_op_dif_err);
5372 if (!phba->debug_writeGuard) {
5373 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5374 "0802 Cannot create debugfs writeGuard\n");
5375 goto debug_failed;
5376 }
5377
5378 snprintf(name, sizeof(name), "writeAppInjErr");
5379 phba->debug_writeApp =
5380 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5381 phba->hba_debugfs_root,
5382 phba, &lpfc_debugfs_op_dif_err);
5383 if (!phba->debug_writeApp) {
5384 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5385 "0803 Cannot create debugfs writeApp\n");
5386 goto debug_failed;
5387 }
5388
5389 snprintf(name, sizeof(name), "writeRefInjErr");
5390 phba->debug_writeRef =
5391 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5392 phba->hba_debugfs_root,
5393 phba, &lpfc_debugfs_op_dif_err);
5394 if (!phba->debug_writeRef) {
5395 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5396 "0804 Cannot create debugfs writeRef\n");
5397 goto debug_failed;
5398 }
5399
5400 snprintf(name, sizeof(name), "readGuardInjErr");
5401 phba->debug_readGuard =
5402 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5403 phba->hba_debugfs_root,
5404 phba, &lpfc_debugfs_op_dif_err);
5405 if (!phba->debug_readGuard) {
5406 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5407 "0808 Cannot create debugfs readGuard\n");
5408 goto debug_failed;
5409 }
5410
5411 snprintf(name, sizeof(name), "readAppInjErr");
5412 phba->debug_readApp =
5413 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5414 phba->hba_debugfs_root,
5415 phba, &lpfc_debugfs_op_dif_err);
5416 if (!phba->debug_readApp) {
5417 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5418 "0805 Cannot create debugfs readApp\n");
5419 goto debug_failed;
5420 }
5421
5422 snprintf(name, sizeof(name), "readRefInjErr");
5423 phba->debug_readRef =
5424 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5425 phba->hba_debugfs_root,
5426 phba, &lpfc_debugfs_op_dif_err);
5427 if (!phba->debug_readRef) {
5428 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5429 "0806 Cannot create debugfs readApp\n");
5430 goto debug_failed;
5431 }
5432
5433
5434 if (lpfc_debugfs_max_slow_ring_trc) {
5435 num = lpfc_debugfs_max_slow_ring_trc - 1;
5436 if (num & lpfc_debugfs_max_slow_ring_trc) {
5437
5438 num = lpfc_debugfs_max_slow_ring_trc;
5439 i = 0;
5440 while (num > 1) {
5441 num = num >> 1;
5442 i++;
5443 }
5444 lpfc_debugfs_max_slow_ring_trc = (1 << i);
5445 pr_err("lpfc_debugfs_max_disc_trc changed to "
5446 "%d\n", lpfc_debugfs_max_disc_trc);
5447 }
5448 }
5449
5450 snprintf(name, sizeof(name), "slow_ring_trace");
5451 phba->debug_slow_ring_trc =
5452 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5453 phba->hba_debugfs_root,
5454 phba, &lpfc_debugfs_op_slow_ring_trc);
5455 if (!phba->debug_slow_ring_trc) {
5456 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5457 "0415 Cannot create debugfs "
5458 "slow_ring_trace\n");
5459 goto debug_failed;
5460 }
5461 if (!phba->slow_ring_trc) {
5462 phba->slow_ring_trc = kmalloc(
5463 (sizeof(struct lpfc_debugfs_trc) *
5464 lpfc_debugfs_max_slow_ring_trc),
5465 GFP_KERNEL);
5466 if (!phba->slow_ring_trc) {
5467 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5468 "0416 Cannot create debugfs "
5469 "slow_ring buffer\n");
5470 goto debug_failed;
5471 }
5472 atomic_set(&phba->slow_ring_trc_cnt, 0);
5473 memset(phba->slow_ring_trc, 0,
5474 (sizeof(struct lpfc_debugfs_trc) *
5475 lpfc_debugfs_max_slow_ring_trc));
5476 }
5477
5478 snprintf(name, sizeof(name), "nvmeio_trc");
5479 phba->debug_nvmeio_trc =
5480 debugfs_create_file(name, 0644,
5481 phba->hba_debugfs_root,
5482 phba, &lpfc_debugfs_op_nvmeio_trc);
5483 if (!phba->debug_nvmeio_trc) {
5484 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5485 "0574 No create debugfs nvmeio_trc\n");
5486 goto debug_failed;
5487 }
5488
5489 atomic_set(&phba->nvmeio_trc_cnt, 0);
5490 if (lpfc_debugfs_max_nvmeio_trc) {
5491 num = lpfc_debugfs_max_nvmeio_trc - 1;
5492 if (num & lpfc_debugfs_max_disc_trc) {
5493
5494 num = lpfc_debugfs_max_nvmeio_trc;
5495 i = 0;
5496 while (num > 1) {
5497 num = num >> 1;
5498 i++;
5499 }
5500 lpfc_debugfs_max_nvmeio_trc = (1 << i);
5501 lpfc_printf_log(phba, KERN_ERR, LOG_INIT,
5502 "0575 lpfc_debugfs_max_nvmeio_trc "
5503 "changed to %d\n",
5504 lpfc_debugfs_max_nvmeio_trc);
5505 }
5506 phba->nvmeio_trc_size = lpfc_debugfs_max_nvmeio_trc;
5507
5508
5509 phba->nvmeio_trc = kzalloc(
5510 (sizeof(struct lpfc_debugfs_nvmeio_trc) *
5511 phba->nvmeio_trc_size), GFP_KERNEL);
5512
5513 if (!phba->nvmeio_trc) {
5514 lpfc_printf_log(phba, KERN_ERR, LOG_INIT,
5515 "0576 Cannot create debugfs "
5516 "nvmeio_trc buffer\n");
5517 goto nvmeio_off;
5518 }
5519 phba->nvmeio_trc_on = 1;
5520 phba->nvmeio_trc_output_idx = 0;
5521 phba->nvmeio_trc = NULL;
5522 } else {
5523nvmeio_off:
5524 phba->nvmeio_trc_size = 0;
5525 phba->nvmeio_trc_on = 0;
5526 phba->nvmeio_trc_output_idx = 0;
5527 phba->nvmeio_trc = NULL;
5528 }
5529 }
5530
5531 snprintf(name, sizeof(name), "vport%d", vport->vpi);
5532 if (!vport->vport_debugfs_root) {
5533 vport->vport_debugfs_root =
5534 debugfs_create_dir(name, phba->hba_debugfs_root);
5535 if (!vport->vport_debugfs_root) {
5536 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5537 "0417 Can't create debugfs\n");
5538 goto debug_failed;
5539 }
5540 atomic_inc(&phba->debugfs_vport_count);
5541 }
5542
5543 if (lpfc_debugfs_max_disc_trc) {
5544 num = lpfc_debugfs_max_disc_trc - 1;
5545 if (num & lpfc_debugfs_max_disc_trc) {
5546
5547 num = lpfc_debugfs_max_disc_trc;
5548 i = 0;
5549 while (num > 1) {
5550 num = num >> 1;
5551 i++;
5552 }
5553 lpfc_debugfs_max_disc_trc = (1 << i);
5554 pr_err("lpfc_debugfs_max_disc_trc changed to %d\n",
5555 lpfc_debugfs_max_disc_trc);
5556 }
5557 }
5558
5559 vport->disc_trc = kzalloc(
5560 (sizeof(struct lpfc_debugfs_trc) * lpfc_debugfs_max_disc_trc),
5561 GFP_KERNEL);
5562
5563 if (!vport->disc_trc) {
5564 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5565 "0418 Cannot create debugfs disc trace "
5566 "buffer\n");
5567 goto debug_failed;
5568 }
5569 atomic_set(&vport->disc_trc_cnt, 0);
5570
5571 snprintf(name, sizeof(name), "discovery_trace");
5572 vport->debug_disc_trc =
5573 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5574 vport->vport_debugfs_root,
5575 vport, &lpfc_debugfs_op_disc_trc);
5576 if (!vport->debug_disc_trc) {
5577 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5578 "0419 Cannot create debugfs "
5579 "discovery_trace\n");
5580 goto debug_failed;
5581 }
5582 snprintf(name, sizeof(name), "nodelist");
5583 vport->debug_nodelist =
5584 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5585 vport->vport_debugfs_root,
5586 vport, &lpfc_debugfs_op_nodelist);
5587 if (!vport->debug_nodelist) {
5588 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5589 "2985 Can't create debugfs nodelist\n");
5590 goto debug_failed;
5591 }
5592
5593 snprintf(name, sizeof(name), "nvmestat");
5594 vport->debug_nvmestat =
5595 debugfs_create_file(name, 0644,
5596 vport->vport_debugfs_root,
5597 vport, &lpfc_debugfs_op_nvmestat);
5598 if (!vport->debug_nvmestat) {
5599 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5600 "0811 Cannot create debugfs nvmestat\n");
5601 goto debug_failed;
5602 }
5603
5604 snprintf(name, sizeof(name), "nvmektime");
5605 vport->debug_nvmektime =
5606 debugfs_create_file(name, 0644,
5607 vport->vport_debugfs_root,
5608 vport, &lpfc_debugfs_op_nvmektime);
5609 if (!vport->debug_nvmektime) {
5610 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5611 "0815 Cannot create debugfs nvmektime\n");
5612 goto debug_failed;
5613 }
5614
5615 snprintf(name, sizeof(name), "cpucheck");
5616 vport->debug_cpucheck =
5617 debugfs_create_file(name, 0644,
5618 vport->vport_debugfs_root,
5619 vport, &lpfc_debugfs_op_cpucheck);
5620 if (!vport->debug_cpucheck) {
5621 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5622 "0819 Cannot create debugfs cpucheck\n");
5623 goto debug_failed;
5624 }
5625
5626
5627
5628
5629
5630
5631 if (!pport_setup)
5632 goto debug_failed;
5633
5634
5635
5636
5637 if (phba->sli_rev < LPFC_SLI_REV4)
5638 goto debug_failed;
5639
5640 snprintf(name, sizeof(name), "iDiag");
5641 if (!phba->idiag_root) {
5642 phba->idiag_root =
5643 debugfs_create_dir(name, phba->hba_debugfs_root);
5644 if (!phba->idiag_root) {
5645 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5646 "2922 Can't create idiag debugfs\n");
5647 goto debug_failed;
5648 }
5649
5650 memset(&idiag, 0, sizeof(idiag));
5651 }
5652
5653
5654 snprintf(name, sizeof(name), "pciCfg");
5655 if (!phba->idiag_pci_cfg) {
5656 phba->idiag_pci_cfg =
5657 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5658 phba->idiag_root, phba, &lpfc_idiag_op_pciCfg);
5659 if (!phba->idiag_pci_cfg) {
5660 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5661 "2923 Can't create idiag debugfs\n");
5662 goto debug_failed;
5663 }
5664 idiag.offset.last_rd = 0;
5665 }
5666
5667
5668 snprintf(name, sizeof(name), "barAcc");
5669 if (!phba->idiag_bar_acc) {
5670 phba->idiag_bar_acc =
5671 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5672 phba->idiag_root, phba, &lpfc_idiag_op_barAcc);
5673 if (!phba->idiag_bar_acc) {
5674 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5675 "3056 Can't create idiag debugfs\n");
5676 goto debug_failed;
5677 }
5678 idiag.offset.last_rd = 0;
5679 }
5680
5681
5682 snprintf(name, sizeof(name), "queInfo");
5683 if (!phba->idiag_que_info) {
5684 phba->idiag_que_info =
5685 debugfs_create_file(name, S_IFREG|S_IRUGO,
5686 phba->idiag_root, phba, &lpfc_idiag_op_queInfo);
5687 if (!phba->idiag_que_info) {
5688 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5689 "2924 Can't create idiag debugfs\n");
5690 goto debug_failed;
5691 }
5692 }
5693
5694
5695 snprintf(name, sizeof(name), "queAcc");
5696 if (!phba->idiag_que_acc) {
5697 phba->idiag_que_acc =
5698 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5699 phba->idiag_root, phba, &lpfc_idiag_op_queAcc);
5700 if (!phba->idiag_que_acc) {
5701 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5702 "2926 Can't create idiag debugfs\n");
5703 goto debug_failed;
5704 }
5705 }
5706
5707
5708 snprintf(name, sizeof(name), "drbAcc");
5709 if (!phba->idiag_drb_acc) {
5710 phba->idiag_drb_acc =
5711 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5712 phba->idiag_root, phba, &lpfc_idiag_op_drbAcc);
5713 if (!phba->idiag_drb_acc) {
5714 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5715 "2927 Can't create idiag debugfs\n");
5716 goto debug_failed;
5717 }
5718 }
5719
5720
5721 snprintf(name, sizeof(name), "ctlAcc");
5722 if (!phba->idiag_ctl_acc) {
5723 phba->idiag_ctl_acc =
5724 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5725 phba->idiag_root, phba, &lpfc_idiag_op_ctlAcc);
5726 if (!phba->idiag_ctl_acc) {
5727 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5728 "2981 Can't create idiag debugfs\n");
5729 goto debug_failed;
5730 }
5731 }
5732
5733
5734 snprintf(name, sizeof(name), "mbxAcc");
5735 if (!phba->idiag_mbx_acc) {
5736 phba->idiag_mbx_acc =
5737 debugfs_create_file(name, S_IFREG|S_IRUGO|S_IWUSR,
5738 phba->idiag_root, phba, &lpfc_idiag_op_mbxAcc);
5739 if (!phba->idiag_mbx_acc) {
5740 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5741 "2980 Can't create idiag debugfs\n");
5742 goto debug_failed;
5743 }
5744 }
5745
5746
5747 if (phba->sli4_hba.extents_in_use) {
5748 snprintf(name, sizeof(name), "extAcc");
5749 if (!phba->idiag_ext_acc) {
5750 phba->idiag_ext_acc =
5751 debugfs_create_file(name,
5752 S_IFREG|S_IRUGO|S_IWUSR,
5753 phba->idiag_root, phba,
5754 &lpfc_idiag_op_extAcc);
5755 if (!phba->idiag_ext_acc) {
5756 lpfc_printf_vlog(vport, KERN_ERR, LOG_INIT,
5757 "2986 Cant create "
5758 "idiag debugfs\n");
5759 goto debug_failed;
5760 }
5761 }
5762 }
5763
5764debug_failed:
5765 return;
5766#endif
5767}
5768
5769
5770
5771
5772
5773
5774
5775
5776
5777
5778
5779
5780inline void
5781lpfc_debugfs_terminate(struct lpfc_vport *vport)
5782{
5783#ifdef CONFIG_SCSI_LPFC_DEBUG_FS
5784 struct lpfc_hba *phba = vport->phba;
5785
5786 kfree(vport->disc_trc);
5787 vport->disc_trc = NULL;
5788
5789 debugfs_remove(vport->debug_disc_trc);
5790 vport->debug_disc_trc = NULL;
5791
5792 debugfs_remove(vport->debug_nodelist);
5793 vport->debug_nodelist = NULL;
5794
5795 debugfs_remove(vport->debug_nvmestat);
5796 vport->debug_nvmestat = NULL;
5797
5798 debugfs_remove(vport->debug_nvmektime);
5799 vport->debug_nvmektime = NULL;
5800
5801 debugfs_remove(vport->debug_cpucheck);
5802 vport->debug_cpucheck = NULL;
5803
5804 if (vport->vport_debugfs_root) {
5805 debugfs_remove(vport->vport_debugfs_root);
5806 vport->vport_debugfs_root = NULL;
5807 atomic_dec(&phba->debugfs_vport_count);
5808 }
5809
5810 if (atomic_read(&phba->debugfs_vport_count) == 0) {
5811
5812 debugfs_remove(phba->debug_hbqinfo);
5813 phba->debug_hbqinfo = NULL;
5814
5815 debugfs_remove(phba->debug_dumpHBASlim);
5816 phba->debug_dumpHBASlim = NULL;
5817
5818 debugfs_remove(phba->debug_dumpHostSlim);
5819 phba->debug_dumpHostSlim = NULL;
5820
5821 debugfs_remove(phba->debug_dumpData);
5822 phba->debug_dumpData = NULL;
5823
5824 debugfs_remove(phba->debug_dumpDif);
5825 phba->debug_dumpDif = NULL;
5826
5827 debugfs_remove(phba->debug_InjErrLBA);
5828 phba->debug_InjErrLBA = NULL;
5829
5830 debugfs_remove(phba->debug_InjErrNPortID);
5831 phba->debug_InjErrNPortID = NULL;
5832
5833 debugfs_remove(phba->debug_InjErrWWPN);
5834 phba->debug_InjErrWWPN = NULL;
5835
5836 debugfs_remove(phba->debug_writeGuard);
5837 phba->debug_writeGuard = NULL;
5838
5839 debugfs_remove(phba->debug_writeApp);
5840 phba->debug_writeApp = NULL;
5841
5842 debugfs_remove(phba->debug_writeRef);
5843 phba->debug_writeRef = NULL;
5844
5845 debugfs_remove(phba->debug_readGuard);
5846 phba->debug_readGuard = NULL;
5847
5848 debugfs_remove(phba->debug_readApp);
5849 phba->debug_readApp = NULL;
5850
5851 debugfs_remove(phba->debug_readRef);
5852 phba->debug_readRef = NULL;
5853
5854 kfree(phba->slow_ring_trc);
5855 phba->slow_ring_trc = NULL;
5856
5857
5858 debugfs_remove(phba->debug_slow_ring_trc);
5859 phba->debug_slow_ring_trc = NULL;
5860
5861 debugfs_remove(phba->debug_nvmeio_trc);
5862 phba->debug_nvmeio_trc = NULL;
5863
5864 kfree(phba->nvmeio_trc);
5865 phba->nvmeio_trc = NULL;
5866
5867
5868
5869
5870 if (phba->sli_rev == LPFC_SLI_REV4) {
5871
5872 debugfs_remove(phba->idiag_ext_acc);
5873 phba->idiag_ext_acc = NULL;
5874
5875
5876 debugfs_remove(phba->idiag_mbx_acc);
5877 phba->idiag_mbx_acc = NULL;
5878
5879
5880 debugfs_remove(phba->idiag_ctl_acc);
5881 phba->idiag_ctl_acc = NULL;
5882
5883
5884 debugfs_remove(phba->idiag_drb_acc);
5885 phba->idiag_drb_acc = NULL;
5886
5887
5888 debugfs_remove(phba->idiag_que_acc);
5889 phba->idiag_que_acc = NULL;
5890
5891
5892 debugfs_remove(phba->idiag_que_info);
5893 phba->idiag_que_info = NULL;
5894
5895
5896 debugfs_remove(phba->idiag_bar_acc);
5897 phba->idiag_bar_acc = NULL;
5898
5899
5900 debugfs_remove(phba->idiag_pci_cfg);
5901 phba->idiag_pci_cfg = NULL;
5902
5903
5904 debugfs_remove(phba->idiag_root);
5905 phba->idiag_root = NULL;
5906 }
5907
5908 if (phba->hba_debugfs_root) {
5909 debugfs_remove(phba->hba_debugfs_root);
5910 phba->hba_debugfs_root = NULL;
5911 atomic_dec(&lpfc_debugfs_hba_count);
5912 }
5913
5914 if (atomic_read(&lpfc_debugfs_hba_count) == 0) {
5915 debugfs_remove(lpfc_debugfs_root);
5916 lpfc_debugfs_root = NULL;
5917 }
5918 }
5919#endif
5920 return;
5921}
5922
5923
5924
5925
5926
5927
5928
5929
5930
5931
5932
5933
5934
5935void
5936lpfc_debug_dump_all_queues(struct lpfc_hba *phba)
5937{
5938 int idx;
5939
5940
5941
5942
5943 lpfc_debug_dump_wq(phba, DUMP_MBX, 0);
5944 lpfc_debug_dump_wq(phba, DUMP_ELS, 0);
5945 lpfc_debug_dump_wq(phba, DUMP_NVMELS, 0);
5946
5947 for (idx = 0; idx < phba->cfg_fcp_io_channel; idx++)
5948 lpfc_debug_dump_wq(phba, DUMP_FCP, idx);
5949
5950 for (idx = 0; idx < phba->cfg_nvme_io_channel; idx++)
5951 lpfc_debug_dump_wq(phba, DUMP_NVME, idx);
5952
5953 lpfc_debug_dump_hdr_rq(phba);
5954 lpfc_debug_dump_dat_rq(phba);
5955
5956
5957
5958 lpfc_debug_dump_cq(phba, DUMP_MBX, 0);
5959 lpfc_debug_dump_cq(phba, DUMP_ELS, 0);
5960 lpfc_debug_dump_cq(phba, DUMP_NVMELS, 0);
5961
5962 for (idx = 0; idx < phba->cfg_fcp_io_channel; idx++)
5963 lpfc_debug_dump_cq(phba, DUMP_FCP, idx);
5964
5965 for (idx = 0; idx < phba->cfg_nvme_io_channel; idx++)
5966 lpfc_debug_dump_cq(phba, DUMP_NVME, idx);
5967
5968
5969
5970
5971 for (idx = 0; idx < phba->io_channel_irqs; idx++)
5972 lpfc_debug_dump_hba_eq(phba, idx);
5973}
5974