Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
L
linux-davinci
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Redmine
Redmine
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Operations
Operations
Metrics
Environments
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
linux
linux-davinci
Commits
2a69bf42
Commit
2a69bf42
authored
Sep 12, 2006
by
Jeff Garzik
Browse files
Options
Browse Files
Download
Plain Diff
Merge tag 'r8169-20060912-00' of
git://electric-eye.fr.zoreil.com/home/romieu/linux-2.6
into tmp
parents
cb930205
b39fe41f
Changes
1
Show whitespace changes
Inline
Side-by-side
Showing
1 changed file
with
380 additions
and
276 deletions
+380
-276
drivers/net/r8169.c
drivers/net/r8169.c
+380
-276
No files found.
drivers/net/r8169.c
View file @
2a69bf42
...
...
@@ -81,7 +81,7 @@ VERSION 2.2LK <2005/01/25>
#ifdef RTL8169_DEBUG
#define assert(expr) \
if
(!(expr)) { \
if
(!(expr)) { \
printk( "Assertion failed! %s,%s,%s,line=%d\n", \
#expr,__FILE__,__FUNCTION__,__LINE__); \
}
...
...
@@ -150,11 +150,16 @@ static const int multicast_filter_limit = 32;
#define RTL_R32(reg) ((unsigned long) readl (ioaddr + (reg)))
enum
mac_version
{
RTL_GIGA_MAC_VER_B
=
0x00
,
/* RTL_GIGA_MAC_VER_C = 0x03, */
RTL_GIGA_MAC_VER_D
=
0x01
,
RTL_GIGA_MAC_VER_E
=
0x02
,
RTL_GIGA_MAC_VER_X
=
0x04
/* Greater than RTL_GIGA_MAC_VER_E */
RTL_GIGA_MAC_VER_01
=
0x00
,
RTL_GIGA_MAC_VER_02
=
0x01
,
RTL_GIGA_MAC_VER_03
=
0x02
,
RTL_GIGA_MAC_VER_04
=
0x03
,
RTL_GIGA_MAC_VER_05
=
0x04
,
RTL_GIGA_MAC_VER_11
=
0x0b
,
RTL_GIGA_MAC_VER_12
=
0x0c
,
RTL_GIGA_MAC_VER_13
=
0x0d
,
RTL_GIGA_MAC_VER_14
=
0x0e
,
RTL_GIGA_MAC_VER_15
=
0x0f
};
enum
phy_version
{
...
...
@@ -166,7 +171,6 @@ enum phy_version {
RTL_GIGA_PHY_VER_H
=
0x08
,
/* PHY Reg 0x03 bit0-3 == 0x0003 */
};
#define _R(NAME,MAC,MASK) \
{ .name = NAME, .mac_version = MAC, .RxConfigMask = MASK }
...
...
@@ -175,19 +179,44 @@ static const struct {
u8
mac_version
;
u32
RxConfigMask
;
/* Clears the bits supported by this chip */
}
rtl_chip_info
[]
=
{
_R
(
"RTL8169"
,
RTL_GIGA_MAC_VER_B
,
0xff7e1880
),
_R
(
"RTL8169s/8110s"
,
RTL_GIGA_MAC_VER_D
,
0xff7e1880
),
_R
(
"RTL8169s/8110s"
,
RTL_GIGA_MAC_VER_E
,
0xff7e1880
),
_R
(
"RTL8169s/8110s"
,
RTL_GIGA_MAC_VER_X
,
0xff7e1880
),
_R
(
"RTL8169"
,
RTL_GIGA_MAC_VER_01
,
0xff7e1880
),
_R
(
"RTL8169s/8110s"
,
RTL_GIGA_MAC_VER_02
,
0xff7e1880
),
_R
(
"RTL8169s/8110s"
,
RTL_GIGA_MAC_VER_03
,
0xff7e1880
),
_R
(
"RTL8169sb/8110sb"
,
RTL_GIGA_MAC_VER_04
,
0xff7e1880
),
_R
(
"RTL8169sc/8110sc"
,
RTL_GIGA_MAC_VER_05
,
0xff7e1880
),
_R
(
"RTL8168b/8111b"
,
RTL_GIGA_MAC_VER_11
,
0xff7e1880
),
// PCI-E
_R
(
"RTL8168b/8111b"
,
RTL_GIGA_MAC_VER_12
,
0xff7e1880
),
// PCI-E
_R
(
"RTL8101e"
,
RTL_GIGA_MAC_VER_13
,
0xff7e1880
),
// PCI-E 8139
_R
(
"RTL8100e"
,
RTL_GIGA_MAC_VER_14
,
0xff7e1880
),
// PCI-E 8139
_R
(
"RTL8100e"
,
RTL_GIGA_MAC_VER_15
,
0xff7e1880
)
// PCI-E 8139
};
#undef _R
enum
cfg_version
{
RTL_CFG_0
=
0x00
,
RTL_CFG_1
,
RTL_CFG_2
};
static
const
struct
{
unsigned
int
region
;
unsigned
int
align
;
}
rtl_cfg_info
[]
=
{
[
RTL_CFG_0
]
=
{
1
,
NET_IP_ALIGN
},
[
RTL_CFG_1
]
=
{
2
,
NET_IP_ALIGN
},
[
RTL_CFG_2
]
=
{
2
,
8
}
};
static
struct
pci_device_id
rtl8169_pci_tbl
[]
=
{
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8169
),
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8129
),
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_DLINK
,
0x4300
),
},
{
PCI_DEVICE
(
0x16ec
,
0x0116
),
},
{
PCI_VENDOR_ID_LINKSYS
,
0x1032
,
PCI_ANY_ID
,
0x0024
,
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8129
),
0
,
0
,
RTL_CFG_0
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8136
),
0
,
0
,
RTL_CFG_2
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8167
),
0
,
0
,
RTL_CFG_1
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8168
),
0
,
0
,
RTL_CFG_2
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_REALTEK
,
0x8169
),
0
,
0
,
RTL_CFG_0
},
{
PCI_DEVICE
(
PCI_VENDOR_ID_DLINK
,
0x4300
),
0
,
0
,
RTL_CFG_0
},
{
PCI_DEVICE
(
0x16ec
,
0x0116
),
0
,
0
,
RTL_CFG_0
},
{
PCI_VENDOR_ID_LINKSYS
,
0x1032
,
PCI_ANY_ID
,
0x0024
,
0
,
0
,
RTL_CFG_0
},
{
0
,},
};
...
...
@@ -257,10 +286,11 @@ enum RTL8169_register_content {
RxOK
=
0x01
,
/* RxStatusDesc */
RxRES
=
0x00200000
,
RxCRC
=
0x00080000
,
RxRUNT
=
0x00100000
,
RxRWT
=
0x00400000
,
RxFOVF
=
(
1
<<
23
),
RxRWT
=
(
1
<<
22
),
RxRES
=
(
1
<<
21
),
RxRUNT
=
(
1
<<
20
),
RxCRC
=
(
1
<<
19
),
/* ChipCmdBits */
CmdReset
=
0x10
,
...
...
@@ -326,30 +356,6 @@ enum RTL8169_register_content {
LinkStatus
=
0x02
,
FullDup
=
0x01
,
/* GIGABIT_PHY_registers */
PHY_CTRL_REG
=
0
,
PHY_STAT_REG
=
1
,
PHY_AUTO_NEGO_REG
=
4
,
PHY_1000_CTRL_REG
=
9
,
/* GIGABIT_PHY_REG_BIT */
PHY_Restart_Auto_Nego
=
0x0200
,
PHY_Enable_Auto_Nego
=
0x1000
,
/* PHY_STAT_REG = 1 */
PHY_Auto_Neco_Comp
=
0x0020
,
/* PHY_AUTO_NEGO_REG = 4 */
PHY_Cap_10_Half
=
0x0020
,
PHY_Cap_10_Full
=
0x0040
,
PHY_Cap_100_Half
=
0x0080
,
PHY_Cap_100_Full
=
0x0100
,
/* PHY_1000_CTRL_REG = 9 */
PHY_Cap_1000_Full
=
0x0200
,
PHY_Cap_Null
=
0x0
,
/* _MediaType */
_10_Half
=
0x01
,
_10_Full
=
0x02
,
...
...
@@ -433,6 +439,7 @@ struct rtl8169_private {
dma_addr_t
RxPhyAddr
;
struct
sk_buff
*
Rx_skbuff
[
NUM_RX_DESC
];
/* Rx data buffers */
struct
ring_info
tx_skb
[
NUM_TX_DESC
];
/* Tx data buffers */
unsigned
align
;
unsigned
rx_buf_sz
;
struct
timer_list
timer
;
u16
cp_cmd
;
...
...
@@ -490,11 +497,6 @@ static const u16 rtl8169_napi_event =
static
const
unsigned
int
rtl8169_rx_config
=
(
RX_FIFO_THRESH
<<
RxCfgFIFOShift
)
|
(
RX_DMA_BURST
<<
RxCfgDMAShift
);
#define PHY_Cap_10_Half_Or_Less PHY_Cap_10_Half
#define PHY_Cap_10_Full_Or_Less PHY_Cap_10_Full | PHY_Cap_10_Half_Or_Less
#define PHY_Cap_100_Half_Or_Less PHY_Cap_100_Half | PHY_Cap_10_Full_Or_Less
#define PHY_Cap_100_Full_Or_Less PHY_Cap_100_Full | PHY_Cap_100_Half_Or_Less
static
void
mdio_write
(
void
__iomem
*
ioaddr
,
int
RegAddr
,
int
value
)
{
int
i
;
...
...
@@ -547,7 +549,7 @@ static unsigned int rtl8169_tbi_reset_pending(void __iomem *ioaddr)
static
unsigned
int
rtl8169_xmii_reset_pending
(
void
__iomem
*
ioaddr
)
{
return
mdio_read
(
ioaddr
,
0
)
&
0x8000
;
return
mdio_read
(
ioaddr
,
MII_BMCR
)
&
BMCR_RESET
;
}
static
unsigned
int
rtl8169_tbi_link_ok
(
void
__iomem
*
ioaddr
)
...
...
@@ -569,8 +571,8 @@ static void rtl8169_xmii_reset_enable(void __iomem *ioaddr)
{
unsigned
int
val
;
val
=
(
mdio_read
(
ioaddr
,
PHY_CTRL_REG
)
|
0x8000
)
&
0xffff
;
mdio_write
(
ioaddr
,
PHY_CTRL_REG
,
val
);
val
=
(
mdio_read
(
ioaddr
,
MII_BMCR
)
|
BMCR_RESET
)
&
0xffff
;
mdio_write
(
ioaddr
,
MII_BMCR
,
val
);
}
static
void
rtl8169_check_link_status
(
struct
net_device
*
dev
,
...
...
@@ -745,38 +747,57 @@ static int rtl8169_set_speed_xmii(struct net_device *dev,
void
__iomem
*
ioaddr
=
tp
->
mmio_addr
;
int
auto_nego
,
giga_ctrl
;
auto_nego
=
mdio_read
(
ioaddr
,
PHY_AUTO_NEGO_REG
);
auto_nego
&=
~
(
PHY_Cap_10_Half
|
PHY_Cap_10_Full
|
PHY_Cap_100_Half
|
PHY_Cap_100_Full
);
giga_ctrl
=
mdio_read
(
ioaddr
,
PHY_1000_CTRL_REG
);
giga_ctrl
&=
~
(
PHY_Cap_1000_Full
|
PHY_Cap_Null
);
auto_nego
=
mdio_read
(
ioaddr
,
MII_ADVERTISE
);
auto_nego
&=
~
(
ADVERTISE_10HALF
|
ADVERTISE_10FULL
|
ADVERTISE_100HALF
|
ADVERTISE_100FULL
);
giga_ctrl
=
mdio_read
(
ioaddr
,
MII_CTRL1000
);
giga_ctrl
&=
~
(
ADVERTISE_1000FULL
|
ADVERTISE_1000HALF
);
if
(
autoneg
==
AUTONEG_ENABLE
)
{
auto_nego
|=
(
PHY_Cap_10_Half
|
PHY_Cap_10_Full
|
PHY_Cap_100_Half
|
PHY_Cap_100_Full
);
giga_ctrl
|=
PHY_Cap_1000_Full
;
auto_nego
|=
(
ADVERTISE_10HALF
|
ADVERTISE_10FULL
|
ADVERTISE_100HALF
|
ADVERTISE_100FULL
);
giga_ctrl
|=
ADVERTISE_1000FULL
|
ADVERTISE_1000HALF
;
}
else
{
if
(
speed
==
SPEED_10
)
auto_nego
|=
PHY_Cap_10_Half
|
PHY_Cap_10_Full
;
auto_nego
|=
ADVERTISE_10HALF
|
ADVERTISE_10FULL
;
else
if
(
speed
==
SPEED_100
)
auto_nego
|=
PHY_Cap_100_Half
|
PHY_Cap_100_Full
;
auto_nego
|=
ADVERTISE_100HALF
|
ADVERTISE_100FULL
;
else
if
(
speed
==
SPEED_1000
)
giga_ctrl
|=
PHY_Cap_1000_Full
;
giga_ctrl
|=
ADVERTISE_1000FULL
|
ADVERTISE_1000HALF
;
if
(
duplex
==
DUPLEX_HALF
)
auto_nego
&=
~
(
PHY_Cap_10_Full
|
PHY_Cap_100_Full
);
auto_nego
&=
~
(
ADVERTISE_10FULL
|
ADVERTISE_100FULL
);
if
(
duplex
==
DUPLEX_FULL
)
auto_nego
&=
~
(
PHY_Cap_10_Half
|
PHY_Cap_100_Half
);
auto_nego
&=
~
(
ADVERTISE_10HALF
|
ADVERTISE_100HALF
);
/* This tweak comes straight from Realtek's driver. */
if
((
speed
==
SPEED_100
)
&&
(
duplex
==
DUPLEX_HALF
)
&&
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_13
))
{
auto_nego
=
ADVERTISE_100HALF
|
ADVERTISE_CSMA
;
}
}
/* The 8100e/8101e do Fast Ethernet only. */
if
((
tp
->
mac_version
==
RTL_GIGA_MAC_VER_13
)
||
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_14
)
||
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_15
))
{
if
((
giga_ctrl
&
(
ADVERTISE_1000FULL
|
ADVERTISE_1000HALF
))
&&
netif_msg_link
(
tp
))
{
printk
(
KERN_INFO
"%s: PHY does not support 1000Mbps.
\n
"
,
dev
->
name
);
}
giga_ctrl
&=
~
(
ADVERTISE_1000FULL
|
ADVERTISE_1000HALF
);
}
auto_nego
|=
ADVERTISE_PAUSE_CAP
|
ADVERTISE_PAUSE_ASYM
;
tp
->
phy_auto_nego_reg
=
auto_nego
;
tp
->
phy_1000_ctrl_reg
=
giga_ctrl
;
mdio_write
(
ioaddr
,
PHY_AUTO_NEGO_REG
,
auto_nego
);
mdio_write
(
ioaddr
,
PHY_1000_CTRL_REG
,
giga_ctrl
);
mdio_write
(
ioaddr
,
PHY_CTRL_REG
,
PHY_Enable_Auto_Nego
|
PHY_Restart_Auto_Nego
);
mdio_write
(
ioaddr
,
MII_ADVERTISE
,
auto_nego
);
mdio_write
(
ioaddr
,
MII_CTRL1000
,
giga_ctrl
);
mdio_write
(
ioaddr
,
MII_BMCR
,
BMCR_ANENABLE
|
BMCR_ANRESTART
);
return
0
;
}
...
...
@@ -788,7 +809,7 @@ static int rtl8169_set_speed(struct net_device *dev,
ret
=
tp
->
set_speed
(
dev
,
autoneg
,
speed
,
duplex
);
if
(
netif_running
(
dev
)
&&
(
tp
->
phy_1000_ctrl_reg
&
PHY_Cap_1000_Full
))
if
(
netif_running
(
dev
)
&&
(
tp
->
phy_1000_ctrl_reg
&
ADVERTISE_1000FULL
))
mod_timer
(
&
tp
->
timer
,
jiffies
+
RTL8169_PHY_TIMEOUT
);
return
ret
;
...
...
@@ -941,15 +962,15 @@ static void rtl8169_gset_xmii(struct net_device *dev, struct ethtool_cmd *cmd)
cmd
->
autoneg
=
1
;
cmd
->
advertising
=
ADVERTISED_TP
|
ADVERTISED_Autoneg
;
if
(
tp
->
phy_auto_nego_reg
&
PHY_Cap_10_Half
)
if
(
tp
->
phy_auto_nego_reg
&
ADVERTISE_10HALF
)
cmd
->
advertising
|=
ADVERTISED_10baseT_Half
;
if
(
tp
->
phy_auto_nego_reg
&
PHY_Cap_10_Full
)
if
(
tp
->
phy_auto_nego_reg
&
ADVERTISE_10FULL
)
cmd
->
advertising
|=
ADVERTISED_10baseT_Full
;
if
(
tp
->
phy_auto_nego_reg
&
PHY_Cap_100_Half
)
if
(
tp
->
phy_auto_nego_reg
&
ADVERTISE_100HALF
)
cmd
->
advertising
|=
ADVERTISED_100baseT_Half
;
if
(
tp
->
phy_auto_nego_reg
&
PHY_Cap_100_Full
)
if
(
tp
->
phy_auto_nego_reg
&
ADVERTISE_100FULL
)
cmd
->
advertising
|=
ADVERTISED_100baseT_Full
;
if
(
tp
->
phy_1000_ctrl_reg
&
PHY_Cap_1000_Full
)
if
(
tp
->
phy_1000_ctrl_reg
&
ADVERTISE_1000FULL
)
cmd
->
advertising
|=
ADVERTISED_1000baseT_Full
;
status
=
RTL_R8
(
PHYstatus
);
...
...
@@ -961,6 +982,11 @@ static void rtl8169_gset_xmii(struct net_device *dev, struct ethtool_cmd *cmd)
else
if
(
status
&
_10bps
)
cmd
->
speed
=
SPEED_10
;
if
(
status
&
TxFlowCtrl
)
cmd
->
advertising
|=
ADVERTISED_Asym_Pause
;
if
(
status
&
RxFlowCtrl
)
cmd
->
advertising
|=
ADVERTISED_Pause
;
cmd
->
duplex
=
((
status
&
_1000bpsF
)
||
(
status
&
FullDup
))
?
DUPLEX_FULL
:
DUPLEX_HALF
;
}
...
...
@@ -1140,10 +1166,16 @@ static void rtl8169_get_mac_version(struct rtl8169_private *tp, void __iomem *io
u32
mask
;
int
mac_version
;
}
mac_info
[]
=
{
{
0x1
<<
28
,
RTL_GIGA_MAC_VER_X
},
{
0x1
<<
26
,
RTL_GIGA_MAC_VER_E
},
{
0x1
<<
23
,
RTL_GIGA_MAC_VER_D
},
{
0x00000000
,
RTL_GIGA_MAC_VER_B
}
/* Catch-all */
{
0x38800000
,
RTL_GIGA_MAC_VER_15
},
{
0x38000000
,
RTL_GIGA_MAC_VER_12
},
{
0x34000000
,
RTL_GIGA_MAC_VER_13
},
{
0x30800000
,
RTL_GIGA_MAC_VER_14
},
{
0x30000000
,
RTL_GIGA_MAC_VER_11
},
{
0x18000000
,
RTL_GIGA_MAC_VER_05
},
{
0x10000000
,
RTL_GIGA_MAC_VER_04
},
{
0x04000000
,
RTL_GIGA_MAC_VER_03
},
{
0x00800000
,
RTL_GIGA_MAC_VER_02
},
{
0x00000000
,
RTL_GIGA_MAC_VER_01
}
/* Catch-all */
},
*
p
=
mac_info
;
u32
reg
;
...
...
@@ -1155,24 +1187,7 @@ static void rtl8169_get_mac_version(struct rtl8169_private *tp, void __iomem *io
static
void
rtl8169_print_mac_version
(
struct
rtl8169_private
*
tp
)
{
struct
{
int
version
;
char
*
msg
;
}
mac_print
[]
=
{
{
RTL_GIGA_MAC_VER_E
,
"RTL_GIGA_MAC_VER_E"
},
{
RTL_GIGA_MAC_VER_D
,
"RTL_GIGA_MAC_VER_D"
},
{
RTL_GIGA_MAC_VER_B
,
"RTL_GIGA_MAC_VER_B"
},
{
0
,
NULL
}
},
*
p
;
for
(
p
=
mac_print
;
p
->
msg
;
p
++
)
{
if
(
tp
->
mac_version
==
p
->
version
)
{
dprintk
(
"mac_version == %s (%04d)
\n
"
,
p
->
msg
,
p
->
version
);
return
;
}
}
dprintk
(
"mac_version == Unknown
\n
"
);
dprintk
(
"mac_version = 0x%02x
\n
"
,
tp
->
mac_version
);
}
static
void
rtl8169_get_phy_version
(
struct
rtl8169_private
*
tp
,
void
__iomem
*
ioaddr
)
...
...
@@ -1189,7 +1204,7 @@ static void rtl8169_get_phy_version(struct rtl8169_private *tp, void __iomem *io
},
*
p
=
phy_info
;
u16
reg
;
reg
=
mdio_read
(
ioaddr
,
3
)
&
0xffff
;
reg
=
mdio_read
(
ioaddr
,
MII_PHYSID2
)
&
0xffff
;
while
((
reg
&
p
->
mask
)
!=
p
->
set
)
p
++
;
tp
->
phy_version
=
p
->
phy_version
;
...
...
@@ -1257,7 +1272,7 @@ static void rtl8169_hw_phy_config(struct net_device *dev)
rtl8169_print_mac_version
(
tp
);
rtl8169_print_phy_version
(
tp
);
if
(
tp
->
mac_version
<=
RTL_GIGA_MAC_VER_
B
)
if
(
tp
->
mac_version
<=
RTL_GIGA_MAC_VER_
01
)
return
;
if
(
tp
->
phy_version
>=
RTL_GIGA_PHY_VER_H
)
return
;
...
...
@@ -1267,7 +1282,7 @@ static void rtl8169_hw_phy_config(struct net_device *dev)
/* Shazam ! */
if
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_
X
)
{
if
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_
04
)
{
mdio_write
(
ioaddr
,
31
,
0x0001
);
mdio_write
(
ioaddr
,
9
,
0x273a
);
mdio_write
(
ioaddr
,
14
,
0x7bfb
);
...
...
@@ -1306,10 +1321,10 @@ static void rtl8169_phy_timer(unsigned long __opaque)
void
__iomem
*
ioaddr
=
tp
->
mmio_addr
;
unsigned
long
timeout
=
RTL8169_PHY_TIMEOUT
;
assert
(
tp
->
mac_version
>
RTL_GIGA_MAC_VER_
B
);
assert
(
tp
->
mac_version
>
RTL_GIGA_MAC_VER_
01
);
assert
(
tp
->
phy_version
<
RTL_GIGA_PHY_VER_H
);
if
(
!
(
tp
->
phy_1000_ctrl_reg
&
PHY_Cap_1000_Full
))
if
(
!
(
tp
->
phy_1000_ctrl_reg
&
ADVERTISE_1000FULL
))
return
;
spin_lock_irq
(
&
tp
->
lock
);
...
...
@@ -1342,7 +1357,7 @@ static inline void rtl8169_delete_timer(struct net_device *dev)
struct
rtl8169_private
*
tp
=
netdev_priv
(
dev
);
struct
timer_list
*
timer
=
&
tp
->
timer
;
if
((
tp
->
mac_version
<=
RTL_GIGA_MAC_VER_
B
)
||
if
((
tp
->
mac_version
<=
RTL_GIGA_MAC_VER_
01
)
||
(
tp
->
phy_version
>=
RTL_GIGA_PHY_VER_H
))
return
;
...
...
@@ -1354,7 +1369,7 @@ static inline void rtl8169_request_timer(struct net_device *dev)
struct
rtl8169_private
*
tp
=
netdev_priv
(
dev
);
struct
timer_list
*
timer
=
&
tp
->
timer
;
if
((
tp
->
mac_version
<=
RTL_GIGA_MAC_VER_
B
)
||
if
((
tp
->
mac_version
<=
RTL_GIGA_MAC_VER_
01
)
||
(
tp
->
phy_version
>=
RTL_GIGA_PHY_VER_H
))
return
;
...
...
@@ -1382,6 +1397,41 @@ static void rtl8169_netpoll(struct net_device *dev)
}
#endif
static
void
__rtl8169_set_mac_addr
(
struct
net_device
*
dev
,
void
__iomem
*
ioaddr
)
{
unsigned
int
i
,
j
;
RTL_W8
(
Cfg9346
,
Cfg9346_Unlock
);
for
(
i
=
0
;
i
<
2
;
i
++
)
{
__le32
l
=
0
;
for
(
j
=
0
;
j
<
4
;
j
++
)
{
l
<<=
8
;
l
|=
dev
->
dev_addr
[
4
*
i
+
j
];
}
RTL_W32
(
MAC0
+
4
*
i
,
cpu_to_be32
(
l
));
}
RTL_W8
(
Cfg9346
,
Cfg9346_Lock
);
}
static
int
rtl8169_set_mac_addr
(
struct
net_device
*
dev
,
void
*
p
)
{
struct
rtl8169_private
*
tp
=
netdev_priv
(
dev
);
struct
sockaddr
*
addr
=
p
;
if
(
!
is_valid_ether_addr
(
addr
->
sa_data
))
return
-
EINVAL
;
memcpy
(
dev
->
dev_addr
,
addr
->
sa_data
,
dev
->
addr_len
);
if
(
netif_running
(
dev
))
{
spin_lock_irq
(
&
tp
->
lock
);
__rtl8169_set_mac_addr
(
dev
,
tp
->
mmio_addr
);
spin_unlock_irq
(
&
tp
->
lock
);
}
return
0
;
}
static
void
rtl8169_release_board
(
struct
pci_dev
*
pdev
,
struct
net_device
*
dev
,
void
__iomem
*
ioaddr
)
{
...
...
@@ -1391,23 +1441,87 @@ static void rtl8169_release_board(struct pci_dev *pdev, struct net_device *dev,
free_netdev
(
dev
);
}
static
void
rtl8169_init_phy
(
struct
net_device
*
dev
,
struct
rtl8169_private
*
tp
)
{
void
__iomem
*
ioaddr
=
tp
->
mmio_addr
;
static
int
board_idx
=
-
1
;
u8
autoneg
,
duplex
;
u16
speed
;
board_idx
++
;
rtl8169_hw_phy_config
(
dev
);
dprintk
(
"Set MAC Reg C+CR Offset 0x82h = 0x01h
\n
"
);
RTL_W8
(
0x82
,
0x01
);
if
(
tp
->
mac_version
<
RTL_GIGA_MAC_VER_03
)
{
dprintk
(
"Set PCI Latency=0x40
\n
"
);
pci_write_config_byte
(
tp
->
pci_dev
,
PCI_LATENCY_TIMER
,
0x40
);
}
if
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_02
)
{
dprintk
(
"Set MAC Reg C+CR Offset 0x82h = 0x01h
\n
"
);
RTL_W8
(
0x82
,
0x01
);
dprintk
(
"Set PHY Reg 0x0bh = 0x00h
\n
"
);
mdio_write
(
ioaddr
,
0x0b
,
0x0000
);
//w 0x0b 15 0 0
}
rtl8169_link_option
(
board_idx
,
&
autoneg
,
&
speed
,
&
duplex
);
rtl8169_set_speed
(
dev
,
autoneg
,
speed
,
duplex
);
if
((
RTL_R8
(
PHYstatus
)
&
TBI_Enable
)
&&
netif_msg_link
(
tp
))
printk
(
KERN_INFO
PFX
"%s: TBI auto-negotiating
\n
"
,
dev
->
name
);
}
static
int
rtl8169_ioctl
(
struct
net_device
*
dev
,
struct
ifreq
*
ifr
,
int
cmd
)
{
struct
rtl8169_private
*
tp
=
netdev_priv
(
dev
);
struct
mii_ioctl_data
*
data
=
if_mii
(
ifr
);
if
(
!
netif_running
(
dev
))
return
-
ENODEV
;
switch
(
cmd
)
{
case
SIOCGMIIPHY
:
data
->
phy_id
=
32
;
/* Internal PHY */
return
0
;
case
SIOCGMIIREG
:
data
->
val_out
=
mdio_read
(
tp
->
mmio_addr
,
data
->
reg_num
&
0x1f
);
return
0
;
case
SIOCSMIIREG
:
if
(
!
capable
(
CAP_NET_ADMIN
))
return
-
EPERM
;
mdio_write
(
tp
->
mmio_addr
,
data
->
reg_num
&
0x1f
,
data
->
val_in
);
return
0
;
}
return
-
EOPNOTSUPP
;
}
static
int
__devinit
rtl8169_init_board
(
struct
pci_dev
*
pdev
,
struct
net_device
**
dev_out
,
void
__iomem
**
ioaddr_out
)
rtl8169_init_one
(
struct
pci_dev
*
pdev
,
const
struct
pci_device_id
*
ent
)
{
void
__iomem
*
ioaddr
;
struct
net_device
*
dev
;
const
unsigned
int
region
=
rtl_cfg_info
[
ent
->
driver_data
].
region
;
struct
rtl8169_private
*
tp
;
int
rc
=
-
ENOMEM
,
i
,
acpi_idle_state
=
0
,
pm_cap
;
struct
net_device
*
dev
;
void
__iomem
*
ioaddr
;
unsigned
int
i
,
pm_cap
;
int
rc
;
assert
(
ioaddr_out
!=
NULL
);
if
(
netif_msg_drv
(
&
debug
))
{
printk
(
KERN_INFO
"%s Gigabit Ethernet driver %s loaded
\n
"
,
MODULENAME
,
RTL8169_VERSION
);
}
/* dev zeroed in alloc_etherdev */
dev
=
alloc_etherdev
(
sizeof
(
*
tp
));
if
(
dev
==
NULL
)
{
if
(
!
dev
)
{
if
(
netif_msg_drv
(
&
debug
))
dev_err
(
&
pdev
->
dev
,
"unable to alloc new ethernet
\n
"
);
goto
err_out
;
rc
=
-
ENOMEM
;
goto
out
;
}
SET_MODULE_OWNER
(
dev
);
...
...
@@ -1420,48 +1534,53 @@ rtl8169_init_board(struct pci_dev *pdev, struct net_device **dev_out,
if
(
rc
<
0
)
{
if
(
netif_msg_probe
(
tp
))
dev_err
(
&
pdev
->
dev
,
"enable failure
\n
"
);
goto
err_out_free_dev
;
goto
err_out_free_dev
_1
;
}
rc
=
pci_set_mwi
(
pdev
);
if
(
rc
<
0
)
goto
err_out_disable
;
goto
err_out_disable
_2
;
/* save power state before pci_enable_device overwrites it */
pm_cap
=
pci_find_capability
(
pdev
,
PCI_CAP_ID_PM
);
if
(
pm_cap
)
{
u16
pwr_command
;
u16
pwr_command
,
acpi_idle_state
;
pci_read_config_word
(
pdev
,
pm_cap
+
PCI_PM_CTRL
,
&
pwr_command
);
acpi_idle_state
=
pwr_command
&
PCI_PM_CTRL_STATE_MASK
;
}
else
{
if
(
netif_msg_probe
(
tp
))
if
(
netif_msg_probe
(
tp
))
{
dev_err
(
&
pdev
->
dev
,
"PowerManagement capability not found.
\n
"
);
}
}
/* make sure PCI base addr 1 is MMIO */
if
(
!
(
pci_resource_flags
(
pdev
,
1
)
&
IORESOURCE_MEM
))
{
if
(
netif_msg_probe
(
tp
))
if
(
!
(
pci_resource_flags
(
pdev
,
region
)
&
IORESOURCE_MEM
))
{
if
(
netif_msg_probe
(
tp
))
{
dev_err
(
&
pdev
->
dev
,
"region #1 not an MMIO resource, aborting
\n
"
);
"region #%d not an MMIO resource, aborting
\n
"
,
region
);
}
rc
=
-
ENODEV
;
goto
err_out_mwi
;
goto
err_out_mwi
_3
;
}
/* check for weird/broken PCI region reporting */
if
(
pci_resource_len
(
pdev
,
1
)
<
R8169_REGS_SIZE
)
{
if
(
netif_msg_probe
(
tp
))
if
(
pci_resource_len
(
pdev
,
region
)
<
R8169_REGS_SIZE
)
{
if
(
netif_msg_probe
(
tp
))
{
dev_err
(
&
pdev
->
dev
,
"Invalid PCI region size(s), aborting
\n
"
);
}
rc
=
-
ENODEV
;
goto
err_out_mwi
;
goto
err_out_mwi
_3
;
}
rc
=
pci_request_regions
(
pdev
,
MODULENAME
);
if
(
rc
<
0
)
{
if
(
netif_msg_probe
(
tp
))
dev_err
(
&
pdev
->
dev
,
"could not request regions.
\n
"
);
goto
err_out_mwi
;
goto
err_out_mwi
_3
;
}
tp
->
cp_cmd
=
PCIMulRW
|
RxChkSum
;
...
...
@@ -1473,22 +1592,23 @@ rtl8169_init_board(struct pci_dev *pdev, struct net_device **dev_out,
}
else
{
rc
=
pci_set_dma_mask
(
pdev
,
DMA_32BIT_MASK
);
if
(
rc
<
0
)
{
if
(
netif_msg_probe
(
tp
))
if
(
netif_msg_probe
(
tp
))
{
dev_err
(
&
pdev
->
dev
,
"DMA configuration failed.
\n
"
);
goto
err_out_free_res
;
}
goto
err_out_free_res_4
;
}
}
pci_set_master
(
pdev
);
/* ioremap MMIO region */
ioaddr
=
ioremap
(
pci_resource_start
(
pdev
,
1
),
R8169_REGS_SIZE
);
if
(
ioaddr
==
NULL
)
{
ioaddr
=
ioremap
(
pci_resource_start
(
pdev
,
region
),
R8169_REGS_SIZE
);
if
(
!
ioaddr
)
{
if
(
netif_msg_probe
(
tp
))
dev_err
(
&
pdev
->
dev
,
"cannot remap MMIO, aborting
\n
"
);
rc
=
-
EIO
;
goto
err_out_free_res
;
goto
err_out_free_res
_4
;
}
/* Unneeded ? Don't mess with Mrs. Murphy. */
...
...
@@ -1498,10 +1618,10 @@ rtl8169_init_board(struct pci_dev *pdev, struct net_device **dev_out,
RTL_W8
(
ChipCmd
,
CmdReset
);
/* Check that the chip has finished the reset. */
for
(
i
=
100
0
;
i
>
0
;
i
--
)
{
for
(
i
=
100
;
i
>
0
;
i
--
)
{
if
((
RTL_R8
(
ChipCmd
)
&
CmdReset
)
==
0
)
break
;
udelay
(
10
);
msleep_interruptible
(
1
);
}
/* Identify chip attached to board */
...
...
@@ -1531,56 +1651,6 @@ rtl8169_init_board(struct pci_dev *pdev, struct net_device **dev_out,
RTL_W8
(
Config5
,
RTL_R8
(
Config5
)
&
PMEStatus
);
RTL_W8
(
Cfg9346
,
Cfg9346_Lock
);
*
ioaddr_out
=
ioaddr
;
*
dev_out
=
dev
;
out:
return
rc
;
err_out_free_res:
pci_release_regions
(
pdev
);
err_out_mwi:
pci_clear_mwi
(
pdev
);
err_out_disable:
pci_disable_device
(
pdev
);
err_out_free_dev:
free_netdev
(
dev
);
err_out:
*
ioaddr_out
=
NULL
;
*
dev_out
=
NULL
;
goto
out
;
}
static
int
__devinit
rtl8169_init_one
(
struct
pci_dev
*
pdev
,
const
struct
pci_device_id
*
ent
)
{
struct
net_device
*
dev
=
NULL
;
struct
rtl8169_private
*
tp
;
void
__iomem
*
ioaddr
=
NULL
;
static
int
board_idx
=
-
1
;
u8
autoneg
,
duplex
;
u16
speed
;
int
i
,
rc
;
assert
(
pdev
!=
NULL
);
assert
(
ent
!=
NULL
);
board_idx
++
;
if
(
netif_msg_drv
(
&
debug
))
{
printk
(
KERN_INFO
"%s Gigabit Ethernet driver %s loaded
\n
"
,
MODULENAME
,
RTL8169_VERSION
);
}
rc
=
rtl8169_init_board
(
pdev
,
&
dev
,
&
ioaddr
);
if
(
rc
)
return
rc
;
tp
=
netdev_priv
(
dev
);
assert
(
ioaddr
!=
NULL
);
if
(
RTL_R8
(
PHYstatus
)
&
TBI_Enable
)
{
tp
->
set_speed
=
rtl8169_set_speed_tbi
;
tp
->
get_settings
=
rtl8169_gset_tbi
;
...
...
@@ -1588,13 +1658,15 @@ rtl8169_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
tp
->
phy_reset_pending
=
rtl8169_tbi_reset_pending
;
tp
->
link_ok
=
rtl8169_tbi_link_ok
;
tp
->
phy_1000_ctrl_reg
=
PHY_Cap_1000_Full
;
/* Implied by TBI */
tp
->
phy_1000_ctrl_reg
=
ADVERTISE_1000FULL
;
/* Implied by TBI */
}
else
{
tp
->
set_speed
=
rtl8169_set_speed_xmii
;
tp
->
get_settings
=
rtl8169_gset_xmii
;
tp
->
phy_reset_enable
=
rtl8169_xmii_reset_enable
;
tp
->
phy_reset_pending
=
rtl8169_xmii_reset_pending
;
tp
->
link_ok
=
rtl8169_xmii_link_ok
;
dev
->
do_ioctl
=
rtl8169_ioctl
;
}
/* Get MAC address. FIXME: read EEPROM */
...
...
@@ -1609,6 +1681,7 @@ rtl8169_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
dev
->
stop
=
rtl8169_close
;
dev
->
tx_timeout
=
rtl8169_tx_timeout
;
dev
->
set_multicast_list
=
rtl8169_set_rx_mode
;
dev
->
set_mac_address
=
rtl8169_set_mac_addr
;
dev
->
watchdog_timeo
=
RTL8169_TX_TIMEOUT
;
dev
->
irq
=
pdev
->
irq
;
dev
->
base_addr
=
(
unsigned
long
)
ioaddr
;
...
...
@@ -1632,19 +1705,13 @@ rtl8169_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
tp
->
intr_mask
=
0xffff
;
tp
->
pci_dev
=
pdev
;
tp
->
mmio_addr
=
ioaddr
;
tp
->
align
=
rtl_cfg_info
[
ent
->
driver_data
].
align
;
spin_lock_init
(
&
tp
->
lock
);
rc
=
register_netdev
(
dev
);
if
(
rc
)
{
rtl8169_release_board
(
pdev
,
dev
,
ioaddr
);
return
rc
;
}
if
(
netif_msg_probe
(
tp
))
{
printk
(
KERN_DEBUG
"%s: Identified chip type is '%s'.
\n
"
,
dev
->
name
,
rtl_chip_info
[
tp
->
chipset
].
name
);
}
if
(
rc
<
0
)
goto
err_out_unmap_5
;
pci_set_drvdata
(
pdev
,
dev
);
...
...
@@ -1653,38 +1720,29 @@ rtl8169_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
"%2.2x:%2.2x:%2.2x:%2.2x:%2.2x:%2.2x, "
"IRQ %d
\n
"
,
dev
->
name
,
rtl_chip_info
[
ent
->
driver_data
].
name
,
rtl_chip_info
[
tp
->
chipset
].
name
,
dev
->
base_addr
,
dev
->
dev_addr
[
0
],
dev
->
dev_addr
[
1
],
dev
->
dev_addr
[
2
],
dev
->
dev_addr
[
3
],
dev
->
dev_addr
[
4
],
dev
->
dev_addr
[
5
],
dev
->
irq
);
}
rtl8169_hw_phy_config
(
dev
);
dprintk
(
"Set MAC Reg C+CR Offset 0x82h = 0x01h
\n
"
);
RTL_W8
(
0x82
,
0x01
);
if
(
tp
->
mac_version
<
RTL_GIGA_MAC_VER_E
)
{
dprintk
(
"Set PCI Latency=0x40
\n
"
);
pci_write_config_byte
(
pdev
,
PCI_LATENCY_TIMER
,
0x40
);
}
if
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_D
)
{
dprintk
(
"Set MAC Reg C+CR Offset 0x82h = 0x01h
\n
"
);
RTL_W8
(
0x82
,
0x01
);
dprintk
(
"Set PHY Reg 0x0bh = 0x00h
\n
"
);
mdio_write
(
ioaddr
,
0x0b
,
0x0000
);
//w 0x0b 15 0 0
}
rtl8169_link_option
(
board_idx
,
&
autoneg
,
&
speed
,
&
duplex
);
rtl8169_set_speed
(
dev
,
autoneg
,
speed
,
duplex
);
rtl8169_init_phy
(
dev
,
tp
);
if
((
RTL_R8
(
PHYstatus
)
&
TBI_Enable
)
&&
netif_msg_link
(
tp
))
printk
(
KERN_INFO
PFX
"%s: TBI auto-negotiating
\n
"
,
dev
->
name
)
;
out:
return
rc
;
return
0
;
err_out_unmap_5:
iounmap
(
ioaddr
);
err_out_free_res_4:
pci_release_regions
(
pdev
);
err_out_mwi_3:
pci_clear_mwi
(
pdev
);
err_out_disable_2:
pci_disable_device
(
pdev
);
err_out_free_dev_1:
free_netdev
(
dev
);
goto
out
;
}
static
void
__devexit
...
...
@@ -1780,20 +1838,41 @@ rtl8169_hw_start(struct net_device *dev)
{
struct
rtl8169_private
*
tp
=
netdev_priv
(
dev
);
void
__iomem
*
ioaddr
=
tp
->
mmio_addr
;
struct
pci_dev
*
pdev
=
tp
->
pci_dev
;
u32
i
;
/* Soft reset the chip. */
RTL_W8
(
ChipCmd
,
CmdReset
);
/* Check that the chip has finished the reset. */
for
(
i
=
100
0
;
i
>
0
;
i
--
)
{
for
(
i
=
100
;
i
>
0
;
i
--
)
{
if
((
RTL_R8
(
ChipCmd
)
&
CmdReset
)
==
0
)
break
;
udelay
(
10
);
msleep_interruptible
(
1
);
}
if
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_13
)
{
pci_write_config_word
(
pdev
,
0x68
,
0x00
);
pci_write_config_word
(
pdev
,
0x69
,
0x08
);
}
/* Undocumented stuff. */
if
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_05
)
{
u16
cmd
;
/* Realtek's r1000_n.c driver uses '&& 0x01' here. Well... */
if
((
RTL_R8
(
Config2
)
&
0x07
)
&
0x01
)
RTL_W32
(
0x7c
,
0x0007ffff
);
RTL_W32
(
0x7c
,
0x0007ff00
);
pci_read_config_word
(
pdev
,
PCI_COMMAND
,
&
cmd
);
cmd
=
cmd
&
0xef
;
pci_write_config_word
(
pdev
,
PCI_COMMAND
,
cmd
);
}
RTL_W8
(
Cfg9346
,
Cfg9346_Unlock
);
RTL_W8
(
ChipCmd
,
CmdTxEnb
|
CmdRxEnb
);
RTL_W8
(
EarlyTxThres
,
EarlyTxThld
);
/* Low hurts. Let's disable the filtering. */
...
...
@@ -1805,32 +1884,40 @@ rtl8169_hw_start(struct net_device *dev)
RTL_W32
(
RxConfig
,
i
);
/* Set DMA burst size and Interframe Gap Time */
RTL_W32
(
TxConfig
,
(
TX_DMA_BURST
<<
TxDMAShift
)
|
(
InterFrameGap
<<
TxInterFrameGapShift
));
tp
->
cp_cmd
|=
RTL_R16
(
CPlusCmd
);
RTL_W16
(
CPlusCmd
,
tp
->
cp_cmd
);
RTL_W32
(
TxConfig
,
(
TX_DMA_BURST
<<
TxDMAShift
)
|
(
InterFrameGap
<<
TxInterFrameGapShift
));
if
((
tp
->
mac_version
==
RTL_GIGA_MAC_VER_D
)
||
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_E
))
{
tp
->
cp_cmd
|=
RTL_R16
(
CPlusCmd
)
|
PCIMulRW
;
if
((
tp
->
mac_version
==
RTL_GIGA_MAC_VER_02
)
||
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_03
))
{
dprintk
(
KERN_INFO
PFX
"Set MAC Reg C+CR Offset 0xE0. "
"Bit-3 and bit-14 MUST be 1
\n
"
);
tp
->
cp_cmd
|=
(
1
<<
14
)
|
PCIMulRW
;
RTL_W16
(
CPlusCmd
,
tp
->
cp_cmd
);
tp
->
cp_cmd
|=
(
1
<<
14
);
}
RTL_W16
(
CPlusCmd
,
tp
->
cp_cmd
);
/*
* Undocumented corner. Supposedly:
* (TxTimer << 12) | (TxPackets << 8) | (RxTimer << 4) | RxPackets
*/
RTL_W16
(
IntrMitigate
,
0x0000
);
RTL_W32
(
TxDescStartAddrLow
,
((
u64
)
tp
->
TxPhyAddr
&
DMA_32BIT_MASK
));
/*
* Magic spell: some iop3xx ARM board needs the TxDescAddrHigh
* register to be written before TxDescAddrLow to work.
* Switching from MMIO to I/O access fixes the issue as well.
*/
RTL_W32
(
TxDescStartAddrHigh
,
((
u64
)
tp
->
TxPhyAddr
>>
32
));
RTL_W32
(
RxDescAddrLow
,
((
u64
)
tp
->
R
xPhyAddr
&
DMA_32BIT_MASK
));
RTL_W32
(
TxDescStartAddrLow
,
((
u64
)
tp
->
T
xPhyAddr
&
DMA_32BIT_MASK
));
RTL_W32
(
RxDescAddrHigh
,
((
u64
)
tp
->
RxPhyAddr
>>
32
));
RTL_W32
(
RxDescAddrLow
,
((
u64
)
tp
->
RxPhyAddr
&
DMA_32BIT_MASK
));
RTL_W8
(
ChipCmd
,
CmdTxEnb
|
CmdRxEnb
);
RTL_W8
(
Cfg9346
,
Cfg9346_Lock
);
udelay
(
10
);
/* Initially a 10 us delay. Turned it into a PCI commit. - FR */
RTL_R8
(
IntrMask
);
RTL_W32
(
RxMissed
,
0
);
...
...
@@ -1842,6 +1929,8 @@ rtl8169_hw_start(struct net_device *dev)
/* Enable all known interrupts by setting the interrupt mask. */
RTL_W16
(
IntrMask
,
rtl8169_intr_mask
);
__rtl8169_set_mac_addr
(
dev
,
ioaddr
);
netif_start_queue
(
dev
);
}
...
...
@@ -1910,17 +1999,18 @@ static inline void rtl8169_map_to_asic(struct RxDesc *desc, dma_addr_t mapping,
}
static
int
rtl8169_alloc_rx_skb
(
struct
pci_dev
*
pdev
,
struct
sk_buff
**
sk_buff
,
struct
RxDesc
*
desc
,
int
rx_buf_sz
)
struct
RxDesc
*
desc
,
int
rx_buf_sz
,
unsigned
int
align
)
{
struct
sk_buff
*
skb
;
dma_addr_t
mapping
;
int
ret
=
0
;
skb
=
dev_alloc_skb
(
rx_buf_sz
+
NET_IP_ALIGN
);
skb
=
dev_alloc_skb
(
rx_buf_sz
+
align
);
if
(
!
skb
)
goto
err_out
;
skb_reserve
(
skb
,
NET_IP_ALIGN
);
skb_reserve
(
skb
,
align
);
*
sk_buff
=
skb
;
mapping
=
pci_map_single
(
pdev
,
skb
->
data
,
rx_buf_sz
,
...
...
@@ -1961,7 +2051,7 @@ static u32 rtl8169_rx_fill(struct rtl8169_private *tp, struct net_device *dev,
continue
;
ret
=
rtl8169_alloc_rx_skb
(
tp
->
pci_dev
,
tp
->
Rx_skbuff
+
i
,
tp
->
RxDescArray
+
i
,
tp
->
rx_buf_sz
);
tp
->
RxDescArray
+
i
,
tp
->
rx_buf_sz
,
tp
->
align
);
if
(
ret
<
0
)
break
;
}
...
...
@@ -2190,7 +2280,7 @@ static int rtl8169_start_xmit(struct sk_buff *skb, struct net_device *dev)
dma_addr_t
mapping
;
u32
status
,
len
;
u32
opts1
;
int
ret
=
0
;
int
ret
=
NETDEV_TX_OK
;
if
(
unlikely
(
TX_BUFFS_AVAIL
(
tp
)
<
skb_shinfo
(
skb
)
->
nr_frags
))
{
if
(
netif_msg_drv
(
tp
))
{
...
...
@@ -2255,7 +2345,7 @@ out:
err_stop:
netif_stop_queue
(
dev
);
ret
=
1
;
ret
=
NETDEV_TX_BUSY
;
err_update_stats:
tp
->
stats
.
tx_dropped
++
;
goto
out
;
...
...
@@ -2372,16 +2462,17 @@ static inline void rtl8169_rx_csum(struct sk_buff *skb, struct RxDesc *desc)
}
static
inline
int
rtl8169_try_rx_copy
(
struct
sk_buff
**
sk_buff
,
int
pkt_size
,
struct
RxDesc
*
desc
,
int
rx_buf_sz
)
struct
RxDesc
*
desc
,
int
rx_buf_sz
,
unsigned
int
align
)
{
int
ret
=
-
1
;
if
(
pkt_size
<
rx_copybreak
)
{
struct
sk_buff
*
skb
;
skb
=
dev_alloc_skb
(
pkt_size
+
NET_IP_ALIGN
);
skb
=
dev_alloc_skb
(
pkt_size
+
align
);
if
(
skb
)
{
skb_reserve
(
skb
,
NET_IP_ALIGN
);
skb_reserve
(
skb
,
align
);
eth_copy_and_sum
(
skb
,
sk_buff
[
0
]
->
data
,
pkt_size
,
0
);
*
sk_buff
=
skb
;
rtl8169_mark_to_asic
(
desc
,
rx_buf_sz
);
...
...
@@ -2427,6 +2518,10 @@ rtl8169_rx_interrupt(struct net_device *dev, struct rtl8169_private *tp,
tp
->
stats
.
rx_length_errors
++
;
if
(
status
&
RxCRC
)
tp
->
stats
.
rx_crc_errors
++
;
if
(
status
&
RxFOVF
)
{
rtl8169_schedule_work
(
dev
,
rtl8169_reset_task
);
tp
->
stats
.
rx_fifo_errors
++
;
}
rtl8169_mark_to_asic
(
desc
,
tp
->
rx_buf_sz
);
}
else
{
struct
sk_buff
*
skb
=
tp
->
Rx_skbuff
[
entry
];
...
...
@@ -2453,7 +2548,7 @@ rtl8169_rx_interrupt(struct net_device *dev, struct rtl8169_private *tp,
PCI_DMA_FROMDEVICE
);
if
(
rtl8169_try_rx_copy
(
&
skb
,
pkt_size
,
desc
,
tp
->
rx_buf_sz
))
{
tp
->
rx_buf_sz
,
tp
->
align
))
{
pci_action
=
pci_unmap_single
;
tp
->
Rx_skbuff
[
entry
]
=
NULL
;
}
...
...
@@ -2716,6 +2811,15 @@ rtl8169_set_rx_mode(struct net_device *dev)
tmp
=
rtl8169_rx_config
|
rx_mode
|
(
RTL_R32
(
RxConfig
)
&
rtl_chip_info
[
tp
->
chipset
].
RxConfigMask
);
if
((
tp
->
mac_version
==
RTL_GIGA_MAC_VER_11
)
||
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_12
)
||
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_13
)
||
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_14
)
||
(
tp
->
mac_version
==
RTL_GIGA_MAC_VER_15
))
{
mc_filter
[
0
]
=
0xffffffff
;
mc_filter
[
1
]
=
0xffffffff
;
}
RTL_W32
(
RxConfig
,
tmp
);
RTL_W32
(
MAR0
+
0
,
mc_filter
[
0
]);
RTL_W32
(
MAR0
+
4
,
mc_filter
[
1
]);
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment