diff options
-rw-r--r-- | drivers/infiniband/hw/mthca/mthca_cmd.c | 32 | ||||
-rw-r--r-- | drivers/infiniband/hw/mthca/mthca_cmd.h | 9 | ||||
-rw-r--r-- | drivers/infiniband/hw/mthca/mthca_dev.h | 5 | ||||
-rw-r--r-- | drivers/infiniband/hw/mthca/mthca_main.c | 122 | ||||
-rw-r--r-- | drivers/infiniband/hw/mthca/mthca_provider.c | 10 |
5 files changed, 109 insertions, 69 deletions
diff --git a/drivers/infiniband/hw/mthca/mthca_cmd.c b/drivers/infiniband/hw/mthca/mthca_cmd.c index 1e60487ecd7f..e15c1e2deab4 100644 --- a/drivers/infiniband/hw/mthca/mthca_cmd.c +++ b/drivers/infiniband/hw/mthca/mthca_cmd.c | |||
@@ -1085,6 +1085,34 @@ out: | |||
1085 | return err; | 1085 | return err; |
1086 | } | 1086 | } |
1087 | 1087 | ||
1088 | static void get_board_id(void *vsd, char *board_id) | ||
1089 | { | ||
1090 | int i; | ||
1091 | |||
1092 | #define VSD_OFFSET_SIG1 0x00 | ||
1093 | #define VSD_OFFSET_SIG2 0xde | ||
1094 | #define VSD_OFFSET_MLX_BOARD_ID 0xd0 | ||
1095 | #define VSD_OFFSET_TS_BOARD_ID 0x20 | ||
1096 | |||
1097 | #define VSD_SIGNATURE_TOPSPIN 0x5ad | ||
1098 | |||
1099 | memset(board_id, 0, MTHCA_BOARD_ID_LEN); | ||
1100 | |||
1101 | if (be16_to_cpup(vsd + VSD_OFFSET_SIG1) == VSD_SIGNATURE_TOPSPIN && | ||
1102 | be16_to_cpup(vsd + VSD_OFFSET_SIG2) == VSD_SIGNATURE_TOPSPIN) { | ||
1103 | strlcpy(board_id, vsd + VSD_OFFSET_TS_BOARD_ID, MTHCA_BOARD_ID_LEN); | ||
1104 | } else { | ||
1105 | /* | ||
1106 | * The board ID is a string but the firmware byte | ||
1107 | * swaps each 4-byte word before passing it back to | ||
1108 | * us. Therefore we need to swab it before printing. | ||
1109 | */ | ||
1110 | for (i = 0; i < 4; ++i) | ||
1111 | ((u32 *) board_id)[i] = | ||
1112 | swab32(*(u32 *) (vsd + VSD_OFFSET_MLX_BOARD_ID + i * 4)); | ||
1113 | } | ||
1114 | } | ||
1115 | |||
1088 | int mthca_QUERY_ADAPTER(struct mthca_dev *dev, | 1116 | int mthca_QUERY_ADAPTER(struct mthca_dev *dev, |
1089 | struct mthca_adapter *adapter, u8 *status) | 1117 | struct mthca_adapter *adapter, u8 *status) |
1090 | { | 1118 | { |
@@ -1097,6 +1125,7 @@ int mthca_QUERY_ADAPTER(struct mthca_dev *dev, | |||
1097 | #define QUERY_ADAPTER_DEVICE_ID_OFFSET 0x04 | 1125 | #define QUERY_ADAPTER_DEVICE_ID_OFFSET 0x04 |
1098 | #define QUERY_ADAPTER_REVISION_ID_OFFSET 0x08 | 1126 | #define QUERY_ADAPTER_REVISION_ID_OFFSET 0x08 |
1099 | #define QUERY_ADAPTER_INTA_PIN_OFFSET 0x10 | 1127 | #define QUERY_ADAPTER_INTA_PIN_OFFSET 0x10 |
1128 | #define QUERY_ADAPTER_VSD_OFFSET 0x20 | ||
1100 | 1129 | ||
1101 | mailbox = mthca_alloc_mailbox(dev, GFP_KERNEL); | 1130 | mailbox = mthca_alloc_mailbox(dev, GFP_KERNEL); |
1102 | if (IS_ERR(mailbox)) | 1131 | if (IS_ERR(mailbox)) |
@@ -1114,6 +1143,9 @@ int mthca_QUERY_ADAPTER(struct mthca_dev *dev, | |||
1114 | MTHCA_GET(adapter->revision_id, outbox, QUERY_ADAPTER_REVISION_ID_OFFSET); | 1143 | MTHCA_GET(adapter->revision_id, outbox, QUERY_ADAPTER_REVISION_ID_OFFSET); |
1115 | MTHCA_GET(adapter->inta_pin, outbox, QUERY_ADAPTER_INTA_PIN_OFFSET); | 1144 | MTHCA_GET(adapter->inta_pin, outbox, QUERY_ADAPTER_INTA_PIN_OFFSET); |
1116 | 1145 | ||
1146 | get_board_id(outbox + QUERY_ADAPTER_VSD_OFFSET / 4, | ||
1147 | adapter->board_id); | ||
1148 | |||
1117 | out: | 1149 | out: |
1118 | mthca_free_mailbox(dev, mailbox); | 1150 | mthca_free_mailbox(dev, mailbox); |
1119 | return err; | 1151 | return err; |
diff --git a/drivers/infiniband/hw/mthca/mthca_cmd.h b/drivers/infiniband/hw/mthca/mthca_cmd.h index 75a629639445..4e0062778ff9 100644 --- a/drivers/infiniband/hw/mthca/mthca_cmd.h +++ b/drivers/infiniband/hw/mthca/mthca_cmd.h | |||
@@ -184,10 +184,11 @@ struct mthca_dev_lim { | |||
184 | }; | 184 | }; |
185 | 185 | ||
186 | struct mthca_adapter { | 186 | struct mthca_adapter { |
187 | u32 vendor_id; | 187 | u32 vendor_id; |
188 | u32 device_id; | 188 | u32 device_id; |
189 | u32 revision_id; | 189 | u32 revision_id; |
190 | u8 inta_pin; | 190 | char board_id[MTHCA_BOARD_ID_LEN]; |
191 | u8 inta_pin; | ||
191 | }; | 192 | }; |
192 | 193 | ||
193 | struct mthca_init_hca_param { | 194 | struct mthca_init_hca_param { |
diff --git a/drivers/infiniband/hw/mthca/mthca_dev.h b/drivers/infiniband/hw/mthca/mthca_dev.h index 3519ca4e086c..c8f67c034183 100644 --- a/drivers/infiniband/hw/mthca/mthca_dev.h +++ b/drivers/infiniband/hw/mthca/mthca_dev.h | |||
@@ -69,6 +69,10 @@ enum { | |||
69 | }; | 69 | }; |
70 | 70 | ||
71 | enum { | 71 | enum { |
72 | MTHCA_BOARD_ID_LEN = 64 | ||
73 | }; | ||
74 | |||
75 | enum { | ||
72 | MTHCA_EQ_CONTEXT_SIZE = 0x40, | 76 | MTHCA_EQ_CONTEXT_SIZE = 0x40, |
73 | MTHCA_CQ_CONTEXT_SIZE = 0x40, | 77 | MTHCA_CQ_CONTEXT_SIZE = 0x40, |
74 | MTHCA_QP_CONTEXT_SIZE = 0x200, | 78 | MTHCA_QP_CONTEXT_SIZE = 0x200, |
@@ -248,6 +252,7 @@ struct mthca_dev { | |||
248 | unsigned long device_cap_flags; | 252 | unsigned long device_cap_flags; |
249 | 253 | ||
250 | u32 rev_id; | 254 | u32 rev_id; |
255 | char board_id[MTHCA_BOARD_ID_LEN]; | ||
251 | 256 | ||
252 | /* firmware info */ | 257 | /* firmware info */ |
253 | u64 fw_ver; | 258 | u64 fw_ver; |
diff --git a/drivers/infiniband/hw/mthca/mthca_main.c b/drivers/infiniband/hw/mthca/mthca_main.c index 2d539403bdac..2f039680239c 100644 --- a/drivers/infiniband/hw/mthca/mthca_main.c +++ b/drivers/infiniband/hw/mthca/mthca_main.c | |||
@@ -213,7 +213,6 @@ static int __devinit mthca_init_tavor(struct mthca_dev *mdev) | |||
213 | struct mthca_dev_lim dev_lim; | 213 | struct mthca_dev_lim dev_lim; |
214 | struct mthca_profile profile; | 214 | struct mthca_profile profile; |
215 | struct mthca_init_hca_param init_hca; | 215 | struct mthca_init_hca_param init_hca; |
216 | struct mthca_adapter adapter; | ||
217 | 216 | ||
218 | err = mthca_SYS_EN(mdev, &status); | 217 | err = mthca_SYS_EN(mdev, &status); |
219 | if (err) { | 218 | if (err) { |
@@ -271,26 +270,8 @@ static int __devinit mthca_init_tavor(struct mthca_dev *mdev) | |||
271 | goto err_disable; | 270 | goto err_disable; |
272 | } | 271 | } |
273 | 272 | ||
274 | err = mthca_QUERY_ADAPTER(mdev, &adapter, &status); | ||
275 | if (err) { | ||
276 | mthca_err(mdev, "QUERY_ADAPTER command failed, aborting.\n"); | ||
277 | goto err_close; | ||
278 | } | ||
279 | if (status) { | ||
280 | mthca_err(mdev, "QUERY_ADAPTER returned status 0x%02x, " | ||
281 | "aborting.\n", status); | ||
282 | err = -EINVAL; | ||
283 | goto err_close; | ||
284 | } | ||
285 | |||
286 | mdev->eq_table.inta_pin = adapter.inta_pin; | ||
287 | mdev->rev_id = adapter.revision_id; | ||
288 | |||
289 | return 0; | 273 | return 0; |
290 | 274 | ||
291 | err_close: | ||
292 | mthca_CLOSE_HCA(mdev, 0, &status); | ||
293 | |||
294 | err_disable: | 275 | err_disable: |
295 | mthca_SYS_DIS(mdev, &status); | 276 | mthca_SYS_DIS(mdev, &status); |
296 | 277 | ||
@@ -507,7 +488,6 @@ static int __devinit mthca_init_arbel(struct mthca_dev *mdev) | |||
507 | struct mthca_dev_lim dev_lim; | 488 | struct mthca_dev_lim dev_lim; |
508 | struct mthca_profile profile; | 489 | struct mthca_profile profile; |
509 | struct mthca_init_hca_param init_hca; | 490 | struct mthca_init_hca_param init_hca; |
510 | struct mthca_adapter adapter; | ||
511 | u64 icm_size; | 491 | u64 icm_size; |
512 | u8 status; | 492 | u8 status; |
513 | int err; | 493 | int err; |
@@ -575,21 +555,6 @@ static int __devinit mthca_init_arbel(struct mthca_dev *mdev) | |||
575 | goto err_free_icm; | 555 | goto err_free_icm; |
576 | } | 556 | } |
577 | 557 | ||
578 | err = mthca_QUERY_ADAPTER(mdev, &adapter, &status); | ||
579 | if (err) { | ||
580 | mthca_err(mdev, "QUERY_ADAPTER command failed, aborting.\n"); | ||
581 | goto err_free_icm; | ||
582 | } | ||
583 | if (status) { | ||
584 | mthca_err(mdev, "QUERY_ADAPTER returned status 0x%02x, " | ||
585 | "aborting.\n", status); | ||
586 | err = -EINVAL; | ||
587 | goto err_free_icm; | ||
588 | } | ||
589 | |||
590 | mdev->eq_table.inta_pin = adapter.inta_pin; | ||
591 | mdev->rev_id = adapter.revision_id; | ||
592 | |||
593 | return 0; | 558 | return 0; |
594 | 559 | ||
595 | err_free_icm: | 560 | err_free_icm: |
@@ -615,12 +580,68 @@ err_disable: | |||
615 | return err; | 580 | return err; |
616 | } | 581 | } |
617 | 582 | ||
583 | static void mthca_close_hca(struct mthca_dev *mdev) | ||
584 | { | ||
585 | u8 status; | ||
586 | |||
587 | mthca_CLOSE_HCA(mdev, 0, &status); | ||
588 | |||
589 | if (mthca_is_memfree(mdev)) { | ||
590 | mthca_free_icm_table(mdev, mdev->cq_table.table); | ||
591 | mthca_free_icm_table(mdev, mdev->qp_table.rdb_table); | ||
592 | mthca_free_icm_table(mdev, mdev->qp_table.eqp_table); | ||
593 | mthca_free_icm_table(mdev, mdev->qp_table.qp_table); | ||
594 | mthca_free_icm_table(mdev, mdev->mr_table.mpt_table); | ||
595 | mthca_free_icm_table(mdev, mdev->mr_table.mtt_table); | ||
596 | mthca_unmap_eq_icm(mdev); | ||
597 | |||
598 | mthca_UNMAP_ICM_AUX(mdev, &status); | ||
599 | mthca_free_icm(mdev, mdev->fw.arbel.aux_icm); | ||
600 | |||
601 | mthca_UNMAP_FA(mdev, &status); | ||
602 | mthca_free_icm(mdev, mdev->fw.arbel.fw_icm); | ||
603 | |||
604 | if (!(mdev->mthca_flags & MTHCA_FLAG_NO_LAM)) | ||
605 | mthca_DISABLE_LAM(mdev, &status); | ||
606 | } else | ||
607 | mthca_SYS_DIS(mdev, &status); | ||
608 | } | ||
609 | |||
618 | static int __devinit mthca_init_hca(struct mthca_dev *mdev) | 610 | static int __devinit mthca_init_hca(struct mthca_dev *mdev) |
619 | { | 611 | { |
612 | u8 status; | ||
613 | int err; | ||
614 | struct mthca_adapter adapter; | ||
615 | |||
620 | if (mthca_is_memfree(mdev)) | 616 | if (mthca_is_memfree(mdev)) |
621 | return mthca_init_arbel(mdev); | 617 | err = mthca_init_arbel(mdev); |
622 | else | 618 | else |
623 | return mthca_init_tavor(mdev); | 619 | err = mthca_init_tavor(mdev); |
620 | |||
621 | if (err) | ||
622 | return err; | ||
623 | |||
624 | err = mthca_QUERY_ADAPTER(mdev, &adapter, &status); | ||
625 | if (err) { | ||
626 | mthca_err(mdev, "QUERY_ADAPTER command failed, aborting.\n"); | ||
627 | goto err_close; | ||
628 | } | ||
629 | if (status) { | ||
630 | mthca_err(mdev, "QUERY_ADAPTER returned status 0x%02x, " | ||
631 | "aborting.\n", status); | ||
632 | err = -EINVAL; | ||
633 | goto err_close; | ||
634 | } | ||
635 | |||
636 | mdev->eq_table.inta_pin = adapter.inta_pin; | ||
637 | mdev->rev_id = adapter.revision_id; | ||
638 | memcpy(mdev->board_id, adapter.board_id, sizeof mdev->board_id); | ||
639 | |||
640 | return 0; | ||
641 | |||
642 | err_close: | ||
643 | mthca_close_hca(mdev); | ||
644 | return err; | ||
624 | } | 645 | } |
625 | 646 | ||
626 | static int __devinit mthca_setup_hca(struct mthca_dev *dev) | 647 | static int __devinit mthca_setup_hca(struct mthca_dev *dev) |
@@ -845,33 +866,6 @@ static int __devinit mthca_enable_msi_x(struct mthca_dev *mdev) | |||
845 | return 0; | 866 | return 0; |
846 | } | 867 | } |
847 | 868 | ||
848 | static void mthca_close_hca(struct mthca_dev *mdev) | ||
849 | { | ||
850 | u8 status; | ||
851 | |||
852 | mthca_CLOSE_HCA(mdev, 0, &status); | ||
853 | |||
854 | if (mthca_is_memfree(mdev)) { | ||
855 | mthca_free_icm_table(mdev, mdev->cq_table.table); | ||
856 | mthca_free_icm_table(mdev, mdev->qp_table.rdb_table); | ||
857 | mthca_free_icm_table(mdev, mdev->qp_table.eqp_table); | ||
858 | mthca_free_icm_table(mdev, mdev->qp_table.qp_table); | ||
859 | mthca_free_icm_table(mdev, mdev->mr_table.mpt_table); | ||
860 | mthca_free_icm_table(mdev, mdev->mr_table.mtt_table); | ||
861 | mthca_unmap_eq_icm(mdev); | ||
862 | |||
863 | mthca_UNMAP_ICM_AUX(mdev, &status); | ||
864 | mthca_free_icm(mdev, mdev->fw.arbel.aux_icm); | ||
865 | |||
866 | mthca_UNMAP_FA(mdev, &status); | ||
867 | mthca_free_icm(mdev, mdev->fw.arbel.fw_icm); | ||
868 | |||
869 | if (!(mdev->mthca_flags & MTHCA_FLAG_NO_LAM)) | ||
870 | mthca_DISABLE_LAM(mdev, &status); | ||
871 | } else | ||
872 | mthca_SYS_DIS(mdev, &status); | ||
873 | } | ||
874 | |||
875 | /* Types of supported HCA */ | 869 | /* Types of supported HCA */ |
876 | enum { | 870 | enum { |
877 | TAVOR, /* MT23108 */ | 871 | TAVOR, /* MT23108 */ |
diff --git a/drivers/infiniband/hw/mthca/mthca_provider.c b/drivers/infiniband/hw/mthca/mthca_provider.c index e2db5e001869..f5e135f1dc59 100644 --- a/drivers/infiniband/hw/mthca/mthca_provider.c +++ b/drivers/infiniband/hw/mthca/mthca_provider.c | |||
@@ -958,14 +958,22 @@ static ssize_t show_hca(struct class_device *cdev, char *buf) | |||
958 | } | 958 | } |
959 | } | 959 | } |
960 | 960 | ||
961 | static ssize_t show_board(struct class_device *cdev, char *buf) | ||
962 | { | ||
963 | struct mthca_dev *dev = container_of(cdev, struct mthca_dev, ib_dev.class_dev); | ||
964 | return sprintf(buf, "%.*s\n", MTHCA_BOARD_ID_LEN, dev->board_id); | ||
965 | } | ||
966 | |||
961 | static CLASS_DEVICE_ATTR(hw_rev, S_IRUGO, show_rev, NULL); | 967 | static CLASS_DEVICE_ATTR(hw_rev, S_IRUGO, show_rev, NULL); |
962 | static CLASS_DEVICE_ATTR(fw_ver, S_IRUGO, show_fw_ver, NULL); | 968 | static CLASS_DEVICE_ATTR(fw_ver, S_IRUGO, show_fw_ver, NULL); |
963 | static CLASS_DEVICE_ATTR(hca_type, S_IRUGO, show_hca, NULL); | 969 | static CLASS_DEVICE_ATTR(hca_type, S_IRUGO, show_hca, NULL); |
970 | static CLASS_DEVICE_ATTR(board_id, S_IRUGO, show_board, NULL); | ||
964 | 971 | ||
965 | static struct class_device_attribute *mthca_class_attributes[] = { | 972 | static struct class_device_attribute *mthca_class_attributes[] = { |
966 | &class_device_attr_hw_rev, | 973 | &class_device_attr_hw_rev, |
967 | &class_device_attr_fw_ver, | 974 | &class_device_attr_fw_ver, |
968 | &class_device_attr_hca_type | 975 | &class_device_attr_hca_type, |
976 | &class_device_attr_board_id | ||
969 | }; | 977 | }; |
970 | 978 | ||
971 | int mthca_register_device(struct mthca_dev *dev) | 979 | int mthca_register_device(struct mthca_dev *dev) |