Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-only
0002 /*
0003  * This driver adds support for PCIe PMU RCiEP device. Related
0004  * perf events are bandwidth, latency etc.
0005  *
0006  * Copyright (C) 2021 HiSilicon Limited
0007  * Author: Qi Liu <liuqi115@huawei.com>
0008  */
0009 #include <linux/bitfield.h>
0010 #include <linux/bitmap.h>
0011 #include <linux/bug.h>
0012 #include <linux/device.h>
0013 #include <linux/err.h>
0014 #include <linux/interrupt.h>
0015 #include <linux/irq.h>
0016 #include <linux/kernel.h>
0017 #include <linux/list.h>
0018 #include <linux/module.h>
0019 #include <linux/pci.h>
0020 #include <linux/perf_event.h>
0021 
0022 #define DRV_NAME "hisi_pcie_pmu"
0023 /* Define registers */
0024 #define HISI_PCIE_GLOBAL_CTRL       0x00
0025 #define HISI_PCIE_EVENT_CTRL        0x010
0026 #define HISI_PCIE_CNT           0x090
0027 #define HISI_PCIE_EXT_CNT       0x110
0028 #define HISI_PCIE_INT_STAT      0x150
0029 #define HISI_PCIE_INT_MASK      0x154
0030 #define HISI_PCIE_REG_BDF       0xfe0
0031 #define HISI_PCIE_REG_VERSION       0xfe4
0032 #define HISI_PCIE_REG_INFO      0xfe8
0033 
0034 /* Define command in HISI_PCIE_GLOBAL_CTRL */
0035 #define HISI_PCIE_GLOBAL_EN     0x01
0036 #define HISI_PCIE_GLOBAL_NONE       0
0037 
0038 /* Define command in HISI_PCIE_EVENT_CTRL */
0039 #define HISI_PCIE_EVENT_EN      BIT_ULL(20)
0040 #define HISI_PCIE_RESET_CNT     BIT_ULL(22)
0041 #define HISI_PCIE_INIT_SET      BIT_ULL(34)
0042 #define HISI_PCIE_THR_EN        BIT_ULL(26)
0043 #define HISI_PCIE_TARGET_EN     BIT_ULL(32)
0044 #define HISI_PCIE_TRIG_EN       BIT_ULL(52)
0045 
0046 /* Define offsets in HISI_PCIE_EVENT_CTRL */
0047 #define HISI_PCIE_EVENT_M       GENMASK_ULL(15, 0)
0048 #define HISI_PCIE_THR_MODE_M        GENMASK_ULL(27, 27)
0049 #define HISI_PCIE_THR_M         GENMASK_ULL(31, 28)
0050 #define HISI_PCIE_TARGET_M      GENMASK_ULL(52, 36)
0051 #define HISI_PCIE_TRIG_MODE_M       GENMASK_ULL(53, 53)
0052 #define HISI_PCIE_TRIG_M        GENMASK_ULL(59, 56)
0053 
0054 #define HISI_PCIE_MAX_COUNTERS      8
0055 #define HISI_PCIE_REG_STEP      8
0056 #define HISI_PCIE_THR_MAX_VAL       10
0057 #define HISI_PCIE_TRIG_MAX_VAL      10
0058 #define HISI_PCIE_MAX_PERIOD        (GENMASK_ULL(63, 0))
0059 #define HISI_PCIE_INIT_VAL      BIT_ULL(63)
0060 
0061 struct hisi_pcie_pmu {
0062     struct perf_event *hw_events[HISI_PCIE_MAX_COUNTERS];
0063     struct hlist_node node;
0064     struct pci_dev *pdev;
0065     struct pmu pmu;
0066     void __iomem *base;
0067     int irq;
0068     u32 identifier;
0069     /* Minimum and maximum BDF of root ports monitored by PMU */
0070     u16 bdf_min;
0071     u16 bdf_max;
0072     int on_cpu;
0073 };
0074 
0075 struct hisi_pcie_reg_pair {
0076     u16 lo;
0077     u16 hi;
0078 };
0079 
0080 #define to_pcie_pmu(p)  (container_of((p), struct hisi_pcie_pmu, pmu))
0081 #define GET_PCI_DEVFN(bdf)  ((bdf) & 0xff)
0082 
0083 #define HISI_PCIE_PMU_FILTER_ATTR(_name, _config, _hi, _lo)       \
0084     static u64 hisi_pcie_get_##_name(struct perf_event *event)    \
0085     {                                 \
0086         return FIELD_GET(GENMASK(_hi, _lo), event->attr._config); \
0087     }                                 \
0088 
0089 HISI_PCIE_PMU_FILTER_ATTR(event, config, 16, 0);
0090 HISI_PCIE_PMU_FILTER_ATTR(thr_len, config1, 3, 0);
0091 HISI_PCIE_PMU_FILTER_ATTR(thr_mode, config1, 4, 4);
0092 HISI_PCIE_PMU_FILTER_ATTR(trig_len, config1, 8, 5);
0093 HISI_PCIE_PMU_FILTER_ATTR(trig_mode, config1, 9, 9);
0094 HISI_PCIE_PMU_FILTER_ATTR(port, config2, 15, 0);
0095 HISI_PCIE_PMU_FILTER_ATTR(bdf, config2, 31, 16);
0096 
0097 static ssize_t hisi_pcie_format_sysfs_show(struct device *dev, struct device_attribute *attr,
0098                        char *buf)
0099 {
0100     struct dev_ext_attribute *eattr;
0101 
0102     eattr = container_of(attr, struct dev_ext_attribute, attr);
0103 
0104     return sysfs_emit(buf, "%s\n", (char *)eattr->var);
0105 }
0106 
0107 static ssize_t hisi_pcie_event_sysfs_show(struct device *dev, struct device_attribute *attr,
0108                       char *buf)
0109 {
0110     struct perf_pmu_events_attr *pmu_attr =
0111         container_of(attr, struct perf_pmu_events_attr, attr);
0112 
0113     return sysfs_emit(buf, "config=0x%llx\n", pmu_attr->id);
0114 }
0115 
0116 #define HISI_PCIE_PMU_FORMAT_ATTR(_name, _format)                              \
0117     (&((struct dev_ext_attribute[]){                                       \
0118         { .attr = __ATTR(_name, 0444, hisi_pcie_format_sysfs_show,     \
0119                  NULL),                                        \
0120           .var = (void *)_format }                                     \
0121     })[0].attr.attr)
0122 
0123 #define HISI_PCIE_PMU_EVENT_ATTR(_name, _id)            \
0124     PMU_EVENT_ATTR_ID(_name, hisi_pcie_event_sysfs_show, _id)
0125 
0126 static ssize_t cpumask_show(struct device *dev, struct device_attribute *attr, char *buf)
0127 {
0128     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(dev_get_drvdata(dev));
0129 
0130     return cpumap_print_to_pagebuf(true, buf, cpumask_of(pcie_pmu->on_cpu));
0131 }
0132 static DEVICE_ATTR_RO(cpumask);
0133 
0134 static ssize_t identifier_show(struct device *dev, struct device_attribute *attr, char *buf)
0135 {
0136     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(dev_get_drvdata(dev));
0137 
0138     return sysfs_emit(buf, "%#x\n", pcie_pmu->identifier);
0139 }
0140 static DEVICE_ATTR_RO(identifier);
0141 
0142 static ssize_t bus_show(struct device *dev, struct device_attribute *attr, char *buf)
0143 {
0144     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(dev_get_drvdata(dev));
0145 
0146     return sysfs_emit(buf, "%#04x\n", PCI_BUS_NUM(pcie_pmu->bdf_min));
0147 }
0148 static DEVICE_ATTR_RO(bus);
0149 
0150 static struct hisi_pcie_reg_pair
0151 hisi_pcie_parse_reg_value(struct hisi_pcie_pmu *pcie_pmu, u32 reg_off)
0152 {
0153     u32 val = readl_relaxed(pcie_pmu->base + reg_off);
0154     struct hisi_pcie_reg_pair regs = {
0155         .lo = val,
0156         .hi = val >> 16,
0157     };
0158 
0159     return regs;
0160 }
0161 
0162 /*
0163  * Hardware counter and ext_counter work together for bandwidth, latency, bus
0164  * utilization and buffer occupancy events. For example, RX memory write latency
0165  * events(index = 0x0010), counter counts total delay cycles and ext_counter
0166  * counts RX memory write PCIe packets number.
0167  *
0168  * As we don't want PMU driver to process these two data, "delay cycles" can
0169  * be treated as an independent event(index = 0x0010), "RX memory write packets
0170  * number" as another(index = 0x10010). BIT 16 is used to distinguish and 0-15
0171  * bits are "real" event index, which can be used to set HISI_PCIE_EVENT_CTRL.
0172  */
0173 #define EXT_COUNTER_IS_USED(idx)        ((idx) & BIT(16))
0174 
0175 static u32 hisi_pcie_get_real_event(struct perf_event *event)
0176 {
0177     return hisi_pcie_get_event(event) & GENMASK(15, 0);
0178 }
0179 
0180 static u32 hisi_pcie_pmu_get_offset(u32 offset, u32 idx)
0181 {
0182     return offset + HISI_PCIE_REG_STEP * idx;
0183 }
0184 
0185 static u32 hisi_pcie_pmu_readl(struct hisi_pcie_pmu *pcie_pmu, u32 reg_offset,
0186                    u32 idx)
0187 {
0188     u32 offset = hisi_pcie_pmu_get_offset(reg_offset, idx);
0189 
0190     return readl_relaxed(pcie_pmu->base + offset);
0191 }
0192 
0193 static void hisi_pcie_pmu_writel(struct hisi_pcie_pmu *pcie_pmu, u32 reg_offset, u32 idx, u32 val)
0194 {
0195     u32 offset = hisi_pcie_pmu_get_offset(reg_offset, idx);
0196 
0197     writel_relaxed(val, pcie_pmu->base + offset);
0198 }
0199 
0200 static u64 hisi_pcie_pmu_readq(struct hisi_pcie_pmu *pcie_pmu, u32 reg_offset, u32 idx)
0201 {
0202     u32 offset = hisi_pcie_pmu_get_offset(reg_offset, idx);
0203 
0204     return readq_relaxed(pcie_pmu->base + offset);
0205 }
0206 
0207 static void hisi_pcie_pmu_writeq(struct hisi_pcie_pmu *pcie_pmu, u32 reg_offset, u32 idx, u64 val)
0208 {
0209     u32 offset = hisi_pcie_pmu_get_offset(reg_offset, idx);
0210 
0211     writeq_relaxed(val, pcie_pmu->base + offset);
0212 }
0213 
0214 static void hisi_pcie_pmu_config_filter(struct perf_event *event)
0215 {
0216     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(event->pmu);
0217     struct hw_perf_event *hwc = &event->hw;
0218     u64 reg = HISI_PCIE_INIT_SET;
0219     u64 port, trig_len, thr_len;
0220 
0221     /* Config HISI_PCIE_EVENT_CTRL according to event. */
0222     reg |= FIELD_PREP(HISI_PCIE_EVENT_M, hisi_pcie_get_real_event(event));
0223 
0224     /* Config HISI_PCIE_EVENT_CTRL according to root port or EP device. */
0225     port = hisi_pcie_get_port(event);
0226     if (port)
0227         reg |= FIELD_PREP(HISI_PCIE_TARGET_M, port);
0228     else
0229         reg |= HISI_PCIE_TARGET_EN |
0230                FIELD_PREP(HISI_PCIE_TARGET_M, hisi_pcie_get_bdf(event));
0231 
0232     /* Config HISI_PCIE_EVENT_CTRL according to trigger condition. */
0233     trig_len = hisi_pcie_get_trig_len(event);
0234     if (trig_len) {
0235         reg |= FIELD_PREP(HISI_PCIE_TRIG_M, trig_len);
0236         reg |= FIELD_PREP(HISI_PCIE_TRIG_MODE_M, hisi_pcie_get_trig_mode(event));
0237         reg |= HISI_PCIE_TRIG_EN;
0238     }
0239 
0240     /* Config HISI_PCIE_EVENT_CTRL according to threshold condition. */
0241     thr_len = hisi_pcie_get_thr_len(event);
0242     if (thr_len) {
0243         reg |= FIELD_PREP(HISI_PCIE_THR_M, thr_len);
0244         reg |= FIELD_PREP(HISI_PCIE_THR_MODE_M, hisi_pcie_get_thr_mode(event));
0245         reg |= HISI_PCIE_THR_EN;
0246     }
0247 
0248     hisi_pcie_pmu_writeq(pcie_pmu, HISI_PCIE_EVENT_CTRL, hwc->idx, reg);
0249 }
0250 
0251 static void hisi_pcie_pmu_clear_filter(struct perf_event *event)
0252 {
0253     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(event->pmu);
0254     struct hw_perf_event *hwc = &event->hw;
0255 
0256     hisi_pcie_pmu_writeq(pcie_pmu, HISI_PCIE_EVENT_CTRL, hwc->idx, HISI_PCIE_INIT_SET);
0257 }
0258 
0259 static bool hisi_pcie_pmu_valid_requester_id(struct hisi_pcie_pmu *pcie_pmu, u32 bdf)
0260 {
0261     struct pci_dev *root_port, *pdev;
0262     u16 rp_bdf;
0263 
0264     pdev = pci_get_domain_bus_and_slot(pci_domain_nr(pcie_pmu->pdev->bus), PCI_BUS_NUM(bdf),
0265                        GET_PCI_DEVFN(bdf));
0266     if (!pdev)
0267         return false;
0268 
0269     root_port = pcie_find_root_port(pdev);
0270     if (!root_port) {
0271         pci_dev_put(pdev);
0272         return false;
0273     }
0274 
0275     pci_dev_put(pdev);
0276     rp_bdf = pci_dev_id(root_port);
0277     return rp_bdf >= pcie_pmu->bdf_min && rp_bdf <= pcie_pmu->bdf_max;
0278 }
0279 
0280 static bool hisi_pcie_pmu_valid_filter(struct perf_event *event,
0281                        struct hisi_pcie_pmu *pcie_pmu)
0282 {
0283     u32 requester_id = hisi_pcie_get_bdf(event);
0284 
0285     if (hisi_pcie_get_thr_len(event) > HISI_PCIE_THR_MAX_VAL)
0286         return false;
0287 
0288     if (hisi_pcie_get_trig_len(event) > HISI_PCIE_TRIG_MAX_VAL)
0289         return false;
0290 
0291     if (requester_id) {
0292         if (!hisi_pcie_pmu_valid_requester_id(pcie_pmu, requester_id))
0293             return false;
0294     }
0295 
0296     return true;
0297 }
0298 
0299 static bool hisi_pcie_pmu_cmp_event(struct perf_event *target,
0300                     struct perf_event *event)
0301 {
0302     return hisi_pcie_get_real_event(target) == hisi_pcie_get_real_event(event);
0303 }
0304 
0305 static bool hisi_pcie_pmu_validate_event_group(struct perf_event *event)
0306 {
0307     struct perf_event *sibling, *leader = event->group_leader;
0308     struct perf_event *event_group[HISI_PCIE_MAX_COUNTERS];
0309     int counters = 1;
0310     int num;
0311 
0312     event_group[0] = leader;
0313     if (!is_software_event(leader)) {
0314         if (leader->pmu != event->pmu)
0315             return false;
0316 
0317         if (leader != event && !hisi_pcie_pmu_cmp_event(leader, event))
0318             event_group[counters++] = event;
0319     }
0320 
0321     for_each_sibling_event(sibling, event->group_leader) {
0322         if (is_software_event(sibling))
0323             continue;
0324 
0325         if (sibling->pmu != event->pmu)
0326             return false;
0327 
0328         for (num = 0; num < counters; num++) {
0329             if (hisi_pcie_pmu_cmp_event(event_group[num], sibling))
0330                 break;
0331         }
0332 
0333         if (num == counters)
0334             event_group[counters++] = sibling;
0335     }
0336 
0337     return counters <= HISI_PCIE_MAX_COUNTERS;
0338 }
0339 
0340 static int hisi_pcie_pmu_event_init(struct perf_event *event)
0341 {
0342     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(event->pmu);
0343     struct hw_perf_event *hwc = &event->hw;
0344 
0345     event->cpu = pcie_pmu->on_cpu;
0346 
0347     if (EXT_COUNTER_IS_USED(hisi_pcie_get_event(event)))
0348         hwc->event_base = HISI_PCIE_EXT_CNT;
0349     else
0350         hwc->event_base = HISI_PCIE_CNT;
0351 
0352     if (event->attr.type != event->pmu->type)
0353         return -ENOENT;
0354 
0355     /* Sampling is not supported. */
0356     if (is_sampling_event(event) || event->attach_state & PERF_ATTACH_TASK)
0357         return -EOPNOTSUPP;
0358 
0359     if (!hisi_pcie_pmu_valid_filter(event, pcie_pmu))
0360         return -EINVAL;
0361 
0362     if (!hisi_pcie_pmu_validate_event_group(event))
0363         return -EINVAL;
0364 
0365     return 0;
0366 }
0367 
0368 static u64 hisi_pcie_pmu_read_counter(struct perf_event *event)
0369 {
0370     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(event->pmu);
0371     u32 idx = event->hw.idx;
0372 
0373     return hisi_pcie_pmu_readq(pcie_pmu, event->hw.event_base, idx);
0374 }
0375 
0376 static int hisi_pcie_pmu_find_related_event(struct hisi_pcie_pmu *pcie_pmu,
0377                         struct perf_event *event)
0378 {
0379     struct perf_event *sibling;
0380     int idx;
0381 
0382     for (idx = 0; idx < HISI_PCIE_MAX_COUNTERS; idx++) {
0383         sibling = pcie_pmu->hw_events[idx];
0384         if (!sibling)
0385             continue;
0386 
0387         if (!hisi_pcie_pmu_cmp_event(sibling, event))
0388             continue;
0389 
0390         /* Related events must be used in group */
0391         if (sibling->group_leader == event->group_leader)
0392             return idx;
0393         else
0394             return -EINVAL;
0395     }
0396 
0397     return idx;
0398 }
0399 
0400 static int hisi_pcie_pmu_get_event_idx(struct hisi_pcie_pmu *pcie_pmu)
0401 {
0402     int idx;
0403 
0404     for (idx = 0; idx < HISI_PCIE_MAX_COUNTERS; idx++) {
0405         if (!pcie_pmu->hw_events[idx])
0406             return idx;
0407     }
0408 
0409     return -EINVAL;
0410 }
0411 
0412 static void hisi_pcie_pmu_event_update(struct perf_event *event)
0413 {
0414     struct hw_perf_event *hwc = &event->hw;
0415     u64 new_cnt, prev_cnt, delta;
0416 
0417     do {
0418         prev_cnt = local64_read(&hwc->prev_count);
0419         new_cnt = hisi_pcie_pmu_read_counter(event);
0420     } while (local64_cmpxchg(&hwc->prev_count, prev_cnt,
0421                  new_cnt) != prev_cnt);
0422 
0423     delta = (new_cnt - prev_cnt) & HISI_PCIE_MAX_PERIOD;
0424     local64_add(delta, &event->count);
0425 }
0426 
0427 static void hisi_pcie_pmu_read(struct perf_event *event)
0428 {
0429     hisi_pcie_pmu_event_update(event);
0430 }
0431 
0432 static void hisi_pcie_pmu_set_period(struct perf_event *event)
0433 {
0434     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(event->pmu);
0435     struct hw_perf_event *hwc = &event->hw;
0436     int idx = hwc->idx;
0437 
0438     local64_set(&hwc->prev_count, HISI_PCIE_INIT_VAL);
0439     hisi_pcie_pmu_writeq(pcie_pmu, HISI_PCIE_CNT, idx, HISI_PCIE_INIT_VAL);
0440     hisi_pcie_pmu_writeq(pcie_pmu, HISI_PCIE_EXT_CNT, idx, HISI_PCIE_INIT_VAL);
0441 }
0442 
0443 static void hisi_pcie_pmu_enable_counter(struct hisi_pcie_pmu *pcie_pmu, struct hw_perf_event *hwc)
0444 {
0445     u32 idx = hwc->idx;
0446     u64 val;
0447 
0448     val = hisi_pcie_pmu_readq(pcie_pmu, HISI_PCIE_EVENT_CTRL, idx);
0449     val |= HISI_PCIE_EVENT_EN;
0450     hisi_pcie_pmu_writeq(pcie_pmu, HISI_PCIE_EVENT_CTRL, idx, val);
0451 }
0452 
0453 static void hisi_pcie_pmu_disable_counter(struct hisi_pcie_pmu *pcie_pmu, struct hw_perf_event *hwc)
0454 {
0455     u32 idx = hwc->idx;
0456     u64 val;
0457 
0458     val = hisi_pcie_pmu_readq(pcie_pmu, HISI_PCIE_EVENT_CTRL, idx);
0459     val &= ~HISI_PCIE_EVENT_EN;
0460     hisi_pcie_pmu_writeq(pcie_pmu, HISI_PCIE_EVENT_CTRL, idx, val);
0461 }
0462 
0463 static void hisi_pcie_pmu_enable_int(struct hisi_pcie_pmu *pcie_pmu, struct hw_perf_event *hwc)
0464 {
0465     u32 idx = hwc->idx;
0466 
0467     hisi_pcie_pmu_writel(pcie_pmu, HISI_PCIE_INT_MASK, idx, 0);
0468 }
0469 
0470 static void hisi_pcie_pmu_disable_int(struct hisi_pcie_pmu *pcie_pmu, struct hw_perf_event *hwc)
0471 {
0472     u32 idx = hwc->idx;
0473 
0474     hisi_pcie_pmu_writel(pcie_pmu, HISI_PCIE_INT_MASK, idx, 1);
0475 }
0476 
0477 static void hisi_pcie_pmu_reset_counter(struct hisi_pcie_pmu *pcie_pmu, int idx)
0478 {
0479     hisi_pcie_pmu_writeq(pcie_pmu, HISI_PCIE_EVENT_CTRL, idx, HISI_PCIE_RESET_CNT);
0480     hisi_pcie_pmu_writeq(pcie_pmu, HISI_PCIE_EVENT_CTRL, idx, HISI_PCIE_INIT_SET);
0481 }
0482 
0483 static void hisi_pcie_pmu_start(struct perf_event *event, int flags)
0484 {
0485     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(event->pmu);
0486     struct hw_perf_event *hwc = &event->hw;
0487     int idx = hwc->idx;
0488     u64 prev_cnt;
0489 
0490     if (WARN_ON_ONCE(!(hwc->state & PERF_HES_STOPPED)))
0491         return;
0492 
0493     WARN_ON_ONCE(!(hwc->state & PERF_HES_UPTODATE));
0494     hwc->state = 0;
0495 
0496     hisi_pcie_pmu_config_filter(event);
0497     hisi_pcie_pmu_enable_counter(pcie_pmu, hwc);
0498     hisi_pcie_pmu_enable_int(pcie_pmu, hwc);
0499     hisi_pcie_pmu_set_period(event);
0500 
0501     if (flags & PERF_EF_RELOAD) {
0502         prev_cnt = local64_read(&hwc->prev_count);
0503         hisi_pcie_pmu_writeq(pcie_pmu, hwc->event_base, idx, prev_cnt);
0504     }
0505 
0506     perf_event_update_userpage(event);
0507 }
0508 
0509 static void hisi_pcie_pmu_stop(struct perf_event *event, int flags)
0510 {
0511     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(event->pmu);
0512     struct hw_perf_event *hwc = &event->hw;
0513 
0514     hisi_pcie_pmu_event_update(event);
0515     hisi_pcie_pmu_disable_int(pcie_pmu, hwc);
0516     hisi_pcie_pmu_disable_counter(pcie_pmu, hwc);
0517     hisi_pcie_pmu_clear_filter(event);
0518     WARN_ON_ONCE(hwc->state & PERF_HES_STOPPED);
0519     hwc->state |= PERF_HES_STOPPED;
0520 
0521     if (hwc->state & PERF_HES_UPTODATE)
0522         return;
0523 
0524     hwc->state |= PERF_HES_UPTODATE;
0525 }
0526 
0527 static int hisi_pcie_pmu_add(struct perf_event *event, int flags)
0528 {
0529     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(event->pmu);
0530     struct hw_perf_event *hwc = &event->hw;
0531     int idx;
0532 
0533     hwc->state = PERF_HES_STOPPED | PERF_HES_UPTODATE;
0534 
0535     /* Check all working events to find a related event. */
0536     idx = hisi_pcie_pmu_find_related_event(pcie_pmu, event);
0537     if (idx < 0)
0538         return idx;
0539 
0540     /* Current event shares an enabled counter with the related event */
0541     if (idx < HISI_PCIE_MAX_COUNTERS) {
0542         hwc->idx = idx;
0543         goto start_count;
0544     }
0545 
0546     idx = hisi_pcie_pmu_get_event_idx(pcie_pmu);
0547     if (idx < 0)
0548         return idx;
0549 
0550     hwc->idx = idx;
0551     pcie_pmu->hw_events[idx] = event;
0552     /* Reset Counter to avoid previous statistic interference. */
0553     hisi_pcie_pmu_reset_counter(pcie_pmu, idx);
0554 
0555 start_count:
0556     if (flags & PERF_EF_START)
0557         hisi_pcie_pmu_start(event, PERF_EF_RELOAD);
0558 
0559     return 0;
0560 }
0561 
0562 static void hisi_pcie_pmu_del(struct perf_event *event, int flags)
0563 {
0564     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(event->pmu);
0565     struct hw_perf_event *hwc = &event->hw;
0566 
0567     hisi_pcie_pmu_stop(event, PERF_EF_UPDATE);
0568     pcie_pmu->hw_events[hwc->idx] = NULL;
0569     perf_event_update_userpage(event);
0570 }
0571 
0572 static void hisi_pcie_pmu_enable(struct pmu *pmu)
0573 {
0574     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(pmu);
0575     int num;
0576 
0577     for (num = 0; num < HISI_PCIE_MAX_COUNTERS; num++) {
0578         if (pcie_pmu->hw_events[num])
0579             break;
0580     }
0581 
0582     if (num == HISI_PCIE_MAX_COUNTERS)
0583         return;
0584 
0585     writel(HISI_PCIE_GLOBAL_EN, pcie_pmu->base + HISI_PCIE_GLOBAL_CTRL);
0586 }
0587 
0588 static void hisi_pcie_pmu_disable(struct pmu *pmu)
0589 {
0590     struct hisi_pcie_pmu *pcie_pmu = to_pcie_pmu(pmu);
0591 
0592     writel(HISI_PCIE_GLOBAL_NONE, pcie_pmu->base + HISI_PCIE_GLOBAL_CTRL);
0593 }
0594 
0595 static irqreturn_t hisi_pcie_pmu_irq(int irq, void *data)
0596 {
0597     struct hisi_pcie_pmu *pcie_pmu = data;
0598     irqreturn_t ret = IRQ_NONE;
0599     struct perf_event *event;
0600     u32 overflown;
0601     int idx;
0602 
0603     for (idx = 0; idx < HISI_PCIE_MAX_COUNTERS; idx++) {
0604         overflown = hisi_pcie_pmu_readl(pcie_pmu, HISI_PCIE_INT_STAT, idx);
0605         if (!overflown)
0606             continue;
0607 
0608         /* Clear status of interrupt. */
0609         hisi_pcie_pmu_writel(pcie_pmu, HISI_PCIE_INT_STAT, idx, 1);
0610         event = pcie_pmu->hw_events[idx];
0611         if (!event)
0612             continue;
0613 
0614         hisi_pcie_pmu_event_update(event);
0615         hisi_pcie_pmu_set_period(event);
0616         ret = IRQ_HANDLED;
0617     }
0618 
0619     return ret;
0620 }
0621 
0622 static int hisi_pcie_pmu_irq_register(struct pci_dev *pdev, struct hisi_pcie_pmu *pcie_pmu)
0623 {
0624     int irq, ret;
0625 
0626     ret = pci_alloc_irq_vectors(pdev, 1, 1, PCI_IRQ_MSI);
0627     if (ret < 0) {
0628         pci_err(pdev, "Failed to enable MSI vectors: %d\n", ret);
0629         return ret;
0630     }
0631 
0632     irq = pci_irq_vector(pdev, 0);
0633     ret = request_irq(irq, hisi_pcie_pmu_irq, IRQF_NOBALANCING | IRQF_NO_THREAD, DRV_NAME,
0634               pcie_pmu);
0635     if (ret) {
0636         pci_err(pdev, "Failed to register IRQ: %d\n", ret);
0637         pci_free_irq_vectors(pdev);
0638         return ret;
0639     }
0640 
0641     pcie_pmu->irq = irq;
0642 
0643     return 0;
0644 }
0645 
0646 static void hisi_pcie_pmu_irq_unregister(struct pci_dev *pdev, struct hisi_pcie_pmu *pcie_pmu)
0647 {
0648     free_irq(pcie_pmu->irq, pcie_pmu);
0649     pci_free_irq_vectors(pdev);
0650 }
0651 
0652 static int hisi_pcie_pmu_online_cpu(unsigned int cpu, struct hlist_node *node)
0653 {
0654     struct hisi_pcie_pmu *pcie_pmu = hlist_entry_safe(node, struct hisi_pcie_pmu, node);
0655 
0656     if (pcie_pmu->on_cpu == -1) {
0657         pcie_pmu->on_cpu = cpu;
0658         WARN_ON(irq_set_affinity(pcie_pmu->irq, cpumask_of(cpu)));
0659     }
0660 
0661     return 0;
0662 }
0663 
0664 static int hisi_pcie_pmu_offline_cpu(unsigned int cpu, struct hlist_node *node)
0665 {
0666     struct hisi_pcie_pmu *pcie_pmu = hlist_entry_safe(node, struct hisi_pcie_pmu, node);
0667     unsigned int target;
0668 
0669     /* Nothing to do if this CPU doesn't own the PMU */
0670     if (pcie_pmu->on_cpu != cpu)
0671         return 0;
0672 
0673     pcie_pmu->on_cpu = -1;
0674     /* Choose a new CPU from all online cpus. */
0675     target = cpumask_first(cpu_online_mask);
0676     if (target >= nr_cpu_ids) {
0677         pci_err(pcie_pmu->pdev, "There is no CPU to set\n");
0678         return 0;
0679     }
0680 
0681     perf_pmu_migrate_context(&pcie_pmu->pmu, cpu, target);
0682     /* Use this CPU for event counting */
0683     pcie_pmu->on_cpu = target;
0684     WARN_ON(irq_set_affinity(pcie_pmu->irq, cpumask_of(target)));
0685 
0686     return 0;
0687 }
0688 
0689 static struct attribute *hisi_pcie_pmu_events_attr[] = {
0690     HISI_PCIE_PMU_EVENT_ATTR(rx_mwr_latency, 0x0010),
0691     HISI_PCIE_PMU_EVENT_ATTR(rx_mwr_cnt, 0x10010),
0692     HISI_PCIE_PMU_EVENT_ATTR(rx_mrd_latency, 0x0210),
0693     HISI_PCIE_PMU_EVENT_ATTR(rx_mrd_cnt, 0x10210),
0694     HISI_PCIE_PMU_EVENT_ATTR(tx_mrd_latency, 0x0011),
0695     HISI_PCIE_PMU_EVENT_ATTR(tx_mrd_cnt, 0x10011),
0696     HISI_PCIE_PMU_EVENT_ATTR(rx_mrd_flux, 0x1005),
0697     HISI_PCIE_PMU_EVENT_ATTR(rx_mrd_time, 0x11005),
0698     HISI_PCIE_PMU_EVENT_ATTR(tx_mrd_flux, 0x2004),
0699     HISI_PCIE_PMU_EVENT_ATTR(tx_mrd_time, 0x12004),
0700     NULL
0701 };
0702 
0703 static struct attribute_group hisi_pcie_pmu_events_group = {
0704     .name = "events",
0705     .attrs = hisi_pcie_pmu_events_attr,
0706 };
0707 
0708 static struct attribute *hisi_pcie_pmu_format_attr[] = {
0709     HISI_PCIE_PMU_FORMAT_ATTR(event, "config:0-16"),
0710     HISI_PCIE_PMU_FORMAT_ATTR(thr_len, "config1:0-3"),
0711     HISI_PCIE_PMU_FORMAT_ATTR(thr_mode, "config1:4"),
0712     HISI_PCIE_PMU_FORMAT_ATTR(trig_len, "config1:5-8"),
0713     HISI_PCIE_PMU_FORMAT_ATTR(trig_mode, "config1:9"),
0714     HISI_PCIE_PMU_FORMAT_ATTR(port, "config2:0-15"),
0715     HISI_PCIE_PMU_FORMAT_ATTR(bdf, "config2:16-31"),
0716     NULL
0717 };
0718 
0719 static const struct attribute_group hisi_pcie_pmu_format_group = {
0720     .name = "format",
0721     .attrs = hisi_pcie_pmu_format_attr,
0722 };
0723 
0724 static struct attribute *hisi_pcie_pmu_bus_attrs[] = {
0725     &dev_attr_bus.attr,
0726     NULL
0727 };
0728 
0729 static const struct attribute_group hisi_pcie_pmu_bus_attr_group = {
0730     .attrs = hisi_pcie_pmu_bus_attrs,
0731 };
0732 
0733 static struct attribute *hisi_pcie_pmu_cpumask_attrs[] = {
0734     &dev_attr_cpumask.attr,
0735     NULL
0736 };
0737 
0738 static const struct attribute_group hisi_pcie_pmu_cpumask_attr_group = {
0739     .attrs = hisi_pcie_pmu_cpumask_attrs,
0740 };
0741 
0742 static struct attribute *hisi_pcie_pmu_identifier_attrs[] = {
0743     &dev_attr_identifier.attr,
0744     NULL
0745 };
0746 
0747 static const struct attribute_group hisi_pcie_pmu_identifier_attr_group = {
0748     .attrs = hisi_pcie_pmu_identifier_attrs,
0749 };
0750 
0751 static const struct attribute_group *hisi_pcie_pmu_attr_groups[] = {
0752     &hisi_pcie_pmu_events_group,
0753     &hisi_pcie_pmu_format_group,
0754     &hisi_pcie_pmu_bus_attr_group,
0755     &hisi_pcie_pmu_cpumask_attr_group,
0756     &hisi_pcie_pmu_identifier_attr_group,
0757     NULL
0758 };
0759 
0760 static int hisi_pcie_alloc_pmu(struct pci_dev *pdev, struct hisi_pcie_pmu *pcie_pmu)
0761 {
0762     struct hisi_pcie_reg_pair regs;
0763     u16 sicl_id, core_id;
0764     char *name;
0765 
0766     regs = hisi_pcie_parse_reg_value(pcie_pmu, HISI_PCIE_REG_BDF);
0767     pcie_pmu->bdf_min = regs.lo;
0768     pcie_pmu->bdf_max = regs.hi;
0769 
0770     regs = hisi_pcie_parse_reg_value(pcie_pmu, HISI_PCIE_REG_INFO);
0771     sicl_id = regs.hi;
0772     core_id = regs.lo;
0773 
0774     name = devm_kasprintf(&pdev->dev, GFP_KERNEL, "hisi_pcie%u_core%u", sicl_id, core_id);
0775     if (!name)
0776         return -ENOMEM;
0777 
0778     pcie_pmu->pdev = pdev;
0779     pcie_pmu->on_cpu = -1;
0780     pcie_pmu->identifier = readl(pcie_pmu->base + HISI_PCIE_REG_VERSION);
0781     pcie_pmu->pmu = (struct pmu) {
0782         .name       = name,
0783         .module     = THIS_MODULE,
0784         .event_init = hisi_pcie_pmu_event_init,
0785         .pmu_enable = hisi_pcie_pmu_enable,
0786         .pmu_disable    = hisi_pcie_pmu_disable,
0787         .add        = hisi_pcie_pmu_add,
0788         .del        = hisi_pcie_pmu_del,
0789         .start      = hisi_pcie_pmu_start,
0790         .stop       = hisi_pcie_pmu_stop,
0791         .read       = hisi_pcie_pmu_read,
0792         .task_ctx_nr    = perf_invalid_context,
0793         .attr_groups    = hisi_pcie_pmu_attr_groups,
0794         .capabilities   = PERF_PMU_CAP_NO_EXCLUDE,
0795     };
0796 
0797     return 0;
0798 }
0799 
0800 static int hisi_pcie_init_pmu(struct pci_dev *pdev, struct hisi_pcie_pmu *pcie_pmu)
0801 {
0802     int ret;
0803 
0804     pcie_pmu->base = pci_ioremap_bar(pdev, 2);
0805     if (!pcie_pmu->base) {
0806         pci_err(pdev, "Ioremap failed for pcie_pmu resource\n");
0807         return -ENOMEM;
0808     }
0809 
0810     ret = hisi_pcie_alloc_pmu(pdev, pcie_pmu);
0811     if (ret)
0812         goto err_iounmap;
0813 
0814     ret = hisi_pcie_pmu_irq_register(pdev, pcie_pmu);
0815     if (ret)
0816         goto err_iounmap;
0817 
0818     ret = cpuhp_state_add_instance(CPUHP_AP_PERF_ARM_HISI_PCIE_PMU_ONLINE, &pcie_pmu->node);
0819     if (ret) {
0820         pci_err(pdev, "Failed to register hotplug: %d\n", ret);
0821         goto err_irq_unregister;
0822     }
0823 
0824     ret = perf_pmu_register(&pcie_pmu->pmu, pcie_pmu->pmu.name, -1);
0825     if (ret) {
0826         pci_err(pdev, "Failed to register PCIe PMU: %d\n", ret);
0827         goto err_hotplug_unregister;
0828     }
0829 
0830     return ret;
0831 
0832 err_hotplug_unregister:
0833     cpuhp_state_remove_instance_nocalls(
0834         CPUHP_AP_PERF_ARM_HISI_PCIE_PMU_ONLINE, &pcie_pmu->node);
0835 
0836 err_irq_unregister:
0837     hisi_pcie_pmu_irq_unregister(pdev, pcie_pmu);
0838 
0839 err_iounmap:
0840     iounmap(pcie_pmu->base);
0841 
0842     return ret;
0843 }
0844 
0845 static void hisi_pcie_uninit_pmu(struct pci_dev *pdev)
0846 {
0847     struct hisi_pcie_pmu *pcie_pmu = pci_get_drvdata(pdev);
0848 
0849     perf_pmu_unregister(&pcie_pmu->pmu);
0850     cpuhp_state_remove_instance_nocalls(
0851         CPUHP_AP_PERF_ARM_HISI_PCIE_PMU_ONLINE, &pcie_pmu->node);
0852     hisi_pcie_pmu_irq_unregister(pdev, pcie_pmu);
0853     iounmap(pcie_pmu->base);
0854 }
0855 
0856 static int hisi_pcie_init_dev(struct pci_dev *pdev)
0857 {
0858     int ret;
0859 
0860     ret = pcim_enable_device(pdev);
0861     if (ret) {
0862         pci_err(pdev, "Failed to enable PCI device: %d\n", ret);
0863         return ret;
0864     }
0865 
0866     ret = pcim_iomap_regions(pdev, BIT(2), DRV_NAME);
0867     if (ret < 0) {
0868         pci_err(pdev, "Failed to request PCI mem regions: %d\n", ret);
0869         return ret;
0870     }
0871 
0872     pci_set_master(pdev);
0873 
0874     return 0;
0875 }
0876 
0877 static int hisi_pcie_pmu_probe(struct pci_dev *pdev, const struct pci_device_id *id)
0878 {
0879     struct hisi_pcie_pmu *pcie_pmu;
0880     int ret;
0881 
0882     pcie_pmu = devm_kzalloc(&pdev->dev, sizeof(*pcie_pmu), GFP_KERNEL);
0883     if (!pcie_pmu)
0884         return -ENOMEM;
0885 
0886     ret = hisi_pcie_init_dev(pdev);
0887     if (ret)
0888         return ret;
0889 
0890     ret = hisi_pcie_init_pmu(pdev, pcie_pmu);
0891     if (ret)
0892         return ret;
0893 
0894     pci_set_drvdata(pdev, pcie_pmu);
0895 
0896     return ret;
0897 }
0898 
0899 static void hisi_pcie_pmu_remove(struct pci_dev *pdev)
0900 {
0901     hisi_pcie_uninit_pmu(pdev);
0902     pci_set_drvdata(pdev, NULL);
0903 }
0904 
0905 static const struct pci_device_id hisi_pcie_pmu_ids[] = {
0906     { PCI_DEVICE(PCI_VENDOR_ID_HUAWEI, 0xa12d) },
0907     { 0, }
0908 };
0909 MODULE_DEVICE_TABLE(pci, hisi_pcie_pmu_ids);
0910 
0911 static struct pci_driver hisi_pcie_pmu_driver = {
0912     .name = DRV_NAME,
0913     .id_table = hisi_pcie_pmu_ids,
0914     .probe = hisi_pcie_pmu_probe,
0915     .remove = hisi_pcie_pmu_remove,
0916 };
0917 
0918 static int __init hisi_pcie_module_init(void)
0919 {
0920     int ret;
0921 
0922     ret = cpuhp_setup_state_multi(CPUHP_AP_PERF_ARM_HISI_PCIE_PMU_ONLINE,
0923                       "AP_PERF_ARM_HISI_PCIE_PMU_ONLINE",
0924                       hisi_pcie_pmu_online_cpu,
0925                       hisi_pcie_pmu_offline_cpu);
0926     if (ret) {
0927         pr_err("Failed to setup PCIe PMU hotplug: %d\n", ret);
0928         return ret;
0929     }
0930 
0931     ret = pci_register_driver(&hisi_pcie_pmu_driver);
0932     if (ret)
0933         cpuhp_remove_multi_state(CPUHP_AP_PERF_ARM_HISI_PCIE_PMU_ONLINE);
0934 
0935     return ret;
0936 }
0937 module_init(hisi_pcie_module_init);
0938 
0939 static void __exit hisi_pcie_module_exit(void)
0940 {
0941     pci_unregister_driver(&hisi_pcie_pmu_driver);
0942     cpuhp_remove_multi_state(CPUHP_AP_PERF_ARM_HISI_PCIE_PMU_ONLINE);
0943 }
0944 module_exit(hisi_pcie_module_exit);
0945 
0946 MODULE_DESCRIPTION("HiSilicon PCIe PMU driver");
0947 MODULE_LICENSE("GPL v2");
0948 MODULE_AUTHOR("Qi Liu <liuqi115@huawei.com>");