mirror of https://gerrit.osmocom.org/libosmocore
gsm/lapdm: Prevent LAPD tx_queue from filling up in polling mode
If LAPDm receives an I-Frame while there already is an I-Frame in the tx_queue the code generates an additional RR (to acknowledge the received I-Frame). Instead, N(R) of the I-Frame in the tx_queue should be updated to ACK the data.
This commit is contained in:
parent
09129352f9
commit
3dc4e16786
|
@ -0,0 +1,2 @@
|
|||
#library what description / commit summary line
|
||||
libosmogsm abi-change Prevent LAPD tx_queue from filling up in polling mode
|
|
@ -125,6 +125,7 @@ struct lapd_datalink {
|
|||
int (*send_dlsap)(struct osmo_dlsap_prim *dp,
|
||||
struct lapd_msg_ctx *lctx);
|
||||
int (*send_ph_data_req)(struct lapd_msg_ctx *lctx, struct msgb *msg);
|
||||
int (*update_pending_frames)(struct lapd_msg_ctx *lctx);
|
||||
struct {
|
||||
/*! \brief filled-in once we set the lapd_mode above */
|
||||
struct lapd_cr_ent loc2rem;
|
||||
|
|
|
@ -1607,6 +1607,12 @@ static int lapd_rx_i(struct msgb *msg, struct lapd_msg_ctx *lctx)
|
|||
if (!dl->own_busy) {
|
||||
/* NOTE: V(R) is already set above */
|
||||
rc = lapd_send_i(lctx, __LINE__);
|
||||
|
||||
/* if update_pending_iframe returns 0 it updated
|
||||
* the lapd header of an iframe in the tx queue */
|
||||
if (rc && dl->update_pending_frames)
|
||||
rc = dl->update_pending_frames(lctx);
|
||||
|
||||
if (rc) {
|
||||
LOGP(DLLAPD, LOGL_INFO, "we are not busy and "
|
||||
"have no pending data, send RR\n");
|
||||
|
|
|
@ -114,6 +114,7 @@ enum lapdm_format {
|
|||
static int lapdm_send_ph_data_req(struct lapd_msg_ctx *lctx, struct msgb *msg);
|
||||
static int send_rslms_dlsap(struct osmo_dlsap_prim *dp,
|
||||
struct lapd_msg_ctx *lctx);
|
||||
static int update_pending_frames(struct lapd_msg_ctx *lctx);
|
||||
|
||||
static void lapdm_dl_init(struct lapdm_datalink *dl,
|
||||
struct lapdm_entity *entity, int t200)
|
||||
|
@ -124,6 +125,7 @@ static void lapdm_dl_init(struct lapdm_datalink *dl,
|
|||
dl->dl.reestablish = 0; /* GSM uses no reestablish */
|
||||
dl->dl.send_ph_data_req = lapdm_send_ph_data_req;
|
||||
dl->dl.send_dlsap = send_rslms_dlsap;
|
||||
dl->dl.update_pending_frames = update_pending_frames;
|
||||
dl->dl.n200_est_rel = N200_EST_REL;
|
||||
dl->dl.n200 = N200;
|
||||
dl->dl.t203_sec = 0; dl->dl.t203_usec = 0;
|
||||
|
@ -488,6 +490,25 @@ static int lapdm_send_ph_data_req(struct lapd_msg_ctx *lctx, struct msgb *msg)
|
|||
23);
|
||||
}
|
||||
|
||||
static int update_pending_frames(struct lapd_msg_ctx *lctx)
|
||||
{
|
||||
struct lapd_datalink *dl = lctx->dl;
|
||||
struct msgb *msg;
|
||||
int rc = -1;
|
||||
|
||||
llist_for_each_entry(msg, &dl->tx_queue, list) {
|
||||
if (LAPDm_CTRL_is_I(msg->l2h[1])) {
|
||||
msg->l2h[1] = LAPDm_CTRL_I(dl->v_recv, LAPDm_CTRL_I_Ns(msg->l2h[1]),
|
||||
LAPDm_CTRL_PF_BIT(msg->l2h[1]));
|
||||
rc = 0;
|
||||
} else if (LAPDm_CTRL_is_S(msg->l2h[1])) {
|
||||
LOGP(DLLAPD, LOGL_ERROR, "Supervisory frame in queue, this shouldn't happen\n");
|
||||
}
|
||||
}
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
/* input into layer2 (from layer 1) */
|
||||
static int l2_ph_data_ind(struct msgb *msg, struct lapdm_entity *le,
|
||||
uint8_t chan_nr, uint8_t link_id)
|
||||
|
|
|
@ -621,17 +621,13 @@ const uint8_t gprs_susp[] = {
|
|||
0xd2, 0x6f, 0x09, 0xf1, 0x07, 0x00, 0x01, 0x00, 0x02
|
||||
};
|
||||
|
||||
const uint8_t gprs_susp_ack[] = {
|
||||
0x01, 0x41, 0x01
|
||||
};
|
||||
|
||||
const uint8_t cipher_cmd[] = {
|
||||
0x06, 0x35, 0x01
|
||||
};
|
||||
|
||||
/* The cipher command we send to the MS */
|
||||
/* The cipher command we send to the MS after updating our N(R) */
|
||||
const uint8_t cipher_cmd_out[] = {
|
||||
0x03, 0x20, 0x0d, 0x06, 0x35, 0x01
|
||||
0x03, 0x40, 0x0d, 0x06, 0x35, 0x01
|
||||
};
|
||||
|
||||
uint8_t cipher_compl[] = {
|
||||
|
@ -730,7 +726,7 @@ static void test_lapdm_desync()
|
|||
|
||||
rc = dequeue_prim(&bts_to_ms_channel.lapdm_dcch, &pp, "DCCH");
|
||||
CHECK_RC(rc);
|
||||
OSMO_ASSERT(memcmp(pp.oph.msg->l2h, gprs_susp_ack, ARRAY_SIZE(gprs_susp_ack)) == 0);
|
||||
OSMO_ASSERT(memcmp(pp.oph.msg->l2h, cipher_compl_ack, ARRAY_SIZE(cipher_compl_ack)) == 0);
|
||||
|
||||
printf("\nEstablishing SAPI=3\n");
|
||||
send_sabm(&bts_to_ms_channel, 3, NULL, 0);
|
||||
|
@ -746,7 +742,7 @@ static void test_lapdm_desync()
|
|||
|
||||
rc = dequeue_prim(&bts_to_ms_channel.lapdm_dcch, &pp, "DCCH");
|
||||
CHECK_RC(rc);
|
||||
OSMO_ASSERT(memcmp(pp.oph.msg->l2h, cipher_compl_ack, ARRAY_SIZE(cipher_compl_ack)) == 0);
|
||||
OSMO_ASSERT(memcmp(pp.oph.msg->l2h, cp_data_1_ack, ARRAY_SIZE(cp_data_1_ack)) == 0);
|
||||
|
||||
/* clean up */
|
||||
lapdm_channel_exit(&bts_to_ms_channel);
|
||||
|
|
|
@ -68,27 +68,24 @@ Sending GPRS Suspend Request
|
|||
bts_to_ms_dummy_tx_cb: MS->BTS(us) message 22
|
||||
|
||||
Dumping queue:
|
||||
00 00 17 [L2]> 03 20 0d [L3]> 06 35 01
|
||||
00 00 17 [L2]> 01 41 01
|
||||
00 00 17 [L2]> 03 40 0d [L3]> 06 35 01
|
||||
|
||||
Took message from DCCH queue: L2 header size 3, L3 size 20, SAP 0x1000000, 0/0, Link 0x00
|
||||
Message: [L2]> 03 20 0d [L3]> 06 35 01 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b
|
||||
Message: [L2]> 03 40 0d [L3]> 06 35 01 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b
|
||||
|
||||
Sending Cipher Mode Complete
|
||||
bts_to_ms_dummy_tx_cb: MS->BTS(us) message 11
|
||||
|
||||
Dumping queue:
|
||||
00 00 17 [L2]> 01 41 01
|
||||
00 00 17 [L2]> 01 61 01
|
||||
|
||||
Took message from DCCH queue: L2 header size 23, L3 size 0, SAP 0x1000000, 0/0, Link 0x00
|
||||
Message: [L2]> 01 41 01 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b
|
||||
Message: [L2]> 01 61 01 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b
|
||||
|
||||
Establishing SAPI=3
|
||||
bts_to_ms_dummy_tx_cb: MS->BTS(us) message 6
|
||||
|
||||
Dumping queue:
|
||||
00 00 17 [L2]> 01 61 01
|
||||
|
||||
Took message from DCCH queue: L2 header size 3, L3 size 20, SAP 0x1000000, 0/0, Link 0x03
|
||||
Message: [L2]> 0d 73 01 [L3]> 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b
|
||||
|
@ -96,8 +93,7 @@ Message: [L2]> 0d 73 01 [L3]> 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b
|
|||
Sending CP-DATA
|
||||
|
||||
Dumping queue:
|
||||
00 00 17 [L2]> 01 61 01
|
||||
|
||||
Took message from DCCH queue: L2 header size 23, L3 size 0, SAP 0x1000000, 0/0, Link 0x00
|
||||
Message: [L2]> 01 61 01 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b
|
||||
Took message from DCCH queue: L2 header size 23, L3 size 0, SAP 0x1000000, 0/0, Link 0x03
|
||||
Message: [L2]> 0d 21 01 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b 2b
|
||||
Success.
|
||||
|
|
Loading…
Reference in New Issue