xref: /linux/drivers/net/ethernet/mucse/rnpgbe/rnpgbe_main.c (revision 24f171c7e145f43b9f187578e89b0982ce87e54c)
1 // SPDX-License-Identifier: GPL-2.0
2 /* Copyright(c) 2020 - 2025 Mucse Corporation. */
3 
4 #include <linux/pci.h>
5 #include <net/rtnetlink.h>
6 #include <linux/etherdevice.h>
7 
8 #include "rnpgbe.h"
9 #include "rnpgbe_hw.h"
10 #include "rnpgbe_mbx_fw.h"
11 
12 static const char rnpgbe_driver_name[] = "rnpgbe";
13 
14 /* rnpgbe_pci_tbl - PCI Device ID Table
15  *
16  * { PCI_VDEVICE(Vendor ID, Device ID),
17  *   private_data (used for different hw chip) }
18  */
19 static struct pci_device_id rnpgbe_pci_tbl[] = {
20 	{ PCI_VDEVICE(MUCSE, RNPGBE_DEVICE_ID_N210), board_n210 },
21 	{ PCI_VDEVICE(MUCSE, RNPGBE_DEVICE_ID_N210L), board_n210 },
22 	{ PCI_VDEVICE(MUCSE, RNPGBE_DEVICE_ID_N500_DUAL_PORT), board_n500 },
23 	{ PCI_VDEVICE(MUCSE, RNPGBE_DEVICE_ID_N500_QUAD_PORT), board_n500 },
24 	/* required last entry */
25 	{0, },
26 };
27 
28 /**
29  * rnpgbe_open - Called when a network interface is made active
30  * @netdev: network interface device structure
31  *
32  * The open entry point is called when a network interface is made
33  * active by the system (IFF_UP).
34  *
35  * Return: 0
36  **/
37 static int rnpgbe_open(struct net_device *netdev)
38 {
39 	return 0;
40 }
41 
42 /**
43  * rnpgbe_close - Disables a network interface
44  * @netdev: network interface device structure
45  *
46  * The close entry point is called when an interface is de-activated
47  * by the OS.
48  *
49  * Return: 0, this is not allowed to fail
50  **/
51 static int rnpgbe_close(struct net_device *netdev)
52 {
53 	return 0;
54 }
55 
56 /**
57  * rnpgbe_xmit_frame - Send a skb to driver
58  * @skb: skb structure to be sent
59  * @netdev: network interface device structure
60  *
61  * Return: NETDEV_TX_OK
62  **/
63 static netdev_tx_t rnpgbe_xmit_frame(struct sk_buff *skb,
64 				     struct net_device *netdev)
65 {
66 	struct mucse *mucse = netdev_priv(netdev);
67 
68 	dev_kfree_skb_any(skb);
69 	mucse->stats.tx_dropped++;
70 
71 	return NETDEV_TX_OK;
72 }
73 
74 static const struct net_device_ops rnpgbe_netdev_ops = {
75 	.ndo_open       = rnpgbe_open,
76 	.ndo_stop       = rnpgbe_close,
77 	.ndo_start_xmit = rnpgbe_xmit_frame,
78 };
79 
80 /**
81  * rnpgbe_add_adapter - Add netdev for this pci_dev
82  * @pdev: PCI device information structure
83  * @board_type: board type
84  *
85  * rnpgbe_add_adapter initializes a netdev for this pci_dev
86  * structure. Initializes Bar map, private structure, and a
87  * hardware reset occur.
88  *
89  * Return: 0 on success, negative errno on failure
90  **/
91 static int rnpgbe_add_adapter(struct pci_dev *pdev,
92 			      int board_type)
93 {
94 	struct net_device *netdev;
95 	u8 perm_addr[ETH_ALEN];
96 	void __iomem *hw_addr;
97 	struct mucse *mucse;
98 	struct mucse_hw *hw;
99 	int err, err_notify;
100 
101 	netdev = alloc_etherdev_mq(sizeof(struct mucse), RNPGBE_MAX_QUEUES);
102 	if (!netdev)
103 		return -ENOMEM;
104 
105 	SET_NETDEV_DEV(netdev, &pdev->dev);
106 	mucse = netdev_priv(netdev);
107 	mucse->netdev = netdev;
108 	mucse->pdev = pdev;
109 	pci_set_drvdata(pdev, mucse);
110 
111 	hw = &mucse->hw;
112 	hw_addr = devm_ioremap(&pdev->dev,
113 			       pci_resource_start(pdev, 2),
114 			       pci_resource_len(pdev, 2));
115 	if (!hw_addr) {
116 		err = -EIO;
117 		goto err_free_net;
118 	}
119 
120 	hw->hw_addr = hw_addr;
121 	hw->pdev = pdev;
122 
123 	err = rnpgbe_init_hw(hw, board_type);
124 	if (err) {
125 		dev_err(&pdev->dev, "Init hw err %d\n", err);
126 		goto err_free_net;
127 	}
128 	/* Step 1: Send power-up notification to firmware (no response expected)
129 	 * This informs firmware to initialize hardware power state, but
130 	 * firmware only acknowledges receipt without returning data. Must be
131 	 * done before synchronization as firmware may be in low-power idle
132 	 * state initially.
133 	 */
134 	err_notify = rnpgbe_send_notify(hw, true, mucse_fw_powerup);
135 	if (err_notify) {
136 		dev_warn(&pdev->dev, "Send powerup to hw failed %d\n",
137 			 err_notify);
138 		dev_warn(&pdev->dev, "Maybe low performance\n");
139 	}
140 	/* Step 2: Synchronize mailbox communication with firmware (requires
141 	 * response) After power-up, confirm firmware is ready to process
142 	 * requests with responses. This ensures subsequent request/response
143 	 * interactions work reliably.
144 	 */
145 	err = mucse_mbx_sync_fw(hw);
146 	if (err) {
147 		dev_err(&pdev->dev, "Sync fw failed! %d\n", err);
148 		goto err_powerdown;
149 	}
150 
151 	netdev->netdev_ops = &rnpgbe_netdev_ops;
152 	err = rnpgbe_reset_hw(hw);
153 	if (err) {
154 		dev_err(&pdev->dev, "Hw reset failed %d\n", err);
155 		goto err_powerdown;
156 	}
157 
158 	err = rnpgbe_get_permanent_mac(hw, perm_addr);
159 	if (!err) {
160 		eth_hw_addr_set(netdev, perm_addr);
161 	} else if (err == -EINVAL) {
162 		dev_warn(&pdev->dev, "Using random MAC\n");
163 		eth_hw_addr_random(netdev);
164 	} else if (err) {
165 		dev_err(&pdev->dev, "get perm_addr failed %d\n", err);
166 		goto err_powerdown;
167 	}
168 
169 	err = register_netdev(netdev);
170 	if (err)
171 		goto err_powerdown;
172 
173 	return 0;
174 err_powerdown:
175 	/* notify powerdown only powerup ok */
176 	if (!err_notify) {
177 		err_notify = rnpgbe_send_notify(hw, false, mucse_fw_powerup);
178 		if (err_notify)
179 			dev_warn(&pdev->dev, "Send powerdown to hw failed %d\n",
180 				 err_notify);
181 	}
182 err_free_net:
183 	free_netdev(netdev);
184 	return err;
185 }
186 
187 /**
188  * rnpgbe_probe - Device initialization routine
189  * @pdev: PCI device information struct
190  * @id: entry in rnpgbe_pci_tbl
191  *
192  * rnpgbe_probe initializes a PF adapter identified by a pci_dev
193  * structure.
194  *
195  * Return: 0 on success, negative errno on failure
196  **/
197 static int rnpgbe_probe(struct pci_dev *pdev, const struct pci_device_id *id)
198 {
199 	int board_type = id->driver_data;
200 	int err;
201 
202 	err = pci_enable_device_mem(pdev);
203 	if (err)
204 		return err;
205 
206 	err = dma_set_coherent_mask(&pdev->dev, DMA_BIT_MASK(56));
207 	if (err) {
208 		dev_err(&pdev->dev,
209 			"No usable DMA configuration, aborting %d\n", err);
210 		goto err_disable_dev;
211 	}
212 
213 	err = pci_request_mem_regions(pdev, rnpgbe_driver_name);
214 	if (err) {
215 		dev_err(&pdev->dev,
216 			"pci_request_selected_regions failed %d\n", err);
217 		goto err_disable_dev;
218 	}
219 
220 	pci_set_master(pdev);
221 	err = pci_save_state(pdev);
222 	if (err) {
223 		dev_err(&pdev->dev, "pci_save_state failed %d\n", err);
224 		goto err_free_regions;
225 	}
226 
227 	err = rnpgbe_add_adapter(pdev, board_type);
228 	if (err)
229 		goto err_free_regions;
230 
231 	return 0;
232 err_free_regions:
233 	pci_release_mem_regions(pdev);
234 err_disable_dev:
235 	pci_disable_device(pdev);
236 	return err;
237 }
238 
239 /**
240  * rnpgbe_rm_adapter - Remove netdev for this mucse structure
241  * @pdev: PCI device information struct
242  *
243  * rnpgbe_rm_adapter remove a netdev for this mucse structure
244  **/
245 static void rnpgbe_rm_adapter(struct pci_dev *pdev)
246 {
247 	struct mucse *mucse = pci_get_drvdata(pdev);
248 	struct mucse_hw *hw = &mucse->hw;
249 	struct net_device *netdev;
250 	int err;
251 
252 	if (!mucse)
253 		return;
254 	netdev = mucse->netdev;
255 	unregister_netdev(netdev);
256 	err = rnpgbe_send_notify(hw, false, mucse_fw_powerup);
257 	if (err)
258 		dev_warn(&pdev->dev, "Send powerdown to hw failed %d\n", err);
259 	free_netdev(netdev);
260 }
261 
262 /**
263  * rnpgbe_remove - Device removal routine
264  * @pdev: PCI device information struct
265  *
266  * rnpgbe_remove is called by the PCI subsystem to alert the driver
267  * that it should release a PCI device. This could be caused by a
268  * Hot-Plug event, or because the driver is going to be removed from
269  * memory.
270  **/
271 static void rnpgbe_remove(struct pci_dev *pdev)
272 {
273 	rnpgbe_rm_adapter(pdev);
274 	pci_release_mem_regions(pdev);
275 	pci_disable_device(pdev);
276 }
277 
278 /**
279  * rnpgbe_dev_shutdown - Device shutdown routine
280  * @pdev: PCI device information struct
281  **/
282 static void rnpgbe_dev_shutdown(struct pci_dev *pdev)
283 {
284 	struct mucse *mucse = pci_get_drvdata(pdev);
285 	struct net_device *netdev = mucse->netdev;
286 
287 	rtnl_lock();
288 	netif_device_detach(netdev);
289 	if (netif_running(netdev))
290 		rnpgbe_close(netdev);
291 	rtnl_unlock();
292 	pci_disable_device(pdev);
293 }
294 
295 /**
296  * rnpgbe_shutdown - Device shutdown routine
297  * @pdev: PCI device information struct
298  *
299  * rnpgbe_shutdown is called by the PCI subsystem to alert the driver
300  * that os shutdown. Device should setup wakeup state here.
301  **/
302 static void rnpgbe_shutdown(struct pci_dev *pdev)
303 {
304 	rnpgbe_dev_shutdown(pdev);
305 }
306 
307 static struct pci_driver rnpgbe_driver = {
308 	.name     = rnpgbe_driver_name,
309 	.id_table = rnpgbe_pci_tbl,
310 	.probe    = rnpgbe_probe,
311 	.remove   = rnpgbe_remove,
312 	.shutdown = rnpgbe_shutdown,
313 };
314 
315 module_pci_driver(rnpgbe_driver);
316 
317 MODULE_DEVICE_TABLE(pci, rnpgbe_pci_tbl);
318 MODULE_AUTHOR("Yibo Dong, <dong100@mucse.com>");
319 MODULE_DESCRIPTION("Mucse(R) 1 Gigabit PCI Express Network Driver");
320 MODULE_LICENSE("GPL");
321