From 643aad2ef4b0677b95aa94f5eb7a2d01db1fe004 Mon Sep 17 00:00:00 2001 From: Sylvain Munaut Date: Sun, 24 Apr 2011 11:20:48 +0200 Subject: [PATCH] fw/l1: Add a queue for traffic frame to send to network (TRAFFIC_REQ) Also hard limit to maximum 4 pending frames (should not happen !), the upstream is supposed to do its own flow control. Written-by: Andreas Eversberg Signed-off-by: Sylvain Munaut --- src/target/firmware/include/layer1/sync.h | 1 + src/target/firmware/layer1/l23_api.c | 27 +++++++++++++++++++++++ 2 files changed, 28 insertions(+) diff --git a/src/target/firmware/include/layer1/sync.h b/src/target/firmware/include/layer1/sync.h index 8ed2cb1..4247dab 100644 --- a/src/target/firmware/include/layer1/sync.h +++ b/src/target/firmware/include/layer1/sync.h @@ -27,6 +27,7 @@ struct l1_cell_info { enum l1s_chan { L1S_CHAN_MAIN, L1S_CHAN_SACCH, + L1S_CHAN_TRAFFIC, _NUM_L1S_CHAN }; diff --git a/src/target/firmware/layer1/l23_api.c b/src/target/firmware/layer1/l23_api.c index 3baba17..2a22db8 100644 --- a/src/target/firmware/layer1/l23_api.c +++ b/src/target/firmware/layer1/l23_api.c @@ -303,6 +303,7 @@ static void l1ctl_rx_dm_rel_req(struct msgb *msg) l1s.dedicated.type = GSM_DCHAN_NONE; l1a_txq_msgb_flush(&l1s.tx_queue[L1S_CHAN_MAIN]); l1a_txq_msgb_flush(&l1s.tx_queue[L1S_CHAN_SACCH]); + l1a_txq_msgb_flush(&l1s.tx_queue[L1S_CHAN_TRAFFIC]); l1a_meas_msgb_set(NULL); dsp_load_ciph_param(0, NULL); l1a_tch_mode_set(GSM48_CMODE_SIGN); @@ -517,6 +518,28 @@ static void l1ctl_rx_neigh_pm_req(struct msgb *msg) mframe_enable(MF_TASK_NEIGH_PM51); } +/* receive a L1CTL_TRAFFIC_REQ from L23 */ +static void l1ctl_rx_traffic_req(struct msgb *msg) +{ + struct l1ctl_hdr *l1h = (struct l1ctl_hdr *) msg->data; + struct l1ctl_info_ul *ul = (struct l1ctl_info_ul *) l1h->data; + struct l1ctl_traffic_req *tr = (struct l1ctl_traffic_req *) ul->payload; + int num = 0; + + /* printd("L1CTL_TRAFFIC_REQ\n"); */ /* Very verbose, can overwelm serial */ + + msg->l2h = tr->data; + + num = l1a_txq_msgb_count(&l1s.tx_queue[L1S_CHAN_TRAFFIC]); + if (num >= 4) { + printd("dropping traffic frame\n"); + msgb_free(msg); + return; + } + + l1a_txq_msgb_enq(&l1s.tx_queue[L1S_CHAN_TRAFFIC], msg); +} + /* callback from SERCOMM when L2 sends a message to L1 */ static void l1a_l23_rx_cb(uint8_t dlci, struct msgb *msg) { @@ -580,6 +603,10 @@ static void l1a_l23_rx_cb(uint8_t dlci, struct msgb *msg) case L1CTL_NEIGH_PM_REQ: l1ctl_rx_neigh_pm_req(msg); break; + case L1CTL_TRAFFIC_REQ: + l1ctl_rx_traffic_req(msg); + /* we have to keep the msgb, not free it! */ + goto exit_nofree; } exit_msgbfree: -- 2.20.1