|
49 | 49 | #include <linux/log2.h>
|
50 | 50 | #include <linux/aer.h>
|
51 | 51 | #include <linux/bitmap.h>
|
| 52 | +#include <linux/ptp_clock_kernel.h> |
| 53 | +#include <linux/timecounter.h> |
52 | 54 | #include <linux/cpu_rmap.h>
|
53 | 55 | #include <linux/cpumask.h>
|
54 | 56 | #include <net/pkt_cls.h>
|
|
63 | 65 | #include "bnxt_ethtool.h"
|
64 | 66 | #include "bnxt_dcb.h"
|
65 | 67 | #include "bnxt_xdp.h"
|
| 68 | +#include "bnxt_ptp.h" |
66 | 69 | #include "bnxt_vfr.h"
|
67 | 70 | #include "bnxt_tc.h"
|
68 | 71 | #include "bnxt_devlink.h"
|
@@ -7391,6 +7394,56 @@ int bnxt_hwrm_func_resc_qcaps(struct bnxt *bp, bool all)
|
7391 | 7394 | return rc;
|
7392 | 7395 | }
|
7393 | 7396 |
|
| 7397 | +/* bp->hwrm_cmd_lock already held. */ |
| 7398 | +static int __bnxt_hwrm_ptp_qcfg(struct bnxt *bp) |
| 7399 | +{ |
| 7400 | + struct hwrm_port_mac_ptp_qcfg_output *resp = bp->hwrm_cmd_resp_addr; |
| 7401 | + struct hwrm_port_mac_ptp_qcfg_input req = {0}; |
| 7402 | + struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; |
| 7403 | + u8 flags; |
| 7404 | + int rc; |
| 7405 | + |
| 7406 | + if (bp->hwrm_spec_code < 0x10801) { |
| 7407 | + rc = -ENODEV; |
| 7408 | + goto no_ptp; |
| 7409 | + } |
| 7410 | + |
| 7411 | + req.port_id = cpu_to_le16(bp->pf.port_id); |
| 7412 | + bnxt_hwrm_cmd_hdr_init(bp, &req, HWRM_PORT_MAC_PTP_QCFG, -1, -1); |
| 7413 | + rc = _hwrm_send_message(bp, &req, sizeof(req), HWRM_CMD_TIMEOUT); |
| 7414 | + if (rc) |
| 7415 | + goto no_ptp; |
| 7416 | + |
| 7417 | + flags = resp->flags; |
| 7418 | + if (!(flags & PORT_MAC_PTP_QCFG_RESP_FLAGS_HWRM_ACCESS)) { |
| 7419 | + rc = -ENODEV; |
| 7420 | + goto no_ptp; |
| 7421 | + } |
| 7422 | + if (!ptp) { |
| 7423 | + ptp = kzalloc(sizeof(*ptp), GFP_KERNEL); |
| 7424 | + if (!ptp) |
| 7425 | + return -ENOMEM; |
| 7426 | + ptp->bp = bp; |
| 7427 | + bp->ptp_cfg = ptp; |
| 7428 | + } |
| 7429 | + if (flags & PORT_MAC_PTP_QCFG_RESP_FLAGS_PARTIAL_DIRECT_ACCESS_REF_CLOCK) { |
| 7430 | + ptp->refclk_regs[0] = le32_to_cpu(resp->ts_ref_clock_reg_lower); |
| 7431 | + ptp->refclk_regs[1] = le32_to_cpu(resp->ts_ref_clock_reg_upper); |
| 7432 | + } else if (bp->flags & BNXT_FLAG_CHIP_P5) { |
| 7433 | + ptp->refclk_regs[0] = BNXT_TS_REG_TIMESYNC_TS0_LOWER; |
| 7434 | + ptp->refclk_regs[1] = BNXT_TS_REG_TIMESYNC_TS0_UPPER; |
| 7435 | + } else { |
| 7436 | + rc = -ENODEV; |
| 7437 | + goto no_ptp; |
| 7438 | + } |
| 7439 | + return 0; |
| 7440 | + |
| 7441 | +no_ptp: |
| 7442 | + kfree(ptp); |
| 7443 | + bp->ptp_cfg = NULL; |
| 7444 | + return rc; |
| 7445 | +} |
| 7446 | + |
7394 | 7447 | static int __bnxt_hwrm_func_qcaps(struct bnxt *bp)
|
7395 | 7448 | {
|
7396 | 7449 | int rc = 0;
|
@@ -7462,6 +7515,8 @@ static int __bnxt_hwrm_func_qcaps(struct bnxt *bp)
|
7462 | 7515 | bp->flags &= ~BNXT_FLAG_WOL_CAP;
|
7463 | 7516 | if (flags & FUNC_QCAPS_RESP_FLAGS_WOL_MAGICPKT_SUPPORTED)
|
7464 | 7517 | bp->flags |= BNXT_FLAG_WOL_CAP;
|
| 7518 | + if (flags & FUNC_QCAPS_RESP_FLAGS_PTP_SUPPORTED) |
| 7519 | + __bnxt_hwrm_ptp_qcfg(bp); |
7465 | 7520 | } else {
|
7466 | 7521 | #ifdef CONFIG_BNXT_SRIOV
|
7467 | 7522 | struct bnxt_vf_info *vf = &bp->vf;
|
@@ -12571,6 +12626,8 @@ static void bnxt_remove_one(struct pci_dev *pdev)
|
12571 | 12626 | bnxt_dcb_free(bp);
|
12572 | 12627 | kfree(bp->edev);
|
12573 | 12628 | bp->edev = NULL;
|
| 12629 | + kfree(bp->ptp_cfg); |
| 12630 | + bp->ptp_cfg = NULL; |
12574 | 12631 | kfree(bp->fw_health);
|
12575 | 12632 | bp->fw_health = NULL;
|
12576 | 12633 | bnxt_cleanup_pci(bp);
|
@@ -13161,6 +13218,8 @@ static int bnxt_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
|
13161 | 13218 | bnxt_free_hwrm_short_cmd_req(bp);
|
13162 | 13219 | bnxt_free_hwrm_resources(bp);
|
13163 | 13220 | bnxt_ethtool_free(bp);
|
| 13221 | + kfree(bp->ptp_cfg); |
| 13222 | + bp->ptp_cfg = NULL; |
13164 | 13223 | kfree(bp->fw_health);
|
13165 | 13224 | bp->fw_health = NULL;
|
13166 | 13225 | bnxt_cleanup_pci(bp);
|
|
0 commit comments