pespin has uploaded this change for review. ( https://gerrit.osmocom.org/c/osmo-pcu/+/30565 )
Change subject: sched: Pass pdch to *_create_rlcmac_msg() functions ......................................................................
sched: Pass pdch to *_create_rlcmac_msg() functions
The pdch pointer contains more info than just timeslot number. For instance, it contains information about the TRX owning the TS.
Change-Id: Ic31a7360a29e61f70bb1338ddab6f5f31aa8b26e --- M src/gprs_ms.c M src/gprs_ms.h M src/gprs_rlcmac_sched.cpp M src/nacc_fsm.c M src/nacc_fsm.h M src/tbf_dl_ass_fsm.c M src/tbf_dl_ass_fsm.h M src/tbf_ul_ack_fsm.c M src/tbf_ul_ack_fsm.h M src/tbf_ul_ass_fsm.c M src/tbf_ul_ass_fsm.h M tests/tbf/TbfTest.cpp 12 files changed, 60 insertions(+), 50 deletions(-)
git pull ssh://gerrit.osmocom.org:29418/osmo-pcu refs/changes/65/30565/1
diff --git a/src/gprs_ms.c b/src/gprs_ms.c index edb6fba..933953e 100644 --- a/src/gprs_ms.c +++ b/src/gprs_ms.c @@ -1059,15 +1059,16 @@ return false; }
-struct msgb *ms_nacc_create_rlcmac_msg(struct GprsMs *ms, struct gprs_rlcmac_tbf *tbf, uint32_t fn, uint8_t ts) +struct msgb *ms_nacc_create_rlcmac_msg(struct GprsMs *ms, struct gprs_rlcmac_tbf *tbf, + const struct gprs_rlcmac_pdch *pdch, uint32_t fn) { int rc; struct nacc_ev_create_rlcmac_msg_ctx data_ctx;
data_ctx = (struct nacc_ev_create_rlcmac_msg_ctx) { .tbf = tbf, + .pdch = pdch, .fn = fn, - .ts = ts, .msg = NULL, };
diff --git a/src/gprs_ms.h b/src/gprs_ms.h index 41ef2ad..4ff261c 100644 --- a/src/gprs_ms.h +++ b/src/gprs_ms.h @@ -143,7 +143,8 @@
int ms_nacc_start(struct GprsMs *ms, Packet_Cell_Change_Notification_t *notif); bool ms_nacc_rts(const struct GprsMs *ms); -struct msgb *ms_nacc_create_rlcmac_msg(struct GprsMs *ms, struct gprs_rlcmac_tbf *tbf, uint32_t fn, uint8_t ts); +struct msgb *ms_nacc_create_rlcmac_msg(struct GprsMs *ms, struct gprs_rlcmac_tbf *tbf, + const struct gprs_rlcmac_pdch *pdch, uint32_t fn);
struct gprs_rlcmac_ul_tbf *ms_new_ul_tbf_assigned_pacch(struct GprsMs *ms, int8_t use_trx); struct gprs_rlcmac_ul_tbf *ms_new_ul_tbf_assigned_agch(struct GprsMs *ms); diff --git a/src/gprs_rlcmac_sched.cpp b/src/gprs_rlcmac_sched.cpp index a201b92..87a3733 100644 --- a/src/gprs_rlcmac_sched.cpp +++ b/src/gprs_rlcmac_sched.cpp @@ -139,7 +139,6 @@ tbfs->dl_ass, tbfs->ul_ack, tbfs->nacc }; - uint8_t ts = pdch->ts_no;
/* Send Packet Application Information first (ETWS primary notifications) */ msg = sched_app_info(tbfs->dl_ass); @@ -156,15 +155,15 @@ * received, thus preventing the others from being processed. */ if (tbf == tbfs->ul_ass && tbf->ul_ass_state_is(TBF_UL_ASS_SEND_ASS_REJ)) - msg = tbf_ul_ass_create_rlcmac_msg(tbfs->ul_ass, fn, ts); + msg = tbf_ul_ass_create_rlcmac_msg(tbfs->ul_ass, pdch, fn); else if (tbf == tbfs->ul_ass && tbf->direction == GPRS_RLCMAC_DL_TBF) - msg = tbf_ul_ass_create_rlcmac_msg(tbfs->ul_ass, fn, ts); + msg = tbf_ul_ass_create_rlcmac_msg(tbfs->ul_ass, pdch, fn); else if (tbf == tbfs->dl_ass && tbf->direction == GPRS_RLCMAC_UL_TBF) - msg = tbf_dl_ass_create_rlcmac_msg(tbfs->dl_ass, fn, ts); + msg = tbf_dl_ass_create_rlcmac_msg(tbfs->dl_ass, pdch, fn); else if (tbf == tbfs->ul_ack) - msg = tbf_ul_ack_create_rlcmac_msg(tbfs->ul_ack, fn, ts); + msg = tbf_ul_ack_create_rlcmac_msg(tbfs->ul_ack, pdch, fn); else if (tbf == tbfs->nacc) { - msg = ms_nacc_create_rlcmac_msg(tbf->ms(), tbf, fn, ts); + msg = ms_nacc_create_rlcmac_msg(tbf->ms(), tbf, pdch, fn); }
if (!msg) { @@ -185,10 +184,10 @@ */ if (tbfs->dl_ass) { tbf = tbfs->dl_ass; - msg = tbf_dl_ass_create_rlcmac_msg(tbfs->dl_ass, fn, ts); + msg = tbf_dl_ass_create_rlcmac_msg(tbfs->dl_ass, pdch, fn); } else if (tbfs->ul_ass) { tbf = tbfs->ul_ass; - msg = tbf_ul_ass_create_rlcmac_msg(tbfs->ul_ass, fn, ts); + msg = tbf_ul_ass_create_rlcmac_msg(tbfs->ul_ass, pdch, fn); } }
diff --git a/src/nacc_fsm.c b/src/nacc_fsm.c index 864f196..004b120 100644 --- a/src/nacc_fsm.c +++ b/src/nacc_fsm.c @@ -168,7 +168,7 @@ struct GprsMs *ms = tbf_ms(tbf); unsigned int rrbp;
- rc = tbf_check_polling(tbf, data->fn, data->ts, new_poll_fn, &rrbp); + rc = tbf_check_polling(tbf, data->fn, data->pdch->ts_no, new_poll_fn, &rrbp); if (rc < 0) { LOGP(DTBF, LOGL_ERROR, "Failed registering poll for Pkt Cell Chg Continue (%d)\n", rc); return NULL; @@ -202,10 +202,10 @@ LOGP(DNACC, LOGL_DEBUG, "------------------------- TX : Packet Cell Change Continue -------------------------\n"); rate_ctr_inc(rate_ctr_group_get_ctr(bts_rate_counters(ms->bts), CTR_PKT_CELL_CHG_CONTINUE)); talloc_free(mac_control_block); - tbf_set_polling(tbf, *new_poll_fn, data->ts, PDCH_ULC_POLL_CELL_CHG_CONTINUE); + tbf_set_polling(tbf, *new_poll_fn, data->pdch->ts_no, PDCH_ULC_POLL_CELL_CHG_CONTINUE); LOGPTBF(tbf, LOGL_DEBUG, "Scheduled 'Packet Cell Change Continue' polling on PACCH (FN=%d, TS=%d)\n", - *new_poll_fn, data->ts); + *new_poll_fn, data->pdch->ts_no); return msg;
free_ret: @@ -608,7 +608,7 @@ data_ctx = (struct nacc_ev_create_rlcmac_msg_ctx *)data; data_ctx->msg = create_packet_cell_chg_continue(ctx, data_ctx, &ctx->continue_poll_fn); if (data_ctx->msg) { - ctx->continue_poll_ts = data_ctx->ts; + ctx->continue_poll_ts = data_ctx->pdch->ts_no; nacc_fsm_state_chg(fi, NACC_ST_WAIT_CELL_CHG_CONTINUE_ACK); } break; diff --git a/src/nacc_fsm.h b/src/nacc_fsm.h index b67ba11..c051637 100644 --- a/src/nacc_fsm.h +++ b/src/nacc_fsm.h @@ -60,8 +60,8 @@ /* passed as data in NACC_EV_CREATE_RLCMAC_MSG */ struct nacc_ev_create_rlcmac_msg_ctx { struct gprs_rlcmac_tbf *tbf; /* target tbf to create messages for */ + const struct gprs_rlcmac_pdch *pdch; /* TS where the created DL ctrl block is to be sent */ uint32_t fn; /* FN where the created DL ctrl block is to be sent */ - uint8_t ts; /* TS where the created DL ctrl block is to be sent */ struct msgb *msg; /* to be filled by FSM during event processing */ };
diff --git a/src/tbf_dl_ass_fsm.c b/src/tbf_dl_ass_fsm.c index d4dafe2..99e77e1 100644 --- a/src/tbf_dl_ass_fsm.c +++ b/src/tbf_dl_ass_fsm.c @@ -59,9 +59,9 @@ bool old_tfi_is_valid = tbf_is_tfi_assigned(ctx->tbf);
/* We only use this function in control TS (PACCH) so that MS can always answer the poll */ - OSMO_ASSERT(tbf_is_control_ts(ctx->tbf, &tbf_get_trx(ctx->tbf)->pdch[d->ts])); + OSMO_ASSERT(tbf_is_control_ts(ctx->tbf, d->pdch));
- rc = tbf_check_polling(ctx->tbf, d->fn, d->ts, &new_poll_fn, &rrbp); + rc = tbf_check_polling(ctx->tbf, d->fn, d->pdch->ts_no, &new_poll_fn, &rrbp); if (rc < 0) return NULL;
@@ -113,9 +113,9 @@ LOGP(DTBF, LOGL_DEBUG, "------------------------- TX : Packet Downlink Assignment -------------------------\n"); bts_do_rate_ctr_inc(ms->bts, CTR_PKT_DL_ASSIGNMENT);
- tbf_set_polling(ctx->tbf, new_poll_fn, d->ts, PDCH_ULC_POLL_DL_ASS); + tbf_set_polling(ctx->tbf, new_poll_fn, d->pdch->ts_no, PDCH_ULC_POLL_DL_ASS); LOGPTBF(ctx->tbf, LOGL_INFO, "Scheduled DL Assignment polling on PACCH (FN=%d, TS=%d)\n", - new_poll_fn, d->ts); + new_poll_fn, d->pdch->ts_no);
talloc_free(mac_control_block); return msg; @@ -233,12 +233,14 @@ }
-struct msgb *tbf_dl_ass_create_rlcmac_msg(const struct gprs_rlcmac_tbf* tbf, uint32_t fn, uint8_t ts) +struct msgb *tbf_dl_ass_create_rlcmac_msg(const struct gprs_rlcmac_tbf* tbf, + const struct gprs_rlcmac_pdch *pdch, + uint32_t fn) { int rc; struct tbf_dl_ass_ev_create_rlcmac_msg_ctx data_ctx = { + .pdch = pdch, .fn = fn, - .ts = ts, .msg = NULL, };
diff --git a/src/tbf_dl_ass_fsm.h b/src/tbf_dl_ass_fsm.h index dc5f9b2..36e01af 100644 --- a/src/tbf_dl_ass_fsm.h +++ b/src/tbf_dl_ass_fsm.h @@ -56,11 +56,13 @@
/* passed as data in TBF_DL_ASS_EV_CREATE_RLCMAC_MSG */ struct tbf_dl_ass_ev_create_rlcmac_msg_ctx { + const struct gprs_rlcmac_pdch *pdch; /* TS where the created DL ctrl block is to be sent */ uint32_t fn; /* FN where the created DL ctrl block is to be sent */ - uint8_t ts; /* TS where the created DL ctrl block is to be sent */ struct msgb *msg; /* to be filled by FSM during event processing */ };
-struct msgb *tbf_dl_ass_create_rlcmac_msg(const struct gprs_rlcmac_tbf* tbf, uint32_t fn, uint8_t ts); +struct msgb *tbf_dl_ass_create_rlcmac_msg(const struct gprs_rlcmac_tbf* tbf, + const struct gprs_rlcmac_pdch *pdch, + uint32_t fn); bool tbf_dl_ass_rts(const struct gprs_rlcmac_tbf* tbf, const struct gprs_rlcmac_pdch *pdch); diff --git a/src/tbf_ul_ack_fsm.c b/src/tbf_ul_ack_fsm.c index 1421c68..9501190 100644 --- a/src/tbf_ul_ack_fsm.c +++ b/src/tbf_ul_ack_fsm.c @@ -59,7 +59,7 @@ struct GprsMs *ms = tbf_ms(ul_tbf_as_tbf(tbf));
if (final) { - rc = tbf_check_polling(ul_tbf_as_tbf(tbf), d->fn, d->ts, &new_poll_fn, &rrbp); + rc = tbf_check_polling(ul_tbf_as_tbf(tbf), d->fn, d->pdch->ts_no, &new_poll_fn, &rrbp); if (rc < 0) return NULL; } @@ -93,10 +93,10 @@ osmo_fsm_inst_dispatch(tbf_state_fi(ul_tbf_as_tbf(ctx->tbf)), TBF_EV_CONTENTION_RESOLUTION_MS_SUCCESS, NULL);
if (final) { - tbf_set_polling(ul_tbf_as_tbf(tbf), new_poll_fn, d->ts, PDCH_ULC_POLL_UL_ACK); + tbf_set_polling(ul_tbf_as_tbf(tbf), new_poll_fn, d->pdch->ts_no, PDCH_ULC_POLL_UL_ACK); LOGPTBFUL(tbf, LOGL_DEBUG, "Scheduled UL Acknowledgement polling on PACCH (FN=%d, TS=%d)\n", - new_poll_fn, d->ts); + new_poll_fn, d->pdch->ts_no); }
return msg; @@ -221,12 +221,14 @@ }
-struct msgb *tbf_ul_ack_create_rlcmac_msg(const struct gprs_rlcmac_ul_tbf *ul_tbf, uint32_t fn, uint8_t ts) +struct msgb *tbf_ul_ack_create_rlcmac_msg(const struct gprs_rlcmac_ul_tbf *ul_tbf, + const struct gprs_rlcmac_pdch *pdch, + uint32_t fn) { int rc; struct tbf_ul_ack_ev_create_rlcmac_msg_ctx data_ctx = { + .pdch = pdch, .fn = fn, - .ts = ts, .msg = NULL, };
diff --git a/src/tbf_ul_ack_fsm.h b/src/tbf_ul_ack_fsm.h index e06728e..d0005eb 100644 --- a/src/tbf_ul_ack_fsm.h +++ b/src/tbf_ul_ack_fsm.h @@ -57,13 +57,15 @@
/* passed as data in TBF_UL_ACK_EV_CREATE_RLCMAC_MSG */ struct tbf_ul_ack_ev_create_rlcmac_msg_ctx { + const struct gprs_rlcmac_pdch *pdch; /* TS where the created DL ctrl block is to be sent */ uint32_t fn; /* FN where the created DL ctrl block is to be sent */ - uint8_t ts; /* TS where the created DL ctrl block is to be sent */ struct msgb *msg; /* to be filled by FSM during event processing */ };
-struct msgb *tbf_ul_ack_create_rlcmac_msg(const struct gprs_rlcmac_ul_tbf *ul_tbf, uint32_t fn, uint8_t ts); +struct msgb *tbf_ul_ack_create_rlcmac_msg(const struct gprs_rlcmac_ul_tbf *ul_tbf, + const struct gprs_rlcmac_pdch *pdch, + uint32_t fn); bool tbf_ul_ack_rts(const struct gprs_rlcmac_ul_tbf *ul_tbf, const struct gprs_rlcmac_pdch *pdch); bool tbf_ul_ack_waiting_cnf_final_ack(const struct gprs_rlcmac_ul_tbf *ul_tbf); bool tbf_ul_ack_exp_ctrl_ack(const struct gprs_rlcmac_ul_tbf *ul_tbf, uint32_t fn, uint8_t ts); diff --git a/src/tbf_ul_ass_fsm.c b/src/tbf_ul_ass_fsm.c index cff17bc..4433338 100644 --- a/src/tbf_ul_ass_fsm.c +++ b/src/tbf_ul_ass_fsm.c @@ -83,7 +83,7 @@ unsigned int rrbp; uint32_t new_poll_fn;
- rc = tbf_check_polling(ctx->tbf, d->fn, d->ts, &new_poll_fn, &rrbp); + rc = tbf_check_polling(ctx->tbf, d->fn, d->pdch->ts_no, &new_poll_fn, &rrbp); if (rc < 0) return NULL;
@@ -128,9 +128,9 @@ LOGP(DTBF, LOGL_DEBUG, "------------------------- TX : Packet Uplink Assignment -------------------------\n"); bts_do_rate_ctr_inc(ms->bts, CTR_PKT_UL_ASSIGNMENT);
- tbf_set_polling(ctx->tbf, new_poll_fn, d->ts, PDCH_ULC_POLL_UL_ASS); + tbf_set_polling(ctx->tbf, new_poll_fn, d->pdch->ts_no, PDCH_ULC_POLL_UL_ASS); LOGPTBF(ctx->tbf, LOGL_INFO, "Scheduled UL Assignment polling on PACCH (FN=%d, TS=%d)\n", - new_poll_fn, d->ts); + new_poll_fn, d->pdch->ts_no);
talloc_free(mac_control_block); return msg; @@ -326,12 +326,14 @@ }
-struct msgb *tbf_ul_ass_create_rlcmac_msg(const struct gprs_rlcmac_tbf* tbf, uint32_t fn, uint8_t ts) +struct msgb *tbf_ul_ass_create_rlcmac_msg(const struct gprs_rlcmac_tbf* tbf, + const struct gprs_rlcmac_pdch *pdch, + uint32_t fn) { int rc; struct tbf_ul_ass_ev_create_rlcmac_msg_ctx data_ctx = { + .pdch = pdch, .fn = fn, - .ts = ts, .msg = NULL, };
diff --git a/src/tbf_ul_ass_fsm.h b/src/tbf_ul_ass_fsm.h index 9b0de38..4c7518d 100644 --- a/src/tbf_ul_ass_fsm.h +++ b/src/tbf_ul_ass_fsm.h @@ -59,11 +59,13 @@
/* passed as data in TBF_UL_ASS_EV_CREATE_RLCMAC_MSG */ struct tbf_ul_ass_ev_create_rlcmac_msg_ctx { + const struct gprs_rlcmac_pdch *pdch; /* TS where the created DL ctrl block is to be sent */ uint32_t fn; /* FN where the created DL ctrl block is to be sent */ - uint8_t ts; /* TS where the created DL ctrl block is to be sent */ struct msgb *msg; /* to be filled by FSM during event processing */ };
-struct msgb *tbf_ul_ass_create_rlcmac_msg(const struct gprs_rlcmac_tbf* tbf, uint32_t fn, uint8_t ts); +struct msgb *tbf_ul_ass_create_rlcmac_msg(const struct gprs_rlcmac_tbf* tbf, + const struct gprs_rlcmac_pdch *pdch, + uint32_t fn); bool tbf_ul_ass_rts(const struct gprs_rlcmac_tbf* tbf, const struct gprs_rlcmac_pdch *pdch); diff --git a/tests/tbf/TbfTest.cpp b/tests/tbf/TbfTest.cpp index f94c8de..79d0f63 100644 --- a/tests/tbf/TbfTest.cpp +++ b/tests/tbf/TbfTest.cpp @@ -831,7 +831,7 @@ pdch->rcv_block(data_msg, 42, *fn, &meas);
osmo_fsm_inst_dispatch(ul_tbf->ul_ack_fsm.fi, TBF_UL_ACK_EV_SCHED_ACK, NULL); - struct msgb *msg1 = tbf_ul_ack_create_rlcmac_msg(ul_tbf, *fn, ts_no); + struct msgb *msg1 = tbf_ul_ack_create_rlcmac_msg(ul_tbf, pdch, *fn);
static uint8_t exp1[] = { 0x40, 0x24, 0x01, 0x0b, 0x3e, 0x24, 0x46, 0x68, 0x9c, 0x70, 0x87, 0xb0, 0x06, 0x2b, 0x2b, 0x2b, 0x2b, 0x2b, 0x2b, 0x2b, 0x2b, 0x2b, 0x2b @@ -859,7 +859,7 @@ pdch->rcv_block(data_msg, 42, *fn, &meas);
osmo_fsm_inst_dispatch(ul_tbf->ul_ack_fsm.fi, TBF_UL_ACK_EV_SCHED_ACK, NULL); - msg1 = tbf_ul_ack_create_rlcmac_msg(ul_tbf, *fn, ts_no); + msg1 = tbf_ul_ack_create_rlcmac_msg(ul_tbf, pdch, *fn);
static uint8_t exp2[] = { 0x40, 0x24, 0x01, 0x0b, 0x3e, 0x24, 0x46, 0x68, 0x9c, 0x70, 0x88, 0xb0, 0x06, 0x8b, 0x2b, 0x2b, 0x2b, 0x2b, 0x2b, 0x2b, 0x2b, 0x2b, 0x2b @@ -1380,7 +1380,7 @@ GprsMs *ms; uint8_t trx_no = 0; int tfi = 0; - struct gprs_rlcmac_pdch *pdch; + struct gprs_rlcmac_pdch *pdch = &bts->trx[trx_no].pdch[ts_no];
/* send fake data with cv=0*/ struct gprs_rlc_ul_header_egprs_3 *hdr3 = NULL; @@ -1410,11 +1410,10 @@ data[5] = 0x0; data[6] = 0x2b; data[7] = 0x2b; - pdch = &bts->trx[trx_no].pdch[ts_no]; pdch->rcv_block(&data[0], sizeof(data), *fn, &meas); } osmo_fsm_inst_dispatch(ul_tbf->ul_ack_fsm.fi, TBF_UL_ACK_EV_SCHED_ACK, NULL); - tbf_ul_ack_create_rlcmac_msg(ul_tbf, *fn, ts_no); + tbf_ul_ack_create_rlcmac_msg(ul_tbf, pdch, *fn); memset(data, 0x2b, sizeof(data)); hdr3 = (struct gprs_rlc_ul_header_egprs_3 *)data; hdr3->r = 0; @@ -1461,7 +1460,7 @@ GprsMs *ms; uint8_t trx_no = 0; int tfi = 0; - struct gprs_rlcmac_pdch *pdch; + struct gprs_rlcmac_pdch *pdch = &bts->trx[trx_no].pdch[ts_no];
check_tbf(ul_tbf); /* send fake data with cv=0*/ @@ -1493,11 +1492,10 @@ data[5] = 0x0; data[6] = 0x2b; data[7] = 0x2b; - pdch = &bts->trx[trx_no].pdch[ts_no]; pdch->rcv_block(&data[0], sizeof(data), *fn, &meas); } osmo_fsm_inst_dispatch(ul_tbf->ul_ack_fsm.fi, TBF_UL_ACK_EV_SCHED_ACK, NULL); - tbf_ul_ack_create_rlcmac_msg(ul_tbf, *fn, ts_no); + tbf_ul_ack_create_rlcmac_msg(ul_tbf, pdch, *fn); memset(data, 0x2b, sizeof(data)); hdr3 = (struct gprs_rlc_ul_header_egprs_3 *)data; hdr3->r = 0; @@ -1522,7 +1520,7 @@ pdch = &bts->trx[trx_no].pdch[ts_no]; pdch->rcv_block(&data[0], sizeof(data), *fn, &meas); osmo_fsm_inst_dispatch(ul_tbf->ul_ack_fsm.fi, TBF_UL_ACK_EV_SCHED_ACK, NULL); - tbf_ul_ack_create_rlcmac_msg(ul_tbf, *fn, ts_no); + tbf_ul_ack_create_rlcmac_msg(ul_tbf, pdch, *fn);
request_dl_rlc_block(ul_tbf, fn);
@@ -1545,7 +1543,7 @@ uint8_t trx_no = 0; int tfi = 0; gprs_rlcmac_ul_tbf *ul_tbf; - struct gprs_rlcmac_pdch *pdch; + struct gprs_rlcmac_pdch *pdch = &bts->trx[trx_no].pdch[ts_no];
/* check the TBF */ ul_tbf = bts_ul_tbf_by_tfi(bts, tfi, trx_no, ts_no); @@ -1581,11 +1579,10 @@ data[5] = 0x0; data[6] = 0x2b; data[7] = 0x2b; - pdch = &bts->trx[trx_no].pdch[ts_no]; pdch->rcv_block(&data[0], sizeof(data), *fn, &meas); } osmo_fsm_inst_dispatch(ul_tbf->ul_ack_fsm.fi, TBF_UL_ACK_EV_SCHED_ACK, NULL); - tbf_ul_ack_create_rlcmac_msg(ul_tbf, *fn, ts_no); + tbf_ul_ack_create_rlcmac_msg(ul_tbf, pdch, *fn); memset(data, 0x2b, sizeof(data)); hdr3 = (struct gprs_rlc_ul_header_egprs_3 *)data; hdr3->r = 0;