diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/gsm/lapd_core.c | 24 | 
1 files changed, 21 insertions, 3 deletions
| diff --git a/src/gsm/lapd_core.c b/src/gsm/lapd_core.c index c81c2fbf..b1b5a1ba 100644 --- a/src/gsm/lapd_core.c +++ b/src/gsm/lapd_core.c @@ -1497,14 +1497,32 @@ static int lapd_rx_i(struct msgb *msg, struct lapd_msg_ctx *lctx)  		     "V(R)=%u\n", ns, dl->v_recv);  		/* discard data */  		msgb_free(msg); -		if (!dl->seq_err_cond) { +		if (dl->seq_err_cond != 1) {  			/* FIXME: help me understand what exactly todo here -			dl->seq_err_cond = 1;  			*/ +			dl->seq_err_cond = 1;  			lapd_send_rej(lctx, lctx->p_f);  		} else { +			/* If there are two subsequent sequence errors received, +			 * ignore it. (Ignore every second subsequent error.) +			 * This happens if our reply with the REJ is too slow, +			 * so the remote gets a T200 timeout and sends another +			 * frame with a sequence error. +			 * Test showed that replying with two subsequent REJ +			 * messages could the remote L2 process to abort. +			 * Replying too slow shouldn't happen, but may happen +			 * over serial link between BB and LAPD. +			 */ +			dl->seq_err_cond = 2;  		} -		return -EIO; +		/* Even if N(s) sequence error, acknowledge to N(R)-1 */ +		/* 5.5.3.1: Acknowlege all transmitted frames up the N(R)-1 */ +		lapd_acknowledge(lctx); /* V(A) is also set here */ + +		/* Send message, if possible due to acknowledged data */ +		lapd_send_i(lctx, __LINE__); + +		return 0;  	}  	dl->seq_err_cond = 0; | 
