Advertisement
Guest User

Untitled

a guest
May 21st, 2013
195
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 93.55 KB | None | 0 0
  1. From 1c31c288bc1e853e3226ba593a13a0492b39c9e8 Mon Sep 17 00:00:00 2001
  2. From: John Crispin <blogic@openwrt.org>
  3. Date: Fri, 15 Mar 2013 19:07:05 +0100
  4. Subject: [PATCH 120/121] NET: MIPS: add ralink SoC ethernet driver
  5.  
  6. Add support for Ralink FE and ESW.
  7.  
  8. Signed-off-by: John Crispin <blogic@openwrt.org>
  9. ---
  10. .../include/asm/mach-ralink/rt305x_esw_platform.h | 27 +
  11. arch/mips/ralink/rt305x.c | 1 +
  12. drivers/net/ethernet/Kconfig | 1 +
  13. drivers/net/ethernet/Makefile | 1 +
  14. drivers/net/ethernet/ramips/Kconfig | 18 +
  15. drivers/net/ethernet/ramips/Makefile | 9 +
  16. drivers/net/ethernet/ramips/ramips_debugfs.c | 127 ++
  17. drivers/net/ethernet/ramips/ramips_esw.c | 1220 +++++++++++++++++++
  18. drivers/net/ethernet/ramips/ramips_eth.h | 375 ++++++
  19. drivers/net/ethernet/ramips/ramips_main.c | 1285 ++++++++++++++++++++
  20. 10 files changed, 3064 insertions(+)
  21. create mode 100644 arch/mips/include/asm/mach-ralink/rt305x_esw_platform.h
  22. create mode 100644 drivers/net/ethernet/ramips/Kconfig
  23. create mode 100644 drivers/net/ethernet/ramips/Makefile
  24. create mode 100644 drivers/net/ethernet/ramips/ramips_debugfs.c
  25. create mode 100644 drivers/net/ethernet/ramips/ramips_esw.c
  26. create mode 100644 drivers/net/ethernet/ramips/ramips_eth.h
  27. create mode 100644 drivers/net/ethernet/ramips/ramips_main.c
  28.  
  29. Index: linux-3.8.12/arch/mips/include/asm/mach-ralink/rt305x_esw_platform.h
  30. ===================================================================
  31. --- /dev/null 1970-01-01 00:00:00.000000000 +0000
  32. +++ linux-3.8.12/arch/mips/include/asm/mach-ralink/rt305x_esw_platform.h 2013-05-20 18:44:40.000000000 +0400
  33. @@ -0,0 +1,28 @@
  34. +/*
  35. + * Ralink RT305x SoC platform device registration
  36. + *
  37. + * Copyright (C) 2010 Gabor Juhos <juhosg@openwrt.org>
  38. + *
  39. + * This program is free software; you can redistribute it and/or modify it
  40. + * under the terms of the GNU General Public License version 2 as published
  41. + * by the Free Software Foundation.
  42. + */
  43. +
  44. +#ifndef _RT305X_ESW_PLATFORM_H
  45. +#define _RT305X_ESW_PLATFORM_H
  46. +
  47. +enum {
  48. + RT305X_ESW_VLAN_CONFIG_NONE = 0,
  49. + RT305X_ESW_VLAN_CONFIG_LLLLW,
  50. + RT305X_ESW_VLAN_CONFIG_WLLLL,
  51. +};
  52. +
  53. +struct rt305x_esw_platform_data
  54. +{
  55. + u8 vlan_config;
  56. + u32 reg_initval_fct2;
  57. + u32 reg_initval_fpa2;
  58. + u8 led_polarity;
  59. +};
  60. +
  61. +#endif /* _RT305X_ESW_PLATFORM_H */
  62. Index: linux-3.8.12/arch/mips/ralink/rt305x.c
  63. ===================================================================
  64. --- linux-3.8.12.orig/arch/mips/ralink/rt305x.c 2013-05-20 18:44:39.000000000 +0400
  65. +++ linux-3.8.12/arch/mips/ralink/rt305x.c 2013-05-20 18:44:40.000000000 +0400
  66. @@ -221,6 +221,7 @@
  67. }
  68.  
  69. ralink_clk_add("cpu", cpu_rate);
  70. + ralink_clk_add("sys", sys_rate);
  71. ralink_clk_add("10000b00.spi", sys_rate);
  72. ralink_clk_add("10000100.timer", wdt_rate);
  73. ralink_clk_add("10000120.watchdog", wdt_rate);
  74. Index: linux-3.8.12/drivers/net/ethernet/Kconfig
  75. ===================================================================
  76. --- linux-3.8.12.orig/drivers/net/ethernet/Kconfig 2013-05-08 07:33:25.000000000 +0400
  77. +++ linux-3.8.12/drivers/net/ethernet/Kconfig 2013-05-20 18:44:40.000000000 +0400
  78. @@ -136,6 +136,7 @@
  79. source "drivers/net/ethernet/pasemi/Kconfig"
  80. source "drivers/net/ethernet/qlogic/Kconfig"
  81. source "drivers/net/ethernet/racal/Kconfig"
  82. +source "drivers/net/ethernet/ramips/Kconfig"
  83. source "drivers/net/ethernet/realtek/Kconfig"
  84. source "drivers/net/ethernet/renesas/Kconfig"
  85. source "drivers/net/ethernet/rdc/Kconfig"
  86. Index: linux-3.8.12/drivers/net/ethernet/Makefile
  87. ===================================================================
  88. --- linux-3.8.12.orig/drivers/net/ethernet/Makefile 2013-05-08 07:33:25.000000000 +0400
  89. +++ linux-3.8.12/drivers/net/ethernet/Makefile 2013-05-20 18:44:40.000000000 +0400
  90. @@ -54,6 +54,7 @@
  91. obj-$(CONFIG_NET_VENDOR_PASEMI) += pasemi/
  92. obj-$(CONFIG_NET_VENDOR_QLOGIC) += qlogic/
  93. obj-$(CONFIG_NET_VENDOR_RACAL) += racal/
  94. +obj-$(CONFIG_NET_RAMIPS) += ramips/
  95. obj-$(CONFIG_NET_VENDOR_REALTEK) += realtek/
  96. obj-$(CONFIG_SH_ETH) += renesas/
  97. obj-$(CONFIG_NET_VENDOR_RDC) += rdc/
  98. Index: linux-3.8.12/drivers/net/ethernet/ramips/Kconfig
  99. ===================================================================
  100. --- /dev/null 1970-01-01 00:00:00.000000000 +0000
  101. +++ linux-3.8.12/drivers/net/ethernet/ramips/Kconfig 2013-05-20 18:44:40.000000000 +0400
  102. @@ -0,0 +1,18 @@
  103. +config NET_RAMIPS
  104. + tristate "Ralink RT288X/RT3X5X/RT3662/RT3883 ethernet driver"
  105. + depends on RALINK
  106. + select PHYLIB if (SOC_RT288X || SOC_RT3883)
  107. + select SWCONFIG if SOC_RT305X
  108. + help
  109. + This driver supports the etehrnet mac inside the ralink wisocs
  110. +
  111. +if NET_RAMIPS
  112. +
  113. +config NET_RAMIPS_DEBUG
  114. + bool "Enable debug messages in the Ralink ethernet driver"
  115. +
  116. +config NET_RAMIPS_DEBUG_FS
  117. + bool "Enable debugfs support for the Ralink ethernet driver"
  118. + depends on DEBUG_FS
  119. +
  120. +endif
  121. Index: linux-3.8.12/drivers/net/ethernet/ramips/Makefile
  122. ===================================================================
  123. --- /dev/null 1970-01-01 00:00:00.000000000 +0000
  124. +++ linux-3.8.12/drivers/net/ethernet/ramips/Makefile 2013-05-20 18:44:40.000000000 +0400
  125. @@ -0,0 +1,9 @@
  126. +#
  127. +# Makefile for the Ramips SoCs built-in ethernet macs
  128. +#
  129. +
  130. +ramips-y += ramips_main.o
  131. +
  132. +ramips-$(CONFIG_NET_RAMIPS_DEBUG_FS) += ramips_debugfs.o
  133. +
  134. +obj-$(CONFIG_NET_RAMIPS) += ramips.o
  135. Index: linux-3.8.12/drivers/net/ethernet/ramips/ramips_debugfs.c
  136. ===================================================================
  137. --- /dev/null 1970-01-01 00:00:00.000000000 +0000
  138. +++ linux-3.8.12/drivers/net/ethernet/ramips/ramips_debugfs.c 2013-05-20 18:44:40.000000000 +0400
  139. @@ -0,0 +1,127 @@
  140. +/*
  141. + * Ralink SoC ethernet driver debugfs code
  142. + *
  143. + * Copyright (C) 2011-2012 Gabor Juhos <juhosg@openwrt.org>
  144. + *
  145. + * This program is free software; you can redistribute it and/or modify it
  146. + * under the terms of the GNU General Public License version 2 as published
  147. + * by the Free Software Foundation.
  148. + */
  149. +
  150. +#include <linux/debugfs.h>
  151. +#include <linux/module.h>
  152. +#include <linux/phy.h>
  153. +
  154. +#include "ramips_eth.h"
  155. +
  156. +static struct dentry *raeth_debugfs_root;
  157. +
  158. +static int raeth_debugfs_generic_open(struct inode *inode, struct file *file)
  159. +{
  160. + file->private_data = inode->i_private;
  161. + return 0;
  162. +}
  163. +
  164. +void raeth_debugfs_update_int_stats(struct raeth_priv *re, u32 status)
  165. +{
  166. + re->debug.int_stats.total += !!status;
  167. +
  168. + re->debug.int_stats.rx_delayed += !!(status & RAMIPS_RX_DLY_INT);
  169. + re->debug.int_stats.rx_done0 += !!(status & RAMIPS_RX_DONE_INT0);
  170. + re->debug.int_stats.rx_coherent += !!(status & RAMIPS_RX_COHERENT);
  171. +
  172. + re->debug.int_stats.tx_delayed += !!(status & RAMIPS_TX_DLY_INT);
  173. + re->debug.int_stats.tx_done0 += !!(status & RAMIPS_TX_DONE_INT0);
  174. + re->debug.int_stats.tx_done1 += !!(status & RAMIPS_TX_DONE_INT1);
  175. + re->debug.int_stats.tx_done2 += !!(status & RAMIPS_TX_DONE_INT2);
  176. + re->debug.int_stats.tx_done3 += !!(status & RAMIPS_TX_DONE_INT3);
  177. + re->debug.int_stats.tx_coherent += !!(status & RAMIPS_TX_COHERENT);
  178. +
  179. + re->debug.int_stats.pse_fq_empty += !!(status & RAMIPS_PSE_FQ_EMPTY);
  180. + re->debug.int_stats.pse_p0_fc += !!(status & RAMIPS_PSE_P0_FC);
  181. + re->debug.int_stats.pse_p1_fc += !!(status & RAMIPS_PSE_P1_FC);
  182. + re->debug.int_stats.pse_p2_fc += !!(status & RAMIPS_PSE_P2_FC);
  183. + re->debug.int_stats.pse_buf_drop += !!(status & RAMIPS_PSE_BUF_DROP);
  184. +}
  185. +
  186. +static ssize_t read_file_int_stats(struct file *file, char __user *user_buf,
  187. + size_t count, loff_t *ppos)
  188. +{
  189. +#define PR_INT_STAT(_label, _field) \
  190. + len += snprintf(buf + len, sizeof(buf) - len, \
  191. + "%-18s: %10lu\n", _label, re->debug.int_stats._field);
  192. +
  193. + struct raeth_priv *re = file->private_data;
  194. + char buf[512];
  195. + unsigned int len = 0;
  196. + unsigned long flags;
  197. +
  198. + spin_lock_irqsave(&re->page_lock, flags);
  199. +
  200. + PR_INT_STAT("RX Delayed", rx_delayed);
  201. + PR_INT_STAT("RX Done 0", rx_done0);
  202. + PR_INT_STAT("RX Coherent", rx_coherent);
  203. +
  204. + PR_INT_STAT("TX Delayed", tx_delayed);
  205. + PR_INT_STAT("TX Done 0", tx_done0);
  206. + PR_INT_STAT("TX Done 1", tx_done1);
  207. + PR_INT_STAT("TX Done 2", tx_done2);
  208. + PR_INT_STAT("TX Done 3", tx_done3);
  209. + PR_INT_STAT("TX Coherent", tx_coherent);
  210. +
  211. + PR_INT_STAT("PSE FQ empty", pse_fq_empty);
  212. + PR_INT_STAT("CDMA Flow control", pse_p0_fc);
  213. + PR_INT_STAT("GDMA1 Flow control", pse_p1_fc);
  214. + PR_INT_STAT("GDMA2 Flow control", pse_p2_fc);
  215. + PR_INT_STAT("PSE discard", pse_buf_drop);
  216. +
  217. + len += snprintf(buf + len, sizeof(buf) - len, "\n");
  218. + PR_INT_STAT("Total", total);
  219. +
  220. + spin_unlock_irqrestore(&re->page_lock, flags);
  221. +
  222. + return simple_read_from_buffer(user_buf, count, ppos, buf, len);
  223. +#undef PR_INT_STAT
  224. +}
  225. +
  226. +static const struct file_operations raeth_fops_int_stats = {
  227. + .open = raeth_debugfs_generic_open,
  228. + .read = read_file_int_stats,
  229. + .owner = THIS_MODULE
  230. +};
  231. +
  232. +void raeth_debugfs_exit(struct raeth_priv *re)
  233. +{
  234. + debugfs_remove_recursive(re->debug.debugfs_dir);
  235. +}
  236. +
  237. +int raeth_debugfs_init(struct raeth_priv *re)
  238. +{
  239. + re->debug.debugfs_dir = debugfs_create_dir(re->netdev->name,
  240. + raeth_debugfs_root);
  241. + if (!re->debug.debugfs_dir)
  242. + return -ENOMEM;
  243. +
  244. + debugfs_create_file("int_stats", S_IRUGO, re->debug.debugfs_dir,
  245. + re, &raeth_fops_int_stats);
  246. +
  247. + return 0;
  248. +}
  249. +
  250. +int raeth_debugfs_root_init(void)
  251. +{
  252. + if (raeth_debugfs_root)
  253. + return -EBUSY;
  254. +
  255. + raeth_debugfs_root = debugfs_create_dir("raeth", NULL);
  256. + if (!raeth_debugfs_root)
  257. + return -ENOENT;
  258. +
  259. + return 0;
  260. +}
  261. +
  262. +void raeth_debugfs_root_exit(void)
  263. +{
  264. + debugfs_remove(raeth_debugfs_root);
  265. + raeth_debugfs_root = NULL;
  266. +}
  267. Index: linux-3.8.12/drivers/net/ethernet/ramips/ramips_esw.c
  268. ===================================================================
  269. --- /dev/null 1970-01-01 00:00:00.000000000 +0000
  270. +++ linux-3.8.12/drivers/net/ethernet/ramips/ramips_esw.c 2013-05-20 18:57:32.000000000 +0400
  271. @@ -0,0 +1,1438 @@
  272. +#include <linux/ioport.h>
  273. +#include <linux/switch.h>
  274. +#include <linux/mii.h>
  275. +
  276. +#include <ralink_regs.h>
  277. +#include <rt305x.h>
  278. +#include <rt305x_esw_platform.h>
  279. +
  280. +/*
  281. + * HW limitations for this switch:
  282. + * - No large frame support (PKT_MAX_LEN at most 1536)
  283. + * - Can't have untagged vlan and tagged vlan on one port at the same time,
  284. + * though this might be possible using the undocumented PPE.
  285. + */
  286. +
  287. +#define RT305X_ESW_REG_ISR 0x00
  288. +#define RT305X_ESW_REG_IMR 0x04
  289. +#define RT305X_ESW_REG_FCT0 0x08
  290. +#define RT305X_ESW_REG_PFC1 0x14
  291. +#define RT305X_ESW_REG_ATS 0x24
  292. +#define RT305X_ESW_REG_ATS0 0x28
  293. +#define RT305X_ESW_REG_ATS1 0x2c
  294. +#define RT305X_ESW_REG_ATS2 0x30
  295. +#define RT305X_ESW_REG_PVIDC(_n) (0x40 + 4 * (_n))
  296. +#define RT305X_ESW_REG_VLANI(_n) (0x50 + 4 * (_n))
  297. +#define RT305X_ESW_REG_VMSC(_n) (0x70 + 4 * (_n))
  298. +#define RT305X_ESW_REG_POA 0x80
  299. +#define RT305X_ESW_REG_FPA 0x84
  300. +#define RT305X_ESW_REG_SOCPC 0x8c
  301. +#define RT305X_ESW_REG_POC0 0x90
  302. +#define RT305X_ESW_REG_POC1 0x94
  303. +#define RT305X_ESW_REG_POC2 0x98
  304. +#define RT305X_ESW_REG_SGC 0x9c
  305. +#define RT305X_ESW_REG_STRT 0xa0
  306. +#define RT305X_ESW_REG_PCR0 0xc0
  307. +#define RT305X_ESW_REG_PCR1 0xc4
  308. +#define RT305X_ESW_REG_FPA2 0xc8
  309. +#define RT305X_ESW_REG_FCT2 0xcc
  310. +#define RT305X_ESW_REG_SGC2 0xe4
  311. +#define RT305X_ESW_REG_P0LED 0xa4
  312. +#define RT305X_ESW_REG_P1LED 0xa8
  313. +#define RT305X_ESW_REG_P2LED 0xac
  314. +#define RT305X_ESW_REG_P3LED 0xb0
  315. +#define RT305X_ESW_REG_P4LED 0xb4
  316. +#define RT305X_ESW_REG_P0PC 0xe8
  317. +#define RT305X_ESW_REG_P1PC 0xec
  318. +#define RT305X_ESW_REG_P2PC 0xf0
  319. +#define RT305X_ESW_REG_P3PC 0xf4
  320. +#define RT305X_ESW_REG_P4PC 0xf8
  321. +#define RT305X_ESW_REG_P5PC 0xfc
  322. +
  323. +/* RT5350 only registers */
  324. +#define RT305X_ESW_REG_LED_POLARITY 0x168
  325. +#define RT305X_ESW_REG_P0TPC 0x150
  326. +#define RT305X_ESW_REG_P1TPC 0x154
  327. +#define RT305X_ESW_REG_P2TPC 0x158
  328. +#define RT305X_ESW_REG_P3TPC 0x15c
  329. +#define RT305X_ESW_REG_P4TPC 0x160
  330. +#define RT305X_ESW_REG_P5TPC 0x164
  331. +
  332. +#define RT305X_ESW_LED_LINK 0
  333. +#define RT305X_ESW_LED_100M 1
  334. +#define RT305X_ESW_LED_DUPLEX 2
  335. +#define RT305X_ESW_LED_ACTIVITY 3
  336. +#define RT305X_ESW_LED_COLLISION 4
  337. +#define RT305X_ESW_LED_LINKACT 5
  338. +#define RT305X_ESW_LED_DUPLCOLL 6
  339. +#define RT305X_ESW_LED_10MACT 7
  340. +#define RT305X_ESW_LED_100MACT 8
  341. +/* Additional led states not in datasheet: */
  342. +#define RT305X_ESW_LED_BLINK 10
  343. +#define RT305X_ESW_LED_OFF 11
  344. +#define RT305X_ESW_LED_ON 12
  345. +
  346. +#define RT305X_ESW_LINK_S 25
  347. +#define RT305X_ESW_DUPLEX_S 9
  348. +#define RT305X_ESW_SPD_S 0
  349. +
  350. +#define RT305X_ESW_PCR0_WT_NWAY_DATA_S 16
  351. +#define RT305X_ESW_PCR0_WT_PHY_CMD BIT(13)
  352. +#define RT305X_ESW_PCR0_CPU_PHY_REG_S 8
  353. +
  354. +#define RT305X_ESW_PCR1_WT_DONE BIT(0)
  355. +
  356. +#define RT305X_ESW_ATS_TIMEOUT (5 * HZ)
  357. +#define RT305X_ESW_PHY_TIMEOUT (5 * HZ)
  358. +
  359. +#define RT305X_ESW_PVIDC_PVID_M 0xfff
  360. +#define RT305X_ESW_PVIDC_PVID_S 12
  361. +
  362. +#define RT305X_ESW_VLANI_VID_M 0xfff
  363. +#define RT305X_ESW_VLANI_VID_S 12
  364. +
  365. +#define RT305X_ESW_VMSC_MSC_M 0xff
  366. +#define RT305X_ESW_VMSC_MSC_S 8
  367. +
  368. +#define RT305X_ESW_SOCPC_DISUN2CPU_S 0
  369. +#define RT305X_ESW_SOCPC_DISMC2CPU_S 8
  370. +#define RT305X_ESW_SOCPC_DISBC2CPU_S 16
  371. +#define RT305X_ESW_SOCPC_CRC_PADDING BIT(25)
  372. +
  373. +#define RT305X_ESW_POC0_EN_BP_S 0
  374. +#define RT305X_ESW_POC0_EN_FC_S 8
  375. +#define RT305X_ESW_POC0_DIS_RMC2CPU_S 16
  376. +#define RT305X_ESW_POC0_DIS_PORT_M 0x7f
  377. +#define RT305X_ESW_POC0_DIS_PORT_S 23
  378. +
  379. +#define RT305X_ESW_POC2_UNTAG_EN_M 0xff
  380. +#define RT305X_ESW_POC2_UNTAG_EN_S 0
  381. +#define RT305X_ESW_POC2_ENAGING_S 8
  382. +#define RT305X_ESW_POC2_DIS_UC_PAUSE_S 16
  383. +
  384. +#define RT305X_ESW_SGC2_DOUBLE_TAG_M 0x7f
  385. +#define RT305X_ESW_SGC2_DOUBLE_TAG_S 0
  386. +#define RT305X_ESW_SGC2_LAN_PMAP_M 0x3f
  387. +#define RT305X_ESW_SGC2_LAN_PMAP_S 24
  388. +
  389. +#define RT305X_ESW_PFC1_EN_VLAN_M 0xff
  390. +#define RT305X_ESW_PFC1_EN_VLAN_S 16
  391. +#define RT305X_ESW_PFC1_EN_TOS_S 24
  392. +
  393. +#define RT305X_ESW_VLAN_NONE 0xfff
  394. +
  395. +#define RT305X_ESW_POA_LINK_MASK 0x1f
  396. +#define RT305X_ESW_POA_LINK_SHIFT 25
  397. +
  398. +#define RT305X_ESW_PORT_ST_CHG BIT(26)
  399. +#define RT305X_ESW_PORT0 0
  400. +#define RT305X_ESW_PORT1 1
  401. +#define RT305X_ESW_PORT2 2
  402. +#define RT305X_ESW_PORT3 3
  403. +#define RT305X_ESW_PORT4 4
  404. +#define RT305X_ESW_PORT5 5
  405. +#define RT305X_ESW_PORT6 6
  406. +
  407. +#define RT305X_ESW_PORTS_NONE 0
  408. +
  409. +#define RT305X_ESW_PMAP_LLLLLL 0x3f
  410. +#define RT305X_ESW_PMAP_LLLLWL 0x2f
  411. +#define RT305X_ESW_PMAP_WLLLLL 0x3e
  412. +
  413. +#define RT305X_ESW_PORTS_INTERNAL \
  414. + (BIT(RT305X_ESW_PORT0) | BIT(RT305X_ESW_PORT1) | \
  415. + BIT(RT305X_ESW_PORT2) | BIT(RT305X_ESW_PORT3) | \
  416. + BIT(RT305X_ESW_PORT4))
  417. +
  418. +#define RT305X_ESW_PORTS_NOCPU \
  419. + (RT305X_ESW_PORTS_INTERNAL | BIT(RT305X_ESW_PORT5))
  420. +
  421. +#define RT305X_ESW_PORTS_CPU BIT(RT305X_ESW_PORT6)
  422. +
  423. +#define RT305X_ESW_PORTS_ALL \
  424. + (RT305X_ESW_PORTS_NOCPU | RT305X_ESW_PORTS_CPU)
  425. +
  426. +#define RT305X_ESW_NUM_VLANS 16
  427. +#define RT305X_ESW_NUM_VIDS 4096
  428. +#define RT305X_ESW_NUM_PORTS 7
  429. +#define RT305X_ESW_NUM_LANWAN 6
  430. +#define RT305X_ESW_NUM_LEDS 5
  431. +
  432. +enum {
  433. + /* Global attributes. */
  434. + RT305X_ESW_ATTR_ENABLE_VLAN,
  435. + RT305X_ESW_ATTR_ALT_VLAN_DISABLE,
  436. + RT305X_ESW_ATTR_LED_FREQ,
  437. + RT305X_ESW_ATTR_PKT_LENGTH,
  438. + RT305X_ESW_ATTR_BC_STATUS,
  439. + /* Port attributes. */
  440. + RT305X_ESW_ATTR_PORT_DISABLE,
  441. + RT305X_ESW_ATTR_PORT_DOUBLETAG,
  442. + RT305X_ESW_ATTR_PORT_UNTAG,
  443. + RT305X_ESW_ATTR_PORT_LED,
  444. + RT305X_ESW_ATTR_PORT_LAN,
  445. + RT305X_ESW_ATTR_PORT_RECV_BAD,
  446. + RT305X_ESW_ATTR_PORT_RECV_GOOD,
  447. + RT305X_ESW_ATTR_PORT_TR_BAD,
  448. + RT305X_ESW_ATTR_PORT_TR_GOOD,
  449. + RT305X_ESW_ATTR_PORT_LED_POLARITY,
  450. +};
  451. +
  452. +struct rt305x_esw_port {
  453. + bool disable;
  454. + bool doubletag;
  455. + bool untag;
  456. + u8 led;
  457. + u16 pvid;
  458. +};
  459. +
  460. +struct rt305x_esw_vlan {
  461. + u8 ports;
  462. + u16 vid;
  463. +};
  464. +
  465. +struct rt305x_esw {
  466. + struct device *dev;
  467. + void __iomem *base;
  468. + int irq;
  469. + const struct rt305x_esw_platform_data *pdata;
  470. + /* Protects against concurrent register rmw operations. */
  471. + spinlock_t reg_rw_lock;
  472. +
  473. + unsigned char port_map;
  474. + unsigned int reg_initval_fct2;
  475. + unsigned int reg_initval_fpa2;
  476. +
  477. +
  478. + struct switch_dev swdev;
  479. + bool global_vlan_enable;
  480. + bool alt_vlan_disable;
  481. + struct rt305x_esw_vlan vlans[RT305X_ESW_NUM_VLANS];
  482. + struct rt305x_esw_port ports[RT305X_ESW_NUM_PORTS];
  483. + u8 led_polarity; /* LED polarity. RT5350 only */
  484. + u32 sgc; /* SGC value */
  485. +};
  486. +
  487. +static inline void
  488. +rt305x_esw_wr(struct rt305x_esw *esw, u32 val, unsigned reg)
  489. +{
  490. + __raw_writel(val, esw->base + reg);
  491. +}
  492. +
  493. +static inline u32
  494. +rt305x_esw_rr(struct rt305x_esw *esw, unsigned reg)
  495. +{
  496. + return __raw_readl(esw->base + reg);
  497. +}
  498. +
  499. +static inline void
  500. +rt305x_esw_rmw_raw(struct rt305x_esw *esw, unsigned reg, unsigned long mask,
  501. + unsigned long val)
  502. +{
  503. + unsigned long t;
  504. +
  505. + t = __raw_readl(esw->base + reg) & ~mask;
  506. + __raw_writel(t | val, esw->base + reg);
  507. +}
  508. +
  509. +static void
  510. +rt305x_esw_rmw(struct rt305x_esw *esw, unsigned reg, unsigned long mask,
  511. + unsigned long val)
  512. +{
  513. + unsigned long flags;
  514. +
  515. + spin_lock_irqsave(&esw->reg_rw_lock, flags);
  516. + rt305x_esw_rmw_raw(esw, reg, mask, val);
  517. + spin_unlock_irqrestore(&esw->reg_rw_lock, flags);
  518. +}
  519. +
  520. +static u32
  521. +rt305x_mii_write(struct rt305x_esw *esw, u32 phy_addr, u32 phy_register,
  522. + u32 write_data)
  523. +{
  524. + unsigned long t_start = jiffies;
  525. + int ret = 0;
  526. +
  527. + while (1) {
  528. + if (!(rt305x_esw_rr(esw, RT305X_ESW_REG_PCR1) &
  529. + RT305X_ESW_PCR1_WT_DONE))
  530. + break;
  531. + if (time_after(jiffies, t_start + RT305X_ESW_PHY_TIMEOUT)) {
  532. + ret = 1;
  533. + goto out;
  534. + }
  535. + }
  536. +
  537. + write_data &= 0xffff;
  538. + rt305x_esw_wr(esw,
  539. + (write_data << RT305X_ESW_PCR0_WT_NWAY_DATA_S) |
  540. + (phy_register << RT305X_ESW_PCR0_CPU_PHY_REG_S) |
  541. + (phy_addr) | RT305X_ESW_PCR0_WT_PHY_CMD,
  542. + RT305X_ESW_REG_PCR0);
  543. +
  544. + t_start = jiffies;
  545. + while (1) {
  546. + if (rt305x_esw_rr(esw, RT305X_ESW_REG_PCR1) &
  547. + RT305X_ESW_PCR1_WT_DONE)
  548. + break;
  549. +
  550. + if (time_after(jiffies, t_start + RT305X_ESW_PHY_TIMEOUT)) {
  551. + ret = 1;
  552. + break;
  553. + }
  554. + }
  555. +out:
  556. + if (ret)
  557. + printk(KERN_ERR "ramips_eth: MDIO timeout\n");
  558. + return ret;
  559. +}
  560. +
  561. +static unsigned
  562. +rt305x_esw_get_vlan_id(struct rt305x_esw *esw, unsigned vlan)
  563. +{
  564. + unsigned s;
  565. + unsigned val;
  566. +
  567. + s = RT305X_ESW_VLANI_VID_S * (vlan % 2);
  568. + val = rt305x_esw_rr(esw, RT305X_ESW_REG_VLANI(vlan / 2));
  569. + val = (val >> s) & RT305X_ESW_VLANI_VID_M;
  570. +
  571. + return val;
  572. +}
  573. +
  574. +static void
  575. +rt305x_esw_set_vlan_id(struct rt305x_esw *esw, unsigned vlan, unsigned vid)
  576. +{
  577. + unsigned s;
  578. +
  579. + s = RT305X_ESW_VLANI_VID_S * (vlan % 2);
  580. + rt305x_esw_rmw(esw,
  581. + RT305X_ESW_REG_VLANI(vlan / 2),
  582. + RT305X_ESW_VLANI_VID_M << s,
  583. + (vid & RT305X_ESW_VLANI_VID_M) << s);
  584. +}
  585. +
  586. +static unsigned
  587. +rt305x_esw_get_pvid(struct rt305x_esw *esw, unsigned port)
  588. +{
  589. + unsigned s, val;
  590. +
  591. + s = RT305X_ESW_PVIDC_PVID_S * (port % 2);
  592. + val = rt305x_esw_rr(esw, RT305X_ESW_REG_PVIDC(port / 2));
  593. + return (val >> s) & RT305X_ESW_PVIDC_PVID_M;
  594. +}
  595. +
  596. +static void
  597. +rt305x_esw_set_pvid(struct rt305x_esw *esw, unsigned port, unsigned pvid)
  598. +{
  599. + unsigned s;
  600. +
  601. + s = RT305X_ESW_PVIDC_PVID_S * (port % 2);
  602. + rt305x_esw_rmw(esw,
  603. + RT305X_ESW_REG_PVIDC(port / 2),
  604. + RT305X_ESW_PVIDC_PVID_M << s,
  605. + (pvid & RT305X_ESW_PVIDC_PVID_M) << s);
  606. +}
  607. +
  608. +static unsigned
  609. +rt305x_esw_get_vmsc(struct rt305x_esw *esw, unsigned vlan)
  610. +{
  611. + unsigned s, val;
  612. +
  613. + s = RT305X_ESW_VMSC_MSC_S * (vlan % 4);
  614. + val = rt305x_esw_rr(esw, RT305X_ESW_REG_VMSC(vlan / 4));
  615. + val = (val >> s) & RT305X_ESW_VMSC_MSC_M;
  616. +
  617. + return val;
  618. +}
  619. +
  620. +static void
  621. +rt305x_esw_set_vmsc(struct rt305x_esw *esw, unsigned vlan, unsigned msc)
  622. +{
  623. + unsigned s;
  624. +
  625. + s = RT305X_ESW_VMSC_MSC_S * (vlan % 4);
  626. + rt305x_esw_rmw(esw,
  627. + RT305X_ESW_REG_VMSC(vlan / 4),
  628. + RT305X_ESW_VMSC_MSC_M << s,
  629. + (msc & RT305X_ESW_VMSC_MSC_M) << s);
  630. +}
  631. +
  632. +static unsigned
  633. +rt305x_esw_get_port_disable(struct rt305x_esw *esw)
  634. +{
  635. + unsigned reg;
  636. + reg = rt305x_esw_rr(esw, RT305X_ESW_REG_POC0);
  637. + return (reg >> RT305X_ESW_POC0_DIS_PORT_S) &
  638. + RT305X_ESW_POC0_DIS_PORT_M;
  639. +}
  640. +
  641. +static void
  642. +rt305x_esw_set_port_disable(struct rt305x_esw *esw, unsigned disable_mask)
  643. +{
  644. + unsigned old_mask;
  645. + unsigned enable_mask;
  646. + unsigned changed;
  647. + int i;
  648. +
  649. + old_mask = rt305x_esw_get_port_disable(esw);
  650. + changed = old_mask ^ disable_mask;
  651. + enable_mask = old_mask & disable_mask;
  652. +
  653. + /* enable before writing to MII */
  654. + rt305x_esw_rmw(esw, RT305X_ESW_REG_POC0,
  655. + (RT305X_ESW_POC0_DIS_PORT_M <<
  656. + RT305X_ESW_POC0_DIS_PORT_S),
  657. + enable_mask << RT305X_ESW_POC0_DIS_PORT_S);
  658. +
  659. + for (i = 0; i < RT305X_ESW_NUM_LEDS; i++) {
  660. + if (!(changed & (1 << i)))
  661. + continue;
  662. + if (disable_mask & (1 << i)) {
  663. + /* disable */
  664. + rt305x_mii_write(esw, i, MII_BMCR,
  665. + BMCR_PDOWN);
  666. + } else {
  667. + /* enable */
  668. + rt305x_mii_write(esw, i, MII_BMCR,
  669. + BMCR_FULLDPLX |
  670. + BMCR_ANENABLE |
  671. + BMCR_ANRESTART |
  672. + BMCR_SPEED100);
  673. + }
  674. + }
  675. +
  676. + /* disable after writing to MII */
  677. + rt305x_esw_rmw(esw, RT305X_ESW_REG_POC0,
  678. + (RT305X_ESW_POC0_DIS_PORT_M <<
  679. + RT305X_ESW_POC0_DIS_PORT_S),
  680. + disable_mask << RT305X_ESW_POC0_DIS_PORT_S);
  681. +}
  682. +
  683. +static int
  684. +rt305x_esw_apply_config(struct switch_dev *dev);
  685. +
  686. +static void
  687. +rt305x_esw_hw_init(struct rt305x_esw *esw)
  688. +{
  689. + int i;
  690. + u8 port_disable = 0;
  691. + u8 port_map = RT305X_ESW_PMAP_LLLLLL;
  692. +
  693. + /* vodoo from original driver */
  694. + rt305x_esw_wr(esw, 0xC8A07850, RT305X_ESW_REG_FCT0);
  695. + rt305x_esw_wr(esw, 0x00000000, RT305X_ESW_REG_SGC2);
  696. + /* Port priority 1 for all ports, vlan enabled. */
  697. + rt305x_esw_wr(esw, 0x00005555 |
  698. + (RT305X_ESW_PORTS_ALL << RT305X_ESW_PFC1_EN_VLAN_S),
  699. + RT305X_ESW_REG_PFC1);
  700. +
  701. + /* Enable Back Pressure, and Flow Control */
  702. + rt305x_esw_wr(esw,
  703. + ((RT305X_ESW_PORTS_ALL << RT305X_ESW_POC0_EN_BP_S) |
  704. + (RT305X_ESW_PORTS_ALL << RT305X_ESW_POC0_EN_FC_S)),
  705. + RT305X_ESW_REG_POC0);
  706. +
  707. + /* Enable Aging, and VLAN TAG removal */
  708. + rt305x_esw_wr(esw,
  709. + ((RT305X_ESW_PORTS_ALL << RT305X_ESW_POC2_ENAGING_S) |
  710. + (RT305X_ESW_PORTS_NOCPU << RT305X_ESW_POC2_UNTAG_EN_S)),
  711. + RT305X_ESW_REG_POC2);
  712. +
  713. + if (esw->reg_initval_fct2)
  714. + rt305x_esw_wr(esw, esw->reg_initval_fct2, RT305X_ESW_REG_FCT2);
  715. + else
  716. + rt305x_esw_wr(esw, esw->pdata->reg_initval_fct2, RT305X_ESW_REG_FCT2);
  717. +
  718. + /*
  719. + * 300s aging timer, max packet len 1536, broadcast storm prevention
  720. + * disabled, disable collision abort, mac xor48 hash, 10 packet back
  721. + * pressure jam, GMII disable was_transmit, back pressure disabled,
  722. + * 30ms led flash, unmatched IGMP as broadcast, rmc tb fault to all
  723. + * ports.
  724. + */
  725. + rt305x_esw_wr(esw, 0x0008a301, RT305X_ESW_REG_SGC);
  726. + esw->sgc=0x0008a301;
  727. +
  728. + /* Setup SoC Port control register */
  729. + rt305x_esw_wr(esw,
  730. + (RT305X_ESW_SOCPC_CRC_PADDING |
  731. + (RT305X_ESW_PORTS_CPU << RT305X_ESW_SOCPC_DISUN2CPU_S) |
  732. + (RT305X_ESW_PORTS_CPU << RT305X_ESW_SOCPC_DISMC2CPU_S) |
  733. + (RT305X_ESW_PORTS_CPU << RT305X_ESW_SOCPC_DISBC2CPU_S)),
  734. + RT305X_ESW_REG_SOCPC);
  735. +
  736. + if (esw->reg_initval_fpa2)
  737. + rt305x_esw_wr(esw, esw->reg_initval_fpa2, RT305X_ESW_REG_FPA2);
  738. + else
  739. + rt305x_esw_wr(esw, esw->pdata->reg_initval_fpa2, RT305X_ESW_REG_FPA2);
  740. + rt305x_esw_wr(esw, 0x00000000, RT305X_ESW_REG_FPA);
  741. +
  742. + /* Force Link/Activity on ports */
  743. + rt305x_esw_wr(esw, 0x00000005, RT305X_ESW_REG_P0LED);
  744. + rt305x_esw_wr(esw, 0x00000005, RT305X_ESW_REG_P1LED);
  745. + rt305x_esw_wr(esw, 0x00000005, RT305X_ESW_REG_P2LED);
  746. + rt305x_esw_wr(esw, 0x00000005, RT305X_ESW_REG_P3LED);
  747. + rt305x_esw_wr(esw, 0x00000005, RT305X_ESW_REG_P4LED);
  748. +
  749. + if (soc_is_rt5350())
  750. + rt305x_esw_wr(esw,esw->led_polarity, RT305X_ESW_REG_LED_POLARITY);
  751. +
  752. + /* Copy disabled port configuration from bootloader setup */
  753. + port_disable = rt305x_esw_get_port_disable(esw);
  754. + for (i = 0; i < 6; i++)
  755. + esw->ports[i].disable = (port_disable & (1 << i)) != 0;
  756. +
  757. + rt305x_mii_write(esw, 0, 31, 0x8000);
  758. + for (i = 0; i < 5; i++) {
  759. + if (esw->ports[i].disable) {
  760. + rt305x_mii_write(esw, i, MII_BMCR, BMCR_PDOWN);
  761. + } else {
  762. + rt305x_mii_write(esw, i, MII_BMCR,
  763. + BMCR_FULLDPLX |
  764. + BMCR_ANENABLE |
  765. + BMCR_SPEED100);
  766. + }
  767. + /* TX10 waveform coefficient */
  768. + rt305x_mii_write(esw, i, 26, 0x1601);
  769. + /* TX100/TX10 AD/DA current bias */
  770. + rt305x_mii_write(esw, i, 29, 0x7058);
  771. + /* TX100 slew rate control */
  772. + rt305x_mii_write(esw, i, 30, 0x0018);
  773. + }
  774. +
  775. + /* PHY IOT */
  776. + /* select global register */
  777. + rt305x_mii_write(esw, 0, 31, 0x0);
  778. + /* tune TP_IDL tail and head waveform */
  779. + rt305x_mii_write(esw, 0, 22, 0x052f);
  780. + /* set TX10 signal amplitude threshold to minimum */
  781. + rt305x_mii_write(esw, 0, 17, 0x0fe0);
  782. + /* set squelch amplitude to higher threshold */
  783. + rt305x_mii_write(esw, 0, 18, 0x40ba);
  784. + /* longer TP_IDL tail length */
  785. + rt305x_mii_write(esw, 0, 14, 0x65);
  786. + /* select local register */
  787. + rt305x_mii_write(esw, 0, 31, 0x8000);
  788. +
  789. + if (esw->port_map)
  790. + port_map = esw->port_map;
  791. + else
  792. + port_map = RT305X_ESW_PMAP_LLLLLL;
  793. +
  794. + /*
  795. + * Unused HW feature, but still nice to be consistent here...
  796. + * This is also exported to userspace ('lan' attribute) so it's
  797. + * conveniently usable to decide which ports go into the wan vlan by
  798. + * default.
  799. + */
  800. + rt305x_esw_rmw(esw, RT305X_ESW_REG_SGC2,
  801. + RT305X_ESW_SGC2_LAN_PMAP_M << RT305X_ESW_SGC2_LAN_PMAP_S,
  802. + port_map << RT305X_ESW_SGC2_LAN_PMAP_S);
  803. +
  804. + /* make the switch leds blink */
  805. + for (i = 0; i < RT305X_ESW_NUM_LEDS; i++)
  806. + esw->ports[i].led = 0x05;
  807. +
  808. + /* Apply the empty config. */
  809. + rt305x_esw_apply_config(&esw->swdev);
  810. +}
  811. +
  812. +static irqreturn_t
  813. +rt305x_esw_interrupt(int irq, void *_esw)
  814. +{
  815. + struct rt305x_esw *esw = (struct rt305x_esw *) _esw;
  816. + u32 status;
  817. +
  818. + status = rt305x_esw_rr(esw, RT305X_ESW_REG_ISR);
  819. + if (status & RT305X_ESW_PORT_ST_CHG) {
  820. + u32 link = rt305x_esw_rr(esw, RT305X_ESW_REG_POA);
  821. + link >>= RT305X_ESW_POA_LINK_SHIFT;
  822. + link &= RT305X_ESW_POA_LINK_MASK;
  823. + dev_info(esw->dev, "link changed 0x%02X\n", link);
  824. + }
  825. + rt305x_esw_wr(esw, RT305X_ESW_PORT_ST_CHG, RT305X_ESW_REG_ISR);
  826. +
  827. + return IRQ_HANDLED;
  828. +}
  829. +
  830. +static void
  831. +rt305x_esw_request_irq(struct rt305x_esw *esw)
  832. +{
  833. + /* Only unmask the port change interrupt */
  834. + rt305x_esw_wr(esw, ~RT305X_ESW_PORT_ST_CHG, RT305X_ESW_REG_IMR);
  835. +
  836. + /* request the irq handler */
  837. + request_irq(esw->irq, rt305x_esw_interrupt, 0, "esw", esw);
  838. +}
  839. +
  840. +static int
  841. +rt305x_esw_apply_config(struct switch_dev *dev)
  842. +{
  843. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  844. + int i;
  845. + u8 disable = 0;
  846. + u8 doubletag = 0;
  847. + u8 en_vlan = 0;
  848. + u8 untag = 0;
  849. +
  850. + rt305x_esw_wr(esw, esw->sgc, RT305X_ESW_REG_SGC);
  851. +
  852. + for (i = 0; i < RT305X_ESW_NUM_VLANS; i++) {
  853. + u32 vid, vmsc;
  854. + if (esw->global_vlan_enable) {
  855. + vid = esw->vlans[i].vid;
  856. + vmsc = esw->vlans[i].ports;
  857. + } else {
  858. + vid = RT305X_ESW_VLAN_NONE;
  859. + vmsc = RT305X_ESW_PORTS_NONE;
  860. + }
  861. + rt305x_esw_set_vlan_id(esw, i, vid);
  862. + rt305x_esw_set_vmsc(esw, i, vmsc);
  863. + }
  864. +
  865. + if (soc_is_rt5350()) {
  866. + rt305x_esw_wr(esw,esw->led_polarity, RT305X_ESW_REG_LED_POLARITY);
  867. + }
  868. +
  869. + for (i = 0; i < RT305X_ESW_NUM_PORTS; i++) {
  870. + u32 pvid;
  871. + disable |= esw->ports[i].disable << i;
  872. + if (esw->global_vlan_enable) {
  873. + doubletag |= esw->ports[i].doubletag << i;
  874. + en_vlan |= 1 << i;
  875. + untag |= esw->ports[i].untag << i;
  876. + pvid = esw->ports[i].pvid;
  877. + } else {
  878. + int x = esw->alt_vlan_disable ? 0 : 1;
  879. + doubletag |= x << i;
  880. + en_vlan |= x << i;
  881. + untag |= x << i;
  882. + pvid = 0;
  883. + }
  884. + rt305x_esw_set_pvid(esw, i, pvid);
  885. + if (i < RT305X_ESW_NUM_LEDS)
  886. + rt305x_esw_wr(esw, esw->ports[i].led,
  887. + RT305X_ESW_REG_P0LED + 4*i);
  888. + }
  889. +
  890. + rt305x_esw_set_port_disable(esw, disable);
  891. + rt305x_esw_rmw(esw, RT305X_ESW_REG_SGC2,
  892. + (RT305X_ESW_SGC2_DOUBLE_TAG_M <<
  893. + RT305X_ESW_SGC2_DOUBLE_TAG_S),
  894. + doubletag << RT305X_ESW_SGC2_DOUBLE_TAG_S);
  895. + rt305x_esw_rmw(esw, RT305X_ESW_REG_PFC1,
  896. + RT305X_ESW_PFC1_EN_VLAN_M << RT305X_ESW_PFC1_EN_VLAN_S,
  897. + en_vlan << RT305X_ESW_PFC1_EN_VLAN_S);
  898. + rt305x_esw_rmw(esw, RT305X_ESW_REG_POC2,
  899. + RT305X_ESW_POC2_UNTAG_EN_M << RT305X_ESW_POC2_UNTAG_EN_S,
  900. + untag << RT305X_ESW_POC2_UNTAG_EN_S);
  901. +
  902. + if (!esw->global_vlan_enable) {
  903. + /*
  904. + * Still need to put all ports into vlan 0 or they'll be
  905. + * isolated.
  906. + * NOTE: vlan 0 is special, no vlan tag is prepended
  907. + */
  908. + rt305x_esw_set_vlan_id(esw, 0, 0);
  909. + rt305x_esw_set_vmsc(esw, 0, RT305X_ESW_PORTS_ALL);
  910. + }
  911. +
  912. + return 0;
  913. +}
  914. +
  915. +static int
  916. +rt305x_esw_reset_switch(struct switch_dev *dev)
  917. +{
  918. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  919. + esw->global_vlan_enable = 0;
  920. + memset(esw->ports, 0, sizeof(esw->ports));
  921. + memset(esw->vlans, 0, sizeof(esw->vlans));
  922. + rt305x_esw_hw_init(esw);
  923. +
  924. + return 0;
  925. +}
  926. +
  927. +static int
  928. +rt305x_esw_get_vlan_enable(struct switch_dev *dev,
  929. + const struct switch_attr *attr,
  930. + struct switch_val *val)
  931. +{
  932. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  933. +
  934. + val->value.i = esw->global_vlan_enable;
  935. +
  936. + return 0;
  937. +}
  938. +
  939. +static int
  940. +rt305x_esw_set_vlan_enable(struct switch_dev *dev,
  941. + const struct switch_attr *attr,
  942. + struct switch_val *val)
  943. +{
  944. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  945. +
  946. + esw->global_vlan_enable = val->value.i != 0;
  947. +
  948. + return 0;
  949. +}
  950. +
  951. +static int
  952. +rt305x_esw_get_alt_vlan_disable(struct switch_dev *dev,
  953. + const struct switch_attr *attr,
  954. + struct switch_val *val)
  955. +{
  956. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  957. +
  958. + val->value.i = esw->alt_vlan_disable;
  959. +
  960. + return 0;
  961. +}
  962. +
  963. +static int
  964. +rt305x_esw_set_alt_vlan_disable(struct switch_dev *dev,
  965. + const struct switch_attr *attr,
  966. + struct switch_val *val)
  967. +{
  968. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  969. +
  970. + esw->alt_vlan_disable = val->value.i != 0;
  971. +
  972. + return 0;
  973. +}
  974. +
  975. +static int
  976. +rt305x_esw_get_port_link(struct switch_dev *dev,
  977. + int port,
  978. + struct switch_port_link *link)
  979. +{
  980. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  981. + u32 speed, poa;
  982. +
  983. + if (port < 0 || port >= RT305X_ESW_NUM_PORTS)
  984. + return -EINVAL;
  985. +
  986. + poa = rt305x_esw_rr(esw, RT305X_ESW_REG_POA) >> port;
  987. +
  988. + link->link = (poa >> RT305X_ESW_LINK_S) & 1;
  989. + link->duplex = (poa >> RT305X_ESW_DUPLEX_S) & 1;
  990. + if (port < RT305X_ESW_NUM_LEDS) {
  991. + speed = (poa >> RT305X_ESW_SPD_S) & 1;
  992. + } else {
  993. + if (port == RT305X_ESW_NUM_PORTS - 1)
  994. + poa >>= 1;
  995. + speed = (poa >> RT305X_ESW_SPD_S) & 3;
  996. + }
  997. + switch (speed) {
  998. + case 0:
  999. + link->speed = SWITCH_PORT_SPEED_10;
  1000. + break;
  1001. + case 1:
  1002. + link->speed = SWITCH_PORT_SPEED_100;
  1003. + break;
  1004. + case 2:
  1005. + case 3: /* forced gige speed can be 2 or 3 */
  1006. + link->speed = SWITCH_PORT_SPEED_1000;
  1007. + break;
  1008. + default:
  1009. + link->speed = SWITCH_PORT_SPEED_UNKNOWN;
  1010. + break;
  1011. + }
  1012. +
  1013. + return 0;
  1014. +}
  1015. +
  1016. +static int
  1017. +rt305x_esw_get_port_bool(struct switch_dev *dev,
  1018. + const struct switch_attr *attr,
  1019. + struct switch_val *val)
  1020. +{
  1021. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1022. + int idx = val->port_vlan;
  1023. + u32 x, reg, shift;
  1024. +
  1025. + if (idx < 0 || idx >= RT305X_ESW_NUM_PORTS)
  1026. + return -EINVAL;
  1027. +
  1028. + switch (attr->id) {
  1029. + case RT305X_ESW_ATTR_PORT_DISABLE:
  1030. + reg = RT305X_ESW_REG_POC0;
  1031. + shift = RT305X_ESW_POC0_DIS_PORT_S;
  1032. + break;
  1033. + case RT305X_ESW_ATTR_PORT_DOUBLETAG:
  1034. + reg = RT305X_ESW_REG_SGC2;
  1035. + shift = RT305X_ESW_SGC2_DOUBLE_TAG_S;
  1036. + break;
  1037. + case RT305X_ESW_ATTR_PORT_UNTAG:
  1038. + reg = RT305X_ESW_REG_POC2;
  1039. + shift = RT305X_ESW_POC2_UNTAG_EN_S;
  1040. + break;
  1041. + case RT305X_ESW_ATTR_PORT_LAN:
  1042. + reg = RT305X_ESW_REG_SGC2;
  1043. + shift = RT305X_ESW_SGC2_LAN_PMAP_S;
  1044. + if (idx >= RT305X_ESW_NUM_LANWAN)
  1045. + return -EINVAL;
  1046. + break;
  1047. + default:
  1048. + return -EINVAL;
  1049. + }
  1050. +
  1051. + x = rt305x_esw_rr(esw, reg);
  1052. + val->value.i = (x >> (idx + shift)) & 1;
  1053. +
  1054. + return 0;
  1055. +}
  1056. +
  1057. +static int
  1058. +rt305x_esw_set_port_bool(struct switch_dev *dev,
  1059. + const struct switch_attr *attr,
  1060. + struct switch_val *val)
  1061. +{
  1062. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1063. + int idx = val->port_vlan;
  1064. +
  1065. + if (idx < 0 || idx >= RT305X_ESW_NUM_PORTS ||
  1066. + val->value.i < 0 || val->value.i > 1)
  1067. + return -EINVAL;
  1068. +
  1069. + switch (attr->id) {
  1070. + case RT305X_ESW_ATTR_PORT_DISABLE:
  1071. + esw->ports[idx].disable = val->value.i;
  1072. + break;
  1073. + case RT305X_ESW_ATTR_PORT_DOUBLETAG:
  1074. + esw->ports[idx].doubletag = val->value.i;
  1075. + break;
  1076. + case RT305X_ESW_ATTR_PORT_UNTAG:
  1077. + esw->ports[idx].untag = val->value.i;
  1078. + break;
  1079. + default:
  1080. + return -EINVAL;
  1081. + }
  1082. +
  1083. + return 0;
  1084. +}
  1085. +
  1086. +static int
  1087. +rt305x_esw_get_port_recv_badgood(struct switch_dev *dev,
  1088. + const struct switch_attr *attr,
  1089. + struct switch_val *val)
  1090. +{
  1091. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1092. + int idx = val->port_vlan;
  1093. + int shift = attr->id == RT305X_ESW_ATTR_PORT_RECV_GOOD ? 0 : 16;
  1094. + u32 reg;
  1095. +
  1096. + if (idx < 0 || idx >= RT305X_ESW_NUM_LANWAN)
  1097. + return -EINVAL;
  1098. +
  1099. + reg = rt305x_esw_rr(esw, RT305X_ESW_REG_P0PC + 4*idx);
  1100. + val->value.i = (reg >> shift) & 0xffff;
  1101. +
  1102. + return 0;
  1103. +}
  1104. +
  1105. +static int
  1106. +rt305x_esw_get_port_tr_badgood(struct switch_dev *dev,
  1107. + const struct switch_attr *attr,
  1108. + struct switch_val *val)
  1109. +{
  1110. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1111. + int idx = val->port_vlan;
  1112. + int shift = attr->id == RT305X_ESW_ATTR_PORT_TR_GOOD ? 0 : 16;
  1113. + u32 reg;
  1114. +
  1115. + if (!soc_is_rt5350())
  1116. + return -EINVAL;
  1117. +
  1118. + if (idx < 0 || idx >= RT305X_ESW_NUM_LANWAN)
  1119. + return -EINVAL;
  1120. +
  1121. + reg = rt305x_esw_rr(esw, RT305X_ESW_REG_P0TPC + 4*idx);
  1122. + val->value.i = (reg >> shift) & 0xffff;
  1123. + return 0;
  1124. +}
  1125. +
  1126. +static int
  1127. +rt305x_esw_get_port_led(struct switch_dev *dev,
  1128. + const struct switch_attr *attr,
  1129. + struct switch_val *val)
  1130. +{
  1131. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1132. + int idx = val->port_vlan;
  1133. +
  1134. + if (idx < 0 || idx >= RT305X_ESW_NUM_PORTS ||
  1135. + idx >= RT305X_ESW_NUM_LEDS)
  1136. + return -EINVAL;
  1137. +
  1138. + val->value.i = rt305x_esw_rr(esw, RT305X_ESW_REG_P0LED + 4*idx);
  1139. +
  1140. + return 0;
  1141. +}
  1142. +
  1143. +static int
  1144. +rt305x_esw_set_port_led(struct switch_dev *dev,
  1145. + const struct switch_attr *attr,
  1146. + struct switch_val *val)
  1147. +{
  1148. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1149. + int idx = val->port_vlan;
  1150. +
  1151. + if (idx < 0 || idx >= RT305X_ESW_NUM_LEDS)
  1152. + return -EINVAL;
  1153. +
  1154. + esw->ports[idx].led = val->value.i;
  1155. +
  1156. + return 0;
  1157. +}
  1158. +
  1159. +static int
  1160. +rt305x_esw_get_port_pvid(struct switch_dev *dev, int port, int *val)
  1161. +{
  1162. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1163. +
  1164. + if (port >= RT305X_ESW_NUM_PORTS)
  1165. + return -EINVAL;
  1166. +
  1167. + *val = rt305x_esw_get_pvid(esw, port);
  1168. +
  1169. + return 0;
  1170. +}
  1171. +
  1172. +static int
  1173. +rt305x_esw_set_port_pvid(struct switch_dev *dev, int port, int val)
  1174. +{
  1175. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1176. +
  1177. + if (port >= RT305X_ESW_NUM_PORTS)
  1178. + return -EINVAL;
  1179. +
  1180. + esw->ports[port].pvid = val;
  1181. +
  1182. + return 0;
  1183. +}
  1184. +
  1185. +static int
  1186. +rt305x_esw_get_vlan_ports(struct switch_dev *dev, struct switch_val *val)
  1187. +{
  1188. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1189. + u32 vmsc, poc2;
  1190. + int vlan_idx = -1;
  1191. + int i;
  1192. +
  1193. + val->len = 0;
  1194. +
  1195. + if (val->port_vlan < 0 || val->port_vlan >= RT305X_ESW_NUM_VIDS)
  1196. + return -EINVAL;
  1197. +
  1198. + /* valid vlan? */
  1199. + for (i = 0; i < RT305X_ESW_NUM_VLANS; i++) {
  1200. + if (rt305x_esw_get_vlan_id(esw, i) == val->port_vlan &&
  1201. + rt305x_esw_get_vmsc(esw, i) != RT305X_ESW_PORTS_NONE) {
  1202. + vlan_idx = i;
  1203. + break;
  1204. + }
  1205. + }
  1206. +
  1207. + if (vlan_idx == -1)
  1208. + return -EINVAL;
  1209. +
  1210. + vmsc = rt305x_esw_get_vmsc(esw, vlan_idx);
  1211. + poc2 = rt305x_esw_rr(esw, RT305X_ESW_REG_POC2);
  1212. +
  1213. + for (i = 0; i < RT305X_ESW_NUM_PORTS; i++) {
  1214. + struct switch_port *p;
  1215. + int port_mask = 1 << i;
  1216. +
  1217. + if (!(vmsc & port_mask))
  1218. + continue;
  1219. +
  1220. + p = &val->value.ports[val->len++];
  1221. + p->id = i;
  1222. + if (poc2 & (port_mask << RT305X_ESW_POC2_UNTAG_EN_S))
  1223. + p->flags = 0;
  1224. + else
  1225. + p->flags = 1 << SWITCH_PORT_FLAG_TAGGED;
  1226. + }
  1227. +
  1228. + return 0;
  1229. +}
  1230. +
  1231. +static int
  1232. +rt305x_esw_set_vlan_ports(struct switch_dev *dev, struct switch_val *val)
  1233. +{
  1234. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1235. + int ports;
  1236. + int vlan_idx = -1;
  1237. + int i;
  1238. +
  1239. + if (val->port_vlan < 0 || val->port_vlan >= RT305X_ESW_NUM_VIDS ||
  1240. + val->len > RT305X_ESW_NUM_PORTS)
  1241. + return -EINVAL;
  1242. +
  1243. + /* one of the already defined vlans? */
  1244. + for (i = 0; i < RT305X_ESW_NUM_VLANS; i++) {
  1245. + if (esw->vlans[i].vid == val->port_vlan &&
  1246. + esw->vlans[i].ports != RT305X_ESW_PORTS_NONE) {
  1247. + vlan_idx = i;
  1248. + break;
  1249. + }
  1250. + }
  1251. +
  1252. + /* select a free slot */
  1253. + for (i = 0; vlan_idx == -1 && i < RT305X_ESW_NUM_VLANS; i++) {
  1254. + if (esw->vlans[i].ports == RT305X_ESW_PORTS_NONE)
  1255. + vlan_idx = i;
  1256. + }
  1257. +
  1258. + /* bail if all slots are in use */
  1259. + if (vlan_idx == -1)
  1260. + return -EINVAL;
  1261. +
  1262. + ports = RT305X_ESW_PORTS_NONE;
  1263. + for (i = 0; i < val->len; i++) {
  1264. + struct switch_port *p = &val->value.ports[i];
  1265. + int port_mask = 1 << p->id;
  1266. + bool untagged = !(p->flags & (1 << SWITCH_PORT_FLAG_TAGGED));
  1267. +
  1268. + if (p->id >= RT305X_ESW_NUM_PORTS)
  1269. + return -EINVAL;
  1270. +
  1271. + ports |= port_mask;
  1272. + esw->ports[p->id].untag = untagged;
  1273. + }
  1274. + esw->vlans[vlan_idx].ports = ports;
  1275. + if (ports == RT305X_ESW_PORTS_NONE)
  1276. + esw->vlans[vlan_idx].vid = RT305X_ESW_VLAN_NONE;
  1277. + else
  1278. + esw->vlans[vlan_idx].vid = val->port_vlan;
  1279. +
  1280. + return 0;
  1281. +}
  1282. +
  1283. +static int
  1284. +rt305x_esw_set_port_led_polarity(struct switch_dev *dev,
  1285. + const struct switch_attr *attr,
  1286. + struct switch_val *val)
  1287. +{
  1288. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1289. + int idx = val->port_vlan;
  1290. +
  1291. + if (idx < 0 || idx >= RT305X_ESW_NUM_LEDS)
  1292. + return -EINVAL;
  1293. +
  1294. + if (!soc_is_rt5350())
  1295. + return -EINVAL;
  1296. +
  1297. + if (val->value.i==0)
  1298. + esw->led_polarity &= ~ (1 << idx);
  1299. + else
  1300. + esw->led_polarity |= (1 << idx);
  1301. + return 0;
  1302. +}
  1303. +
  1304. +static int
  1305. +rt305x_esw_get_port_led_polarity(struct switch_dev *dev,
  1306. + const struct switch_attr *attr,
  1307. + struct switch_val *val)
  1308. +{
  1309. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1310. + int idx = val->port_vlan;
  1311. +
  1312. + if (!soc_is_rt5350())
  1313. + return -EINVAL;
  1314. +
  1315. +
  1316. + if (idx < 0 || idx >= RT305X_ESW_NUM_PORTS ||
  1317. + idx >= RT305X_ESW_NUM_LEDS)
  1318. + return -EINVAL;
  1319. +
  1320. + val->value.i = (rt305x_esw_rr(esw, RT305X_ESW_REG_LED_POLARITY) >> idx) & 1;
  1321. +
  1322. + return 0;
  1323. +}
  1324. +
  1325. +static int
  1326. +rt305x_esw_set_led_freq(struct switch_dev *dev,
  1327. + const struct switch_attr *attr,
  1328. + struct switch_val *val)
  1329. +{
  1330. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1331. +
  1332. + esw->sgc &= 0xfe7fffff;
  1333. + esw->sgc |= ((val->value.i & 3) << 23);
  1334. + return 0;
  1335. +}
  1336. +
  1337. +static int
  1338. +rt305x_esw_get_led_freq(struct switch_dev *dev,
  1339. + const struct switch_attr *attr,
  1340. + struct switch_val *val)
  1341. +{
  1342. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1343. +
  1344. + val->value.i = (rt305x_esw_rr(esw,RT305X_ESW_REG_SGC) >> 23) & 3;
  1345. +
  1346. + return 0;
  1347. +}
  1348. +
  1349. +static int
  1350. +rt305x_esw_set_pkt_length(struct switch_dev *dev,
  1351. + const struct switch_attr *attr,
  1352. + struct switch_val *val)
  1353. +{
  1354. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1355. +
  1356. + esw->sgc &= 0xffffff3f;
  1357. + esw->sgc |= ((val->value.i & 3) << 6);
  1358. + return 0;
  1359. +}
  1360. +
  1361. +static int
  1362. +rt305x_esw_get_pkt_length(struct switch_dev *dev,
  1363. + const struct switch_attr *attr,
  1364. + struct switch_val *val)
  1365. +{
  1366. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1367. +
  1368. + val->value.i = (rt305x_esw_rr(esw, RT305X_ESW_REG_SGC) >> 6) & 3;
  1369. +
  1370. + return 0;
  1371. +}
  1372. +
  1373. +
  1374. +static int
  1375. +rt305x_esw_set_bc_status(struct switch_dev *dev,
  1376. + const struct switch_attr *attr,
  1377. + struct switch_val *val)
  1378. +{
  1379. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1380. +
  1381. + esw->sgc &= 0xffffffcf;
  1382. + esw->sgc |= ((val->value.i & 3) << 4);
  1383. + return 0;
  1384. +}
  1385. +
  1386. +static int
  1387. +rt305x_esw_get_bc_status(struct switch_dev *dev,
  1388. + const struct switch_attr *attr,
  1389. + struct switch_val *val)
  1390. +{
  1391. + struct rt305x_esw *esw = container_of(dev, struct rt305x_esw, swdev);
  1392. +
  1393. + val->value.i = (rt305x_esw_rr(esw, RT305X_ESW_REG_SGC) >> 4) & 3;
  1394. +
  1395. + return 0;
  1396. +}
  1397. +
  1398. +static const struct switch_attr rt305x_esw_global[] = {
  1399. + {
  1400. + .type = SWITCH_TYPE_INT,
  1401. + .name = "enable_vlan",
  1402. + .description = "VLAN mode (1:enabled)",
  1403. + .max = 1,
  1404. + .id = RT305X_ESW_ATTR_ENABLE_VLAN,
  1405. + .get = rt305x_esw_get_vlan_enable,
  1406. + .set = rt305x_esw_set_vlan_enable,
  1407. + },
  1408. + {
  1409. + .type = SWITCH_TYPE_INT,
  1410. + .name = "alternate_vlan_disable",
  1411. + .description = "Use en_vlan instead of doubletag to disable"
  1412. + " VLAN mode",
  1413. + .max = 1,
  1414. + .id = RT305X_ESW_ATTR_ALT_VLAN_DISABLE,
  1415. + .get = rt305x_esw_get_alt_vlan_disable,
  1416. + .set = rt305x_esw_set_alt_vlan_disable,
  1417. + },
  1418. + {
  1419. + .type = SWITCH_TYPE_INT,
  1420. + .name = "led_freq",
  1421. + .description = "LED Flash frequency (0:30mS, 1:60mS, 2:240mS, 3:480mS)",
  1422. + .max = 3,
  1423. + .id = RT305X_ESW_ATTR_LED_FREQ,
  1424. + .get = rt305x_esw_get_led_freq,
  1425. + .set = rt305x_esw_set_led_freq,
  1426. + },
  1427. + {
  1428. + .type = SWITCH_TYPE_INT,
  1429. + .name = "pkt_maxlen",
  1430. + .description = "Maximum packet lenghth tagged/untagged (0:1536/1536, 1:1522/1518, 2:1526/1522)",
  1431. + .max = 2,
  1432. + .id = RT305X_ESW_ATTR_PKT_LENGTH,
  1433. + .get = rt305x_esw_get_pkt_length,
  1434. + .set = rt305x_esw_set_pkt_length,
  1435. + },
  1436. + {
  1437. + .type = SWITCH_TYPE_INT,
  1438. + .name = "bc_storm_protect",
  1439. + .description = "Global broadcast storm protection (0:Disable, 1:64 blocks, 2:96 blocks, 3:128 blocks)",
  1440. + .max = 2,
  1441. + .id = RT305X_ESW_ATTR_BC_STATUS,
  1442. + .get = rt305x_esw_get_bc_status,
  1443. + .set = rt305x_esw_set_bc_status,
  1444. + },
  1445. +};
  1446. +
  1447. +static const struct switch_attr rt305x_esw_port[] = {
  1448. + {
  1449. + .type = SWITCH_TYPE_INT,
  1450. + .name = "disable",
  1451. + .description = "Port state (1:disabled)",
  1452. + .max = 1,
  1453. + .id = RT305X_ESW_ATTR_PORT_DISABLE,
  1454. + .get = rt305x_esw_get_port_bool,
  1455. + .set = rt305x_esw_set_port_bool,
  1456. + },
  1457. + {
  1458. + .type = SWITCH_TYPE_INT,
  1459. + .name = "doubletag",
  1460. + .description = "Double tagging for incoming vlan packets "
  1461. + "(1:enabled)",
  1462. + .max = 1,
  1463. + .id = RT305X_ESW_ATTR_PORT_DOUBLETAG,
  1464. + .get = rt305x_esw_get_port_bool,
  1465. + .set = rt305x_esw_set_port_bool,
  1466. + },
  1467. + {
  1468. + .type = SWITCH_TYPE_INT,
  1469. + .name = "untag",
  1470. + .description = "Untag (1:strip outgoing vlan tag)",
  1471. + .max = 1,
  1472. + .id = RT305X_ESW_ATTR_PORT_UNTAG,
  1473. + .get = rt305x_esw_get_port_bool,
  1474. + .set = rt305x_esw_set_port_bool,
  1475. + },
  1476. + {
  1477. + .type = SWITCH_TYPE_INT,
  1478. + .name = "led",
  1479. + .description = "LED mode (0:link, 1:100m, 2:duplex, 3:activity,"
  1480. + " 4:collision, 5:linkact, 6:duplcoll, 7:10mact,"
  1481. + " 8:100mact, 10:blink, 11:off, 12:on)",
  1482. + .max = 15,
  1483. + .id = RT305X_ESW_ATTR_PORT_LED,
  1484. + .get = rt305x_esw_get_port_led,
  1485. + .set = rt305x_esw_set_port_led,
  1486. + },
  1487. + {
  1488. + .type = SWITCH_TYPE_INT,
  1489. + .name = "lan",
  1490. + .description = "HW port group (0:wan, 1:lan)",
  1491. + .max = 1,
  1492. + .id = RT305X_ESW_ATTR_PORT_LAN,
  1493. + .get = rt305x_esw_get_port_bool,
  1494. + },
  1495. + {
  1496. + .type = SWITCH_TYPE_INT,
  1497. + .name = "recv_bad",
  1498. + .description = "Receive bad packet counter",
  1499. + .id = RT305X_ESW_ATTR_PORT_RECV_BAD,
  1500. + .get = rt305x_esw_get_port_recv_badgood,
  1501. + },
  1502. + {
  1503. + .type = SWITCH_TYPE_INT,
  1504. + .name = "recv_good",
  1505. + .description = "Receive good packet counter",
  1506. + .id = RT305X_ESW_ATTR_PORT_RECV_GOOD,
  1507. + .get = rt305x_esw_get_port_recv_badgood,
  1508. + },
  1509. + {
  1510. + .type = SWITCH_TYPE_INT,
  1511. + .name = "led_polarity",
  1512. + .description = "LED Polarity for each port (0:low active, 1:high active). rt5350 only",
  1513. + .max = 1,
  1514. + .id = RT305X_ESW_ATTR_PORT_LED_POLARITY,
  1515. + .get = rt305x_esw_get_port_led_polarity,
  1516. + .set = rt305x_esw_set_port_led_polarity,
  1517. + },
  1518. + {
  1519. + .type = SWITCH_TYPE_INT,
  1520. + .name = "tr_bad",
  1521. + .description = "Transmit bad packet counter. rt5350 only",
  1522. + .id = RT305X_ESW_ATTR_PORT_TR_BAD,
  1523. + .get = rt305x_esw_get_port_tr_badgood,
  1524. + },
  1525. + {
  1526. + .type = SWITCH_TYPE_INT,
  1527. + .name = "tr_good",
  1528. + .description = "Transmit good packet counter. rt5350 only",
  1529. + .id = RT305X_ESW_ATTR_PORT_TR_GOOD,
  1530. + .get = rt305x_esw_get_port_tr_badgood,
  1531. + },
  1532. +};
  1533. +
  1534. +static const struct switch_attr rt305x_esw_vlan[] = {
  1535. +};
  1536. +
  1537. +static const struct switch_dev_ops rt305x_esw_ops = {
  1538. + .attr_global = {
  1539. + .attr = rt305x_esw_global,
  1540. + .n_attr = ARRAY_SIZE(rt305x_esw_global),
  1541. + },
  1542. + .attr_port = {
  1543. + .attr = rt305x_esw_port,
  1544. + .n_attr = ARRAY_SIZE(rt305x_esw_port),
  1545. + },
  1546. + .attr_vlan = {
  1547. + .attr = rt305x_esw_vlan,
  1548. + .n_attr = ARRAY_SIZE(rt305x_esw_vlan),
  1549. + },
  1550. + .get_vlan_ports = rt305x_esw_get_vlan_ports,
  1551. + .set_vlan_ports = rt305x_esw_set_vlan_ports,
  1552. + .get_port_pvid = rt305x_esw_get_port_pvid,
  1553. + .set_port_pvid = rt305x_esw_set_port_pvid,
  1554. + .get_port_link = rt305x_esw_get_port_link,
  1555. + .apply_config = rt305x_esw_apply_config,
  1556. + .reset_switch = rt305x_esw_reset_switch,
  1557. +};
  1558. +
  1559. +static struct rt305x_esw_platform_data rt3050_esw_data = {
  1560. + /* All ports are LAN ports. */
  1561. + .vlan_config = RT305X_ESW_VLAN_CONFIG_NONE,
  1562. + .reg_initval_fct2 = 0x00d6500c,
  1563. + /*
  1564. + * ext phy base addr 31, enable port 5 polling, rx/tx clock skew 1,
  1565. + * turbo mii off, rgmi 3.3v off
  1566. + * port5: disabled
  1567. + * port6: enabled, gige, full-duplex, rx/tx-flow-control
  1568. + */
  1569. + .reg_initval_fpa2 = 0x3f502b28,
  1570. +};
  1571. +
  1572. +static const struct of_device_id ralink_esw_match[] = {
  1573. + { .compatible = "ralink,rt3050-esw", .data = &rt3050_esw_data },
  1574. + {},
  1575. +};
  1576. +MODULE_DEVICE_TABLE(of, ralink_esw_match);
  1577. +
  1578. +static int
  1579. +rt305x_esw_probe(struct platform_device *pdev)
  1580. +{
  1581. + struct device_node *np = pdev->dev.of_node;
  1582. + const struct rt305x_esw_platform_data *pdata;
  1583. + const __be32 *port_map, *reg_init, *led_polarity;
  1584. + struct rt305x_esw *esw;
  1585. + struct switch_dev *swdev;
  1586. + struct resource *res, *irq;
  1587. + int err;
  1588. +
  1589. + pdata = pdev->dev.platform_data;
  1590. + if (!pdata) {
  1591. + const struct of_device_id *match;
  1592. + match = of_match_device(ralink_esw_match, &pdev->dev);
  1593. + if (match)
  1594. + pdata = (struct rt305x_esw_platform_data *) match->data;
  1595. + }
  1596. + if (!pdata)
  1597. + return -EINVAL;
  1598. +
  1599. + res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
  1600. + if (!res) {
  1601. + dev_err(&pdev->dev, "no memory resource found\n");
  1602. + return -ENOMEM;
  1603. + }
  1604. +
  1605. + irq = platform_get_resource(pdev, IORESOURCE_IRQ, 0);
  1606. + if (!irq) {
  1607. + dev_err(&pdev->dev, "no irq resource found\n");
  1608. + return -ENOMEM;
  1609. + }
  1610. +
  1611. + esw = kzalloc(sizeof(struct rt305x_esw), GFP_KERNEL);
  1612. + if (!esw) {
  1613. + dev_err(&pdev->dev, "no memory for private data\n");
  1614. + return -ENOMEM;
  1615. + }
  1616. +
  1617. + esw->dev = &pdev->dev;
  1618. + esw->irq = irq->start;
  1619. + esw->base = ioremap(res->start, resource_size(res));
  1620. + if (!esw->base) {
  1621. + dev_err(&pdev->dev, "ioremap failed\n");
  1622. + err = -ENOMEM;
  1623. + goto free_esw;
  1624. + }
  1625. +
  1626. + port_map = of_get_property(np, "ralink,portmap", NULL);
  1627. + if (port_map)
  1628. + esw->port_map = be32_to_cpu(*port_map);
  1629. +
  1630. + reg_init = of_get_property(np, "ralink,fct2", NULL);
  1631. + if (reg_init)
  1632. + esw->reg_initval_fct2 = be32_to_cpu(*reg_init);
  1633. +
  1634. + reg_init = of_get_property(np, "ralink,fpa2", NULL);
  1635. + if (reg_init)
  1636. + esw->reg_initval_fpa2 = be32_to_cpu(*reg_init);
  1637. +
  1638. + led_polarity = of_get_property(np, "ralink,led-polarity", NULL);
  1639. + if (led_polarity && soc_is_rt5350())
  1640. + esw->led_polarity = be32_to_cpu(*led_polarity) & 0x1F;
  1641. +
  1642. + swdev = &esw->swdev;
  1643. + swdev->of_node = pdev->dev.of_node;
  1644. + swdev->name = "rt305x-esw";
  1645. + swdev->alias = "rt305x";
  1646. + swdev->cpu_port = RT305X_ESW_PORT6;
  1647. + swdev->ports = RT305X_ESW_NUM_PORTS;
  1648. + swdev->vlans = RT305X_ESW_NUM_VIDS;
  1649. + swdev->ops = &rt305x_esw_ops;
  1650. +
  1651. + err = register_switch(swdev, NULL);
  1652. + if (err < 0) {
  1653. + dev_err(&pdev->dev, "register_switch failed\n");
  1654. + goto unmap_base;
  1655. + }
  1656. +
  1657. + platform_set_drvdata(pdev, esw);
  1658. +
  1659. + esw->pdata = pdata;
  1660. + spin_lock_init(&esw->reg_rw_lock);
  1661. + rt305x_esw_hw_init(esw);
  1662. + rt305x_esw_request_irq(esw);
  1663. +
  1664. + return 0;
  1665. +
  1666. +unmap_base:
  1667. + iounmap(esw->base);
  1668. +free_esw:
  1669. + kfree(esw);
  1670. + return err;
  1671. +}
  1672. +
  1673. +static int
  1674. +rt305x_esw_remove(struct platform_device *pdev)
  1675. +{
  1676. + struct rt305x_esw *esw;
  1677. +
  1678. + esw = platform_get_drvdata(pdev);
  1679. + if (esw) {
  1680. + unregister_switch(&esw->swdev);
  1681. + platform_set_drvdata(pdev, NULL);
  1682. + iounmap(esw->base);
  1683. + kfree(esw);
  1684. + }
  1685. +
  1686. + return 0;
  1687. +}
  1688. +
  1689. +static struct platform_driver rt305x_esw_driver = {
  1690. + .probe = rt305x_esw_probe,
  1691. + .remove = rt305x_esw_remove,
  1692. + .driver = {
  1693. + .name = "rt305x-esw",
  1694. + .owner = THIS_MODULE,
  1695. + .of_match_table = ralink_esw_match,
  1696. + },
  1697. +};
  1698. +
  1699. +static int __init
  1700. +rt305x_esw_init(void)
  1701. +{
  1702. + return platform_driver_register(&rt305x_esw_driver);
  1703. +}
  1704. +
  1705. +static void
  1706. +rt305x_esw_exit(void)
  1707. +{
  1708. + platform_driver_unregister(&rt305x_esw_driver);
  1709. +}
  1710. Index: linux-3.8.12/drivers/net/ethernet/ramips/ramips_eth.h
  1711. ===================================================================
  1712. --- /dev/null 1970-01-01 00:00:00.000000000 +0000
  1713. +++ linux-3.8.12/drivers/net/ethernet/ramips/ramips_eth.h 2013-05-20 18:44:40.000000000 +0400
  1714. @@ -0,0 +1,375 @@
  1715. +/*
  1716. + * This program is free software; you can redistribute it and/or modify
  1717. + * it under the terms of the GNU General Public License as published by
  1718. + * the Free Software Foundation; version 2 of the License
  1719. + *
  1720. + * This program is distributed in the hope that it will be useful,
  1721. + * but WITHOUT ANY WARRANTY; without even the implied warranty of
  1722. + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  1723. + * GNU General Public License for more details.
  1724. + *
  1725. + * You should have received a copy of the GNU General Public License
  1726. + * along with this program; if not, write to the Free Software
  1727. + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
  1728. + *
  1729. + * based on Ralink SDK3.3
  1730. + * Copyright (C) 2009 John Crispin <blogic@openwrt.org>
  1731. + */
  1732. +
  1733. +#ifndef RAMIPS_ETH_H
  1734. +#define RAMIPS_ETH_H
  1735. +
  1736. +#include <linux/mii.h>
  1737. +#include <linux/interrupt.h>
  1738. +#include <linux/netdevice.h>
  1739. +#include <linux/dma-mapping.h>
  1740. +
  1741. +#define NUM_RX_DESC 256
  1742. +#define NUM_TX_DESC 256
  1743. +
  1744. +#define RAMIPS_DELAY_EN_INT 0x80
  1745. +#define RAMIPS_DELAY_MAX_INT 0x04
  1746. +#define RAMIPS_DELAY_MAX_TOUT 0x04
  1747. +#define RAMIPS_DELAY_CHAN (((RAMIPS_DELAY_EN_INT | RAMIPS_DELAY_MAX_INT) << 8) | RAMIPS_DELAY_MAX_TOUT)
  1748. +#define RAMIPS_DELAY_INIT ((RAMIPS_DELAY_CHAN << 16) | RAMIPS_DELAY_CHAN)
  1749. +#define RAMIPS_PSE_FQFC_CFG_INIT 0x80504000
  1750. +
  1751. +/* interrupt bits */
  1752. +#define RAMIPS_CNT_PPE_AF BIT(31)
  1753. +#define RAMIPS_CNT_GDM_AF BIT(29)
  1754. +#define RAMIPS_PSE_P2_FC BIT(26)
  1755. +#define RAMIPS_PSE_BUF_DROP BIT(24)
  1756. +#define RAMIPS_GDM_OTHER_DROP BIT(23)
  1757. +#define RAMIPS_PSE_P1_FC BIT(22)
  1758. +#define RAMIPS_PSE_P0_FC BIT(21)
  1759. +#define RAMIPS_PSE_FQ_EMPTY BIT(20)
  1760. +#define RAMIPS_GE1_STA_CHG BIT(18)
  1761. +#define RAMIPS_TX_COHERENT BIT(17)
  1762. +#define RAMIPS_RX_COHERENT BIT(16)
  1763. +#define RAMIPS_TX_DONE_INT3 BIT(11)
  1764. +#define RAMIPS_TX_DONE_INT2 BIT(10)
  1765. +#define RAMIPS_TX_DONE_INT1 BIT(9)
  1766. +#define RAMIPS_TX_DONE_INT0 BIT(8)
  1767. +#define RAMIPS_RX_DONE_INT0 BIT(2)
  1768. +#define RAMIPS_TX_DLY_INT BIT(1)
  1769. +#define RAMIPS_RX_DLY_INT BIT(0)
  1770. +
  1771. +#define RT5350_RX_DLY_INT BIT(30)
  1772. +#define RT5350_TX_DLY_INT BIT(28)
  1773. +
  1774. +/* registers */
  1775. +#define RAMIPS_FE_OFFSET 0x0000
  1776. +#define RAMIPS_GDMA_OFFSET 0x0020
  1777. +#define RAMIPS_PSE_OFFSET 0x0040
  1778. +#define RAMIPS_GDMA2_OFFSET 0x0060
  1779. +#define RAMIPS_CDMA_OFFSET 0x0080
  1780. +#define RAMIPS_PDMA_OFFSET 0x0100
  1781. +#define RAMIPS_PPE_OFFSET 0x0200
  1782. +#define RAMIPS_CMTABLE_OFFSET 0x0400
  1783. +#define RAMIPS_POLICYTABLE_OFFSET 0x1000
  1784. +
  1785. +#define RT5350_PDMA_OFFSET 0x0800
  1786. +#define RT5350_SDM_OFFSET 0x0c00
  1787. +
  1788. +#define RAMIPS_MDIO_ACCESS (RAMIPS_FE_OFFSET + 0x00)
  1789. +#define RAMIPS_MDIO_CFG (RAMIPS_FE_OFFSET + 0x04)
  1790. +#define RAMIPS_FE_GLO_CFG (RAMIPS_FE_OFFSET + 0x08)
  1791. +#define RAMIPS_FE_RST_GL (RAMIPS_FE_OFFSET + 0x0C)
  1792. +#define RAMIPS_FE_INT_STATUS (RAMIPS_FE_OFFSET + 0x10)
  1793. +#define RAMIPS_FE_INT_ENABLE (RAMIPS_FE_OFFSET + 0x14)
  1794. +#define RAMIPS_MDIO_CFG2 (RAMIPS_FE_OFFSET + 0x18)
  1795. +#define RAMIPS_FOC_TS_T (RAMIPS_FE_OFFSET + 0x1C)
  1796. +
  1797. +#define RAMIPS_GDMA1_FWD_CFG (RAMIPS_GDMA_OFFSET + 0x00)
  1798. +#define RAMIPS_GDMA1_SCH_CFG (RAMIPS_GDMA_OFFSET + 0x04)
  1799. +#define RAMIPS_GDMA1_SHPR_CFG (RAMIPS_GDMA_OFFSET + 0x08)
  1800. +#define RAMIPS_GDMA1_MAC_ADRL (RAMIPS_GDMA_OFFSET + 0x0C)
  1801. +#define RAMIPS_GDMA1_MAC_ADRH (RAMIPS_GDMA_OFFSET + 0x10)
  1802. +
  1803. +#define RAMIPS_GDMA2_FWD_CFG (RAMIPS_GDMA2_OFFSET + 0x00)
  1804. +#define RAMIPS_GDMA2_SCH_CFG (RAMIPS_GDMA2_OFFSET + 0x04)
  1805. +#define RAMIPS_GDMA2_SHPR_CFG (RAMIPS_GDMA2_OFFSET + 0x08)
  1806. +#define RAMIPS_GDMA2_MAC_ADRL (RAMIPS_GDMA2_OFFSET + 0x0C)
  1807. +#define RAMIPS_GDMA2_MAC_ADRH (RAMIPS_GDMA2_OFFSET + 0x10)
  1808. +
  1809. +#define RAMIPS_PSE_FQ_CFG (RAMIPS_PSE_OFFSET + 0x00)
  1810. +#define RAMIPS_CDMA_FC_CFG (RAMIPS_PSE_OFFSET + 0x04)
  1811. +#define RAMIPS_GDMA1_FC_CFG (RAMIPS_PSE_OFFSET + 0x08)
  1812. +#define RAMIPS_GDMA2_FC_CFG (RAMIPS_PSE_OFFSET + 0x0C)
  1813. +
  1814. +#define RAMIPS_CDMA_CSG_CFG (RAMIPS_CDMA_OFFSET + 0x00)
  1815. +#define RAMIPS_CDMA_SCH_CFG (RAMIPS_CDMA_OFFSET + 0x04)
  1816. +
  1817. +#define RT5350_TX_BASE_PTR0 (RT5350_PDMA_OFFSET + 0x00)
  1818. +#define RT5350_TX_MAX_CNT0 (RT5350_PDMA_OFFSET + 0x04)
  1819. +#define RT5350_TX_CTX_IDX0 (RT5350_PDMA_OFFSET + 0x08)
  1820. +#define RT5350_TX_DTX_IDX0 (RT5350_PDMA_OFFSET + 0x0C)
  1821. +#define RT5350_TX_BASE_PTR1 (RT5350_PDMA_OFFSET + 0x10)
  1822. +#define RT5350_TX_MAX_CNT1 (RT5350_PDMA_OFFSET + 0x14)
  1823. +#define RT5350_TX_CTX_IDX1 (RT5350_PDMA_OFFSET + 0x18)
  1824. +#define RT5350_TX_DTX_IDX1 (RT5350_PDMA_OFFSET + 0x1C)
  1825. +#define RT5350_TX_BASE_PTR2 (RT5350_PDMA_OFFSET + 0x20)
  1826. +#define RT5350_TX_MAX_CNT2 (RT5350_PDMA_OFFSET + 0x24)
  1827. +#define RT5350_TX_CTX_IDX2 (RT5350_PDMA_OFFSET + 0x28)
  1828. +#define RT5350_TX_DTX_IDX2 (RT5350_PDMA_OFFSET + 0x2C)
  1829. +#define RT5350_TX_BASE_PTR3 (RT5350_PDMA_OFFSET + 0x30)
  1830. +#define RT5350_TX_MAX_CNT3 (RT5350_PDMA_OFFSET + 0x34)
  1831. +#define RT5350_TX_CTX_IDX3 (RT5350_PDMA_OFFSET + 0x38)
  1832. +#define RT5350_TX_DTX_IDX3 (RT5350_PDMA_OFFSET + 0x3C)
  1833. +#define RT5350_RX_BASE_PTR0 (RT5350_PDMA_OFFSET + 0x100)
  1834. +#define RT5350_RX_MAX_CNT0 (RT5350_PDMA_OFFSET + 0x104)
  1835. +#define RT5350_RX_CALC_IDX0 (RT5350_PDMA_OFFSET + 0x108)
  1836. +#define RT5350_RX_DRX_IDX0 (RT5350_PDMA_OFFSET + 0x10C)
  1837. +#define RT5350_RX_BASE_PTR1 (RT5350_PDMA_OFFSET + 0x110)
  1838. +#define RT5350_RX_MAX_CNT1 (RT5350_PDMA_OFFSET + 0x114)
  1839. +#define RT5350_RX_CALC_IDX1 (RT5350_PDMA_OFFSET + 0x118)
  1840. +#define RT5350_RX_DRX_IDX1 (RT5350_PDMA_OFFSET + 0x11C)
  1841. +#define RT5350_PDMA_GLO_CFG (RT5350_PDMA_OFFSET + 0x204)
  1842. +#define RT5350_PDMA_RST_CFG (RT5350_PDMA_OFFSET + 0x208)
  1843. +#define RT5350_DLY_INT_CFG (RT5350_PDMA_OFFSET + 0x20c)
  1844. +#define RT5350_FE_INT_STATUS (RT5350_PDMA_OFFSET + 0x220)
  1845. +#define RT5350_FE_INT_ENABLE (RT5350_PDMA_OFFSET + 0x228)
  1846. +#define RT5350_PDMA_SCH_CFG (RT5350_PDMA_OFFSET + 0x280)
  1847. +
  1848. +
  1849. +#define RAMIPS_PDMA_GLO_CFG (RAMIPS_PDMA_OFFSET + 0x00)
  1850. +#define RAMIPS_PDMA_RST_CFG (RAMIPS_PDMA_OFFSET + 0x04)
  1851. +#define RAMIPS_PDMA_SCH_CFG (RAMIPS_PDMA_OFFSET + 0x08)
  1852. +#define RAMIPS_DLY_INT_CFG (RAMIPS_PDMA_OFFSET + 0x0C)
  1853. +#define RAMIPS_TX_BASE_PTR0 (RAMIPS_PDMA_OFFSET + 0x10)
  1854. +#define RAMIPS_TX_MAX_CNT0 (RAMIPS_PDMA_OFFSET + 0x14)
  1855. +#define RAMIPS_TX_CTX_IDX0 (RAMIPS_PDMA_OFFSET + 0x18)
  1856. +#define RAMIPS_TX_DTX_IDX0 (RAMIPS_PDMA_OFFSET + 0x1C)
  1857. +#define RAMIPS_TX_BASE_PTR1 (RAMIPS_PDMA_OFFSET + 0x20)
  1858. +#define RAMIPS_TX_MAX_CNT1 (RAMIPS_PDMA_OFFSET + 0x24)
  1859. +#define RAMIPS_TX_CTX_IDX1 (RAMIPS_PDMA_OFFSET + 0x28)
  1860. +#define RAMIPS_TX_DTX_IDX1 (RAMIPS_PDMA_OFFSET + 0x2C)
  1861. +#define RAMIPS_RX_BASE_PTR0 (RAMIPS_PDMA_OFFSET + 0x30)
  1862. +#define RAMIPS_RX_MAX_CNT0 (RAMIPS_PDMA_OFFSET + 0x34)
  1863. +#define RAMIPS_RX_CALC_IDX0 (RAMIPS_PDMA_OFFSET + 0x38)
  1864. +#define RAMIPS_RX_DRX_IDX0 (RAMIPS_PDMA_OFFSET + 0x3C)
  1865. +#define RAMIPS_TX_BASE_PTR2 (RAMIPS_PDMA_OFFSET + 0x40)
  1866. +#define RAMIPS_TX_MAX_CNT2 (RAMIPS_PDMA_OFFSET + 0x44)
  1867. +#define RAMIPS_TX_CTX_IDX2 (RAMIPS_PDMA_OFFSET + 0x48)
  1868. +#define RAMIPS_TX_DTX_IDX2 (RAMIPS_PDMA_OFFSET + 0x4C)
  1869. +#define RAMIPS_TX_BASE_PTR3 (RAMIPS_PDMA_OFFSET + 0x50)
  1870. +#define RAMIPS_TX_MAX_CNT3 (RAMIPS_PDMA_OFFSET + 0x54)
  1871. +#define RAMIPS_TX_CTX_IDX3 (RAMIPS_PDMA_OFFSET + 0x58)
  1872. +#define RAMIPS_TX_DTX_IDX3 (RAMIPS_PDMA_OFFSET + 0x5C)
  1873. +#define RAMIPS_RX_BASE_PTR1 (RAMIPS_PDMA_OFFSET + 0x60)
  1874. +#define RAMIPS_RX_MAX_CNT1 (RAMIPS_PDMA_OFFSET + 0x64)
  1875. +#define RAMIPS_RX_CALC_IDX1 (RAMIPS_PDMA_OFFSET + 0x68)
  1876. +#define RAMIPS_RX_DRX_IDX1 (RAMIPS_PDMA_OFFSET + 0x6C)
  1877. +
  1878. +#define RT5350_SDM_CFG (RT5350_SDM_OFFSET + 0x00) //Switch DMA configuration
  1879. +#define RT5350_SDM_RRING (RT5350_SDM_OFFSET + 0x04) //Switch DMA Rx Ring
  1880. +#define RT5350_SDM_TRING (RT5350_SDM_OFFSET + 0x08) //Switch DMA Tx Ring
  1881. +#define RT5350_SDM_MAC_ADRL (RT5350_SDM_OFFSET + 0x0C) //Switch MAC address LSB
  1882. +#define RT5350_SDM_MAC_ADRH (RT5350_SDM_OFFSET + 0x10) //Switch MAC Address MSB
  1883. +#define RT5350_SDM_TPCNT (RT5350_SDM_OFFSET + 0x100) //Switch DMA Tx packet count
  1884. +#define RT5350_SDM_TBCNT (RT5350_SDM_OFFSET + 0x104) //Switch DMA Tx byte count
  1885. +#define RT5350_SDM_RPCNT (RT5350_SDM_OFFSET + 0x108) //Switch DMA rx packet count
  1886. +#define RT5350_SDM_RBCNT (RT5350_SDM_OFFSET + 0x10C) //Switch DMA rx byte count
  1887. +#define RT5350_SDM_CS_ERR (RT5350_SDM_OFFSET + 0x110) //Switch DMA rx checksum error count
  1888. +
  1889. +#define RT5350_SDM_ICS_EN BIT(16)
  1890. +#define RT5350_SDM_TCS_EN BIT(17)
  1891. +#define RT5350_SDM_UCS_EN BIT(18)
  1892. +
  1893. +
  1894. +/* MDIO_CFG register bits */
  1895. +#define RAMIPS_MDIO_CFG_AUTO_POLL_EN BIT(29)
  1896. +#define RAMIPS_MDIO_CFG_GP1_BP_EN BIT(16)
  1897. +#define RAMIPS_MDIO_CFG_GP1_FRC_EN BIT(15)
  1898. +#define RAMIPS_MDIO_CFG_GP1_SPEED_10 (0 << 13)
  1899. +#define RAMIPS_MDIO_CFG_GP1_SPEED_100 (1 << 13)
  1900. +#define RAMIPS_MDIO_CFG_GP1_SPEED_1000 (2 << 13)
  1901. +#define RAMIPS_MDIO_CFG_GP1_DUPLEX BIT(12)
  1902. +#define RAMIPS_MDIO_CFG_GP1_FC_TX BIT(11)
  1903. +#define RAMIPS_MDIO_CFG_GP1_FC_RX BIT(10)
  1904. +#define RAMIPS_MDIO_CFG_GP1_LNK_DWN BIT(9)
  1905. +#define RAMIPS_MDIO_CFG_GP1_AN_FAIL BIT(8)
  1906. +#define RAMIPS_MDIO_CFG_MDC_CLK_DIV_1 (0 << 6)
  1907. +#define RAMIPS_MDIO_CFG_MDC_CLK_DIV_2 (1 << 6)
  1908. +#define RAMIPS_MDIO_CFG_MDC_CLK_DIV_4 (2 << 6)
  1909. +#define RAMIPS_MDIO_CFG_MDC_CLK_DIV_8 (3 << 6)
  1910. +#define RAMIPS_MDIO_CFG_TURBO_MII_FREQ BIT(5)
  1911. +#define RAMIPS_MDIO_CFG_TURBO_MII_MODE BIT(4)
  1912. +#define RAMIPS_MDIO_CFG_RX_CLK_SKEW_0 (0 << 2)
  1913. +#define RAMIPS_MDIO_CFG_RX_CLK_SKEW_200 (1 << 2)
  1914. +#define RAMIPS_MDIO_CFG_RX_CLK_SKEW_400 (2 << 2)
  1915. +#define RAMIPS_MDIO_CFG_RX_CLK_SKEW_INV (3 << 2)
  1916. +#define RAMIPS_MDIO_CFG_TX_CLK_SKEW_0 0
  1917. +#define RAMIPS_MDIO_CFG_TX_CLK_SKEW_200 1
  1918. +#define RAMIPS_MDIO_CFG_TX_CLK_SKEW_400 2
  1919. +#define RAMIPS_MDIO_CFG_TX_CLK_SKEW_INV 3
  1920. +
  1921. +/* uni-cast port */
  1922. +#define RAMIPS_GDM1_ICS_EN BIT(22)
  1923. +#define RAMIPS_GDM1_TCS_EN BIT(21)
  1924. +#define RAMIPS_GDM1_UCS_EN BIT(20)
  1925. +#define RAMIPS_GDM1_JMB_EN BIT(19)
  1926. +#define RAMIPS_GDM1_STRPCRC BIT(16)
  1927. +#define RAMIPS_GDM1_UFRC_P_CPU (0 << 12)
  1928. +#define RAMIPS_GDM1_UFRC_P_GDMA1 (1 << 12)
  1929. +#define RAMIPS_GDM1_UFRC_P_PPE (6 << 12)
  1930. +
  1931. +/* checksums */
  1932. +#define RAMIPS_ICS_GEN_EN BIT(2)
  1933. +#define RAMIPS_UCS_GEN_EN BIT(1)
  1934. +#define RAMIPS_TCS_GEN_EN BIT(0)
  1935. +
  1936. +/* dma ring */
  1937. +#define RAMIPS_PST_DRX_IDX0 BIT(16)
  1938. +#define RAMIPS_PST_DTX_IDX3 BIT(3)
  1939. +#define RAMIPS_PST_DTX_IDX2 BIT(2)
  1940. +#define RAMIPS_PST_DTX_IDX1 BIT(1)
  1941. +#define RAMIPS_PST_DTX_IDX0 BIT(0)
  1942. +
  1943. +#define RAMIPS_TX_WB_DDONE BIT(6)
  1944. +#define RAMIPS_RX_DMA_BUSY BIT(3)
  1945. +#define RAMIPS_TX_DMA_BUSY BIT(1)
  1946. +#define RAMIPS_RX_DMA_EN BIT(2)
  1947. +#define RAMIPS_TX_DMA_EN BIT(0)
  1948. +
  1949. +#define RAMIPS_PDMA_SIZE_4DWORDS (0 << 4)
  1950. +#define RAMIPS_PDMA_SIZE_8DWORDS (1 << 4)
  1951. +#define RAMIPS_PDMA_SIZE_16DWORDS (2 << 4)
  1952. +
  1953. +#define RAMIPS_US_CYC_CNT_MASK 0xff
  1954. +#define RAMIPS_US_CYC_CNT_SHIFT 0x8
  1955. +#define RAMIPS_US_CYC_CNT_DIVISOR 1000000
  1956. +
  1957. +#define RX_DMA_PLEN0(_x) (((_x) >> 16) & 0x3fff)
  1958. +#define RX_DMA_LSO BIT(30)
  1959. +#define RX_DMA_DONE BIT(31)
  1960. +
  1961. +struct ramips_rx_dma {
  1962. + unsigned int rxd1;
  1963. + unsigned int rxd2;
  1964. + unsigned int rxd3;
  1965. + unsigned int rxd4;
  1966. +} __packed __aligned(4);
  1967. +
  1968. +#define TX_DMA_PLEN0_MASK ((0x3fff) << 16)
  1969. +#define TX_DMA_PLEN0(_x) (((_x) & 0x3fff) << 16)
  1970. +#define TX_DMA_LSO BIT(30)
  1971. +#define TX_DMA_DONE BIT(31)
  1972. +#define TX_DMA_QN(_x) ((_x) << 16)
  1973. +#define TX_DMA_PN(_x) ((_x) << 24)
  1974. +#define TX_DMA_QN_MASK TX_DMA_QN(0x7)
  1975. +#define TX_DMA_PN_MASK TX_DMA_PN(0x7)
  1976. +
  1977. +struct ramips_tx_dma {
  1978. + unsigned int txd1;
  1979. + unsigned int txd2;
  1980. + unsigned int txd3;
  1981. + unsigned int txd4;
  1982. +} __packed __aligned(4);
  1983. +
  1984. +struct raeth_tx_info {
  1985. + struct ramips_tx_dma *tx_desc;
  1986. + struct sk_buff *tx_skb;
  1987. +};
  1988. +
  1989. +struct raeth_rx_info {
  1990. + struct ramips_rx_dma *rx_desc;
  1991. + struct sk_buff *rx_skb;
  1992. + dma_addr_t rx_dma;
  1993. + unsigned int pad;
  1994. +};
  1995. +
  1996. +struct raeth_int_stats {
  1997. + unsigned long rx_delayed;
  1998. + unsigned long tx_delayed;
  1999. + unsigned long rx_done0;
  2000. + unsigned long tx_done0;
  2001. + unsigned long tx_done1;
  2002. + unsigned long tx_done2;
  2003. + unsigned long tx_done3;
  2004. + unsigned long rx_coherent;
  2005. + unsigned long tx_coherent;
  2006. +
  2007. + unsigned long pse_fq_empty;
  2008. + unsigned long pse_p0_fc;
  2009. + unsigned long pse_p1_fc;
  2010. + unsigned long pse_p2_fc;
  2011. + unsigned long pse_buf_drop;
  2012. +
  2013. + unsigned long total;
  2014. +};
  2015. +
  2016. +struct raeth_debug {
  2017. + struct dentry *debugfs_dir;
  2018. +
  2019. + struct raeth_int_stats int_stats;
  2020. +};
  2021. +
  2022. +struct raeth_priv
  2023. +{
  2024. + struct device_node *of_node;
  2025. +
  2026. + struct raeth_rx_info *rx_info;
  2027. + dma_addr_t rx_desc_dma;
  2028. + struct tasklet_struct rx_tasklet;
  2029. + struct ramips_rx_dma *rx;
  2030. +
  2031. + struct raeth_tx_info *tx_info;
  2032. + dma_addr_t tx_desc_dma;
  2033. + struct tasklet_struct tx_housekeeping_tasklet;
  2034. + struct ramips_tx_dma *tx;
  2035. +
  2036. + unsigned int skb_free_idx;
  2037. +
  2038. + spinlock_t page_lock;
  2039. + struct net_device *netdev;
  2040. + struct device *parent;
  2041. +
  2042. + int link;
  2043. + int speed;
  2044. + int duplex;
  2045. + int tx_fc;
  2046. + int rx_fc;
  2047. +
  2048. + struct mii_bus *mii_bus;
  2049. + int mii_irq[PHY_MAX_ADDR];
  2050. + struct phy_device *phy_dev;
  2051. + spinlock_t phy_lock;
  2052. + unsigned long sys_freq;
  2053. +
  2054. + unsigned char mac[6];
  2055. + void (*reset_fe)(void);
  2056. + int min_pkt_len;
  2057. +
  2058. + u32 phy_mask;
  2059. + phy_interface_t phy_if_mode;
  2060. +
  2061. +#ifdef CONFIG_NET_RAMIPS_DEBUG_FS
  2062. + struct raeth_debug debug;
  2063. +#endif
  2064. +};
  2065. +
  2066. +struct ramips_soc_data
  2067. +{
  2068. + unsigned char mac[6];
  2069. + void (*reset_fe)(void);
  2070. + int min_pkt_len;
  2071. +};
  2072. +
  2073. +
  2074. +#ifdef CONFIG_NET_RAMIPS_DEBUG_FS
  2075. +int raeth_debugfs_root_init(void);
  2076. +void raeth_debugfs_root_exit(void);
  2077. +int raeth_debugfs_init(struct raeth_priv *re);
  2078. +void raeth_debugfs_exit(struct raeth_priv *re);
  2079. +void raeth_debugfs_update_int_stats(struct raeth_priv *re, u32 status);
  2080. +#else
  2081. +static inline int raeth_debugfs_root_init(void) { return 0; }
  2082. +static inline void raeth_debugfs_root_exit(void) {}
  2083. +static inline int raeth_debugfs_init(struct raeth_priv *re) { return 0; }
  2084. +static inline void raeth_debugfs_exit(struct raeth_priv *re) {}
  2085. +static inline void raeth_debugfs_update_int_stats(struct raeth_priv *re,
  2086. + u32 status) {}
  2087. +#endif /* CONFIG_NET_RAMIPS_DEBUG_FS */
  2088. +
  2089. +#endif /* RAMIPS_ETH_H */
  2090. Index: linux-3.8.12/drivers/net/ethernet/ramips/ramips_main.c
  2091. ===================================================================
  2092. --- /dev/null 1970-01-01 00:00:00.000000000 +0000
  2093. +++ linux-3.8.12/drivers/net/ethernet/ramips/ramips_main.c 2013-05-20 18:44:40.000000000 +0400
  2094. @@ -0,0 +1,1285 @@
  2095. +/*
  2096. + * This program is free software; you can redistribute it and/or modify
  2097. + * it under the terms of the GNU General Public License as published by
  2098. + * the Free Software Foundation; version 2 of the License
  2099. + *
  2100. + * This program is distributed in the hope that it will be useful,
  2101. + * but WITHOUT ANY WARRANTY; without even the implied warranty of
  2102. + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  2103. + * GNU General Public License for more details.
  2104. + *
  2105. + * You should have received a copy of the GNU General Public License
  2106. + * along with this program; if not, write to the Free Software
  2107. + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
  2108. + *
  2109. + * Copyright (C) 2009 John Crispin <blogic@openwrt.org>
  2110. + */
  2111. +
  2112. +#include <linux/module.h>
  2113. +#include <linux/kernel.h>
  2114. +#include <linux/types.h>
  2115. +#include <linux/dma-mapping.h>
  2116. +#include <linux/init.h>
  2117. +#include <linux/skbuff.h>
  2118. +#include <linux/etherdevice.h>
  2119. +#include <linux/ethtool.h>
  2120. +#include <linux/platform_device.h>
  2121. +#include <linux/phy.h>
  2122. +#include <linux/of_device.h>
  2123. +#include <linux/clk.h>
  2124. +#include <linux/of_net.h>
  2125. +
  2126. +#include "ramips_eth.h"
  2127. +
  2128. +#define TX_TIMEOUT (20 * HZ / 100)
  2129. +#define MAX_RX_LENGTH 1600
  2130. +
  2131. +#ifdef CONFIG_SOC_RT305X
  2132. +#include <rt305x.h>
  2133. +#include "ramips_esw.c"
  2134. +#else
  2135. +#include <asm/mach-ralink/ralink_regs.h>
  2136. +static inline int rt305x_esw_init(void) { return 0; }
  2137. +static inline void rt305x_esw_exit(void) { }
  2138. +static inline int soc_is_rt5350(void) { return 0; }
  2139. +#endif
  2140. +
  2141. +#define phys_to_bus(a) (a & 0x1FFFFFFF)
  2142. +
  2143. +#ifdef CONFIG_NET_RAMIPS_DEBUG
  2144. +#define RADEBUG(fmt, args...) printk(KERN_DEBUG fmt, ## args)
  2145. +#else
  2146. +#define RADEBUG(fmt, args...) do {} while (0)
  2147. +#endif
  2148. +
  2149. +#define RX_DLY_INT ((soc_is_rt5350())?(RT5350_RX_DLY_INT):(RAMIPS_RX_DLY_INT))
  2150. +#define TX_DLY_INT ((soc_is_rt5350())?(RT5350_TX_DLY_INT):(RAMIPS_TX_DLY_INT))
  2151. +
  2152. +enum raeth_reg {
  2153. + RAETH_REG_PDMA_GLO_CFG = 0,
  2154. + RAETH_REG_PDMA_RST_CFG,
  2155. + RAETH_REG_DLY_INT_CFG,
  2156. + RAETH_REG_TX_BASE_PTR0,
  2157. + RAETH_REG_TX_MAX_CNT0,
  2158. + RAETH_REG_TX_CTX_IDX0,
  2159. + RAETH_REG_RX_BASE_PTR0,
  2160. + RAETH_REG_RX_MAX_CNT0,
  2161. + RAETH_REG_RX_CALC_IDX0,
  2162. + RAETH_REG_FE_INT_ENABLE,
  2163. + RAETH_REG_FE_INT_STATUS,
  2164. + RAETH_REG_COUNT
  2165. +};
  2166. +
  2167. +static const u32 ramips_reg_table[RAETH_REG_COUNT] = {
  2168. + [RAETH_REG_PDMA_GLO_CFG] = RAMIPS_PDMA_GLO_CFG,
  2169. + [RAETH_REG_PDMA_RST_CFG] = RAMIPS_PDMA_RST_CFG,
  2170. + [RAETH_REG_DLY_INT_CFG] = RAMIPS_DLY_INT_CFG,
  2171. + [RAETH_REG_TX_BASE_PTR0] = RAMIPS_TX_BASE_PTR0,
  2172. + [RAETH_REG_TX_MAX_CNT0] = RAMIPS_TX_MAX_CNT0,
  2173. + [RAETH_REG_TX_CTX_IDX0] = RAMIPS_TX_CTX_IDX0,
  2174. + [RAETH_REG_RX_BASE_PTR0] = RAMIPS_RX_BASE_PTR0,
  2175. + [RAETH_REG_RX_MAX_CNT0] = RAMIPS_RX_MAX_CNT0,
  2176. + [RAETH_REG_RX_CALC_IDX0] = RAMIPS_RX_CALC_IDX0,
  2177. + [RAETH_REG_FE_INT_ENABLE] = RAMIPS_FE_INT_ENABLE,
  2178. + [RAETH_REG_FE_INT_STATUS] = RAMIPS_FE_INT_STATUS,
  2179. +};
  2180. +
  2181. +static const u32 rt5350_reg_table[RAETH_REG_COUNT] = {
  2182. + [RAETH_REG_PDMA_GLO_CFG] = RT5350_PDMA_GLO_CFG,
  2183. + [RAETH_REG_PDMA_RST_CFG] = RT5350_PDMA_RST_CFG,
  2184. + [RAETH_REG_DLY_INT_CFG] = RT5350_DLY_INT_CFG,
  2185. + [RAETH_REG_TX_BASE_PTR0] = RT5350_TX_BASE_PTR0,
  2186. + [RAETH_REG_TX_MAX_CNT0] = RT5350_TX_MAX_CNT0,
  2187. + [RAETH_REG_TX_CTX_IDX0] = RT5350_TX_CTX_IDX0,
  2188. + [RAETH_REG_RX_BASE_PTR0] = RT5350_RX_BASE_PTR0,
  2189. + [RAETH_REG_RX_MAX_CNT0] = RT5350_RX_MAX_CNT0,
  2190. + [RAETH_REG_RX_CALC_IDX0] = RT5350_RX_CALC_IDX0,
  2191. + [RAETH_REG_FE_INT_ENABLE] = RT5350_FE_INT_ENABLE,
  2192. + [RAETH_REG_FE_INT_STATUS] = RT5350_FE_INT_STATUS,
  2193. +};
  2194. +
  2195. +static struct net_device * ramips_dev;
  2196. +static void __iomem *ramips_fe_base = 0;
  2197. +
  2198. +static inline u32 get_reg_offset(enum raeth_reg reg)
  2199. +{
  2200. + const u32 *table;
  2201. +
  2202. + if (soc_is_rt5350())
  2203. + table = rt5350_reg_table;
  2204. + else
  2205. + table = ramips_reg_table;
  2206. +
  2207. + return table[reg];
  2208. +}
  2209. +
  2210. +static inline void
  2211. +ramips_fe_wr(u32 val, unsigned reg)
  2212. +{
  2213. + __raw_writel(val, ramips_fe_base + reg);
  2214. +}
  2215. +
  2216. +static inline u32
  2217. +ramips_fe_rr(unsigned reg)
  2218. +{
  2219. + return __raw_readl(ramips_fe_base + reg);
  2220. +}
  2221. +
  2222. +static inline void
  2223. +ramips_fe_twr(u32 val, enum raeth_reg reg)
  2224. +{
  2225. + ramips_fe_wr(val, get_reg_offset(reg));
  2226. +}
  2227. +
  2228. +static inline u32
  2229. +ramips_fe_trr(enum raeth_reg reg)
  2230. +{
  2231. + return ramips_fe_rr(get_reg_offset(reg));
  2232. +}
  2233. +
  2234. +static inline void
  2235. +ramips_fe_int_disable(u32 mask)
  2236. +{
  2237. + ramips_fe_twr(ramips_fe_trr(RAETH_REG_FE_INT_ENABLE) & ~mask,
  2238. + RAETH_REG_FE_INT_ENABLE);
  2239. + /* flush write */
  2240. + ramips_fe_trr(RAETH_REG_FE_INT_ENABLE);
  2241. +}
  2242. +
  2243. +static inline void
  2244. +ramips_fe_int_enable(u32 mask)
  2245. +{
  2246. + ramips_fe_twr(ramips_fe_trr(RAETH_REG_FE_INT_ENABLE) | mask,
  2247. + RAETH_REG_FE_INT_ENABLE);
  2248. + /* flush write */
  2249. + ramips_fe_trr(RAETH_REG_FE_INT_ENABLE);
  2250. +}
  2251. +
  2252. +static inline void
  2253. +ramips_hw_set_macaddr(unsigned char *mac)
  2254. +{
  2255. + if (soc_is_rt5350()) {
  2256. + ramips_fe_wr((mac[0] << 8) | mac[1], RT5350_SDM_MAC_ADRH);
  2257. + ramips_fe_wr((mac[2] << 24) | (mac[3] << 16) | (mac[4] << 8) | mac[5],
  2258. + RT5350_SDM_MAC_ADRL);
  2259. + } else {
  2260. + ramips_fe_wr((mac[0] << 8) | mac[1], RAMIPS_GDMA1_MAC_ADRH);
  2261. + ramips_fe_wr((mac[2] << 24) | (mac[3] << 16) | (mac[4] << 8) | mac[5],
  2262. + RAMIPS_GDMA1_MAC_ADRL);
  2263. + }
  2264. +}
  2265. +
  2266. +static struct sk_buff *
  2267. +ramips_alloc_skb(struct raeth_priv *re)
  2268. +{
  2269. + struct sk_buff *skb;
  2270. +
  2271. + skb = netdev_alloc_skb(re->netdev, MAX_RX_LENGTH + NET_IP_ALIGN);
  2272. + if (!skb)
  2273. + return NULL;
  2274. +
  2275. + skb_reserve(skb, NET_IP_ALIGN);
  2276. +
  2277. + return skb;
  2278. +}
  2279. +
  2280. +static void
  2281. +ramips_ring_setup(struct raeth_priv *re)
  2282. +{
  2283. + int len;
  2284. + int i;
  2285. +
  2286. + memset(re->tx_info, 0, NUM_TX_DESC * sizeof(struct raeth_tx_info));
  2287. +
  2288. + len = NUM_TX_DESC * sizeof(struct ramips_tx_dma);
  2289. + memset(re->tx, 0, len);
  2290. +
  2291. + for (i = 0; i < NUM_TX_DESC; i++) {
  2292. + struct raeth_tx_info *txi;
  2293. + struct ramips_tx_dma *txd;
  2294. +
  2295. + txd = &re->tx[i];
  2296. + txd->txd4 = TX_DMA_QN(3) | TX_DMA_PN(1);
  2297. + txd->txd2 = TX_DMA_LSO | TX_DMA_DONE;
  2298. +
  2299. + txi = &re->tx_info[i];
  2300. + txi->tx_desc = txd;
  2301. + if (txi->tx_skb != NULL) {
  2302. + netdev_warn(re->netdev,
  2303. + "dirty skb for TX desc %d\n", i);
  2304. + txi->tx_skb = NULL;
  2305. + }
  2306. + }
  2307. +
  2308. + len = NUM_RX_DESC * sizeof(struct ramips_rx_dma);
  2309. + memset(re->rx, 0, len);
  2310. +
  2311. + for (i = 0; i < NUM_RX_DESC; i++) {
  2312. + struct raeth_rx_info *rxi;
  2313. + struct ramips_rx_dma *rxd;
  2314. + dma_addr_t dma_addr;
  2315. +
  2316. + rxd = &re->rx[i];
  2317. + rxi = &re->rx_info[i];
  2318. + BUG_ON(rxi->rx_skb == NULL);
  2319. + dma_addr = dma_map_single(&re->netdev->dev, rxi->rx_skb->data,
  2320. + MAX_RX_LENGTH, DMA_FROM_DEVICE);
  2321. + rxi->rx_dma = dma_addr;
  2322. + rxi->rx_desc = rxd;
  2323. +
  2324. + rxd->rxd1 = (unsigned int) dma_addr;
  2325. + rxd->rxd2 = RX_DMA_LSO;
  2326. + }
  2327. +
  2328. + /* flush descriptors */
  2329. + wmb();
  2330. +}
  2331. +
  2332. +static void
  2333. +ramips_ring_cleanup(struct raeth_priv *re)
  2334. +{
  2335. + int i;
  2336. +
  2337. + for (i = 0; i < NUM_RX_DESC; i++) {
  2338. + struct raeth_rx_info *rxi;
  2339. +
  2340. + rxi = &re->rx_info[i];
  2341. + if (rxi->rx_skb)
  2342. + dma_unmap_single(&re->netdev->dev, rxi->rx_dma,
  2343. + MAX_RX_LENGTH, DMA_FROM_DEVICE);
  2344. + }
  2345. +
  2346. + for (i = 0; i < NUM_TX_DESC; i++) {
  2347. + struct raeth_tx_info *txi;
  2348. +
  2349. + txi = &re->tx_info[i];
  2350. + if (txi->tx_skb) {
  2351. + dev_kfree_skb_any(txi->tx_skb);
  2352. + txi->tx_skb = NULL;
  2353. + }
  2354. + }
  2355. +
  2356. + netdev_reset_queue(re->netdev);
  2357. +}
  2358. +
  2359. +#if defined(CONFIG_SOC_RT288X) || defined(CONFIG_SOC_RT3883)
  2360. +
  2361. +#define RAMIPS_MDIO_RETRY 1000
  2362. +
  2363. +static unsigned char *ramips_speed_str(struct raeth_priv *re)
  2364. +{
  2365. + switch (re->speed) {
  2366. + case SPEED_1000:
  2367. + return "1000";
  2368. + case SPEED_100:
  2369. + return "100";
  2370. + case SPEED_10:
  2371. + return "10";
  2372. + }
  2373. +
  2374. + return "?";
  2375. +}
  2376. +
  2377. +static void ramips_link_adjust(struct raeth_priv *re)
  2378. +{
  2379. + u32 mdio_cfg;
  2380. +
  2381. + if (!re->link) {
  2382. + netif_carrier_off(re->netdev);
  2383. + netdev_info(re->netdev, "link down\n");
  2384. + return;
  2385. + }
  2386. +
  2387. + mdio_cfg = RAMIPS_MDIO_CFG_TX_CLK_SKEW_200 |
  2388. + RAMIPS_MDIO_CFG_TX_CLK_SKEW_200 |
  2389. + RAMIPS_MDIO_CFG_GP1_FRC_EN;
  2390. +
  2391. + if (re->duplex == DUPLEX_FULL)
  2392. + mdio_cfg |= RAMIPS_MDIO_CFG_GP1_DUPLEX;
  2393. +
  2394. + if (re->tx_fc)
  2395. + mdio_cfg |= RAMIPS_MDIO_CFG_GP1_FC_TX;
  2396. +
  2397. + if (re->rx_fc)
  2398. + mdio_cfg |= RAMIPS_MDIO_CFG_GP1_FC_RX;
  2399. +
  2400. + switch (re->speed) {
  2401. + case SPEED_10:
  2402. + mdio_cfg |= RAMIPS_MDIO_CFG_GP1_SPEED_10;
  2403. + break;
  2404. + case SPEED_100:
  2405. + mdio_cfg |= RAMIPS_MDIO_CFG_GP1_SPEED_100;
  2406. + break;
  2407. + case SPEED_1000:
  2408. + mdio_cfg |= RAMIPS_MDIO_CFG_GP1_SPEED_1000;
  2409. + break;
  2410. + default:
  2411. + BUG();
  2412. + }
  2413. +
  2414. + ramips_fe_wr(mdio_cfg, RAMIPS_MDIO_CFG);
  2415. +
  2416. + netif_carrier_on(re->netdev);
  2417. + netdev_info(re->netdev, "link up (%sMbps/%s duplex)\n",
  2418. + ramips_speed_str(re),
  2419. + (DUPLEX_FULL == re->duplex) ? "Full" : "Half");
  2420. +}
  2421. +
  2422. +static int
  2423. +ramips_mdio_wait_ready(struct raeth_priv *re)
  2424. +{
  2425. + int retries;
  2426. +
  2427. + retries = RAMIPS_MDIO_RETRY;
  2428. + while (1) {
  2429. + u32 t;
  2430. +
  2431. + t = ramips_fe_rr(RAMIPS_MDIO_ACCESS);
  2432. + if ((t & (0x1 << 31)) == 0)
  2433. + return 0;
  2434. +
  2435. + if (retries-- == 0)
  2436. + break;
  2437. +
  2438. + udelay(1);
  2439. + }
  2440. +
  2441. + dev_err(re->parent, "MDIO operation timed out\n");
  2442. + return -ETIMEDOUT;
  2443. +}
  2444. +
  2445. +static int
  2446. +ramips_mdio_read(struct mii_bus *bus, int phy_addr, int phy_reg)
  2447. +{
  2448. + struct raeth_priv *re = bus->priv;
  2449. + int err;
  2450. + u32 t;
  2451. +
  2452. + err = ramips_mdio_wait_ready(re);
  2453. + if (err)
  2454. + return 0xffff;
  2455. +
  2456. + t = (phy_addr << 24) | (phy_reg << 16);
  2457. + ramips_fe_wr(t, RAMIPS_MDIO_ACCESS);
  2458. + t |= (1 << 31);
  2459. + ramips_fe_wr(t, RAMIPS_MDIO_ACCESS);
  2460. +
  2461. + err = ramips_mdio_wait_ready(re);
  2462. + if (err)
  2463. + return 0xffff;
  2464. +
  2465. + RADEBUG("%s: addr=%04x, reg=%04x, value=%04x\n", __func__,
  2466. + phy_addr, phy_reg, ramips_fe_rr(RAMIPS_MDIO_ACCESS) & 0xffff);
  2467. +
  2468. + return ramips_fe_rr(RAMIPS_MDIO_ACCESS) & 0xffff;
  2469. +}
  2470. +
  2471. +static int
  2472. +ramips_mdio_write(struct mii_bus *bus, int phy_addr, int phy_reg, u16 val)
  2473. +{
  2474. + struct raeth_priv *re = bus->priv;
  2475. + int err;
  2476. + u32 t;
  2477. +
  2478. + RADEBUG("%s: addr=%04x, reg=%04x, value=%04x\n", __func__,
  2479. + phy_addr, phy_reg, ramips_fe_rr(RAMIPS_MDIO_ACCESS) & 0xffff);
  2480. +
  2481. + err = ramips_mdio_wait_ready(re);
  2482. + if (err)
  2483. + return err;
  2484. +
  2485. + t = (1 << 30) | (phy_addr << 24) | (phy_reg << 16) | val;
  2486. + ramips_fe_wr(t, RAMIPS_MDIO_ACCESS);
  2487. + t |= (1 << 31);
  2488. + ramips_fe_wr(t, RAMIPS_MDIO_ACCESS);
  2489. +
  2490. + return ramips_mdio_wait_ready(re);
  2491. +}
  2492. +
  2493. +static int
  2494. +ramips_mdio_reset(struct mii_bus *bus)
  2495. +{
  2496. + /* TODO */
  2497. + return 0;
  2498. +}
  2499. +
  2500. +static int
  2501. +ramips_mdio_init(struct raeth_priv *re)
  2502. +{
  2503. + int err;
  2504. + int i;
  2505. +
  2506. + re->mii_bus = mdiobus_alloc();
  2507. + if (re->mii_bus == NULL)
  2508. + return -ENOMEM;
  2509. +
  2510. + re->mii_bus->name = "ramips_mdio";
  2511. + re->mii_bus->read = ramips_mdio_read;
  2512. + re->mii_bus->write = ramips_mdio_write;
  2513. + re->mii_bus->reset = ramips_mdio_reset;
  2514. + re->mii_bus->irq = re->mii_irq;
  2515. + re->mii_bus->priv = re;
  2516. + re->mii_bus->parent = re->parent;
  2517. +
  2518. + snprintf(re->mii_bus->id, MII_BUS_ID_SIZE, "%s", "ramips_mdio");
  2519. + re->mii_bus->phy_mask = 0;
  2520. +
  2521. + for (i = 0; i < PHY_MAX_ADDR; i++)
  2522. + re->mii_irq[i] = PHY_POLL;
  2523. +
  2524. + err = mdiobus_register(re->mii_bus);
  2525. + if (err)
  2526. + goto err_free_bus;
  2527. +
  2528. + return 0;
  2529. +
  2530. +err_free_bus:
  2531. + kfree(re->mii_bus);
  2532. + return err;
  2533. +}
  2534. +
  2535. +static void
  2536. +ramips_mdio_cleanup(struct raeth_priv *re)
  2537. +{
  2538. + mdiobus_unregister(re->mii_bus);
  2539. + kfree(re->mii_bus);
  2540. +}
  2541. +
  2542. +static void
  2543. +ramips_phy_link_adjust(struct net_device *dev)
  2544. +{
  2545. + struct raeth_priv *re = netdev_priv(dev);
  2546. + struct phy_device *phydev = re->phy_dev;
  2547. + unsigned long flags;
  2548. + int status_change = 0;
  2549. +
  2550. + spin_lock_irqsave(&re->phy_lock, flags);
  2551. +
  2552. + if (phydev->link)
  2553. + if (re->duplex != phydev->duplex ||
  2554. + re->speed != phydev->speed)
  2555. + status_change = 1;
  2556. +
  2557. + if (phydev->link != re->link)
  2558. + status_change = 1;
  2559. +
  2560. + re->link = phydev->link;
  2561. + re->duplex = phydev->duplex;
  2562. + re->speed = phydev->speed;
  2563. +
  2564. + if (status_change)
  2565. + ramips_link_adjust(re);
  2566. +
  2567. + spin_unlock_irqrestore(&re->phy_lock, flags);
  2568. +}
  2569. +
  2570. +static int
  2571. +ramips_phy_connect_multi(struct raeth_priv *re)
  2572. +{
  2573. + struct net_device *netdev = re->netdev;
  2574. + struct phy_device *phydev = NULL;
  2575. + int phy_addr;
  2576. + int ret = 0;
  2577. +
  2578. + for (phy_addr = 0; phy_addr < PHY_MAX_ADDR; phy_addr++) {
  2579. + if (!(re->phy_mask & (1 << phy_addr)))
  2580. + continue;
  2581. +
  2582. + if (re->mii_bus->phy_map[phy_addr] == NULL)
  2583. + continue;
  2584. +
  2585. + RADEBUG("%s: PHY found at %s, uid=%08x\n",
  2586. + netdev->name,
  2587. + dev_name(&re->mii_bus->phy_map[phy_addr]->dev),
  2588. + re->mii_bus->phy_map[phy_addr]->phy_id);
  2589. +
  2590. + if (phydev == NULL)
  2591. + phydev = re->mii_bus->phy_map[phy_addr];
  2592. + }
  2593. +
  2594. + if (!phydev) {
  2595. + netdev_err(netdev, "no PHY found with phy_mask=%08x\n",
  2596. + re->phy_mask);
  2597. + return -ENODEV;
  2598. + }
  2599. +
  2600. + re->phy_dev = phy_connect(netdev, dev_name(&phydev->dev),
  2601. + ramips_phy_link_adjust, 0, re->phy_if_mode);
  2602. +
  2603. + if (IS_ERR(re->phy_dev)) {
  2604. + netdev_err(netdev, "could not connect to PHY at %s\n",
  2605. + dev_name(&phydev->dev));
  2606. + return PTR_ERR(re->phy_dev);
  2607. + }
  2608. +
  2609. + phydev->supported &= PHY_GBIT_FEATURES;
  2610. + phydev->advertising = phydev->supported;
  2611. +
  2612. + RADEBUG("%s: connected to PHY at %s [uid=%08x, driver=%s]\n",
  2613. + netdev->name, dev_name(&phydev->dev),
  2614. + phydev->phy_id, phydev->drv->name);
  2615. +
  2616. + re->link = 0;
  2617. + re->speed = 0;
  2618. + re->duplex = -1;
  2619. + re->rx_fc = 0;
  2620. + re->tx_fc = 0;
  2621. +
  2622. + return ret;
  2623. +}
  2624. +
  2625. +static int
  2626. +ramips_phy_connect_fixed(struct raeth_priv *re)
  2627. +{
  2628. + if (!re->speed) {
  2629. + const __be32 *link;
  2630. + int size;
  2631. +
  2632. + link = of_get_property(re->of_node,
  2633. + "ralink,fixed-link", &size);
  2634. + if (!link || size != (4 * sizeof(*link)))
  2635. + return -ENOENT;
  2636. +
  2637. + re->speed = be32_to_cpup(link++);
  2638. + re->duplex = be32_to_cpup(link++);
  2639. + re->tx_fc = be32_to_cpup(link++);
  2640. + re->rx_fc = be32_to_cpup(link++);
  2641. + }
  2642. +
  2643. + switch (re->speed) {
  2644. + case SPEED_10:
  2645. + case SPEED_100:
  2646. + case SPEED_1000:
  2647. + break;
  2648. + default:
  2649. + netdev_err(re->netdev, "invalid speed specified\n");
  2650. + return -EINVAL;
  2651. + }
  2652. +
  2653. + pr_info("%s: using fixed link parameters\n", re->netdev->name);
  2654. + return 0;
  2655. +}
  2656. +
  2657. +static int
  2658. +ramips_phy_connect(struct raeth_priv *re)
  2659. +{
  2660. + const __be32 *mask;
  2661. +
  2662. + mask = of_get_property(re->of_node, "ralink,phy-mask", NULL);
  2663. + re->phy_if_mode = of_get_phy_mode(re->of_node);
  2664. +
  2665. + if (!re->phy_if_mode || !mask)
  2666. + return ramips_phy_connect_fixed(re);
  2667. +
  2668. + re->phy_mask = be32_to_cpup(mask);
  2669. + return ramips_phy_connect_multi(re);
  2670. +
  2671. +}
  2672. +
  2673. +static void
  2674. +ramips_phy_disconnect(struct raeth_priv *re)
  2675. +{
  2676. + if (re->phy_dev)
  2677. + phy_disconnect(re->phy_dev);
  2678. +}
  2679. +
  2680. +static void
  2681. +ramips_phy_start(struct raeth_priv *re)
  2682. +{
  2683. + unsigned long flags;
  2684. +
  2685. + if (re->phy_dev) {
  2686. + phy_start(re->phy_dev);
  2687. + } else {
  2688. + spin_lock_irqsave(&re->phy_lock, flags);
  2689. + re->link = 1;
  2690. + ramips_link_adjust(re);
  2691. + spin_unlock_irqrestore(&re->phy_lock, flags);
  2692. + }
  2693. +}
  2694. +
  2695. +static void
  2696. +ramips_phy_stop(struct raeth_priv *re)
  2697. +{
  2698. + unsigned long flags;
  2699. +
  2700. + if (re->phy_dev)
  2701. + phy_stop(re->phy_dev);
  2702. +
  2703. + spin_lock_irqsave(&re->phy_lock, flags);
  2704. + re->link = 0;
  2705. + ramips_link_adjust(re);
  2706. + spin_unlock_irqrestore(&re->phy_lock, flags);
  2707. +}
  2708. +#else
  2709. +static inline int
  2710. +ramips_mdio_init(struct raeth_priv *re)
  2711. +{
  2712. + return 0;
  2713. +}
  2714. +
  2715. +static inline void
  2716. +ramips_mdio_cleanup(struct raeth_priv *re)
  2717. +{
  2718. +}
  2719. +
  2720. +static inline int
  2721. +ramips_phy_connect(struct raeth_priv *re)
  2722. +{
  2723. + return 0;
  2724. +}
  2725. +
  2726. +static inline void
  2727. +ramips_phy_disconnect(struct raeth_priv *re)
  2728. +{
  2729. +}
  2730. +
  2731. +static inline void
  2732. +ramips_phy_start(struct raeth_priv *re)
  2733. +{
  2734. +}
  2735. +
  2736. +static inline void
  2737. +ramips_phy_stop(struct raeth_priv *re)
  2738. +{
  2739. +}
  2740. +#endif /* CONFIG_SOC_RT288X || CONFIG_SOC_RT3883 */
  2741. +
  2742. +static void
  2743. +ramips_ring_free(struct raeth_priv *re)
  2744. +{
  2745. + int len;
  2746. + int i;
  2747. +
  2748. + if (re->rx_info) {
  2749. + for (i = 0; i < NUM_RX_DESC; i++) {
  2750. + struct raeth_rx_info *rxi;
  2751. +
  2752. + rxi = &re->rx_info[i];
  2753. + if (rxi->rx_skb)
  2754. + dev_kfree_skb_any(rxi->rx_skb);
  2755. + }
  2756. + kfree(re->rx_info);
  2757. + }
  2758. +
  2759. + if (re->rx) {
  2760. + len = NUM_RX_DESC * sizeof(struct ramips_rx_dma);
  2761. + dma_free_coherent(&re->netdev->dev, len, re->rx,
  2762. + re->rx_desc_dma);
  2763. + }
  2764. +
  2765. + if (re->tx) {
  2766. + len = NUM_TX_DESC * sizeof(struct ramips_tx_dma);
  2767. + dma_free_coherent(&re->netdev->dev, len, re->tx,
  2768. + re->tx_desc_dma);
  2769. + }
  2770. +
  2771. + kfree(re->tx_info);
  2772. +}
  2773. +
  2774. +static int
  2775. +ramips_ring_alloc(struct raeth_priv *re)
  2776. +{
  2777. + int len;
  2778. + int err = -ENOMEM;
  2779. + int i;
  2780. +
  2781. + re->tx_info = kzalloc(NUM_TX_DESC * sizeof(struct raeth_tx_info),
  2782. + GFP_ATOMIC);
  2783. + if (!re->tx_info)
  2784. + goto err_cleanup;
  2785. +
  2786. + re->rx_info = kzalloc(NUM_RX_DESC * sizeof(struct raeth_rx_info),
  2787. + GFP_ATOMIC);
  2788. + if (!re->rx_info)
  2789. + goto err_cleanup;
  2790. +
  2791. + /* allocate tx ring */
  2792. + len = NUM_TX_DESC * sizeof(struct ramips_tx_dma);
  2793. + re->tx = dma_alloc_coherent(&re->netdev->dev, len,
  2794. + &re->tx_desc_dma, GFP_ATOMIC);
  2795. + if (!re->tx)
  2796. + goto err_cleanup;
  2797. +
  2798. + /* allocate rx ring */
  2799. + len = NUM_RX_DESC * sizeof(struct ramips_rx_dma);
  2800. + re->rx = dma_alloc_coherent(&re->netdev->dev, len,
  2801. + &re->rx_desc_dma, GFP_ATOMIC);
  2802. + if (!re->rx)
  2803. + goto err_cleanup;
  2804. +
  2805. + for (i = 0; i < NUM_RX_DESC; i++) {
  2806. + struct sk_buff *skb;
  2807. +
  2808. + skb = ramips_alloc_skb(re);
  2809. + if (!skb)
  2810. + goto err_cleanup;
  2811. +
  2812. + re->rx_info[i].rx_skb = skb;
  2813. + }
  2814. +
  2815. + return 0;
  2816. +
  2817. +err_cleanup:
  2818. + ramips_ring_free(re);
  2819. + return err;
  2820. +}
  2821. +
  2822. +static void
  2823. +ramips_setup_dma(struct raeth_priv *re)
  2824. +{
  2825. + ramips_fe_twr(re->tx_desc_dma, RAETH_REG_TX_BASE_PTR0);
  2826. + ramips_fe_twr(NUM_TX_DESC, RAETH_REG_TX_MAX_CNT0);
  2827. + ramips_fe_twr(0, RAETH_REG_TX_CTX_IDX0);
  2828. + ramips_fe_twr(RAMIPS_PST_DTX_IDX0, RAETH_REG_PDMA_RST_CFG);
  2829. +
  2830. + ramips_fe_twr(re->rx_desc_dma, RAETH_REG_RX_BASE_PTR0);
  2831. + ramips_fe_twr(NUM_RX_DESC, RAETH_REG_RX_MAX_CNT0);
  2832. + ramips_fe_twr((NUM_RX_DESC - 1), RAETH_REG_RX_CALC_IDX0);
  2833. + ramips_fe_twr(RAMIPS_PST_DRX_IDX0, RAETH_REG_PDMA_RST_CFG);
  2834. +}
  2835. +
  2836. +static int
  2837. +ramips_eth_hard_start_xmit(struct sk_buff *skb, struct net_device *dev)
  2838. +{
  2839. + struct raeth_priv *re = netdev_priv(dev);
  2840. + struct raeth_tx_info *txi, *txi_next;
  2841. + struct ramips_tx_dma *txd, *txd_next;
  2842. + unsigned long tx;
  2843. + unsigned int tx_next;
  2844. + dma_addr_t mapped_addr;
  2845. +
  2846. + if (re->min_pkt_len) {
  2847. + if (skb->len < re->min_pkt_len) {
  2848. + if (skb_padto(skb, re->min_pkt_len)) {
  2849. + printk(KERN_ERR
  2850. + "ramips_eth: skb_padto failed\n");
  2851. + kfree_skb(skb);
  2852. + return 0;
  2853. + }
  2854. + skb_put(skb, re->min_pkt_len - skb->len);
  2855. + }
  2856. + }
  2857. +
  2858. + dev->trans_start = jiffies;
  2859. + mapped_addr = dma_map_single(&re->netdev->dev, skb->data, skb->len,
  2860. + DMA_TO_DEVICE);
  2861. +
  2862. + spin_lock(&re->page_lock);
  2863. + tx = ramips_fe_trr(RAETH_REG_TX_CTX_IDX0);
  2864. + tx_next = (tx + 1) % NUM_TX_DESC;
  2865. +
  2866. + txi = &re->tx_info[tx];
  2867. + txd = txi->tx_desc;
  2868. + txi_next = &re->tx_info[tx_next];
  2869. + txd_next = txi_next->tx_desc;
  2870. +
  2871. + if ((txi->tx_skb) || (txi_next->tx_skb) ||
  2872. + !(txd->txd2 & TX_DMA_DONE) ||
  2873. + !(txd_next->txd2 & TX_DMA_DONE))
  2874. + goto out;
  2875. +
  2876. + txi->tx_skb = skb;
  2877. +
  2878. + txd->txd1 = (unsigned int) mapped_addr;
  2879. + wmb();
  2880. + txd->txd2 = TX_DMA_LSO | TX_DMA_PLEN0(skb->len);
  2881. + dev->stats.tx_packets++;
  2882. + dev->stats.tx_bytes += skb->len;
  2883. + ramips_fe_twr(tx_next, RAETH_REG_TX_CTX_IDX0);
  2884. + netdev_sent_queue(dev, skb->len);
  2885. + spin_unlock(&re->page_lock);
  2886. + return NETDEV_TX_OK;
  2887. +
  2888. + out:
  2889. + spin_unlock(&re->page_lock);
  2890. + dev->stats.tx_dropped++;
  2891. + kfree_skb(skb);
  2892. + return NETDEV_TX_OK;
  2893. +}
  2894. +
  2895. +static void
  2896. +ramips_eth_rx_hw(unsigned long ptr)
  2897. +{
  2898. + struct net_device *dev = (struct net_device *) ptr;
  2899. + struct raeth_priv *re = netdev_priv(dev);
  2900. + int rx;
  2901. + int max_rx = 16;
  2902. +
  2903. + rx = ramips_fe_trr(RAETH_REG_RX_CALC_IDX0);
  2904. +
  2905. + while (max_rx) {
  2906. + struct raeth_rx_info *rxi;
  2907. + struct ramips_rx_dma *rxd;
  2908. + struct sk_buff *rx_skb, *new_skb;
  2909. + int pktlen;
  2910. +
  2911. + rx = (rx + 1) % NUM_RX_DESC;
  2912. +
  2913. + rxi = &re->rx_info[rx];
  2914. + rxd = rxi->rx_desc;
  2915. + if (!(rxd->rxd2 & RX_DMA_DONE))
  2916. + break;
  2917. +
  2918. + rx_skb = rxi->rx_skb;
  2919. + pktlen = RX_DMA_PLEN0(rxd->rxd2);
  2920. +
  2921. + new_skb = ramips_alloc_skb(re);
  2922. + /* Reuse the buffer on allocation failures */
  2923. + if (new_skb) {
  2924. + dma_addr_t dma_addr;
  2925. +
  2926. + dma_unmap_single(&re->netdev->dev, rxi->rx_dma,
  2927. + MAX_RX_LENGTH, DMA_FROM_DEVICE);
  2928. +
  2929. + skb_put(rx_skb, pktlen);
  2930. + rx_skb->dev = dev;
  2931. + rx_skb->protocol = eth_type_trans(rx_skb, dev);
  2932. + rx_skb->ip_summed = CHECKSUM_NONE;
  2933. + dev->stats.rx_packets++;
  2934. + dev->stats.rx_bytes += pktlen;
  2935. + netif_rx(rx_skb);
  2936. +
  2937. + rxi->rx_skb = new_skb;
  2938. +
  2939. + dma_addr = dma_map_single(&re->netdev->dev,
  2940. + new_skb->data,
  2941. + MAX_RX_LENGTH,
  2942. + DMA_FROM_DEVICE);
  2943. + rxi->rx_dma = dma_addr;
  2944. + rxd->rxd1 = (unsigned int) dma_addr;
  2945. + wmb();
  2946. + } else {
  2947. + dev->stats.rx_dropped++;
  2948. + }
  2949. +
  2950. + rxd->rxd2 = RX_DMA_LSO;
  2951. + ramips_fe_twr(rx, RAETH_REG_RX_CALC_IDX0);
  2952. + max_rx--;
  2953. + }
  2954. +
  2955. + if (max_rx == 0)
  2956. + tasklet_schedule(&re->rx_tasklet);
  2957. + else
  2958. + ramips_fe_int_enable(RX_DLY_INT);
  2959. +}
  2960. +
  2961. +static void
  2962. +ramips_eth_tx_housekeeping(unsigned long ptr)
  2963. +{
  2964. + struct net_device *dev = (struct net_device*)ptr;
  2965. + struct raeth_priv *re = netdev_priv(dev);
  2966. + unsigned int bytes_compl = 0, pkts_compl = 0;
  2967. +
  2968. + spin_lock(&re->page_lock);
  2969. + while (1) {
  2970. + struct raeth_tx_info *txi;
  2971. + struct ramips_tx_dma *txd;
  2972. +
  2973. + txi = &re->tx_info[re->skb_free_idx];
  2974. + txd = txi->tx_desc;
  2975. +
  2976. + if (!(txd->txd2 & TX_DMA_DONE) || !(txi->tx_skb))
  2977. + break;
  2978. +
  2979. + pkts_compl++;
  2980. + bytes_compl += txi->tx_skb->len;
  2981. +
  2982. + dev_kfree_skb_irq(txi->tx_skb);
  2983. + txi->tx_skb = NULL;
  2984. + re->skb_free_idx++;
  2985. + if (re->skb_free_idx >= NUM_TX_DESC)
  2986. + re->skb_free_idx = 0;
  2987. + }
  2988. + netdev_completed_queue(dev, pkts_compl, bytes_compl);
  2989. + spin_unlock(&re->page_lock);
  2990. +
  2991. + ramips_fe_int_enable(TX_DLY_INT);
  2992. +}
  2993. +
  2994. +static void
  2995. +ramips_eth_timeout(struct net_device *dev)
  2996. +{
  2997. + struct raeth_priv *re = netdev_priv(dev);
  2998. +
  2999. + tasklet_schedule(&re->tx_housekeeping_tasklet);
  3000. +}
  3001. +
  3002. +static irqreturn_t
  3003. +ramips_eth_irq(int irq, void *dev)
  3004. +{
  3005. + struct raeth_priv *re = netdev_priv(dev);
  3006. + unsigned int status;
  3007. +
  3008. + status = ramips_fe_trr(RAETH_REG_FE_INT_STATUS);
  3009. + status &= ramips_fe_trr(RAETH_REG_FE_INT_ENABLE);
  3010. +
  3011. + if (!status)
  3012. + return IRQ_NONE;
  3013. +
  3014. + ramips_fe_twr(status, RAETH_REG_FE_INT_STATUS);
  3015. +
  3016. + if (status & RX_DLY_INT) {
  3017. + ramips_fe_int_disable(RX_DLY_INT);
  3018. + tasklet_schedule(&re->rx_tasklet);
  3019. + }
  3020. +
  3021. + if (status & TX_DLY_INT) {
  3022. + ramips_fe_int_disable(TX_DLY_INT);
  3023. + tasklet_schedule(&re->tx_housekeeping_tasklet);
  3024. + }
  3025. +
  3026. + raeth_debugfs_update_int_stats(re, status);
  3027. +
  3028. + return IRQ_HANDLED;
  3029. +}
  3030. +
  3031. +static int
  3032. +ramips_eth_hw_init(struct net_device *dev)
  3033. +{
  3034. + struct raeth_priv *re = netdev_priv(dev);
  3035. + int err;
  3036. +
  3037. + err = request_irq(dev->irq, ramips_eth_irq, IRQF_DISABLED,
  3038. + dev_name(re->parent), dev);
  3039. + if (err)
  3040. + return err;
  3041. +
  3042. + err = ramips_ring_alloc(re);
  3043. + if (err)
  3044. + goto err_free_irq;
  3045. +
  3046. + ramips_ring_setup(re);
  3047. + ramips_hw_set_macaddr(dev->dev_addr);
  3048. +
  3049. + ramips_setup_dma(re);
  3050. + ramips_fe_wr((ramips_fe_rr(RAMIPS_FE_GLO_CFG) &
  3051. + ~(RAMIPS_US_CYC_CNT_MASK << RAMIPS_US_CYC_CNT_SHIFT)) |
  3052. + ((re->sys_freq / RAMIPS_US_CYC_CNT_DIVISOR) << RAMIPS_US_CYC_CNT_SHIFT),
  3053. + RAMIPS_FE_GLO_CFG);
  3054. +
  3055. + tasklet_init(&re->tx_housekeeping_tasklet, ramips_eth_tx_housekeeping,
  3056. + (unsigned long)dev);
  3057. + tasklet_init(&re->rx_tasklet, ramips_eth_rx_hw, (unsigned long)dev);
  3058. +
  3059. +
  3060. + ramips_fe_twr(RAMIPS_DELAY_INIT, RAETH_REG_DLY_INT_CFG);
  3061. + ramips_fe_twr(TX_DLY_INT | RX_DLY_INT, RAETH_REG_FE_INT_ENABLE);
  3062. + if (soc_is_rt5350()) {
  3063. + ramips_fe_wr(ramips_fe_rr(RT5350_SDM_CFG) &
  3064. + ~(RT5350_SDM_ICS_EN | RT5350_SDM_TCS_EN | RT5350_SDM_UCS_EN | 0xffff),
  3065. + RT5350_SDM_CFG);
  3066. + } else {
  3067. + ramips_fe_wr(ramips_fe_rr(RAMIPS_GDMA1_FWD_CFG) &
  3068. + ~(RAMIPS_GDM1_ICS_EN | RAMIPS_GDM1_TCS_EN | RAMIPS_GDM1_UCS_EN | 0xffff),
  3069. + RAMIPS_GDMA1_FWD_CFG);
  3070. + ramips_fe_wr(ramips_fe_rr(RAMIPS_CDMA_CSG_CFG) &
  3071. + ~(RAMIPS_ICS_GEN_EN | RAMIPS_TCS_GEN_EN | RAMIPS_UCS_GEN_EN),
  3072. + RAMIPS_CDMA_CSG_CFG);
  3073. + ramips_fe_wr(RAMIPS_PSE_FQFC_CFG_INIT, RAMIPS_PSE_FQ_CFG);
  3074. + }
  3075. + ramips_fe_wr(1, RAMIPS_FE_RST_GL);
  3076. + ramips_fe_wr(0, RAMIPS_FE_RST_GL);
  3077. +
  3078. + return 0;
  3079. +
  3080. +err_free_irq:
  3081. + free_irq(dev->irq, dev);
  3082. + return err;
  3083. +}
  3084. +
  3085. +static int
  3086. +ramips_eth_open(struct net_device *dev)
  3087. +{
  3088. + struct raeth_priv *re = netdev_priv(dev);
  3089. +
  3090. + ramips_fe_twr((ramips_fe_trr(RAETH_REG_PDMA_GLO_CFG) & 0xff) |
  3091. + (RAMIPS_TX_WB_DDONE | RAMIPS_RX_DMA_EN |
  3092. + RAMIPS_TX_DMA_EN | RAMIPS_PDMA_SIZE_4DWORDS),
  3093. + RAETH_REG_PDMA_GLO_CFG);
  3094. + ramips_phy_start(re);
  3095. + netif_start_queue(dev);
  3096. + return 0;
  3097. +}
  3098. +
  3099. +static int
  3100. +ramips_eth_stop(struct net_device *dev)
  3101. +{
  3102. + struct raeth_priv *re = netdev_priv(dev);
  3103. +
  3104. + ramips_fe_twr(ramips_fe_trr(RAETH_REG_PDMA_GLO_CFG) &
  3105. + ~(RAMIPS_TX_WB_DDONE | RAMIPS_RX_DMA_EN | RAMIPS_TX_DMA_EN),
  3106. + RAETH_REG_PDMA_GLO_CFG);
  3107. +
  3108. + netif_stop_queue(dev);
  3109. + ramips_phy_stop(re);
  3110. + RADEBUG("ramips_eth: stopped\n");
  3111. + return 0;
  3112. +}
  3113. +
  3114. +static int __init
  3115. +ramips_eth_probe(struct net_device *dev)
  3116. +{
  3117. + struct raeth_priv *re = netdev_priv(dev);
  3118. + int err;
  3119. +
  3120. + BUG_ON(!re->reset_fe);
  3121. + re->reset_fe();
  3122. + net_srandom(jiffies);
  3123. + memcpy(dev->dev_addr, re->mac, ETH_ALEN);
  3124. + of_get_mac_address_mtd(re->of_node, dev->dev_addr);
  3125. + ether_setup(dev);
  3126. + dev->mtu = 1500;
  3127. + dev->watchdog_timeo = TX_TIMEOUT;
  3128. + spin_lock_init(&re->page_lock);
  3129. + spin_lock_init(&re->phy_lock);
  3130. +
  3131. + err = ramips_mdio_init(re);
  3132. + if (err)
  3133. + return err;
  3134. +
  3135. + err = ramips_phy_connect(re);
  3136. + if (err)
  3137. + goto err_mdio_cleanup;
  3138. +
  3139. + err = raeth_debugfs_init(re);
  3140. + if (err)
  3141. + goto err_phy_disconnect;
  3142. +
  3143. + err = ramips_eth_hw_init(dev);
  3144. + if (err)
  3145. + goto err_debugfs;
  3146. +
  3147. + return 0;
  3148. +
  3149. +err_debugfs:
  3150. + raeth_debugfs_exit(re);
  3151. +err_phy_disconnect:
  3152. + ramips_phy_disconnect(re);
  3153. +err_mdio_cleanup:
  3154. + ramips_mdio_cleanup(re);
  3155. + return err;
  3156. +}
  3157. +
  3158. +static void
  3159. +ramips_eth_uninit(struct net_device *dev)
  3160. +{
  3161. + struct raeth_priv *re = netdev_priv(dev);
  3162. +
  3163. + raeth_debugfs_exit(re);
  3164. + ramips_phy_disconnect(re);
  3165. + ramips_mdio_cleanup(re);
  3166. + ramips_fe_twr(0, RAETH_REG_FE_INT_ENABLE);
  3167. + free_irq(dev->irq, dev);
  3168. + tasklet_kill(&re->tx_housekeeping_tasklet);
  3169. + tasklet_kill(&re->rx_tasklet);
  3170. + ramips_ring_cleanup(re);
  3171. + ramips_ring_free(re);
  3172. +}
  3173. +
  3174. +static const struct net_device_ops ramips_eth_netdev_ops = {
  3175. + .ndo_init = ramips_eth_probe,
  3176. + .ndo_uninit = ramips_eth_uninit,
  3177. + .ndo_open = ramips_eth_open,
  3178. + .ndo_stop = ramips_eth_stop,
  3179. + .ndo_start_xmit = ramips_eth_hard_start_xmit,
  3180. + .ndo_tx_timeout = ramips_eth_timeout,
  3181. + .ndo_change_mtu = eth_change_mtu,
  3182. + .ndo_set_mac_address = eth_mac_addr,
  3183. + .ndo_validate_addr = eth_validate_addr,
  3184. +};
  3185. +
  3186. +#ifdef CONFIG_SOC_RT305X
  3187. +static void rt305x_fe_reset(void)
  3188. +{
  3189. +#define RT305X_RESET_FE BIT(21)
  3190. +#define RT305X_RESET_ESW BIT(23)
  3191. +#define SYSC_REG_RESET_CTRL 0x034
  3192. + u32 reset_bits = RT305X_RESET_FE;
  3193. +
  3194. + if (soc_is_rt5350())
  3195. + reset_bits |= RT305X_RESET_ESW;
  3196. + rt_sysc_w32(reset_bits, SYSC_REG_RESET_CTRL);
  3197. + rt_sysc_w32(0, SYSC_REG_RESET_CTRL);
  3198. +}
  3199. +
  3200. +struct ramips_soc_data rt3050_data = {
  3201. + .mac = { 0x00, 0x11, 0x22, 0x33, 0x44, 0x55 },
  3202. + .reset_fe = rt305x_fe_reset,
  3203. + .min_pkt_len = 64,
  3204. +};
  3205. +
  3206. +static const struct of_device_id ralink_eth_match[] = {
  3207. + { .compatible = "ralink,rt3050-eth", .data = &rt3050_data },
  3208. + {},
  3209. +};
  3210. +#else
  3211. +static void rt3883_fe_reset(void)
  3212. +{
  3213. +#define RT3883_SYSC_REG_RSTCTRL 0x34
  3214. +#define RT3883_RSTCTRL_FE BIT(21)
  3215. + u32 t;
  3216. +
  3217. + t = rt_sysc_r32(RT3883_SYSC_REG_RSTCTRL);
  3218. + t |= RT3883_RSTCTRL_FE;
  3219. + rt_sysc_w32(t , RT3883_SYSC_REG_RSTCTRL);
  3220. +
  3221. + t &= ~RT3883_RSTCTRL_FE;
  3222. + rt_sysc_w32(t, RT3883_SYSC_REG_RSTCTRL);
  3223. +}
  3224. +
  3225. +struct ramips_soc_data rt3883_data = {
  3226. + .mac = { 0x00, 0x11, 0x22, 0x33, 0x44, 0x55 },
  3227. + .reset_fe = rt3883_fe_reset,
  3228. + .min_pkt_len = 64,
  3229. +};
  3230. +
  3231. +static const struct of_device_id ralink_eth_match[] = {
  3232. + { .compatible = "ralink,rt3883-eth", .data = &rt3883_data },
  3233. + {},
  3234. +};
  3235. +#endif
  3236. +MODULE_DEVICE_TABLE(of, ralink_eth_match);
  3237. +
  3238. +static int
  3239. +ramips_eth_plat_probe(struct platform_device *plat)
  3240. +{
  3241. + struct raeth_priv *re;
  3242. + struct resource *res;
  3243. + struct clk *clk;
  3244. + int err;
  3245. + const struct of_device_id *match;
  3246. + const struct ramips_soc_data *soc = NULL;
  3247. +
  3248. + match = of_match_device(ralink_eth_match, &plat->dev);
  3249. + if (match)
  3250. + soc = (const struct ramips_soc_data *) match->data;
  3251. +
  3252. + if (!soc) {
  3253. + dev_err(&plat->dev, "no platform data specified\n");
  3254. + return -EINVAL;
  3255. + }
  3256. +
  3257. + res = platform_get_resource(plat, IORESOURCE_MEM, 0);
  3258. + if (!res) {
  3259. + dev_err(&plat->dev, "no memory resource found\n");
  3260. + return -ENXIO;
  3261. + }
  3262. +
  3263. + ramips_fe_base = ioremap_nocache(res->start, res->end - res->start + 1);
  3264. + if (!ramips_fe_base)
  3265. + return -ENOMEM;
  3266. +
  3267. + ramips_dev = alloc_etherdev(sizeof(struct raeth_priv));
  3268. + if (!ramips_dev) {
  3269. + dev_err(&plat->dev, "alloc_etherdev failed\n");
  3270. + err = -ENOMEM;
  3271. + goto err_unmap;
  3272. + }
  3273. +
  3274. + strcpy(ramips_dev->name, "eth%d");
  3275. + ramips_dev->irq = platform_get_irq(plat, 0);
  3276. + if (ramips_dev->irq < 0) {
  3277. + dev_err(&plat->dev, "no IRQ resource found\n");
  3278. + err = -ENXIO;
  3279. + goto err_free_dev;
  3280. + }
  3281. + ramips_dev->addr_len = ETH_ALEN;
  3282. + ramips_dev->base_addr = (unsigned long)ramips_fe_base;
  3283. + ramips_dev->netdev_ops = &ramips_eth_netdev_ops;
  3284. +
  3285. + re = netdev_priv(ramips_dev);
  3286. +
  3287. + clk = clk_get(&plat->dev, NULL);
  3288. + if (IS_ERR(clk))
  3289. + panic("unable to get SYS clock, err=%ld", PTR_ERR(clk));
  3290. + re->sys_freq = clk_get_rate(clk);
  3291. +
  3292. + re->netdev = ramips_dev;
  3293. + re->of_node = plat->dev.of_node;
  3294. + re->parent = &plat->dev;
  3295. + memcpy(re->mac, soc->mac, 6);
  3296. + re->reset_fe = soc->reset_fe;
  3297. + re->min_pkt_len = soc->min_pkt_len;
  3298. +
  3299. + err = register_netdev(ramips_dev);
  3300. + if (err) {
  3301. + dev_err(&plat->dev, "error bringing up device\n");
  3302. + goto err_free_dev;
  3303. + }
  3304. +
  3305. + netdev_info(ramips_dev, "done loading\n");
  3306. + return 0;
  3307. +
  3308. + err_free_dev:
  3309. + kfree(ramips_dev);
  3310. + err_unmap:
  3311. + iounmap(ramips_fe_base);
  3312. + return err;
  3313. +}
  3314. +
  3315. +static int
  3316. +ramips_eth_plat_remove(struct platform_device *plat)
  3317. +{
  3318. + unregister_netdev(ramips_dev);
  3319. + free_netdev(ramips_dev);
  3320. + RADEBUG("ramips_eth: unloaded\n");
  3321. + return 0;
  3322. +}
  3323. +
  3324. +
  3325. +
  3326. +static struct platform_driver ramips_eth_driver = {
  3327. + .probe = ramips_eth_plat_probe,
  3328. + .remove = ramips_eth_plat_remove,
  3329. + .driver = {
  3330. + .name = "ramips_eth",
  3331. + .owner = THIS_MODULE,
  3332. + .of_match_table = ralink_eth_match
  3333. + },
  3334. +};
  3335. +
  3336. +static int __init
  3337. +ramips_eth_init(void)
  3338. +{
  3339. + int ret;
  3340. +
  3341. + ret = raeth_debugfs_root_init();
  3342. + if (ret)
  3343. + goto err_out;
  3344. +
  3345. + ret = rt305x_esw_init();
  3346. + if (ret)
  3347. + goto err_debugfs_exit;
  3348. +
  3349. + ret = platform_driver_register(&ramips_eth_driver);
  3350. + if (ret) {
  3351. + printk(KERN_ERR
  3352. + "ramips_eth: Error registering platfom driver!\n");
  3353. + goto esw_cleanup;
  3354. + }
  3355. +
  3356. + return 0;
  3357. +
  3358. +esw_cleanup:
  3359. + rt305x_esw_exit();
  3360. +err_debugfs_exit:
  3361. + raeth_debugfs_root_exit();
  3362. +err_out:
  3363. + return ret;
  3364. +}
  3365. +
  3366. +static void __exit
  3367. +ramips_eth_cleanup(void)
  3368. +{
  3369. + platform_driver_unregister(&ramips_eth_driver);
  3370. + rt305x_esw_exit();
  3371. + raeth_debugfs_root_exit();
  3372. +}
  3373. +
  3374. +module_init(ramips_eth_init);
  3375. +module_exit(ramips_eth_cleanup);
  3376. +
  3377. +MODULE_LICENSE("GPL");
  3378. +MODULE_AUTHOR("John Crispin <blogic@openwrt.org>");
  3379. +MODULE_DESCRIPTION("ethernet driver for ramips boards");
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement