Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
Linux-御风守护者
linux
提交
54c852a2
L
linux
项目概览
Linux-御风守护者
/
linux
与 Fork 源项目一致
从无法访问的项目Fork
通知
1
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
L
linux
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
54c852a2
编写于
5月 06, 2008
作者:
J
Jeff Garzik
提交者:
Jeff Garzik
5月 06, 2008
浏览文件
操作
浏览文件
下载
差异文件
Merge branch 'for-2.6.26' of
git://git.farnsworth.org/dale/linux-2.6-mv643xx_eth
into upstream
上级
7ab267d4
ce4e2e45
变更
6
显示空白变更内容
内联
并排
Showing
6 changed file
with
148 addition
and
39 deletion
+148
-39
arch/arm/mach-orion5x/common.c
arch/arm/mach-orion5x/common.c
+2
-0
arch/powerpc/platforms/chrp/pegasos_eth.c
arch/powerpc/platforms/chrp/pegasos_eth.c
+4
-0
arch/powerpc/sysdev/mv64x60_dev.c
arch/powerpc/sysdev/mv64x60_dev.c
+2
-0
arch/ppc/syslib/mv64x60.c
arch/ppc/syslib/mv64x60.c
+3
-0
drivers/net/mv643xx_eth.c
drivers/net/mv643xx_eth.c
+123
-37
include/linux/mv643xx_eth.h
include/linux/mv643xx_eth.h
+14
-2
未找到文件。
arch/arm/mach-orion5x/common.c
浏览文件 @
54c852a2
...
...
@@ -223,7 +223,9 @@ static struct platform_device orion5x_eth = {
void
__init
orion5x_eth_init
(
struct
mv643xx_eth_platform_data
*
eth_data
)
{
eth_data
->
shared
=
&
orion5x_eth_shared
;
orion5x_eth
.
dev
.
platform_data
=
eth_data
;
platform_device_register
(
&
orion5x_eth_shared
);
platform_device_register
(
&
orion5x_eth
);
}
...
...
arch/powerpc/platforms/chrp/pegasos_eth.c
浏览文件 @
54c852a2
...
...
@@ -58,7 +58,9 @@ static struct resource mv643xx_eth0_resources[] = {
static
struct
mv643xx_eth_platform_data
eth0_pd
=
{
.
shared
=
&
mv643xx_eth_shared_device
,
.
port_number
=
0
,
.
tx_sram_addr
=
PEGASOS2_SRAM_BASE_ETH0
,
.
tx_sram_size
=
PEGASOS2_SRAM_TXRING_SIZE
,
.
tx_queue_size
=
PEGASOS2_SRAM_TXRING_SIZE
/
16
,
...
...
@@ -88,7 +90,9 @@ static struct resource mv643xx_eth1_resources[] = {
};
static
struct
mv643xx_eth_platform_data
eth1_pd
=
{
.
shared
=
&
mv643xx_eth_shared_device
,
.
port_number
=
1
,
.
tx_sram_addr
=
PEGASOS2_SRAM_BASE_ETH1
,
.
tx_sram_size
=
PEGASOS2_SRAM_TXRING_SIZE
,
.
tx_queue_size
=
PEGASOS2_SRAM_TXRING_SIZE
/
16
,
...
...
arch/powerpc/sysdev/mv64x60_dev.c
浏览文件 @
54c852a2
...
...
@@ -239,6 +239,8 @@ static int __init mv64x60_eth_device_setup(struct device_node *np, int id,
memset
(
&
pdata
,
0
,
sizeof
(
pdata
));
pdata
.
shared
=
shared_pdev
;
prop
=
of_get_property
(
np
,
"reg"
,
NULL
);
if
(
!
prop
)
return
-
ENODEV
;
...
...
arch/ppc/syslib/mv64x60.c
浏览文件 @
54c852a2
...
...
@@ -341,6 +341,7 @@ static struct resource mv64x60_eth0_resources[] = {
};
static
struct
mv643xx_eth_platform_data
eth0_pd
=
{
.
shared
=
&
mv64x60_eth_shared_device
;
.
port_number
=
0
,
};
...
...
@@ -366,6 +367,7 @@ static struct resource mv64x60_eth1_resources[] = {
};
static
struct
mv643xx_eth_platform_data
eth1_pd
=
{
.
shared
=
&
mv64x60_eth_shared_device
;
.
port_number
=
1
,
};
...
...
@@ -391,6 +393,7 @@ static struct resource mv64x60_eth2_resources[] = {
};
static
struct
mv643xx_eth_platform_data
eth2_pd
=
{
.
shared
=
&
mv64x60_eth_shared_device
;
.
port_number
=
2
,
};
...
...
drivers/net/mv643xx_eth.c
浏览文件 @
54c852a2
...
...
@@ -91,6 +91,11 @@
*/
#define PHY_ADDR_REG 0x0000
#define SMI_REG 0x0004
#define WINDOW_BASE(i) (0x0200 + ((i) << 3))
#define WINDOW_SIZE(i) (0x0204 + ((i) << 3))
#define WINDOW_REMAP_HIGH(i) (0x0280 + ((i) << 2))
#define WINDOW_BAR_ENABLE 0x0290
#define WINDOW_PROTECT(i) (0x0294 + ((i) << 4))
/*
* Per-port registers.
...
...
@@ -507,9 +512,23 @@ struct mv643xx_mib_counters {
u32
late_collision
;
};
struct
mv643xx_shared_private
{
void
__iomem
*
eth_base
;
/* used to protect SMI_REG, which is shared across ports */
spinlock_t
phy_lock
;
u32
win_protect
;
unsigned
int
t_clk
;
};
struct
mv643xx_private
{
struct
mv643xx_shared_private
*
shared
;
int
port_num
;
/* User Ethernet port number */
struct
mv643xx_shared_private
*
shared_smi
;
u32
rx_sram_addr
;
/* Base address of rx sram area */
u32
rx_sram_size
;
/* Size of rx sram area */
u32
tx_sram_addr
;
/* Base address of tx sram area */
...
...
@@ -614,19 +633,14 @@ static const struct ethtool_ops mv643xx_ethtool_ops;
static
char
mv643xx_driver_name
[]
=
"mv643xx_eth"
;
static
char
mv643xx_driver_version
[]
=
"1.0"
;
static
void
__iomem
*
mv643xx_eth_base
;
/* used to protect SMI_REG, which is shared across ports */
static
DEFINE_SPINLOCK
(
mv643xx_eth_phy_lock
);
static
inline
u32
rdl
(
struct
mv643xx_private
*
mp
,
int
offset
)
{
return
readl
(
m
v643xx_
eth_base
+
offset
);
return
readl
(
m
p
->
shared
->
eth_base
+
offset
);
}
static
inline
void
wrl
(
struct
mv643xx_private
*
mp
,
int
offset
,
u32
data
)
{
writel
(
data
,
m
v643xx_
eth_base
+
offset
);
writel
(
data
,
m
p
->
shared
->
eth_base
+
offset
);
}
/*
...
...
@@ -1119,7 +1133,6 @@ static irqreturn_t mv643xx_eth_int_handler(int irq, void *dev_id)
*
* INPUT:
* struct mv643xx_private *mp Ethernet port
* unsigned int t_clk t_clk of the MV-643xx chip in HZ units
* unsigned int delay Delay in usec
*
* OUTPUT:
...
...
@@ -1130,10 +1143,10 @@ static irqreturn_t mv643xx_eth_int_handler(int irq, void *dev_id)
*
*/
static
unsigned
int
eth_port_set_rx_coal
(
struct
mv643xx_private
*
mp
,
unsigned
int
t_clk
,
unsigned
int
delay
)
unsigned
int
delay
)
{
unsigned
int
port_num
=
mp
->
port_num
;
unsigned
int
coal
=
((
t_clk
/
1000000
)
*
delay
)
/
64
;
unsigned
int
coal
=
((
mp
->
shared
->
t_clk
/
1000000
)
*
delay
)
/
64
;
/* Set RX Coalescing mechanism */
wrl
(
mp
,
SDMA_CONFIG_REG
(
port_num
),
...
...
@@ -1158,7 +1171,6 @@ static unsigned int eth_port_set_rx_coal(struct mv643xx_private *mp,
*
* INPUT:
* struct mv643xx_private *mp Ethernet port
* unsigned int t_clk t_clk of the MV-643xx chip in HZ units
* unsigned int delay Delay in uSeconds
*
* OUTPUT:
...
...
@@ -1169,9 +1181,9 @@ static unsigned int eth_port_set_rx_coal(struct mv643xx_private *mp,
*
*/
static
unsigned
int
eth_port_set_tx_coal
(
struct
mv643xx_private
*
mp
,
unsigned
int
t_clk
,
unsigned
int
delay
)
unsigned
int
delay
)
{
unsigned
int
coal
=
((
t_clk
/
1000000
)
*
delay
)
/
64
;
unsigned
int
coal
=
((
mp
->
shared
->
t_clk
/
1000000
)
*
delay
)
/
64
;
/* Set TX Coalescing mechanism */
wrl
(
mp
,
TX_FIFO_URGENT_THRESHOLD_REG
(
mp
->
port_num
),
coal
<<
4
);
...
...
@@ -1413,11 +1425,11 @@ static int mv643xx_eth_open(struct net_device *dev)
#ifdef MV643XX_COAL
mp
->
rx_int_coal
=
eth_port_set_rx_coal
(
mp
,
133000000
,
MV643XX_RX_COAL
);
eth_port_set_rx_coal
(
mp
,
MV643XX_RX_COAL
);
#endif
mp
->
tx_int_coal
=
eth_port_set_tx_coal
(
mp
,
133000000
,
MV643XX_TX_COAL
);
eth_port_set_tx_coal
(
mp
,
MV643XX_TX_COAL
);
/* Unmask phy and link status changes interrupts */
wrl
(
mp
,
INTERRUPT_EXTEND_MASK_REG
(
port_num
),
ETH_INT_UNMASK_ALL_EXT
);
...
...
@@ -1827,6 +1839,11 @@ static int mv643xx_eth_probe(struct platform_device *pdev)
return
-
ENODEV
;
}
if
(
pd
->
shared
==
NULL
)
{
printk
(
KERN_ERR
"No mv643xx_eth_platform_data->shared
\n
"
);
return
-
ENODEV
;
}
dev
=
alloc_etherdev
(
sizeof
(
struct
mv643xx_private
));
if
(
!
dev
)
return
-
ENOMEM
;
...
...
@@ -1877,8 +1894,16 @@ static int mv643xx_eth_probe(struct platform_device *pdev)
spin_lock_init
(
&
mp
->
lock
);
mp
->
shared
=
platform_get_drvdata
(
pd
->
shared
);
port_num
=
mp
->
port_num
=
pd
->
port_number
;
if
(
mp
->
shared
->
win_protect
)
wrl
(
mp
,
WINDOW_PROTECT
(
port_num
),
mp
->
shared
->
win_protect
);
mp
->
shared_smi
=
mp
->
shared
;
if
(
pd
->
shared_smi
!=
NULL
)
mp
->
shared_smi
=
platform_get_drvdata
(
pd
->
shared_smi
);
/* set default config values */
eth_port_uc_addr_get
(
mp
,
dev
->
dev_addr
);
mp
->
rx_ring_size
=
PORT_DEFAULT_RECEIVE_QUEUE_SIZE
;
...
...
@@ -1983,30 +2008,91 @@ static int mv643xx_eth_remove(struct platform_device *pdev)
return
0
;
}
static
void
mv643xx_eth_conf_mbus_windows
(
struct
mv643xx_shared_private
*
msp
,
struct
mbus_dram_target_info
*
dram
)
{
void
__iomem
*
base
=
msp
->
eth_base
;
u32
win_enable
;
u32
win_protect
;
int
i
;
for
(
i
=
0
;
i
<
6
;
i
++
)
{
writel
(
0
,
base
+
WINDOW_BASE
(
i
));
writel
(
0
,
base
+
WINDOW_SIZE
(
i
));
if
(
i
<
4
)
writel
(
0
,
base
+
WINDOW_REMAP_HIGH
(
i
));
}
win_enable
=
0x3f
;
win_protect
=
0
;
for
(
i
=
0
;
i
<
dram
->
num_cs
;
i
++
)
{
struct
mbus_dram_window
*
cs
=
dram
->
cs
+
i
;
writel
((
cs
->
base
&
0xffff0000
)
|
(
cs
->
mbus_attr
<<
8
)
|
dram
->
mbus_dram_target_id
,
base
+
WINDOW_BASE
(
i
));
writel
((
cs
->
size
-
1
)
&
0xffff0000
,
base
+
WINDOW_SIZE
(
i
));
win_enable
&=
~
(
1
<<
i
);
win_protect
|=
3
<<
(
2
*
i
);
}
writel
(
win_enable
,
base
+
WINDOW_BAR_ENABLE
);
msp
->
win_protect
=
win_protect
;
}
static
int
mv643xx_eth_shared_probe
(
struct
platform_device
*
pdev
)
{
static
int
mv643xx_version_printed
=
0
;
struct
mv643xx_eth_shared_platform_data
*
pd
=
pdev
->
dev
.
platform_data
;
struct
mv643xx_shared_private
*
msp
;
struct
resource
*
res
;
int
ret
;
if
(
!
mv643xx_version_printed
++
)
printk
(
KERN_NOTICE
"MV-643xx 10/100/1000 Ethernet Driver
\n
"
);
ret
=
-
EINVAL
;
res
=
platform_get_resource
(
pdev
,
IORESOURCE_MEM
,
0
);
if
(
res
==
NULL
)
return
-
ENODEV
;
goto
out
;
mv643xx_eth_base
=
ioremap
(
res
->
start
,
res
->
end
-
res
->
start
+
1
);
if
(
mv643xx_eth_base
==
NULL
)
return
-
ENOMEM
;
ret
=
-
ENOMEM
;
msp
=
kmalloc
(
sizeof
(
*
msp
),
GFP_KERNEL
);
if
(
msp
==
NULL
)
goto
out
;
memset
(
msp
,
0
,
sizeof
(
*
msp
));
msp
->
eth_base
=
ioremap
(
res
->
start
,
res
->
end
-
res
->
start
+
1
);
if
(
msp
->
eth_base
==
NULL
)
goto
out_free
;
spin_lock_init
(
&
msp
->
phy_lock
);
msp
->
t_clk
=
(
pd
!=
NULL
&&
pd
->
t_clk
!=
0
)
?
pd
->
t_clk
:
133000000
;
platform_set_drvdata
(
pdev
,
msp
);
/*
* (Re-)program MBUS remapping windows if we are asked to.
*/
if
(
pd
!=
NULL
&&
pd
->
dram
!=
NULL
)
mv643xx_eth_conf_mbus_windows
(
msp
,
pd
->
dram
);
return
0
;
out_free:
kfree
(
msp
);
out:
return
ret
;
}
static
int
mv643xx_eth_shared_remove
(
struct
platform_device
*
pdev
)
{
iounmap
(
mv643xx_eth_base
);
mv643xx_eth_base
=
NULL
;
struct
mv643xx_shared_private
*
msp
=
platform_get_drvdata
(
pdev
);
iounmap
(
msp
->
eth_base
);
kfree
(
msp
);
return
0
;
}
...
...
@@ -2906,15 +2992,16 @@ static void eth_port_reset(struct mv643xx_private *mp)
static
void
eth_port_read_smi_reg
(
struct
mv643xx_private
*
mp
,
unsigned
int
phy_reg
,
unsigned
int
*
value
)
{
void
__iomem
*
smi_reg
=
mp
->
shared_smi
->
eth_base
+
SMI_REG
;
int
phy_addr
=
ethernet_phy_get
(
mp
);
unsigned
long
flags
;
int
i
;
/* the SMI register is a shared resource */
spin_lock_irqsave
(
&
m
v643xx_eth_
phy_lock
,
flags
);
spin_lock_irqsave
(
&
m
p
->
shared_smi
->
phy_lock
,
flags
);
/* wait for the SMI register to become available */
for
(
i
=
0
;
r
dl
(
mp
,
SMI_REG
)
&
ETH_SMI_BUSY
;
i
++
)
{
for
(
i
=
0
;
r
eadl
(
smi_reg
)
&
ETH_SMI_BUSY
;
i
++
)
{
if
(
i
==
PHY_WAIT_ITERATIONS
)
{
printk
(
"%s: PHY busy timeout
\n
"
,
mp
->
dev
->
name
);
goto
out
;
...
...
@@ -2922,11 +3009,11 @@ static void eth_port_read_smi_reg(struct mv643xx_private *mp,
udelay
(
PHY_WAIT_MICRO_SECONDS
);
}
wr
l
(
mp
,
SMI_REG
,
(
phy_addr
<<
16
)
|
(
phy_reg
<<
21
)
|
ETH_SMI_OPCODE_READ
);
wr
itel
((
phy_addr
<<
16
)
|
(
phy_reg
<<
21
)
|
ETH_SMI_OPCODE_READ
,
smi_reg
);
/* now wait for the data to be valid */
for
(
i
=
0
;
!
(
r
dl
(
mp
,
SMI_REG
)
&
ETH_SMI_READ_VALID
);
i
++
)
{
for
(
i
=
0
;
!
(
r
eadl
(
smi_reg
)
&
ETH_SMI_READ_VALID
);
i
++
)
{
if
(
i
==
PHY_WAIT_ITERATIONS
)
{
printk
(
"%s: PHY read timeout
\n
"
,
mp
->
dev
->
name
);
goto
out
;
...
...
@@ -2934,9 +3021,9 @@ static void eth_port_read_smi_reg(struct mv643xx_private *mp,
udelay
(
PHY_WAIT_MICRO_SECONDS
);
}
*
value
=
r
dl
(
mp
,
SMI_REG
)
&
0xffff
;
*
value
=
r
eadl
(
smi_reg
)
&
0xffff
;
out:
spin_unlock_irqrestore
(
&
m
v643xx_eth_
phy_lock
,
flags
);
spin_unlock_irqrestore
(
&
m
p
->
shared_smi
->
phy_lock
,
flags
);
}
/*
...
...
@@ -2962,17 +3049,16 @@ static void eth_port_read_smi_reg(struct mv643xx_private *mp,
static
void
eth_port_write_smi_reg
(
struct
mv643xx_private
*
mp
,
unsigned
int
phy_reg
,
unsigned
int
value
)
{
int
phy_addr
;
int
i
;
void
__iomem
*
smi_reg
=
mp
->
shared_smi
->
eth_base
+
SMI_REG
;
int
phy_addr
=
ethernet_phy_get
(
mp
)
;
unsigned
long
flags
;
phy_addr
=
ethernet_phy_get
(
mp
);
int
i
;
/* the SMI register is a shared resource */
spin_lock_irqsave
(
&
m
v643xx_eth_
phy_lock
,
flags
);
spin_lock_irqsave
(
&
m
p
->
shared_smi
->
phy_lock
,
flags
);
/* wait for the SMI register to become available */
for
(
i
=
0
;
r
dl
(
mp
,
SMI_REG
)
&
ETH_SMI_BUSY
;
i
++
)
{
for
(
i
=
0
;
r
eadl
(
smi_reg
)
&
ETH_SMI_BUSY
;
i
++
)
{
if
(
i
==
PHY_WAIT_ITERATIONS
)
{
printk
(
"%s: PHY busy timeout
\n
"
,
mp
->
dev
->
name
);
goto
out
;
...
...
@@ -2980,10 +3066,10 @@ static void eth_port_write_smi_reg(struct mv643xx_private *mp,
udelay
(
PHY_WAIT_MICRO_SECONDS
);
}
wr
l
(
mp
,
SMI_REG
,
(
phy_addr
<<
16
)
|
(
phy_reg
<<
21
)
|
ETH_SMI_OPCODE_WRITE
|
(
value
&
0xffff
)
);
wr
itel
(
(
phy_addr
<<
16
)
|
(
phy_reg
<<
21
)
|
ETH_SMI_OPCODE_WRITE
|
(
value
&
0xffff
),
smi_reg
);
out:
spin_unlock_irqrestore
(
&
m
v643xx_eth_
phy_lock
,
flags
);
spin_unlock_irqrestore
(
&
m
p
->
shared_smi
->
phy_lock
,
flags
);
}
/*
...
...
include/linux/mv643xx_eth.h
浏览文件 @
54c852a2
/*
* MV-643XX ethernet platform device data definition file.
*/
#ifndef __LINUX_MV643XX_ETH_H
#define __LINUX_MV643XX_ETH_H
#define MV643XX_ETH_SHARED_NAME "mv643xx_eth_shared"
#define MV643XX_ETH_NAME "mv643xx_eth"
#include <linux/mbus.h>
#define MV643XX_ETH_SHARED_NAME "mv643xx_eth"
#define MV643XX_ETH_NAME "mv643xx_eth_port"
#define MV643XX_ETH_SHARED_REGS 0x2000
#define MV643XX_ETH_SHARED_REGS_SIZE 0x2000
#define MV643XX_ETH_BAR_4 0x2220
#define MV643XX_ETH_SIZE_REG_4 0x2224
#define MV643XX_ETH_BASE_ADDR_ENABLE_REG 0x2290
struct
mv643xx_eth_shared_platform_data
{
struct
mbus_dram_target_info
*
dram
;
unsigned
int
t_clk
;
};
struct
mv643xx_eth_platform_data
{
struct
platform_device
*
shared
;
int
port_number
;
struct
platform_device
*
shared_smi
;
u16
force_phy_addr
;
/* force override if phy_addr == 0 */
u16
phy_addr
;
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录