net/nfp: remove compile time log
[dpdk.git] / drivers / net / hns3 / hns3_ptp.c
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright(c) 2021-2021 Hisilicon Limited.
3  */
4
5 #include <ethdev_pci.h>
6 #include <rte_io.h>
7 #include <rte_time.h>
8
9 #include "hns3_ethdev.h"
10 #include "hns3_regs.h"
11 #include "hns3_logs.h"
12
13 uint64_t hns3_timestamp_rx_dynflag;
14 int hns3_timestamp_dynfield_offset = -1;
15
16 int
17 hns3_mbuf_dyn_rx_timestamp_register(struct rte_eth_dev *dev,
18                                     struct rte_eth_conf *conf)
19 {
20         struct hns3_adapter *hns = dev->data->dev_private;
21         struct hns3_hw *hw = &hns->hw;
22         int ret;
23
24         if (!(conf->rxmode.offloads & DEV_RX_OFFLOAD_TIMESTAMP))
25                 return 0;
26
27         ret = rte_mbuf_dyn_rx_timestamp_register
28                         (&hns3_timestamp_dynfield_offset,
29                          &hns3_timestamp_rx_dynflag);
30         if (ret) {
31                 hns3_err(hw,
32                         "failed to register Rx timestamp field/flag");
33                 return ret;
34         }
35
36         return 0;
37 }
38
39 static int
40 hns3_ptp_int_en(struct hns3_hw *hw, bool en)
41 {
42         struct hns3_ptp_int_cmd *req;
43         struct hns3_cmd_desc desc;
44         int ret;
45
46         req = (struct hns3_ptp_int_cmd *)desc.data;
47         hns3_cmd_setup_basic_desc(&desc, HNS3_OPC_PTP_INT_EN, false);
48         req->int_en = en ? 1 : 0;
49
50         ret = hns3_cmd_send(hw, &desc, 1);
51         if (ret)
52                 hns3_err(hw,
53                         "failed to %s ptp interrupt, ret = %d\n",
54                         en ? "enable" : "disable", ret);
55
56         return ret;
57 }
58
59 int
60 hns3_ptp_init(struct hns3_hw *hw)
61 {
62         int ret;
63
64         if (!hns3_dev_ptp_supported(hw))
65                 return 0;
66
67         ret = hns3_ptp_int_en(hw, true);
68         if (ret)
69                 return ret;
70
71         /* Start PTP timer */
72         hns3_write_dev(hw, HNS3_CFG_TIME_CYC_EN, 1);
73
74         return 0;
75 }
76
77 static int
78 hns3_timesync_configure(struct hns3_adapter *hns, bool en)
79 {
80         struct hns3_ptp_mode_cfg_cmd *req;
81         struct hns3_hw *hw = &hns->hw;
82         struct hns3_pf *pf = &hns->pf;
83         struct hns3_cmd_desc desc;
84         int val;
85         int ret;
86
87         hns3_cmd_setup_basic_desc(&desc, HNS3_OPC_CFG_PTP_MODE, false);
88
89         req = (struct hns3_ptp_mode_cfg_cmd *)desc.data;
90
91         val = en ? 1 : 0;
92         hns3_set_bit(req->enable, HNS3_PTP_ENABLE_B, val);
93         hns3_set_bit(req->enable, HNS3_PTP_TX_ENABLE_B, val);
94         hns3_set_bit(req->enable, HNS3_PTP_RX_ENABLE_B, val);
95
96         if (en) {
97                 hns3_set_field(req->ptp_type, HNS3_PTP_TYPE_M, HNS3_PTP_TYPE_S,
98                                PTP_TYPE_L2_V2_TYPE);
99                 hns3_set_field(req->v2_message_type_1, HNS3_PTP_MESSAGE_TYPE_M,
100                                HNS3_PTP_MESSAGE_TYPE_S, ALL_PTP_V2_TYPE);
101         }
102
103         ret = hns3_cmd_send(hw, &desc, 1);
104         if (ret) {
105                 hns3_err(hw, "configure PTP time failed, en = %d, ret = %d",
106                          en, ret);
107                 return ret;
108         }
109
110         pf->ptp_enable = en;
111
112         return 0;
113 }
114
115 int
116 hns3_timesync_enable(struct rte_eth_dev *dev)
117 {
118         struct hns3_adapter *hns = dev->data->dev_private;
119         struct hns3_hw *hw = &hns->hw;
120         struct hns3_pf *pf = &hns->pf;
121         int ret;
122
123         if (!hns3_dev_ptp_supported(hw))
124                 return -ENOTSUP;
125
126         if (pf->ptp_enable)
127                 return 0;
128
129         rte_spinlock_lock(&hw->lock);
130         ret = hns3_timesync_configure(hns, true);
131         rte_spinlock_unlock(&hw->lock);
132         return ret;
133 }
134
135 int
136 hns3_timesync_disable(struct rte_eth_dev *dev)
137 {
138         struct hns3_adapter *hns = dev->data->dev_private;
139         struct hns3_hw *hw = &hns->hw;
140         struct hns3_pf *pf = &hns->pf;
141         int ret;
142
143         if (!hns3_dev_ptp_supported(hw))
144                 return -ENOTSUP;
145
146         if (!pf->ptp_enable)
147                 return 0;
148
149         rte_spinlock_lock(&hw->lock);
150         ret = hns3_timesync_configure(hns, false);
151         rte_spinlock_unlock(&hw->lock);
152
153         return ret;
154 }
155
156 int
157 hns3_timesync_read_rx_timestamp(struct rte_eth_dev *dev,
158                                 struct timespec *timestamp,
159                                 uint32_t flags __rte_unused)
160 {
161 #define TIME_RX_STAMP_NS_MASK 0x3FFFFFFF
162         struct hns3_adapter *hns = dev->data->dev_private;
163         struct hns3_hw *hw = &hns->hw;
164         struct hns3_pf *pf = &hns->pf;
165         uint64_t ns, sec;
166
167         if (!hns3_dev_ptp_supported(hw))
168                 return -ENOTSUP;
169
170         ns = pf->rx_timestamp & TIME_RX_STAMP_NS_MASK;
171         sec = upper_32_bits(pf->rx_timestamp);
172
173         ns += sec * NSEC_PER_SEC;
174         *timestamp = rte_ns_to_timespec(ns);
175
176         return 0;
177 }
178
179 int
180 hns3_timesync_read_tx_timestamp(struct rte_eth_dev *dev,
181                                 struct timespec *timestamp)
182 {
183 #define TIME_TX_STAMP_NS_MASK 0x3FFFFFFF
184 #define TIME_TX_STAMP_VALID   24
185 #define TIME_TX_STAMP_CNT_MASK 0x7
186         struct hns3_adapter *hns = dev->data->dev_private;
187         struct hns3_hw *hw = &hns->hw;
188         uint64_t sec;
189         uint64_t tmp;
190         uint64_t ns;
191         int ts_cnt;
192
193         if (!hns3_dev_ptp_supported(hw))
194                 return -ENOTSUP;
195
196         ts_cnt = hns3_read_dev(hw, HNS3_TX_1588_BACK_TSP_CNT) &
197                         TIME_TX_STAMP_CNT_MASK;
198         if (ts_cnt == 0)
199                 return -EINVAL;
200
201         ns = hns3_read_dev(hw, HNS3_TX_1588_TSP_BACK_0) & TIME_TX_STAMP_NS_MASK;
202         sec = hns3_read_dev(hw, HNS3_TX_1588_TSP_BACK_1);
203         tmp = hns3_read_dev(hw, HNS3_TX_1588_TSP_BACK_2) & 0xFFFF;
204         sec = (tmp << 32) | sec;
205
206         ns += sec * NSEC_PER_SEC;
207
208         *timestamp = rte_ns_to_timespec(ns);
209
210         /* Clear current timestamp hardware stores */
211         hns3_read_dev(hw, HNS3_TX_1588_SEQID_BACK);
212
213         return 0;
214 }
215
216 int
217 hns3_timesync_read_time(struct rte_eth_dev *dev, struct timespec *ts)
218 {
219         struct hns3_hw *hw = HNS3_DEV_PRIVATE_TO_HW(dev->data->dev_private);
220         uint64_t ns, sec;
221
222         if (!hns3_dev_ptp_supported(hw))
223                 return -ENOTSUP;
224
225         sec = hns3_read_dev(hw, HNS3_CURR_TIME_OUT_L);
226         sec |= (uint64_t)(hns3_read_dev(hw, HNS3_CURR_TIME_OUT_H) & 0xFFFF)
227                 << 32;
228
229         ns = hns3_read_dev(hw, HNS3_CURR_TIME_OUT_NS);
230         ns += sec * NSEC_PER_SEC;
231         *ts = rte_ns_to_timespec(ns);
232
233         return 0;
234 }
235
236 int
237 hns3_timesync_write_time(struct rte_eth_dev *dev, const struct timespec *ts)
238 {
239         struct hns3_hw *hw = HNS3_DEV_PRIVATE_TO_HW(dev->data->dev_private);
240         uint64_t sec = ts->tv_sec;
241         uint64_t ns = ts->tv_nsec;
242
243         if (!hns3_dev_ptp_supported(hw))
244                 return -ENOTSUP;
245
246         /* Set the timecounters to a new value. */
247         hns3_write_dev(hw, HNS3_CFG_TIME_SYNC_H, upper_32_bits(sec));
248         hns3_write_dev(hw, HNS3_CFG_TIME_SYNC_M, lower_32_bits(sec));
249         hns3_write_dev(hw, HNS3_CFG_TIME_SYNC_L, lower_32_bits(ns));
250         hns3_write_dev(hw, HNS3_CFG_TIME_SYNC_RDY, 1);
251
252         return 0;
253 }
254
255 int
256 hns3_timesync_adjust_time(struct rte_eth_dev *dev, int64_t delta)
257 {
258 #define TIME_SYNC_L_MASK 0x7FFFFFFF
259 #define SYMBOL_BIT_OFFSET 31
260         struct hns3_hw *hw = HNS3_DEV_PRIVATE_TO_HW(dev->data->dev_private);
261         struct timespec cur_time;
262         uint64_t ns;
263
264         if (!hns3_dev_ptp_supported(hw))
265                 return -ENOTSUP;
266
267         (void)hns3_timesync_read_time(dev, &cur_time);
268         ns = rte_timespec_to_ns((const struct timespec *)&cur_time);
269         cur_time = rte_ns_to_timespec(ns + delta);
270         (void)hns3_timesync_write_time(dev, (const struct timespec *)&cur_time);
271
272         return 0;
273 }
274
275 int
276 hns3_restore_ptp(struct hns3_adapter *hns)
277 {
278         struct hns3_pf *pf = &hns->pf;
279         struct hns3_hw *hw = &hns->hw;
280         bool en = pf->ptp_enable;
281         int ret;
282
283         if (!hns3_dev_ptp_supported(hw))
284                 return 0;
285
286         ret = hns3_timesync_configure(hns, en);
287         if (ret)
288                 hns3_err(hw, "restore PTP enable state(%d) failed, ret = %d",
289                          en, ret);
290
291         return ret;
292 }