Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
L
linux
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
Kirill Smelkov
linux
Commits
38171d07
Commit
38171d07
authored
Mar 14, 2002
by
Jes Sorensen
Committed by
Jeff Garzik
Mar 14, 2002
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
acenic gige net driver fixes:
* fix Tigon I support * fix memory leak
parent
6f005af3
Changes
2
Show whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
94 additions
and
44 deletions
+94
-44
drivers/net/acenic.c
drivers/net/acenic.c
+81
-33
drivers/net/acenic.h
drivers/net/acenic.h
+13
-11
No files found.
drivers/net/acenic.c
View file @
38171d07
...
...
@@ -84,8 +84,10 @@
#ifdef CONFIG_ACENIC_OMIT_TIGON_I
#define ACE_IS_TIGON_I(ap) 0
#define ACE_TX_RING_ENTRIES(ap) MAX_TX_RING_ENTRIES
#else
#define ACE_IS_TIGON_I(ap) (ap->version == 1)
#define ACE_TX_RING_ENTRIES(ap) ap->tx_ring_entries
#endif
#ifndef PCI_VENDOR_ID_ALTEON
...
...
@@ -554,7 +556,7 @@ static int tx_ratio[ACE_MAX_MOD_PARMS];
static
int
dis_pci_mem_inval
[
ACE_MAX_MOD_PARMS
]
=
{
1
,
1
,
1
,
1
,
1
,
1
,
1
,
1
};
static
char
version
[]
__initdata
=
"acenic.c: v0.8
7
03/14/2002 Jes Sorensen, linux-acenic@SunSITE.dk
\n
"
"acenic.c: v0.8
8
03/14/2002 Jes Sorensen, linux-acenic@SunSITE.dk
\n
"
" http://home.cern.ch/~jes/gige/acenic.html
\n
"
;
static
struct
net_device
*
root_dev
;
...
...
@@ -960,6 +962,13 @@ static void ace_free_descriptors(struct net_device *dev)
ap
->
evt_ring_dma
);
ap
->
evt_ring
=
NULL
;
}
if
(
ap
->
tx_ring
!=
NULL
&&
!
ACE_IS_TIGON_I
(
ap
))
{
size
=
(
sizeof
(
struct
tx_desc
)
*
MAX_TX_RING_ENTRIES
);
pci_free_consistent
(
ap
->
pdev
,
size
,
ap
->
tx_ring
,
ap
->
tx_ring_dma
);
}
ap
->
tx_ring
=
NULL
;
if
(
ap
->
evt_prd
!=
NULL
)
{
pci_free_consistent
(
ap
->
pdev
,
sizeof
(
u32
),
(
void
*
)
ap
->
evt_prd
,
ap
->
evt_prd_dma
);
...
...
@@ -1006,12 +1015,19 @@ static int ace_allocate_descriptors(struct net_device *dev)
if
(
ap
->
evt_ring
==
NULL
)
goto
fail
;
size
=
(
sizeof
(
struct
tx_desc
)
*
TX_RING_ENTRIES
);
/*
* Only allocate a host TX ring for the Tigon II, the Tigon I
* has to use PCI registers for this ;-(
*/
if
(
!
ACE_IS_TIGON_I
(
ap
))
{
size
=
(
sizeof
(
struct
tx_desc
)
*
MAX_TX_RING_ENTRIES
);
ap
->
tx_ring
=
pci_alloc_consistent
(
ap
->
pdev
,
size
,
&
ap
->
tx_ring_dma
);
ap
->
tx_ring
=
pci_alloc_consistent
(
ap
->
pdev
,
size
,
&
ap
->
tx_ring_dma
);
if
(
ap
->
tx_ring
==
NULL
)
goto
fail
;
}
ap
->
evt_prd
=
pci_alloc_consistent
(
ap
->
pdev
,
sizeof
(
u32
),
&
ap
->
evt_prd_dma
);
...
...
@@ -1145,6 +1161,7 @@ static int __init ace_init(struct net_device *dev)
tigonFwReleaseFix
);
writel
(
0
,
&
regs
->
LocalCtrl
);
ap
->
version
=
1
;
ap
->
tx_ring_entries
=
TIGON_I_TX_RING_ENTRIES
;
break
;
#endif
case
6
:
...
...
@@ -1160,6 +1177,7 @@ static int __init ace_init(struct net_device *dev)
writel
(
SRAM_BANK_512K
,
&
regs
->
LocalCtrl
);
writel
(
SYNC_SRAM_TIMING
,
&
regs
->
MiscCfg
);
ap
->
version
=
2
;
ap
->
tx_ring_entries
=
MAX_TX_RING_ENTRIES
;
break
;
default:
printk
(
KERN_WARNING
" Unsupported Tigon version detected "
...
...
@@ -1390,7 +1408,7 @@ static int __init ace_init(struct net_device *dev)
#ifdef INDEX_DEBUG
spin_lock_init
(
&
ap
->
debug_lock
);
ap
->
last_tx
=
TX_RING_ENTRIES
-
1
;
ap
->
last_tx
=
ACE_TX_RING_ENTRIES
(
ap
)
-
1
;
ap
->
last_std_rx
=
0
;
ap
->
last_mini_rx
=
0
;
#endif
...
...
@@ -1498,12 +1516,30 @@ static int __init ace_init(struct net_device *dev)
*
(
ap
->
rx_ret_prd
)
=
0
;
writel
(
TX_RING_BASE
,
&
regs
->
WinBase
);
memset
(
ap
->
tx_ring
,
0
,
TX_RING_ENTRIES
*
sizeof
(
struct
tx_desc
));
if
(
ACE_IS_TIGON_I
(
ap
))
{
ap
->
tx_ring
=
(
struct
tx_desc
*
)
regs
->
Window
;
for
(
i
=
0
;
i
<
(
TIGON_I_TX_RING_ENTRIES
*
sizeof
(
struct
tx_desc
)
/
4
);
i
++
)
{
writel
(
0
,
(
unsigned
long
)
ap
->
tx_ring
+
i
*
4
);
}
set_aceaddr
(
&
info
->
tx_ctrl
.
rngptr
,
TX_RING_BASE
);
}
else
{
memset
(
ap
->
tx_ring
,
0
,
MAX_TX_RING_ENTRIES
*
sizeof
(
struct
tx_desc
));
set_aceaddr
(
&
info
->
tx_ctrl
.
rngptr
,
ap
->
tx_ring_dma
);
}
info
->
tx_ctrl
.
max_len
=
ACE_TX_RING_ENTRIES
(
ap
);
tmp
=
RCB_FLG_TCP_UDP_SUM
|
RCB_FLG_NO_PSEUDO_HDR
;
info
->
tx_ctrl
.
max_len
=
TX_RING_ENTRIES
;
tmp
=
RCB_FLG_TCP_UDP_SUM
|
RCB_FLG_NO_PSEUDO_HDR
|
RCB_FLG_TX_HOST_RING
;
/*
* The Tigon I does not like having the TX ring in host memory ;-(
*/
if
(
!
ACE_IS_TIGON_I
(
ap
))
tmp
|=
RCB_FLG_TX_HOST_RING
;
#if TX_COAL_INTS_ONLY
tmp
|=
RCB_FLG_COAL_INT_ONLY
;
#endif
...
...
@@ -2264,7 +2300,7 @@ static inline void ace_tx_int(struct net_device *dev,
info
->
skb
=
NULL
;
}
idx
=
(
idx
+
1
)
%
TX_RING_ENTRIES
;
idx
=
(
idx
+
1
)
%
ACE_TX_RING_ENTRIES
(
ap
)
;
}
while
(
idx
!=
txcsm
);
if
(
netif_queue_stopped
(
dev
))
...
...
@@ -2357,7 +2393,7 @@ static void ace_interrupt(int irq, void *dev_id, struct pt_regs *ptregs)
* update releases enough of space, otherwise we just
* wait for device to make more work.
*/
if
(
!
tx_ring_full
(
txcsm
,
ap
->
tx_prd
))
if
(
!
tx_ring_full
(
ap
,
txcsm
,
ap
->
tx_prd
))
ace_tx_int
(
dev
,
txcsm
,
idx
);
}
...
...
@@ -2531,7 +2567,7 @@ static int ace_close(struct net_device *dev)
save_flags
(
flags
);
cli
();
for
(
i
=
0
;
i
<
TX_RING_ENTRIES
;
i
++
)
{
for
(
i
=
0
;
i
<
ACE_TX_RING_ENTRIES
(
ap
)
;
i
++
)
{
struct
sk_buff
*
skb
;
dma_addr_t
mapping
;
struct
tx_ring_info
*
info
;
...
...
@@ -2541,7 +2577,13 @@ static int ace_close(struct net_device *dev)
mapping
=
pci_unmap_addr
(
info
,
mapping
);
if
(
mapping
)
{
memset
(
ap
->
tx_ring
+
i
,
0
,
sizeof
(
struct
tx_desc
));
if
(
ACE_IS_TIGON_I
(
ap
))
{
writel
(
0
,
&
ap
->
tx_ring
[
i
].
addr
.
addrhi
);
writel
(
0
,
&
ap
->
tx_ring
[
i
].
addr
.
addrlo
);
writel
(
0
,
&
ap
->
tx_ring
[
i
].
flagsize
);
}
else
memset
(
ap
->
tx_ring
+
i
,
0
,
sizeof
(
struct
tx_desc
));
pci_unmap_page
(
ap
->
pdev
,
mapping
,
pci_unmap_len
(
info
,
maplen
),
PCI_DMA_TODEVICE
);
...
...
@@ -2587,15 +2629,21 @@ ace_map_tx_skb(struct ace_private *ap, struct sk_buff *skb,
static
inline
void
ace_load_tx_bd
(
struct
tx_desc
*
desc
,
u64
addr
,
u32
flagsize
)
ace_load_tx_bd
(
struct
ace_private
*
ap
,
struct
tx_desc
*
desc
,
u64
addr
,
u32
flagsize
)
{
#if !USE_TX_COAL_NOW
flagsize
&=
~
BD_FLG_COAL_NOW
;
#endif
if
(
!
ACE_IS_TIGON_I
(
ap
))
{
writel
(
addr
>>
32
,
&
desc
->
addr
.
addrhi
);
writel
(
addr
&
0xffffffff
,
&
desc
->
addr
.
addrlo
);
writel
(
flagsize
,
&
desc
->
flagsize
);
}
else
{
desc
->
addr
.
addrhi
=
addr
>>
32
;
desc
->
addr
.
addrlo
=
addr
;
desc
->
flagsize
=
flagsize
;
}
}
...
...
@@ -2615,7 +2663,7 @@ static int ace_start_xmit(struct sk_buff *skb, struct net_device *dev)
restart:
idx
=
ap
->
tx_prd
;
if
(
tx_ring_full
(
ap
->
tx_ret_csm
,
idx
))
if
(
tx_ring_full
(
ap
,
ap
->
tx_ret_csm
,
idx
))
goto
overflow
;
#if MAX_SKB_FRAGS
...
...
@@ -2629,13 +2677,13 @@ static int ace_start_xmit(struct sk_buff *skb, struct net_device *dev)
if
(
skb
->
ip_summed
==
CHECKSUM_HW
)
flagsize
|=
BD_FLG_TCP_UDP_SUM
;
desc
=
ap
->
tx_ring
+
idx
;
idx
=
(
idx
+
1
)
%
TX_RING_ENTRIES
;
idx
=
(
idx
+
1
)
%
ACE_TX_RING_ENTRIES
(
ap
)
;
/* Look at ace_tx_int for explanations. */
if
(
tx_ring_full
(
ap
->
tx_ret_csm
,
idx
))
if
(
tx_ring_full
(
ap
,
ap
->
tx_ret_csm
,
idx
))
flagsize
|=
BD_FLG_COAL_NOW
;
ace_load_tx_bd
(
desc
,
mapping
,
flagsize
);
ace_load_tx_bd
(
ap
,
desc
,
mapping
,
flagsize
);
}
#if MAX_SKB_FRAGS
else
{
...
...
@@ -2647,9 +2695,9 @@ static int ace_start_xmit(struct sk_buff *skb, struct net_device *dev)
if
(
skb
->
ip_summed
==
CHECKSUM_HW
)
flagsize
|=
BD_FLG_TCP_UDP_SUM
;
ace_load_tx_bd
(
ap
->
tx_ring
+
idx
,
mapping
,
flagsize
);
ace_load_tx_bd
(
ap
,
ap
->
tx_ring
+
idx
,
mapping
,
flagsize
);
idx
=
(
idx
+
1
)
%
TX_RING_ENTRIES
;
idx
=
(
idx
+
1
)
%
ACE_TX_RING_ENTRIES
(
ap
)
;
for
(
i
=
0
;
i
<
skb_shinfo
(
skb
)
->
nr_frags
;
i
++
)
{
skb_frag_t
*
frag
=
&
skb_shinfo
(
skb
)
->
frags
[
i
];
...
...
@@ -2666,11 +2714,11 @@ static int ace_start_xmit(struct sk_buff *skb, struct net_device *dev)
flagsize
=
(
frag
->
size
<<
16
);
if
(
skb
->
ip_summed
==
CHECKSUM_HW
)
flagsize
|=
BD_FLG_TCP_UDP_SUM
;
idx
=
(
idx
+
1
)
%
TX_RING_ENTRIES
;
idx
=
(
idx
+
1
)
%
ACE_TX_RING_ENTRIES
(
ap
)
;
if
(
i
==
skb_shinfo
(
skb
)
->
nr_frags
-
1
)
{
flagsize
|=
BD_FLG_END
;
if
(
tx_ring_full
(
ap
->
tx_ret_csm
,
idx
))
if
(
tx_ring_full
(
ap
,
ap
->
tx_ret_csm
,
idx
))
flagsize
|=
BD_FLG_COAL_NOW
;
/*
...
...
@@ -2683,7 +2731,7 @@ static int ace_start_xmit(struct sk_buff *skb, struct net_device *dev)
}
pci_unmap_addr_set
(
info
,
mapping
,
mapping
);
pci_unmap_len_set
(
info
,
maplen
,
frag
->
size
);
ace_load_tx_bd
(
desc
,
mapping
,
flagsize
);
ace_load_tx_bd
(
ap
,
desc
,
mapping
,
flagsize
);
}
}
#endif
...
...
@@ -2701,7 +2749,7 @@ static int ace_start_xmit(struct sk_buff *skb, struct net_device *dev)
* serialized, this is the only situation we have to
* re-test.
*/
if
(
!
tx_ring_full
(
ap
->
tx_ret_csm
,
idx
))
if
(
!
tx_ring_full
(
ap
,
ap
->
tx_ret_csm
,
idx
))
netif_wake_queue
(
dev
);
}
...
...
@@ -2781,7 +2829,7 @@ static int ace_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
if
(
copy_from_user
(
&
ecmd
,
ifr
->
ifr_data
,
sizeof
(
ecmd
)))
return
-
EFAULT
;
switch
(
ecmd
.
cmd
)
{
case
ETHTOOL_GSET
:
{
case
ETHTOOL_GSET
:
ecmd
.
supported
=
(
SUPPORTED_10baseT_Half
|
SUPPORTED_10baseT_Full
|
SUPPORTED_100baseT_Half
|
SUPPORTED_100baseT_Full
|
...
...
@@ -2829,8 +2877,8 @@ static int ace_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
if
(
copy_to_user
(
ifr
->
ifr_data
,
&
ecmd
,
sizeof
(
ecmd
)))
return
-
EFAULT
;
return
0
;
}
case
ETHTOOL_SSET
:
{
case
ETHTOOL_SSET
:
if
(
!
capable
(
CAP_NET_ADMIN
))
return
-
EPERM
;
...
...
@@ -2887,7 +2935,7 @@ static int ace_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
ace_issue_cmd
(
regs
,
&
cmd
);
}
return
0
;
}
case
ETHTOOL_GDRVINFO
:
{
struct
ethtool_drvinfo
info
=
{
ETHTOOL_GDRVINFO
};
strncpy
(
info
.
driver
,
"acenic"
,
sizeof
(
info
.
driver
)
-
1
);
...
...
drivers/net/acenic.h
View file @
38171d07
...
...
@@ -437,10 +437,11 @@ struct cmd {
/*
* TX ring
* TX ring
- maximum TX ring entries for Tigon I's is 128
*/
#define TX_RING_ENTRIES 256
#define TX_RING_SIZE (TX_RING_ENTRIES * sizeof(struct tx_desc))
#define MAX_TX_RING_ENTRIES 256
#define TIGON_I_TX_RING_ENTRIES 128
#define TX_RING_SIZE (MAX_TX_RING_ENTRIES * sizeof(struct tx_desc))
#define TX_RING_BASE 0x3800
struct
tx_desc
{
...
...
@@ -608,7 +609,7 @@ struct tx_ring_info {
*/
struct
ace_skb
{
struct
tx_ring_info
tx_skbuff
[
TX_RING_ENTRIES
];
struct
tx_ring_info
tx_skbuff
[
MAX_
TX_RING_ENTRIES
];
struct
ring_info
rx_std_skbuff
[
RX_STD_RING_ENTRIES
];
struct
ring_info
rx_mini_skbuff
[
RX_MINI_RING_ENTRIES
];
struct
ring_info
rx_jumbo_skbuff
[
RX_JUMBO_RING_ENTRIES
];
...
...
@@ -642,6 +643,7 @@ struct ace_private
u32
tx_prd
;
volatile
u32
tx_ret_csm
;
struct
timer_list
timer
;
int
tx_ring_entries
;
/*
* RX elements
...
...
@@ -692,15 +694,15 @@ struct ace_private
#define TX_RESERVED MAX_SKB_FRAGS
static
inline
int
tx_space
(
u32
csm
,
u32
prd
)
static
inline
int
tx_space
(
struct
ace_private
*
ap
,
u32
csm
,
u32
prd
)
{
return
(
csm
-
prd
-
1
)
&
(
TX_RING_ENTRIES
-
1
);
return
(
csm
-
prd
-
1
)
&
(
ACE_TX_RING_ENTRIES
(
ap
)
-
1
);
}
#define tx_free(ap) tx_space((ap)->tx_ret_csm, (ap)->tx_prd)
#define tx_free(ap) tx_space((ap)->tx_ret_csm, (ap)->tx_prd
, ap
)
#if MAX_SKB_FRAGS
#define tx_ring_full(
csm, prd) (tx_space(
csm, prd) <= TX_RESERVED)
#define tx_ring_full(
ap, csm, prd) (tx_space(ap,
csm, prd) <= TX_RESERVED)
#else
#define tx_ring_full 0
#endif
...
...
@@ -711,7 +713,7 @@ static inline void set_aceaddr(aceaddr *aa, dma_addr_t addr)
u64
baddr
=
(
u64
)
addr
;
aa
->
addrlo
=
baddr
&
0xffffffff
;
aa
->
addrhi
=
baddr
>>
32
;
mb
();
w
mb
();
}
...
...
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