diff options
Diffstat (limited to 'drivers/infiniband/hw/ipath/ipath_mad.c')
-rw-r--r-- | drivers/infiniband/hw/ipath/ipath_mad.c | 123 |
1 files changed, 77 insertions, 46 deletions
diff --git a/drivers/infiniband/hw/ipath/ipath_mad.c b/drivers/infiniband/hw/ipath/ipath_mad.c index 3d1432d1e3f4..d98d5f103700 100644 --- a/drivers/infiniband/hw/ipath/ipath_mad.c +++ b/drivers/infiniband/hw/ipath/ipath_mad.c | |||
@@ -934,6 +934,7 @@ static int recv_pma_get_portsamplescontrol(struct ib_perf *pmp, | |||
934 | struct ib_pma_portsamplescontrol *p = | 934 | struct ib_pma_portsamplescontrol *p = |
935 | (struct ib_pma_portsamplescontrol *)pmp->data; | 935 | (struct ib_pma_portsamplescontrol *)pmp->data; |
936 | struct ipath_ibdev *dev = to_idev(ibdev); | 936 | struct ipath_ibdev *dev = to_idev(ibdev); |
937 | struct ipath_cregs const *crp = dev->dd->ipath_cregs; | ||
937 | unsigned long flags; | 938 | unsigned long flags; |
938 | u8 port_select = p->port_select; | 939 | u8 port_select = p->port_select; |
939 | 940 | ||
@@ -955,7 +956,10 @@ static int recv_pma_get_portsamplescontrol(struct ib_perf *pmp, | |||
955 | p->counter_width = 4; /* 32 bit counters */ | 956 | p->counter_width = 4; /* 32 bit counters */ |
956 | p->counter_mask0_9 = COUNTER_MASK0_9; | 957 | p->counter_mask0_9 = COUNTER_MASK0_9; |
957 | spin_lock_irqsave(&dev->pending_lock, flags); | 958 | spin_lock_irqsave(&dev->pending_lock, flags); |
958 | p->sample_status = dev->pma_sample_status; | 959 | if (crp->cr_psstat) |
960 | p->sample_status = ipath_read_creg32(dev->dd, crp->cr_psstat); | ||
961 | else | ||
962 | p->sample_status = dev->pma_sample_status; | ||
959 | p->sample_start = cpu_to_be32(dev->pma_sample_start); | 963 | p->sample_start = cpu_to_be32(dev->pma_sample_start); |
960 | p->sample_interval = cpu_to_be32(dev->pma_sample_interval); | 964 | p->sample_interval = cpu_to_be32(dev->pma_sample_interval); |
961 | p->tag = cpu_to_be16(dev->pma_tag); | 965 | p->tag = cpu_to_be16(dev->pma_tag); |
@@ -975,8 +979,9 @@ static int recv_pma_set_portsamplescontrol(struct ib_perf *pmp, | |||
975 | struct ib_pma_portsamplescontrol *p = | 979 | struct ib_pma_portsamplescontrol *p = |
976 | (struct ib_pma_portsamplescontrol *)pmp->data; | 980 | (struct ib_pma_portsamplescontrol *)pmp->data; |
977 | struct ipath_ibdev *dev = to_idev(ibdev); | 981 | struct ipath_ibdev *dev = to_idev(ibdev); |
982 | struct ipath_cregs const *crp = dev->dd->ipath_cregs; | ||
978 | unsigned long flags; | 983 | unsigned long flags; |
979 | u32 start; | 984 | u8 status; |
980 | int ret; | 985 | int ret; |
981 | 986 | ||
982 | if (pmp->attr_mod != 0 || | 987 | if (pmp->attr_mod != 0 || |
@@ -986,59 +991,67 @@ static int recv_pma_set_portsamplescontrol(struct ib_perf *pmp, | |||
986 | goto bail; | 991 | goto bail; |
987 | } | 992 | } |
988 | 993 | ||
989 | start = be32_to_cpu(p->sample_start); | 994 | spin_lock_irqsave(&dev->pending_lock, flags); |
990 | if (start != 0) { | 995 | if (crp->cr_psstat) |
991 | spin_lock_irqsave(&dev->pending_lock, flags); | 996 | status = ipath_read_creg32(dev->dd, crp->cr_psstat); |
992 | if (dev->pma_sample_status == IB_PMA_SAMPLE_STATUS_DONE) { | 997 | else |
993 | dev->pma_sample_status = | 998 | status = dev->pma_sample_status; |
994 | IB_PMA_SAMPLE_STATUS_STARTED; | 999 | if (status == IB_PMA_SAMPLE_STATUS_DONE) { |
995 | dev->pma_sample_start = start; | 1000 | dev->pma_sample_start = be32_to_cpu(p->sample_start); |
996 | dev->pma_sample_interval = | 1001 | dev->pma_sample_interval = be32_to_cpu(p->sample_interval); |
997 | be32_to_cpu(p->sample_interval); | 1002 | dev->pma_tag = be16_to_cpu(p->tag); |
998 | dev->pma_tag = be16_to_cpu(p->tag); | 1003 | dev->pma_counter_select[0] = p->counter_select[0]; |
999 | if (p->counter_select[0]) | 1004 | dev->pma_counter_select[1] = p->counter_select[1]; |
1000 | dev->pma_counter_select[0] = | 1005 | dev->pma_counter_select[2] = p->counter_select[2]; |
1001 | p->counter_select[0]; | 1006 | dev->pma_counter_select[3] = p->counter_select[3]; |
1002 | if (p->counter_select[1]) | 1007 | dev->pma_counter_select[4] = p->counter_select[4]; |
1003 | dev->pma_counter_select[1] = | 1008 | if (crp->cr_psstat) { |
1004 | p->counter_select[1]; | 1009 | ipath_write_creg(dev->dd, crp->cr_psinterval, |
1005 | if (p->counter_select[2]) | 1010 | dev->pma_sample_interval); |
1006 | dev->pma_counter_select[2] = | 1011 | ipath_write_creg(dev->dd, crp->cr_psstart, |
1007 | p->counter_select[2]; | 1012 | dev->pma_sample_start); |
1008 | if (p->counter_select[3]) | 1013 | } else |
1009 | dev->pma_counter_select[3] = | 1014 | dev->pma_sample_status = IB_PMA_SAMPLE_STATUS_STARTED; |
1010 | p->counter_select[3]; | ||
1011 | if (p->counter_select[4]) | ||
1012 | dev->pma_counter_select[4] = | ||
1013 | p->counter_select[4]; | ||
1014 | } | ||
1015 | spin_unlock_irqrestore(&dev->pending_lock, flags); | ||
1016 | } | 1015 | } |
1016 | spin_unlock_irqrestore(&dev->pending_lock, flags); | ||
1017 | |||
1017 | ret = recv_pma_get_portsamplescontrol(pmp, ibdev, port); | 1018 | ret = recv_pma_get_portsamplescontrol(pmp, ibdev, port); |
1018 | 1019 | ||
1019 | bail: | 1020 | bail: |
1020 | return ret; | 1021 | return ret; |
1021 | } | 1022 | } |
1022 | 1023 | ||
1023 | static u64 get_counter(struct ipath_ibdev *dev, __be16 sel) | 1024 | static u64 get_counter(struct ipath_ibdev *dev, |
1025 | struct ipath_cregs const *crp, | ||
1026 | __be16 sel) | ||
1024 | { | 1027 | { |
1025 | u64 ret; | 1028 | u64 ret; |
1026 | 1029 | ||
1027 | switch (sel) { | 1030 | switch (sel) { |
1028 | case IB_PMA_PORT_XMIT_DATA: | 1031 | case IB_PMA_PORT_XMIT_DATA: |
1029 | ret = dev->ipath_sword; | 1032 | ret = (crp->cr_psxmitdatacount) ? |
1033 | ipath_read_creg32(dev->dd, crp->cr_psxmitdatacount) : | ||
1034 | dev->ipath_sword; | ||
1030 | break; | 1035 | break; |
1031 | case IB_PMA_PORT_RCV_DATA: | 1036 | case IB_PMA_PORT_RCV_DATA: |
1032 | ret = dev->ipath_rword; | 1037 | ret = (crp->cr_psrcvdatacount) ? |
1038 | ipath_read_creg32(dev->dd, crp->cr_psrcvdatacount) : | ||
1039 | dev->ipath_rword; | ||
1033 | break; | 1040 | break; |
1034 | case IB_PMA_PORT_XMIT_PKTS: | 1041 | case IB_PMA_PORT_XMIT_PKTS: |
1035 | ret = dev->ipath_spkts; | 1042 | ret = (crp->cr_psxmitpktscount) ? |
1043 | ipath_read_creg32(dev->dd, crp->cr_psxmitpktscount) : | ||
1044 | dev->ipath_spkts; | ||
1036 | break; | 1045 | break; |
1037 | case IB_PMA_PORT_RCV_PKTS: | 1046 | case IB_PMA_PORT_RCV_PKTS: |
1038 | ret = dev->ipath_rpkts; | 1047 | ret = (crp->cr_psrcvpktscount) ? |
1048 | ipath_read_creg32(dev->dd, crp->cr_psrcvpktscount) : | ||
1049 | dev->ipath_rpkts; | ||
1039 | break; | 1050 | break; |
1040 | case IB_PMA_PORT_XMIT_WAIT: | 1051 | case IB_PMA_PORT_XMIT_WAIT: |
1041 | ret = dev->ipath_xmit_wait; | 1052 | ret = (crp->cr_psxmitwaitcount) ? |
1053 | ipath_read_creg32(dev->dd, crp->cr_psxmitwaitcount) : | ||
1054 | dev->ipath_xmit_wait; | ||
1042 | break; | 1055 | break; |
1043 | default: | 1056 | default: |
1044 | ret = 0; | 1057 | ret = 0; |
@@ -1053,14 +1066,21 @@ static int recv_pma_get_portsamplesresult(struct ib_perf *pmp, | |||
1053 | struct ib_pma_portsamplesresult *p = | 1066 | struct ib_pma_portsamplesresult *p = |
1054 | (struct ib_pma_portsamplesresult *)pmp->data; | 1067 | (struct ib_pma_portsamplesresult *)pmp->data; |
1055 | struct ipath_ibdev *dev = to_idev(ibdev); | 1068 | struct ipath_ibdev *dev = to_idev(ibdev); |
1069 | struct ipath_cregs const *crp = dev->dd->ipath_cregs; | ||
1070 | u8 status; | ||
1056 | int i; | 1071 | int i; |
1057 | 1072 | ||
1058 | memset(pmp->data, 0, sizeof(pmp->data)); | 1073 | memset(pmp->data, 0, sizeof(pmp->data)); |
1059 | p->tag = cpu_to_be16(dev->pma_tag); | 1074 | p->tag = cpu_to_be16(dev->pma_tag); |
1060 | p->sample_status = cpu_to_be16(dev->pma_sample_status); | 1075 | if (crp->cr_psstat) |
1076 | status = ipath_read_creg32(dev->dd, crp->cr_psstat); | ||
1077 | else | ||
1078 | status = dev->pma_sample_status; | ||
1079 | p->sample_status = cpu_to_be16(status); | ||
1061 | for (i = 0; i < ARRAY_SIZE(dev->pma_counter_select); i++) | 1080 | for (i = 0; i < ARRAY_SIZE(dev->pma_counter_select); i++) |
1062 | p->counter[i] = cpu_to_be32( | 1081 | p->counter[i] = (status != IB_PMA_SAMPLE_STATUS_DONE) ? 0 : |
1063 | get_counter(dev, dev->pma_counter_select[i])); | 1082 | cpu_to_be32( |
1083 | get_counter(dev, crp, dev->pma_counter_select[i])); | ||
1064 | 1084 | ||
1065 | return reply((struct ib_smp *) pmp); | 1085 | return reply((struct ib_smp *) pmp); |
1066 | } | 1086 | } |
@@ -1071,16 +1091,23 @@ static int recv_pma_get_portsamplesresult_ext(struct ib_perf *pmp, | |||
1071 | struct ib_pma_portsamplesresult_ext *p = | 1091 | struct ib_pma_portsamplesresult_ext *p = |
1072 | (struct ib_pma_portsamplesresult_ext *)pmp->data; | 1092 | (struct ib_pma_portsamplesresult_ext *)pmp->data; |
1073 | struct ipath_ibdev *dev = to_idev(ibdev); | 1093 | struct ipath_ibdev *dev = to_idev(ibdev); |
1094 | struct ipath_cregs const *crp = dev->dd->ipath_cregs; | ||
1095 | u8 status; | ||
1074 | int i; | 1096 | int i; |
1075 | 1097 | ||
1076 | memset(pmp->data, 0, sizeof(pmp->data)); | 1098 | memset(pmp->data, 0, sizeof(pmp->data)); |
1077 | p->tag = cpu_to_be16(dev->pma_tag); | 1099 | p->tag = cpu_to_be16(dev->pma_tag); |
1078 | p->sample_status = cpu_to_be16(dev->pma_sample_status); | 1100 | if (crp->cr_psstat) |
1101 | status = ipath_read_creg32(dev->dd, crp->cr_psstat); | ||
1102 | else | ||
1103 | status = dev->pma_sample_status; | ||
1104 | p->sample_status = cpu_to_be16(status); | ||
1079 | /* 64 bits */ | 1105 | /* 64 bits */ |
1080 | p->extended_width = __constant_cpu_to_be32(0x80000000); | 1106 | p->extended_width = __constant_cpu_to_be32(0x80000000); |
1081 | for (i = 0; i < ARRAY_SIZE(dev->pma_counter_select); i++) | 1107 | for (i = 0; i < ARRAY_SIZE(dev->pma_counter_select); i++) |
1082 | p->counter[i] = cpu_to_be64( | 1108 | p->counter[i] = (status != IB_PMA_SAMPLE_STATUS_DONE) ? 0 : |
1083 | get_counter(dev, dev->pma_counter_select[i])); | 1109 | cpu_to_be64( |
1110 | get_counter(dev, crp, dev->pma_counter_select[i])); | ||
1084 | 1111 | ||
1085 | return reply((struct ib_smp *) pmp); | 1112 | return reply((struct ib_smp *) pmp); |
1086 | } | 1113 | } |
@@ -1113,6 +1140,8 @@ static int recv_pma_get_portcounters(struct ib_perf *pmp, | |||
1113 | dev->z_local_link_integrity_errors; | 1140 | dev->z_local_link_integrity_errors; |
1114 | cntrs.excessive_buffer_overrun_errors -= | 1141 | cntrs.excessive_buffer_overrun_errors -= |
1115 | dev->z_excessive_buffer_overrun_errors; | 1142 | dev->z_excessive_buffer_overrun_errors; |
1143 | cntrs.vl15_dropped -= dev->z_vl15_dropped; | ||
1144 | cntrs.vl15_dropped += dev->n_vl15_dropped; | ||
1116 | 1145 | ||
1117 | memset(pmp->data, 0, sizeof(pmp->data)); | 1146 | memset(pmp->data, 0, sizeof(pmp->data)); |
1118 | 1147 | ||
@@ -1156,10 +1185,10 @@ static int recv_pma_get_portcounters(struct ib_perf *pmp, | |||
1156 | cntrs.excessive_buffer_overrun_errors = 0xFUL; | 1185 | cntrs.excessive_buffer_overrun_errors = 0xFUL; |
1157 | p->lli_ebor_errors = (cntrs.local_link_integrity_errors << 4) | | 1186 | p->lli_ebor_errors = (cntrs.local_link_integrity_errors << 4) | |
1158 | cntrs.excessive_buffer_overrun_errors; | 1187 | cntrs.excessive_buffer_overrun_errors; |
1159 | if (dev->n_vl15_dropped > 0xFFFFUL) | 1188 | if (cntrs.vl15_dropped > 0xFFFFUL) |
1160 | p->vl15_dropped = __constant_cpu_to_be16(0xFFFF); | 1189 | p->vl15_dropped = __constant_cpu_to_be16(0xFFFF); |
1161 | else | 1190 | else |
1162 | p->vl15_dropped = cpu_to_be16((u16)dev->n_vl15_dropped); | 1191 | p->vl15_dropped = cpu_to_be16((u16)cntrs.vl15_dropped); |
1163 | if (cntrs.port_xmit_data > 0xFFFFFFFFUL) | 1192 | if (cntrs.port_xmit_data > 0xFFFFFFFFUL) |
1164 | p->port_xmit_data = __constant_cpu_to_be32(0xFFFFFFFF); | 1193 | p->port_xmit_data = __constant_cpu_to_be32(0xFFFFFFFF); |
1165 | else | 1194 | else |
@@ -1262,8 +1291,10 @@ static int recv_pma_set_portcounters(struct ib_perf *pmp, | |||
1262 | dev->z_excessive_buffer_overrun_errors = | 1291 | dev->z_excessive_buffer_overrun_errors = |
1263 | cntrs.excessive_buffer_overrun_errors; | 1292 | cntrs.excessive_buffer_overrun_errors; |
1264 | 1293 | ||
1265 | if (p->counter_select & IB_PMA_SEL_PORT_VL15_DROPPED) | 1294 | if (p->counter_select & IB_PMA_SEL_PORT_VL15_DROPPED) { |
1266 | dev->n_vl15_dropped = 0; | 1295 | dev->n_vl15_dropped = 0; |
1296 | dev->z_vl15_dropped = cntrs.vl15_dropped; | ||
1297 | } | ||
1267 | 1298 | ||
1268 | if (p->counter_select & IB_PMA_SEL_PORT_XMIT_DATA) | 1299 | if (p->counter_select & IB_PMA_SEL_PORT_XMIT_DATA) |
1269 | dev->z_port_xmit_data = cntrs.port_xmit_data; | 1300 | dev->z_port_xmit_data = cntrs.port_xmit_data; |
@@ -1434,7 +1465,7 @@ static int process_subn(struct ib_device *ibdev, int mad_flags, | |||
1434 | * before checking for other consumers. | 1465 | * before checking for other consumers. |
1435 | * Just tell the caller to process it normally. | 1466 | * Just tell the caller to process it normally. |
1436 | */ | 1467 | */ |
1437 | ret = IB_MAD_RESULT_FAILURE; | 1468 | ret = IB_MAD_RESULT_SUCCESS; |
1438 | goto bail; | 1469 | goto bail; |
1439 | default: | 1470 | default: |
1440 | smp->status |= IB_SMP_UNSUP_METHOD; | 1471 | smp->status |= IB_SMP_UNSUP_METHOD; |
@@ -1516,7 +1547,7 @@ static int process_perf(struct ib_device *ibdev, u8 port_num, | |||
1516 | * before checking for other consumers. | 1547 | * before checking for other consumers. |
1517 | * Just tell the caller to process it normally. | 1548 | * Just tell the caller to process it normally. |
1518 | */ | 1549 | */ |
1519 | ret = IB_MAD_RESULT_FAILURE; | 1550 | ret = IB_MAD_RESULT_SUCCESS; |
1520 | goto bail; | 1551 | goto bail; |
1521 | default: | 1552 | default: |
1522 | pmp->status |= IB_SMP_UNSUP_METHOD; | 1553 | pmp->status |= IB_SMP_UNSUP_METHOD; |