diff options
Diffstat (limited to 'drivers/infiniband/hw/mthca/mthca_cmd.c')
-rw-r--r-- | drivers/infiniband/hw/mthca/mthca_cmd.c | 106 |
1 files changed, 81 insertions, 25 deletions
diff --git a/drivers/infiniband/hw/mthca/mthca_cmd.c b/drivers/infiniband/hw/mthca/mthca_cmd.c index 1557a522d831..cc758a2d2bc6 100644 --- a/drivers/infiniband/hw/mthca/mthca_cmd.c +++ b/drivers/infiniband/hw/mthca/mthca_cmd.c | |||
@@ -1,5 +1,6 @@ | |||
1 | /* | 1 | /* |
2 | * Copyright (c) 2004, 2005 Topspin Communications. All rights reserved. | 2 | * Copyright (c) 2004, 2005 Topspin Communications. All rights reserved. |
3 | * Copyright (c) 2005 Mellanox Technologies. All rights reserved. | ||
3 | * | 4 | * |
4 | * This software is available to you under a choice of one of two | 5 | * This software is available to you under a choice of one of two |
5 | * licenses. You may choose to be licensed under the terms of the GNU | 6 | * licenses. You may choose to be licensed under the terms of the GNU |
@@ -36,7 +37,7 @@ | |||
36 | #include <linux/pci.h> | 37 | #include <linux/pci.h> |
37 | #include <linux/errno.h> | 38 | #include <linux/errno.h> |
38 | #include <asm/io.h> | 39 | #include <asm/io.h> |
39 | #include <ib_mad.h> | 40 | #include <rdma/ib_mad.h> |
40 | 41 | ||
41 | #include "mthca_dev.h" | 42 | #include "mthca_dev.h" |
42 | #include "mthca_config_reg.h" | 43 | #include "mthca_config_reg.h" |
@@ -108,6 +109,7 @@ enum { | |||
108 | CMD_SW2HW_SRQ = 0x35, | 109 | CMD_SW2HW_SRQ = 0x35, |
109 | CMD_HW2SW_SRQ = 0x36, | 110 | CMD_HW2SW_SRQ = 0x36, |
110 | CMD_QUERY_SRQ = 0x37, | 111 | CMD_QUERY_SRQ = 0x37, |
112 | CMD_ARM_SRQ = 0x40, | ||
111 | 113 | ||
112 | /* QP/EE commands */ | 114 | /* QP/EE commands */ |
113 | CMD_RST2INIT_QPEE = 0x19, | 115 | CMD_RST2INIT_QPEE = 0x19, |
@@ -219,20 +221,20 @@ static int mthca_cmd_post(struct mthca_dev *dev, | |||
219 | * (and some architectures such as ia64 implement memcpy_toio | 221 | * (and some architectures such as ia64 implement memcpy_toio |
220 | * in terms of writeb). | 222 | * in terms of writeb). |
221 | */ | 223 | */ |
222 | __raw_writel(cpu_to_be32(in_param >> 32), dev->hcr + 0 * 4); | 224 | __raw_writel((__force u32) cpu_to_be32(in_param >> 32), dev->hcr + 0 * 4); |
223 | __raw_writel(cpu_to_be32(in_param & 0xfffffffful), dev->hcr + 1 * 4); | 225 | __raw_writel((__force u32) cpu_to_be32(in_param & 0xfffffffful), dev->hcr + 1 * 4); |
224 | __raw_writel(cpu_to_be32(in_modifier), dev->hcr + 2 * 4); | 226 | __raw_writel((__force u32) cpu_to_be32(in_modifier), dev->hcr + 2 * 4); |
225 | __raw_writel(cpu_to_be32(out_param >> 32), dev->hcr + 3 * 4); | 227 | __raw_writel((__force u32) cpu_to_be32(out_param >> 32), dev->hcr + 3 * 4); |
226 | __raw_writel(cpu_to_be32(out_param & 0xfffffffful), dev->hcr + 4 * 4); | 228 | __raw_writel((__force u32) cpu_to_be32(out_param & 0xfffffffful), dev->hcr + 4 * 4); |
227 | __raw_writel(cpu_to_be32(token << 16), dev->hcr + 5 * 4); | 229 | __raw_writel((__force u32) cpu_to_be32(token << 16), dev->hcr + 5 * 4); |
228 | 230 | ||
229 | /* __raw_writel may not order writes. */ | 231 | /* __raw_writel may not order writes. */ |
230 | wmb(); | 232 | wmb(); |
231 | 233 | ||
232 | __raw_writel(cpu_to_be32((1 << HCR_GO_BIT) | | 234 | __raw_writel((__force u32) cpu_to_be32((1 << HCR_GO_BIT) | |
233 | (event ? (1 << HCA_E_BIT) : 0) | | 235 | (event ? (1 << HCA_E_BIT) : 0) | |
234 | (op_modifier << HCR_OPMOD_SHIFT) | | 236 | (op_modifier << HCR_OPMOD_SHIFT) | |
235 | op), dev->hcr + 6 * 4); | 237 | op), dev->hcr + 6 * 4); |
236 | 238 | ||
237 | out: | 239 | out: |
238 | up(&dev->cmd.hcr_sem); | 240 | up(&dev->cmd.hcr_sem); |
@@ -273,12 +275,14 @@ static int mthca_cmd_poll(struct mthca_dev *dev, | |||
273 | goto out; | 275 | goto out; |
274 | } | 276 | } |
275 | 277 | ||
276 | if (out_is_imm) { | 278 | if (out_is_imm) |
277 | memcpy_fromio(out_param, dev->hcr + HCR_OUT_PARAM_OFFSET, sizeof (u64)); | 279 | *out_param = |
278 | be64_to_cpus(out_param); | 280 | (u64) be32_to_cpu((__force __be32) |
279 | } | 281 | __raw_readl(dev->hcr + HCR_OUT_PARAM_OFFSET)) << 32 | |
282 | (u64) be32_to_cpu((__force __be32) | ||
283 | __raw_readl(dev->hcr + HCR_OUT_PARAM_OFFSET + 4)); | ||
280 | 284 | ||
281 | *status = be32_to_cpu(__raw_readl(dev->hcr + HCR_STATUS_OFFSET)) >> 24; | 285 | *status = be32_to_cpu((__force __be32) __raw_readl(dev->hcr + HCR_STATUS_OFFSET)) >> 24; |
282 | 286 | ||
283 | out: | 287 | out: |
284 | up(&dev->cmd.poll_sem); | 288 | up(&dev->cmd.poll_sem); |
@@ -1029,6 +1033,8 @@ int mthca_QUERY_DEV_LIM(struct mthca_dev *dev, | |||
1029 | 1033 | ||
1030 | mthca_dbg(dev, "Max QPs: %d, reserved QPs: %d, entry size: %d\n", | 1034 | mthca_dbg(dev, "Max QPs: %d, reserved QPs: %d, entry size: %d\n", |
1031 | dev_lim->max_qps, dev_lim->reserved_qps, dev_lim->qpc_entry_sz); | 1035 | dev_lim->max_qps, dev_lim->reserved_qps, dev_lim->qpc_entry_sz); |
1036 | mthca_dbg(dev, "Max SRQs: %d, reserved SRQs: %d, entry size: %d\n", | ||
1037 | dev_lim->max_srqs, dev_lim->reserved_srqs, dev_lim->srq_entry_sz); | ||
1032 | mthca_dbg(dev, "Max CQs: %d, reserved CQs: %d, entry size: %d\n", | 1038 | mthca_dbg(dev, "Max CQs: %d, reserved CQs: %d, entry size: %d\n", |
1033 | dev_lim->max_cqs, dev_lim->reserved_cqs, dev_lim->cqc_entry_sz); | 1039 | dev_lim->max_cqs, dev_lim->reserved_cqs, dev_lim->cqc_entry_sz); |
1034 | mthca_dbg(dev, "Max EQs: %d, reserved EQs: %d, entry size: %d\n", | 1040 | mthca_dbg(dev, "Max EQs: %d, reserved EQs: %d, entry size: %d\n", |
@@ -1082,6 +1088,34 @@ out: | |||
1082 | return err; | 1088 | return err; |
1083 | } | 1089 | } |
1084 | 1090 | ||
1091 | static void get_board_id(void *vsd, char *board_id) | ||
1092 | { | ||
1093 | int i; | ||
1094 | |||
1095 | #define VSD_OFFSET_SIG1 0x00 | ||
1096 | #define VSD_OFFSET_SIG2 0xde | ||
1097 | #define VSD_OFFSET_MLX_BOARD_ID 0xd0 | ||
1098 | #define VSD_OFFSET_TS_BOARD_ID 0x20 | ||
1099 | |||
1100 | #define VSD_SIGNATURE_TOPSPIN 0x5ad | ||
1101 | |||
1102 | memset(board_id, 0, MTHCA_BOARD_ID_LEN); | ||
1103 | |||
1104 | if (be16_to_cpup(vsd + VSD_OFFSET_SIG1) == VSD_SIGNATURE_TOPSPIN && | ||
1105 | be16_to_cpup(vsd + VSD_OFFSET_SIG2) == VSD_SIGNATURE_TOPSPIN) { | ||
1106 | strlcpy(board_id, vsd + VSD_OFFSET_TS_BOARD_ID, MTHCA_BOARD_ID_LEN); | ||
1107 | } else { | ||
1108 | /* | ||
1109 | * The board ID is a string but the firmware byte | ||
1110 | * swaps each 4-byte word before passing it back to | ||
1111 | * us. Therefore we need to swab it before printing. | ||
1112 | */ | ||
1113 | for (i = 0; i < 4; ++i) | ||
1114 | ((u32 *) board_id)[i] = | ||
1115 | swab32(*(u32 *) (vsd + VSD_OFFSET_MLX_BOARD_ID + i * 4)); | ||
1116 | } | ||
1117 | } | ||
1118 | |||
1085 | int mthca_QUERY_ADAPTER(struct mthca_dev *dev, | 1119 | int mthca_QUERY_ADAPTER(struct mthca_dev *dev, |
1086 | struct mthca_adapter *adapter, u8 *status) | 1120 | struct mthca_adapter *adapter, u8 *status) |
1087 | { | 1121 | { |
@@ -1094,6 +1128,7 @@ int mthca_QUERY_ADAPTER(struct mthca_dev *dev, | |||
1094 | #define QUERY_ADAPTER_DEVICE_ID_OFFSET 0x04 | 1128 | #define QUERY_ADAPTER_DEVICE_ID_OFFSET 0x04 |
1095 | #define QUERY_ADAPTER_REVISION_ID_OFFSET 0x08 | 1129 | #define QUERY_ADAPTER_REVISION_ID_OFFSET 0x08 |
1096 | #define QUERY_ADAPTER_INTA_PIN_OFFSET 0x10 | 1130 | #define QUERY_ADAPTER_INTA_PIN_OFFSET 0x10 |
1131 | #define QUERY_ADAPTER_VSD_OFFSET 0x20 | ||
1097 | 1132 | ||
1098 | mailbox = mthca_alloc_mailbox(dev, GFP_KERNEL); | 1133 | mailbox = mthca_alloc_mailbox(dev, GFP_KERNEL); |
1099 | if (IS_ERR(mailbox)) | 1134 | if (IS_ERR(mailbox)) |
@@ -1111,6 +1146,9 @@ int mthca_QUERY_ADAPTER(struct mthca_dev *dev, | |||
1111 | MTHCA_GET(adapter->revision_id, outbox, QUERY_ADAPTER_REVISION_ID_OFFSET); | 1146 | MTHCA_GET(adapter->revision_id, outbox, QUERY_ADAPTER_REVISION_ID_OFFSET); |
1112 | MTHCA_GET(adapter->inta_pin, outbox, QUERY_ADAPTER_INTA_PIN_OFFSET); | 1147 | MTHCA_GET(adapter->inta_pin, outbox, QUERY_ADAPTER_INTA_PIN_OFFSET); |
1113 | 1148 | ||
1149 | get_board_id(outbox + QUERY_ADAPTER_VSD_OFFSET / 4, | ||
1150 | adapter->board_id); | ||
1151 | |||
1114 | out: | 1152 | out: |
1115 | mthca_free_mailbox(dev, mailbox); | 1153 | mthca_free_mailbox(dev, mailbox); |
1116 | return err; | 1154 | return err; |
@@ -1121,7 +1159,7 @@ int mthca_INIT_HCA(struct mthca_dev *dev, | |||
1121 | u8 *status) | 1159 | u8 *status) |
1122 | { | 1160 | { |
1123 | struct mthca_mailbox *mailbox; | 1161 | struct mthca_mailbox *mailbox; |
1124 | u32 *inbox; | 1162 | __be32 *inbox; |
1125 | int err; | 1163 | int err; |
1126 | 1164 | ||
1127 | #define INIT_HCA_IN_SIZE 0x200 | 1165 | #define INIT_HCA_IN_SIZE 0x200 |
@@ -1247,10 +1285,8 @@ int mthca_INIT_IB(struct mthca_dev *dev, | |||
1247 | #define INIT_IB_FLAG_SIG (1 << 18) | 1285 | #define INIT_IB_FLAG_SIG (1 << 18) |
1248 | #define INIT_IB_FLAG_NG (1 << 17) | 1286 | #define INIT_IB_FLAG_NG (1 << 17) |
1249 | #define INIT_IB_FLAG_G0 (1 << 16) | 1287 | #define INIT_IB_FLAG_G0 (1 << 16) |
1250 | #define INIT_IB_FLAG_1X (1 << 8) | ||
1251 | #define INIT_IB_FLAG_4X (1 << 9) | ||
1252 | #define INIT_IB_FLAG_12X (1 << 11) | ||
1253 | #define INIT_IB_VL_SHIFT 4 | 1288 | #define INIT_IB_VL_SHIFT 4 |
1289 | #define INIT_IB_PORT_WIDTH_SHIFT 8 | ||
1254 | #define INIT_IB_MTU_SHIFT 12 | 1290 | #define INIT_IB_MTU_SHIFT 12 |
1255 | #define INIT_IB_MAX_GID_OFFSET 0x06 | 1291 | #define INIT_IB_MAX_GID_OFFSET 0x06 |
1256 | #define INIT_IB_MAX_PKEY_OFFSET 0x0a | 1292 | #define INIT_IB_MAX_PKEY_OFFSET 0x0a |
@@ -1266,12 +1302,11 @@ int mthca_INIT_IB(struct mthca_dev *dev, | |||
1266 | memset(inbox, 0, INIT_IB_IN_SIZE); | 1302 | memset(inbox, 0, INIT_IB_IN_SIZE); |
1267 | 1303 | ||
1268 | flags = 0; | 1304 | flags = 0; |
1269 | flags |= param->enable_1x ? INIT_IB_FLAG_1X : 0; | ||
1270 | flags |= param->enable_4x ? INIT_IB_FLAG_4X : 0; | ||
1271 | flags |= param->set_guid0 ? INIT_IB_FLAG_G0 : 0; | 1305 | flags |= param->set_guid0 ? INIT_IB_FLAG_G0 : 0; |
1272 | flags |= param->set_node_guid ? INIT_IB_FLAG_NG : 0; | 1306 | flags |= param->set_node_guid ? INIT_IB_FLAG_NG : 0; |
1273 | flags |= param->set_si_guid ? INIT_IB_FLAG_SIG : 0; | 1307 | flags |= param->set_si_guid ? INIT_IB_FLAG_SIG : 0; |
1274 | flags |= param->vl_cap << INIT_IB_VL_SHIFT; | 1308 | flags |= param->vl_cap << INIT_IB_VL_SHIFT; |
1309 | flags |= param->port_width << INIT_IB_PORT_WIDTH_SHIFT; | ||
1275 | flags |= param->mtu_cap << INIT_IB_MTU_SHIFT; | 1310 | flags |= param->mtu_cap << INIT_IB_MTU_SHIFT; |
1276 | MTHCA_PUT(inbox, flags, INIT_IB_FLAGS_OFFSET); | 1311 | MTHCA_PUT(inbox, flags, INIT_IB_FLAGS_OFFSET); |
1277 | 1312 | ||
@@ -1342,7 +1377,7 @@ int mthca_MAP_ICM(struct mthca_dev *dev, struct mthca_icm *icm, u64 virt, u8 *st | |||
1342 | int mthca_MAP_ICM_page(struct mthca_dev *dev, u64 dma_addr, u64 virt, u8 *status) | 1377 | int mthca_MAP_ICM_page(struct mthca_dev *dev, u64 dma_addr, u64 virt, u8 *status) |
1343 | { | 1378 | { |
1344 | struct mthca_mailbox *mailbox; | 1379 | struct mthca_mailbox *mailbox; |
1345 | u64 *inbox; | 1380 | __be64 *inbox; |
1346 | int err; | 1381 | int err; |
1347 | 1382 | ||
1348 | mailbox = mthca_alloc_mailbox(dev, GFP_KERNEL); | 1383 | mailbox = mthca_alloc_mailbox(dev, GFP_KERNEL); |
@@ -1468,6 +1503,27 @@ int mthca_HW2SW_CQ(struct mthca_dev *dev, struct mthca_mailbox *mailbox, | |||
1468 | CMD_TIME_CLASS_A, status); | 1503 | CMD_TIME_CLASS_A, status); |
1469 | } | 1504 | } |
1470 | 1505 | ||
1506 | int mthca_SW2HW_SRQ(struct mthca_dev *dev, struct mthca_mailbox *mailbox, | ||
1507 | int srq_num, u8 *status) | ||
1508 | { | ||
1509 | return mthca_cmd(dev, mailbox->dma, srq_num, 0, CMD_SW2HW_SRQ, | ||
1510 | CMD_TIME_CLASS_A, status); | ||
1511 | } | ||
1512 | |||
1513 | int mthca_HW2SW_SRQ(struct mthca_dev *dev, struct mthca_mailbox *mailbox, | ||
1514 | int srq_num, u8 *status) | ||
1515 | { | ||
1516 | return mthca_cmd_box(dev, 0, mailbox->dma, srq_num, 0, | ||
1517 | CMD_HW2SW_SRQ, | ||
1518 | CMD_TIME_CLASS_A, status); | ||
1519 | } | ||
1520 | |||
1521 | int mthca_ARM_SRQ(struct mthca_dev *dev, int srq_num, int limit, u8 *status) | ||
1522 | { | ||
1523 | return mthca_cmd(dev, limit, srq_num, 0, CMD_ARM_SRQ, | ||
1524 | CMD_TIME_CLASS_B, status); | ||
1525 | } | ||
1526 | |||
1471 | int mthca_MODIFY_QP(struct mthca_dev *dev, int trans, u32 num, | 1527 | int mthca_MODIFY_QP(struct mthca_dev *dev, int trans, u32 num, |
1472 | int is_ee, struct mthca_mailbox *mailbox, u32 optmask, | 1528 | int is_ee, struct mthca_mailbox *mailbox, u32 optmask, |
1473 | u8 *status) | 1529 | u8 *status) |
@@ -1513,7 +1569,7 @@ int mthca_MODIFY_QP(struct mthca_dev *dev, int trans, u32 num, | |||
1513 | if (i % 8 == 0) | 1569 | if (i % 8 == 0) |
1514 | printk(" [%02x] ", i * 4); | 1570 | printk(" [%02x] ", i * 4); |
1515 | printk(" %08x", | 1571 | printk(" %08x", |
1516 | be32_to_cpu(((u32 *) mailbox->buf)[i + 2])); | 1572 | be32_to_cpu(((__be32 *) mailbox->buf)[i + 2])); |
1517 | if ((i + 1) % 8 == 0) | 1573 | if ((i + 1) % 8 == 0) |
1518 | printk("\n"); | 1574 | printk("\n"); |
1519 | } | 1575 | } |
@@ -1533,7 +1589,7 @@ int mthca_MODIFY_QP(struct mthca_dev *dev, int trans, u32 num, | |||
1533 | if (i % 8 == 0) | 1589 | if (i % 8 == 0) |
1534 | printk("[%02x] ", i * 4); | 1590 | printk("[%02x] ", i * 4); |
1535 | printk(" %08x", | 1591 | printk(" %08x", |
1536 | be32_to_cpu(((u32 *) mailbox->buf)[i + 2])); | 1592 | be32_to_cpu(((__be32 *) mailbox->buf)[i + 2])); |
1537 | if ((i + 1) % 8 == 0) | 1593 | if ((i + 1) % 8 == 0) |
1538 | printk("\n"); | 1594 | printk("\n"); |
1539 | } | 1595 | } |