Skip to content

Commit 8fdcabe

Browse files
Xie Hedavem330
authored andcommitted
drivers/net/wan/x25_asy: Fix to make it work
This driver is not working because of problems of its receiving code. This patch fixes it to make it work. When the driver receives an LAPB frame, it should first pass the frame to the LAPB module to process. After processing, the LAPB module passes the data (the packet) back to the driver, the driver should then add a one-byte pseudo header and pass the data to upper layers. The changes to the "x25_asy_bump" function and the "x25_asy_data_indication" function are to correctly implement this procedure. Also, the "x25_asy_unesc" function ignores any frame that is shorter than 3 bytes. However the shortest frames are 2-byte long. So we need to change it to allow 2-byte frames to pass. Cc: Eric Dumazet <[email protected]> Cc: Martin Schiller <[email protected]> Signed-off-by: Xie He <[email protected]> Reviewed-by: Martin Schiller <[email protected]> Signed-off-by: David S. Miller <[email protected]>
1 parent b346c0c commit 8fdcabe

File tree

1 file changed

+14
-7
lines changed

1 file changed

+14
-7
lines changed

drivers/net/wan/x25_asy.c

Lines changed: 14 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -183,7 +183,7 @@ static inline void x25_asy_unlock(struct x25_asy *sl)
183183
netif_wake_queue(sl->dev);
184184
}
185185

186-
/* Send one completely decapsulated IP datagram to the IP layer. */
186+
/* Send an LAPB frame to the LAPB module to process. */
187187

188188
static void x25_asy_bump(struct x25_asy *sl)
189189
{
@@ -195,21 +195,19 @@ static void x25_asy_bump(struct x25_asy *sl)
195195
count = sl->rcount;
196196
dev->stats.rx_bytes += count;
197197

198-
skb = dev_alloc_skb(count+1);
198+
skb = dev_alloc_skb(count);
199199
if (skb == NULL) {
200200
netdev_warn(sl->dev, "memory squeeze, dropping packet\n");
201201
dev->stats.rx_dropped++;
202202
return;
203203
}
204-
skb_push(skb, 1); /* LAPB internal control */
205204
skb_put_data(skb, sl->rbuff, count);
206205
skb->protocol = x25_type_trans(skb, sl->dev);
207206
err = lapb_data_received(skb->dev, skb);
208207
if (err != LAPB_OK) {
209208
kfree_skb(skb);
210209
printk(KERN_DEBUG "x25_asy: data received err - %d\n", err);
211210
} else {
212-
netif_rx(skb);
213211
dev->stats.rx_packets++;
214212
}
215213
}
@@ -356,12 +354,21 @@ static netdev_tx_t x25_asy_xmit(struct sk_buff *skb,
356354
*/
357355

358356
/*
359-
* Called when I frame data arrives. We did the work above - throw it
360-
* at the net layer.
357+
* Called when I frame data arrive. We add a pseudo header for upper
358+
* layers and pass it to upper layers.
361359
*/
362360

363361
static int x25_asy_data_indication(struct net_device *dev, struct sk_buff *skb)
364362
{
363+
if (skb_cow(skb, 1)) {
364+
kfree_skb(skb);
365+
return NET_RX_DROP;
366+
}
367+
skb_push(skb, 1);
368+
skb->data[0] = X25_IFACE_DATA;
369+
370+
skb->protocol = x25_type_trans(skb, dev);
371+
365372
return netif_rx(skb);
366373
}
367374

@@ -657,7 +664,7 @@ static void x25_asy_unesc(struct x25_asy *sl, unsigned char s)
657664
switch (s) {
658665
case X25_END:
659666
if (!test_and_clear_bit(SLF_ERROR, &sl->flags) &&
660-
sl->rcount > 2)
667+
sl->rcount >= 2)
661668
x25_asy_bump(sl);
662669
clear_bit(SLF_ESCAPE, &sl->flags);
663670
sl->rcount = 0;

0 commit comments

Comments
 (0)