Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
O
OpenXG-RAN
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
1
Merge Requests
1
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Operations
Operations
Metrics
Environments
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
OpenXG
OpenXG-RAN
Commits
cc154da5
Commit
cc154da5
authored
Dec 04, 2024
by
francescomani
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Procedures for Random Access Response reception
parent
108fdae1
Changes
11
Hide whitespace changes
Inline
Side-by-side
Showing
11 changed files
with
420 additions
and
384 deletions
+420
-384
openair2/LAYER2/NR_MAC_UE/mac_defs.h
openair2/LAYER2/NR_MAC_UE/mac_defs.h
+7
-14
openair2/LAYER2/NR_MAC_UE/mac_proto.h
openair2/LAYER2/NR_MAC_UE/mac_proto.h
+2
-5
openair2/LAYER2/NR_MAC_UE/mac_tables.c
openair2/LAYER2/NR_MAC_UE/mac_tables.c
+0
-24
openair2/LAYER2/NR_MAC_UE/nr_ra_procedures.c
openair2/LAYER2/NR_MAC_UE/nr_ra_procedures.c
+231
-171
openair2/LAYER2/NR_MAC_UE/nr_ue_dci_configuration.c
openair2/LAYER2/NR_MAC_UE/nr_ue_dci_configuration.c
+6
-0
openair2/LAYER2/NR_MAC_UE/nr_ue_power_procedures.c
openair2/LAYER2/NR_MAC_UE/nr_ue_power_procedures.c
+1
-3
openair2/LAYER2/NR_MAC_UE/nr_ue_procedures.c
openair2/LAYER2/NR_MAC_UE/nr_ue_procedures.c
+154
-153
openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c
openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c
+10
-2
openair2/LAYER2/NR_MAC_UE/tests/test_nr_ue_power_procedures.cpp
...r2/LAYER2/NR_MAC_UE/tests/test_nr_ue_power_procedures.cpp
+5
-9
openair2/LAYER2/NR_MAC_UE/tests/test_nr_ue_ra_procedures.cpp
openair2/LAYER2/NR_MAC_UE/tests/test_nr_ue_ra_procedures.cpp
+2
-0
openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.c
openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.c
+2
-3
No files found.
openair2/LAYER2/NR_MAC_UE/mac_defs.h
View file @
cc154da5
...
...
@@ -283,8 +283,6 @@ typedef struct {
int
ra_preamble_rx_target_power
;
/// RA Preamble Power Ramping Step in dB
uint32_t
preamble_power_ramping_step
;
uint8_t
preamble_backoff
;
uint8_t
scaling_factor_bi
;
/// UE configured maximum output power
int
Pc_max
;
}
NR_PRACH_RESOURCES_t
;
...
...
@@ -310,8 +308,6 @@ typedef struct {
bool
cfra
;
/// RA type
nr_ra_type_t
ra_type
;
/// RA rx frame offset: compensate RA rx offset introduced by OAI gNB.
uint8_t
RA_offset
;
/// MsgB SuccessRAR MAC subheader
int8_t
MsgB_R
;
int8_t
MsgB_CH_ACESS_CPEXT
;
...
...
@@ -333,18 +329,15 @@ typedef struct {
int
restricted_set_config
;
// selected SSB for RACH (not the SSB-Index but the cumulative index, excluding not trasmitted SSBs)
int
ra_ssb
;
/// Random-access window counter
int16_t
RA_window_cnt
;
/// Flag to monitor if matching RAPID was received in RAR
uint8_t
RA_RAPID_found
;
/// Flag to monitor if BI was received in RAR
uint8_t
RA_BI_found
;
/// Random-access backoff counter
int16_t
RA_backoff_indicator
;
/// Random-access response window timer
NR_timer_t
response_window_timer
;
bool
start_response_window
;
/// Random-access backoff timer
NR_timer_t
RA_backoff_timer
;
int
RA_backoff_limit
;
uint8_t
scaling_factor_bi
;
/// Flag to indicate whether preambles Group A is selected
bool
RA_GroupA
;
/// RA backoff counter
int16_t
RA_backoff_cnt
;
/// RA max number of preamble transmissions
int
preambleTransMax
;
/// Received TPC command (in dB) from RAR
...
...
openair2/LAYER2/NR_MAC_UE/mac_proto.h
View file @
cc154da5
...
...
@@ -212,7 +212,6 @@ void set_harq_status(NR_UE_MAC_INST_t *mac,
bool
get_downlink_ack
(
NR_UE_MAC_INST_t
*
mac
,
frame_t
frame
,
int
slot
,
PUCCH_sched_t
*
pucch
);
initial_pucch_resource_t
get_initial_pucch_resource
(
const
int
idx
);
void
multiplex_pucch_resource
(
NR_UE_MAC_INST_t
*
mac
,
PUCCH_sched_t
*
pucch
,
int
num_res
);
uint32_t
get_backoff_indicator
(
int
idx
);
int16_t
get_pucch_tx_power_ue
(
NR_UE_MAC_INST_t
*
mac
,
int
scs
,
NR_PUCCH_Config_t
*
pucch_Config
,
...
...
@@ -307,10 +306,6 @@ void nr_ra_failed(NR_UE_MAC_INST_t *mac, uint8_t CC_id, NR_PRACH_RESOURCES_t *pr
void
nr_ra_succeeded
(
NR_UE_MAC_INST_t
*
mac
,
const
uint8_t
gNB_index
,
const
frame_t
frame
,
const
int
slot
);
int16_t
nr_get_RA_window_2Step
(
const
NR_MsgA_ConfigCommon_r16_t
*
msgA_ConfigCommon_r16
);
int16_t
nr_get_RA_window_4Step
(
const
NR_RACH_ConfigCommon_t
*
rach_ConfigCommon
);
void
nr_get_RA_window
(
NR_UE_MAC_INST_t
*
mac
);
/*@mac pointer to MAC instance
...
...
@@ -336,6 +331,8 @@ NR_UE_L2_STATE_t nr_ue_get_sync_state(module_id_t mod_id);
int16_t
get_prach_tx_power
(
NR_UE_MAC_INST_t
*
mac
);
void
schedule_RA_after_SR_failure
(
NR_UE_MAC_INST_t
*
mac
);
void
nr_rar_not_successful
(
NR_UE_MAC_INST_t
*
mac
);
void
ra_resource_selection
(
NR_UE_MAC_INST_t
*
mac
);
void
nr_Msg3_transmitted
(
NR_UE_MAC_INST_t
*
mac
,
uint8_t
CC_id
,
frame_t
frameP
,
slot_t
slotP
,
uint8_t
gNB_id
);
void
trigger_MAC_UE_RA
(
NR_UE_MAC_INST_t
*
mac
,
dci_pdu_rel15_t
*
pdcch_order
);
void
nr_get_Msg3_MsgA_PUSCH_payload
(
NR_UE_MAC_INST_t
*
mac
,
uint8_t
*
buf
,
int
TBS_max
);
...
...
openair2/LAYER2/NR_MAC_UE/mac_tables.c
View file @
cc154da5
...
...
@@ -412,30 +412,6 @@ static const uint8_t table_7_3_2_3_3_4_twoCodeword[6][14] = {
{
2
,
1
,
1
,
1
,
1
,
0
,
0
,
1
,
1
,
1
,
1
,
0
,
0
,
2
},
};
// table 7.2-1 TS 38.321
static
const
uint32_t
table_7_2_1
[
16
]
=
{
5
,
// row index 0
10
,
// row index 1
20
,
// row index 2
30
,
// row index 3
40
,
// row index 4
60
,
// row index 5
80
,
// row index 6
120
,
// row index 7
160
,
// row index 8
240
,
// row index 9
320
,
// row index 10
480
,
// row index 11
960
,
// row index 12
1920
,
// row index 13
};
uint32_t
get_backoff_indicator
(
int
idx
)
{
AssertFatal
(
idx
<
16
,
"Backoff indicator index %d exeeding table size
\n
"
,
idx
);
return
table_7_2_1
[
idx
];
}
static
inline
uint16_t
packBits
(
const
uint8_t
*
toPack
,
const
int
nb
)
{
int
res
=
0
;
...
...
openair2/LAYER2/NR_MAC_UE/nr_ra_procedures.c
View file @
cc154da5
...
...
@@ -450,7 +450,7 @@ static void select_prach_occasion(RA_config_t *ra,
seed
=
1
;
}
else
{
// & to truncate the int64_t and keep only the LSB bits, up to sizeof(int)
seed
=
(
unsigned
int
)
(
rdtsc_oai
()
&
~
0
);
seed
=
(
unsigned
int
)(
rdtsc_oai
()
&
~
0
);
}
int
num_ros_per_ssb
=
0
;
...
...
@@ -630,7 +630,7 @@ static void ra_preamble_msga_transmission(RA_config_t *ra, int scs)
}
// 38.321 Section 5.1.2 Random Access Resource selection
static
void
ra_resource_selection
(
NR_UE_MAC_INST_t
*
mac
)
void
ra_resource_selection
(
NR_UE_MAC_INST_t
*
mac
)
{
configure_ra_preamble
(
mac
);
const
NR_UE_UL_BWP_t
*
current_UL_BWP
=
mac
->
current_UL_BWP
;
...
...
@@ -640,6 +640,189 @@ static void ra_resource_selection(NR_UE_MAC_INST_t *mac)
ra_preamble_msga_transmission
(
&
mac
->
ra
,
mu
);
}
static
int
nr_get_RA_window_2Step_v17
(
long
msgB_ResponseWindow
)
{
switch
(
msgB_ResponseWindow
)
{
case
NR_RACH_ConfigGenericTwoStepRA_r16__ext1__msgB_ResponseWindow_v1700_sl240
:
return
240
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__ext1__msgB_ResponseWindow_v1700_sl640
:
return
640
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__ext1__msgB_ResponseWindow_v1700_sl960
:
return
960
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__ext1__msgB_ResponseWindow_v1700_sl1280
:
return
1280
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__ext1__msgB_ResponseWindow_v1700_sl1920
:
return
1920
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__ext1__msgB_ResponseWindow_v1700_sl2560
:
return
2590
;
default:
AssertFatal
(
false
,
"illegal msgB_responseWindow value %ld
\n
"
,
msgB_ResponseWindow
);
break
;
}
return
0
;
}
static
int
nr_get_RA_window_2Step_v16
(
long
msgB_ResponseWindow
)
{
switch
(
msgB_ResponseWindow
)
{
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl1
:
return
1
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl2
:
return
2
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl4
:
return
4
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl8
:
return
8
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl10
:
return
10
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl20
:
return
20
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl40
:
return
40
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl80
:
return
80
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl160
:
return
160
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl320
:
return
360
;
break
;
default:
AssertFatal
(
false
,
"illegal msgB_responseWindow value %ld
\n
"
,
msgB_ResponseWindow
);
break
;
}
return
0
;
}
static
int
nr_get_RA_window_4Step_v16
(
long
ra_ResponseWindow
)
{
switch
(
ra_ResponseWindow
)
{
case
NR_RACH_ConfigGeneric__ext1__ra_ResponseWindow_v1610_sl60
:
return
60
;
case
NR_RACH_ConfigGeneric__ext1__ra_ResponseWindow_v1610_sl160
:
return
160
;
default:
AssertFatal
(
false
,
"illegal ra_ResponseWindow value %ld
\n
"
,
ra_ResponseWindow
);
}
return
0
;
}
static
int
nr_get_RA_window_4Step_v17
(
long
ra_ResponseWindow
)
{
switch
(
ra_ResponseWindow
)
{
case
NR_RACH_ConfigGeneric__ext2__ra_ResponseWindow_v1700_sl240
:
return
240
;
case
NR_RACH_ConfigGeneric__ext2__ra_ResponseWindow_v1700_sl320
:
return
320
;
case
NR_RACH_ConfigGeneric__ext2__ra_ResponseWindow_v1700_sl640
:
return
640
;
case
NR_RACH_ConfigGeneric__ext2__ra_ResponseWindow_v1700_sl960
:
return
960
;
case
NR_RACH_ConfigGeneric__ext2__ra_ResponseWindow_v1700_sl1280
:
return
1280
;
case
NR_RACH_ConfigGeneric__ext2__ra_ResponseWindow_v1700_sl1920
:
return
1920
;
case
NR_RACH_ConfigGeneric__ext2__ra_ResponseWindow_v1700_sl2560
:
return
2590
;
default:
AssertFatal
(
false
,
"illegal msgB_responseWindow value %ld
\n
"
,
ra_ResponseWindow
);
}
return
0
;
}
static
int
nr_get_RA_window_4Step
(
long
ra_ResponseWindow
)
{
switch
(
ra_ResponseWindow
)
{
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl1
:
return
1
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl2
:
return
2
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl4
:
return
4
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl8
:
return
8
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl10
:
return
10
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl20
:
return
20
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl40
:
return
40
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl80
:
return
80
;
break
;
default:
AssertFatal
(
false
,
"illegal ra_ResponseWindow value %ld
\n
"
,
ra_ResponseWindow
);
break
;
}
return
0
;
}
static
void
setup_ra_response_window
(
RA_config_t
*
ra
,
int
slots_per_frame
,
NR_NTN_Config_r17_t
*
ntn_Config_r17
,
NR_RACH_ConfigGeneric_t
*
configGeneric
,
NR_RACH_ConfigGenericTwoStepRA_r16_t
*
twostep
,
ntn_timing_advance_componets_t
*
ntn_ta
)
{
int
respwind_value
=
0
;
if
(
ra
->
ra_type
==
RA_2_STEP
)
{
long
*
msgB_ResponseWindow
=
twostep
->
msgB_ResponseWindow_r16
;
if
(
msgB_ResponseWindow
)
respwind_value
=
nr_get_RA_window_2Step_v16
(
*
msgB_ResponseWindow
);
if
(
twostep
->
ext1
&&
twostep
->
ext1
->
msgB_ResponseWindow_v1700
)
{
AssertFatal
(
msgB_ResponseWindow
==
NULL
,
"The network does not configure msgB-ResponseWindow-r16 simultaneously with msgB-ResponseWindow-v1700
\n
"
);
msgB_ResponseWindow
=
twostep
->
ext1
->
msgB_ResponseWindow_v1700
;
if
(
msgB_ResponseWindow
)
respwind_value
=
nr_get_RA_window_2Step_v17
(
*
msgB_ResponseWindow
);
}
// The network configures a value lower than or equal to 40ms
int
slots_40ms
=
4
*
slots_per_frame
;
AssertFatal
(
respwind_value
!=
0
&&
respwind_value
<=
slots_40ms
,
"Invalid MSGB response window value
\n
"
);
}
else
{
AssertFatal
(
ra
->
ra_type
==
RA_4_STEP
,
"Invalid RA type
\n
"
);
long
*
response_window
=
NULL
;
if
(
configGeneric
->
ext1
&&
configGeneric
->
ext1
->
ra_ResponseWindow_v1610
)
respwind_value
=
nr_get_RA_window_4Step_v16
(
*
configGeneric
->
ext1
->
ra_ResponseWindow_v1610
);
if
(
configGeneric
->
ext2
&&
configGeneric
->
ext2
->
ra_ResponseWindow_v1700
)
{
AssertFatal
(
response_window
==
NULL
,
"ra_ResponseWindow_v1610 and ra_ResponseWindow_v1700 are mutually exclusive
\n
"
);
respwind_value
=
nr_get_RA_window_4Step_v17
(
*
configGeneric
->
ext2
->
ra_ResponseWindow_v1700
);
}
if
(
!
response_window
)
respwind_value
=
nr_get_RA_window_4Step
(
configGeneric
->
ra_ResponseWindow
);
// The network configures a value lower than or equal to 10ms
AssertFatal
(
respwind_value
!=
0
&&
respwind_value
<=
slots_per_frame
,
"Invalid RAR response window value
\n
"
);
}
int
ta_Common_slots
=
0
;
if
(
ntn_Config_r17
)
{
const
double
ta_Common_ms
=
GET_COMPLETE_TIME_ADVANCE_MS
(
ntn_ta
);
ta_Common_slots
=
(
int
)
ceil
(
ta_Common_ms
*
slots_per_frame
/
10
);
}
nr_timer_setup
(
&
ra
->
response_window_timer
,
respwind_value
+
ta_Common_slots
,
1
);
}
// Random Access procedure initialization as per 5.1.1 and initialization of variables specific
// to Random Access type as specified in clause 5.1.1a (3GPP TS 38.321 version 16.2.1 Release 16)
bool
init_RA
(
NR_UE_MAC_INST_t
*
mac
,
int
frame
)
...
...
@@ -704,8 +887,6 @@ bool init_RA(NR_UE_MAC_INST_t *mac, int frame)
prach_resources
->
preamble_tx_counter
=
1
;
// set the PREAMBLE_POWER_RAMPING_COUNTER to 1
prach_resources
->
preamble_power_ramping_cnt
=
1
;
// set the PREAMBLE_BACKOFF to 0 ms TODO to be set as a timer?
prach_resources
->
preamble_backoff
=
0
;
// set POWER_OFFSET_2STEP_RA to 0 dB
prach_resources
->
power_offset_2step
=
0
;
...
...
@@ -826,7 +1007,7 @@ bool init_RA(NR_UE_MAC_INST_t *mac, int frame)
else
prach_resources
->
preamble_power_ramping_step
=
rach_ConfigGeneric
->
powerRampingStep
<<
1
;
prach_resources
->
scaling_factor_bi
=
1
;
ra
->
scaling_factor_bi
=
1
;
if
(
ra
->
ra_type
==
RA_2_STEP
&&
twostep_generic
&&
twostep_generic
->
msgA_PreambleReceivedTargetPower_r16
)
ra
->
preambleReceivedTargetPower_config
=
*
twostep_generic
->
msgA_PreambleReceivedTargetPower_r16
;
...
...
@@ -863,9 +1044,6 @@ bool init_RA(NR_UE_MAC_INST_t *mac, int frame)
else
ra
->
msg3_deltaPreamble
=
mac
->
current_UL_BWP
->
msg3_DeltaPreamble
?
*
mac
->
current_UL_BWP
->
msg3_DeltaPreamble
<<
1
:
0
;
ra
->
RA_RAPID_found
=
0
;
ra
->
RA_backoff_cnt
=
0
;
ra
->
RA_window_cnt
=
-
1
;
ra
->
new_ssb
=
false
;
if
(
ra
->
ra_type
==
RA_2_STEP
&&
twostep_generic
&&
twostep_generic
->
msgA_PRACH_ConfigurationIndex_r16
)
...
...
@@ -882,18 +1060,16 @@ bool init_RA(NR_UE_MAC_INST_t *mac, int frame)
else
ra
->
num_fd_occasions
=
1
<<
rach_ConfigGeneric
->
msg1_FDM
;
setup_ra_response_window
(
ra
,
mac
->
frame_structure
.
numb_slots_frame
,
mac
->
sc_info
.
ntn_Config_r17
,
rach_ConfigGeneric
,
twostep_generic
,
&
mac
->
ntn_ta
);
ra
->
start_response_window
=
false
;
return
true
;
}
static
void
nr_get_prach_resources
(
NR_UE_MAC_INST_t
*
mac
,
NR_PRACH_RESOURCES_t
*
prach_resources
)
{
const
int
ul_mu
=
mac
->
current_UL_BWP
->
scs
;
const
int
mu
=
nr_get_prach_or_ul_mu
(
mac
->
current_UL_BWP
->
msgA_ConfigCommon_r16
,
mac
->
current_UL_BWP
->
rach_ConfigCommon
,
ul_mu
);
if
(
prach_resources
->
preamble_tx_counter
>
1
)
prach_resources
->
preamble_power_ramping_cnt
++
;
prach_resources
->
ra_preamble_rx_target_power
=
get_ra_preamble_rx_target_power
(
&
mac
->
ra
,
mu
);
}
void
nr_Msg3_transmitted
(
NR_UE_MAC_INST_t
*
mac
,
uint8_t
CC_id
,
frame_t
frameP
,
slot_t
slotP
,
uint8_t
gNB_id
)
{
RA_config_t
*
ra
=
&
mac
->
ra
;
...
...
@@ -1012,48 +1188,15 @@ void nr_ue_manage_ra_procedure(NR_UE_MAC_INST_t *mac, int CC_id, frame_t frame,
LOG_D
(
NR_MAC
,
"[UE %d][%d.%d]: ra_state %d, RA_active %d
\n
"
,
mac
->
ue_id
,
frame
,
nr_slot_tx
,
ra
->
ra_state
,
ra
->
RA_active
);
if
(
ra
->
ra_state
<
nrRA_SUCCEEDED
)
{
if
(
ra
->
RA_window_cnt
!=
-
1
)
{
// RACH is active
LOG_D
(
MAC
,
"[%d.%d] RA is active: RA window count %d, RA backoff count %d
\n
"
,
frame
,
nr_slot_tx
,
ra
->
RA_window_cnt
,
ra
->
RA_backoff_cnt
);
if
(
ra
->
RA_BI_found
){
prach_resources
->
preamble_backoff
=
prach_resources
->
scaling_factor_bi
*
ra
->
RA_backoff_indicator
;
}
else
{
prach_resources
->
preamble_backoff
=
0
;
}
if
(
ra
->
RA_window_cnt
>=
0
&&
ra
->
RA_RAPID_found
==
1
)
{
if
(
ra
->
cfra
)
{
// Reset RA_active flag: it disables Msg3 retransmission (8.3 of TS 38.213)
nr_ra_succeeded
(
mac
,
gNB_id
,
frame
,
nr_slot_tx
);
}
}
else
if
(
ra
->
RA_window_cnt
==
0
&&
!
ra
->
RA_RAPID_found
&&
ra
->
ra_state
!=
nrRA_WAIT_MSGB
)
{
LOG_W
(
MAC
,
"[UE %d][%d:%d] RAR reception failed
\n
"
,
mac
->
ue_id
,
frame
,
nr_slot_tx
);
nr_ra_failed
(
mac
,
CC_id
,
prach_resources
,
frame
,
nr_slot_tx
);
}
else
if
(
ra
->
RA_window_cnt
>
0
)
{
LOG_D
(
MAC
,
"[UE %d][%d.%d]: RAR not received yet (RA window count %d)
\n
"
,
mac
->
ue_id
,
frame
,
nr_slot_tx
,
ra
->
RA_window_cnt
);
// Fill in preamble and PRACH resources
ra
->
RA_window_cnt
--
;
if
(
ra
->
ra_state
==
nrRA_GENERATE_PREAMBLE
)
{
nr_get_prach_resources
(
mac
,
prach_resources
);
}
}
else
if
(
ra
->
RA_backoff_cnt
>
0
)
{
LOG_D
(
MAC
,
"[UE %d][%d.%d]: RAR not received yet (RA backoff count %d)
\n
"
,
mac
->
ue_id
,
frame
,
nr_slot_tx
,
ra
->
RA_backoff_cnt
);
ra
->
RA_backoff_cnt
--
;
if
((
ra
->
RA_backoff_cnt
>
0
&&
ra
->
ra_state
==
nrRA_GENERATE_PREAMBLE
)
||
ra
->
RA_backoff_cnt
==
0
)
{
nr_get_prach_resources
(
mac
,
prach_resources
);
}
}
if
(
nr_timer_is_active
(
&
ra
->
RA_backoff_timer
))
{
// if the criteria (as defined in clause 5.1.2) to select contention-free Random Access Resources
// is met during the backoff time
// TODO verify what does this mean
if
(
ra
->
cfra
)
{
// perform the Random Access Resource selection procedure
nr_timer_stop
(
&
ra
->
RA_backoff_timer
);
mac
->
ra
.
ra_state
=
nrRA_GENERATE_PREAMBLE
;
ra_resource_selection
(
mac
);
}
}
...
...
@@ -1062,102 +1205,6 @@ void nr_ue_manage_ra_procedure(NR_UE_MAC_INST_t *mac, int CC_id, frame_t frame,
}
}
int16_t
nr_get_RA_window_2Step
(
const
NR_MsgA_ConfigCommon_r16_t
*
msgA_ConfigCommon_r16
)
{
int16_t
ra_ResponseWindow
=
*
msgA_ConfigCommon_r16
->
rach_ConfigCommonTwoStepRA_r16
.
rach_ConfigGenericTwoStepRA_r16
.
msgB_ResponseWindow_r16
;
switch
(
ra_ResponseWindow
)
{
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl1
:
return
1
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl2
:
return
2
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl4
:
return
4
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl8
:
return
8
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl10
:
return
10
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl20
:
return
20
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl40
:
return
40
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl80
:
return
80
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl160
:
return
160
;
break
;
case
NR_RACH_ConfigGenericTwoStepRA_r16__msgB_ResponseWindow_r16_sl320
:
return
360
;
break
;
default:
AssertFatal
(
false
,
"illegal msgB_responseWindow value %d
\n
"
,
ra_ResponseWindow
);
break
;
}
return
0
;
}
int16_t
nr_get_RA_window_4Step
(
const
NR_RACH_ConfigCommon_t
*
rach_ConfigCommon
)
{
int16_t
ra_ResponseWindow
=
rach_ConfigCommon
->
rach_ConfigGeneric
.
ra_ResponseWindow
;
switch
(
ra_ResponseWindow
)
{
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl1
:
return
1
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl2
:
return
2
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl4
:
return
4
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl8
:
return
8
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl10
:
return
10
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl20
:
return
20
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl40
:
return
40
;
break
;
case
NR_RACH_ConfigGeneric__ra_ResponseWindow_sl80
:
return
80
;
break
;
default:
AssertFatal
(
false
,
"illegal ra_ResponseWindow value %d
\n
"
,
ra_ResponseWindow
);
break
;
}
return
0
;
}
void
nr_get_RA_window
(
NR_UE_MAC_INST_t
*
mac
)
{
RA_config_t
*
ra
=
&
mac
->
ra
;
NR_RACH_ConfigCommon_t
*
setup
=
mac
->
current_UL_BWP
->
rach_ConfigCommon
;
AssertFatal
(
&
setup
->
rach_ConfigGeneric
!=
NULL
,
"In %s: FATAL! rach_ConfigGeneric is NULL...
\n
"
,
__FUNCTION__
);
const
double
ta_Common_ms
=
GET_COMPLETE_TIME_ADVANCE_MS
(
&
mac
->
ntn_ta
);
int
slots_per_frame
=
mac
->
frame_structure
.
numb_slots_frame
;
const
int
slots_per_ms
=
slots_per_frame
/
10
;
const
int
ra_Offset_slots
=
ra
->
RA_offset
*
slots_per_frame
;
const
int
ta_Common_slots
=
(
int
)
ceil
(
ta_Common_ms
*
slots_per_ms
);
ra
->
RA_window_cnt
=
ra_Offset_slots
+
ta_Common_slots
;
// taking into account the 2 frames gap introduced by OAI gNB
ra
->
RA_window_cnt
+=
ra
->
ra_type
==
RA_2_STEP
?
nr_get_RA_window_2Step
(
mac
->
current_UL_BWP
->
msgA_ConfigCommon_r16
)
:
nr_get_RA_window_4Step
(
mac
->
current_UL_BWP
->
rach_ConfigCommon
);
}
////////////////////////////////////////////////////////////////////////////
/////////* Random Access Contention Resolution (5.1.35 TS 38.321) */////////
////////////////////////////////////////////////////////////////////////////
...
...
@@ -1188,7 +1235,6 @@ void nr_ra_succeeded(NR_UE_MAC_INST_t *mac, const uint8_t gNB_index, const frame
if
(
ra
->
cfra
)
{
LOG_I
(
MAC
,
"[UE %d][%d.%d][RAPROC] RA procedure succeeded. CFRA: RAR successfully received.
\n
"
,
mac
->
ue_id
,
frame
,
slot
);
ra
->
RA_window_cnt
=
-
1
;
}
else
if
(
ra
->
ra_type
==
RA_2_STEP
)
{
LOG_A
(
MAC
,
"[UE %d][%d.%d][RAPROC] 2-Step RA procedure succeeded. CBRA: Contention Resolution is successful.
\n
"
,
...
...
@@ -1210,7 +1256,6 @@ void nr_ra_succeeded(NR_UE_MAC_INST_t *mac, const uint8_t gNB_index, const frame
LOG_D
(
MAC
,
"[UE %d][%d.%d] CBRA: cleared contention resolution timer...
\n
"
,
mac
->
ue_id
,
frame
,
slot
);
}
LOG_D
(
MAC
,
"[UE %d] clearing RA_active flag...
\n
"
,
mac
->
ue_id
);
ra
->
RA_active
=
false
;
ra
->
msg3_C_RNTI
=
false
;
ra
->
ra_state
=
nrRA_SUCCEEDED
;
...
...
@@ -1219,6 +1264,35 @@ void nr_ra_succeeded(NR_UE_MAC_INST_t *mac, const uint8_t gNB_index, const frame
nr_mac_rrc_ra_ind
(
mac
->
ue_id
,
frame
,
true
);
}
void
nr_rar_not_successful
(
NR_UE_MAC_INST_t
*
mac
)
{
LOG_W
(
MAC
,
"[UE %d] RAR reception failed
\n
"
,
mac
->
ue_id
);
RA_config_t
*
ra
=
&
mac
->
ra
;
NR_PRACH_RESOURCES_t
*
prach_resources
=
&
ra
->
prach_resources
;
prach_resources
->
preamble_tx_counter
++
;
bool
ra_completed
=
false
;
if
(
prach_resources
->
preamble_tx_counter
==
ra
->
preambleTransMax
+
1
)
{
// if the Random Access Preamble is transmitted on the SpCell
// TODO to be verified, this means SA if I'm not mistaken
if
(
IS_SA_MODE
(
get_softmodem_params
()))
{
// TODO indicate a Random Access problem to upper layers
}
else
{
// if the Random Access Preamble is transmitted on an SCell:
// consider the Random Access procedure unsuccessfully completed.
ra_completed
=
true
;
ra
->
ra_state
=
nrRA_UE_IDLE
;
}
}
if
(
!
ra_completed
)
{
// select a random backoff time according to a uniform distribution
// between 0 and the PREAMBLE_BACKOFF
uint32_t
seed
=
(
unsigned
int
)(
rdtsc_oai
()
&
~
0
);
uint32_t
random_backoff
=
rand_r
(
&
seed
)
%
ra
->
RA_backoff_limit
;
// in slots
nr_timer_setup
(
&
ra
->
RA_backoff_timer
,
random_backoff
,
1
);
nr_timer_start
(
&
ra
->
RA_backoff_timer
);
}
}
// Handling failure of RA procedure @ MAC layer
// according to section 5 of 3GPP TS 38.321 version 16.2.1 Release 16
// todo:
...
...
@@ -1226,17 +1300,6 @@ void nr_ra_succeeded(NR_UE_MAC_INST_t *mac, const uint8_t gNB_index, const frame
void
nr_ra_failed
(
NR_UE_MAC_INST_t
*
mac
,
uint8_t
CC_id
,
NR_PRACH_RESOURCES_t
*
prach_resources
,
frame_t
frame
,
int
slot
)
{
RA_config_t
*
ra
=
&
mac
->
ra
;
// Random seed generation
unsigned
int
seed
;
if
(
IS_SOFTMODEM_IQPLAYER
||
IS_SOFTMODEM_IQRECORDER
)
{
// Overwrite seed with non-random seed for IQ player/recorder
seed
=
1
;
}
else
{
// & to truncate the int64_t and keep only the LSB bits, up to sizeof(int)
seed
=
(
unsigned
int
)(
rdtsc_oai
()
&
~
0
);
}
ra
->
ra_PreambleIndex
=
-
1
;
ra
->
ra_state
=
nrRA_UE_IDLE
;
...
...
@@ -1255,13 +1318,10 @@ void nr_ra_failed(NR_UE_MAC_INST_t *mac, uint8_t CC_id, NR_PRACH_RESOURCES_t *pr
slot
,
ra
->
preambleTransMax
);
ra
->
RA_backoff_cnt
=
rand_r
(
&
seed
)
%
(
prach_resources
->
preamble_backoff
+
1
);
prach_resources
->
preamble_tx_counter
=
1
;
prach_resources
->
preamble_power_ramping_step
+=
2
;
// 2 dB increment
prach_resources
->
ra_preamble_rx_target_power
=
get_ra_preamble_rx_target_power
(
ra
,
mac
->
current_UL_BWP
->
scs
);
}
else
{
nr_get_RA_window
(
mac
);
}
}
...
...
openair2/LAYER2/NR_MAC_UE/nr_ue_dci_configuration.c
View file @
cc154da5
...
...
@@ -563,6 +563,12 @@ void ue_dci_configuration(NR_UE_MAC_INST_t *mac, fapi_nr_dl_config_request_t *dl
if
(
mac
->
state
==
UE_PERFORMING_RA
&&
mac
->
ra
.
ra_state
>=
nrRA_WAIT_RAR
)
{
// if RA is ongoing use RA search space
if
(
is_ss_monitor_occasion
(
frame
,
slot
,
slots_per_frame
,
pdcch_config
->
ra_SS
))
{
// The RA response window starts at the first symbol of the earliest CORESET
// the UE is configured to receive PDCCH for Type1-PDCCH CSS set
if
(
mac
->
ra
.
start_response_window
)
{
nr_timer_start
(
&
mac
->
ra
.
response_window_timer
);
mac
->
ra
.
start_response_window
=
false
;
}
nr_rnti_type_t
rnti_type
=
0
;
if
(
mac
->
ra
.
ra_type
==
RA_4_STEP
)
{
rnti_type
=
mac
->
ra
.
ra_state
==
nrRA_WAIT_RAR
?
TYPE_RA_RNTI_
:
TYPE_TC_RNTI_
;
...
...
openair2/LAYER2/NR_MAC_UE/nr_ue_power_procedures.c
View file @
cc154da5
...
...
@@ -492,9 +492,7 @@ int get_pusch_tx_power_ue(NR_UE_MAC_INST_t *mac,
if
(
current_UL_BWP
->
msg3_DeltaPreamble
)
{
DELTA_PREAMBLE_MSG3
=
*
current_UL_BWP
->
msg3_DeltaPreamble
;
}
NR_RACH_ConfigCommon_t
*
nr_rach_ConfigCommon
=
current_UL_BWP
->
rach_ConfigCommon
;
long
preambleReceivedTargetPower
=
nr_rach_ConfigCommon
->
rach_ConfigGeneric
.
preambleReceivedTargetPower
;
int
P_O_PRE
=
preambleReceivedTargetPower
;
int
P_O_PRE
=
mac
->
ra
.
prach_resources
.
ra_preamble_rx_target_power
;
P_O_NOMINAL_PUSCH
=
P_O_PRE
+
DELTA_PREAMBLE_MSG3
;
if
(
has_pusch_power_control_config
&&
pusch_Config
->
pusch_PowerControl
->
msg3_Alpha
)
{
...
...
openair2/LAYER2/NR_MAC_UE/nr_ue_procedures.c
View file @
cc154da5
...
...
@@ -59,6 +59,25 @@
// #define DEBUG_MIB
// #define ENABLE_MAC_PAYLOAD_DEBUG 1
// #define DEBUG_RAR
// table 7.2-1 TS 38.321
const
uint16_t
table_7_2_1
[
16
]
=
{
5
,
// row index 0
10
,
// row index 1
20
,
// row index 2
30
,
// row index 3
40
,
// row index 4
60
,
// row index 5
80
,
// row index 6
120
,
// row index 7
160
,
// row index 8
240
,
// row index 9
320
,
// row index 10
480
,
// row index 11
960
,
// row index 12
1920
,
// row index 13
};
/* TS 36.213 Table 9.2.3-3: Mapping of values for one HARQ-ACK bit to sequences */
static
const
int
sequence_cyclic_shift_1_harq_ack_bit
[
2
]
/* HARQ-ACK Value 0 1 */
...
...
@@ -701,7 +720,7 @@ static int nr_ue_process_dci_dl_10(NR_UE_MAC_INST_t *mac,
dlsch_pdu
->
SubcarrierSpacing
=
mac
->
mib
->
subCarrierSpacingCommon
+
2
;
}
else
{
dlsch_pdu
->
SubcarrierSpacing
=
current_DL_BWP
->
scs
;
if
(
mac
->
ra
.
RA_window_cnt
>=
0
&&
rnti_type
==
TYPE_RA_RNTI_
)
{
if
(
nr_timer_is_active
(
&
mac
->
ra
.
response_window_timer
)
&&
rnti_type
==
TYPE_RA_RNTI_
)
{
dl_conf_req
->
pdu_type
=
FAPI_NR_DL_CONFIG_TYPE_RA_DLSCH
;
}
else
{
dl_conf_req
->
pdu_type
=
FAPI_NR_DL_CONFIG_TYPE_DLSCH
;
...
...
@@ -3414,11 +3433,11 @@ static bool check_ra_contention_resolution(const uint8_t *pdu, const uint8_t *co
}
static
int
nr_ue_validate_successrar
(
uint8_t
*
pduP
,
int32_t
pdu_len
,
NR_UE_MAC_INST_t
*
mac
,
uint8_t
gNB_index
,
frame_t
frameP
,
int
slot
)
int32_t
pdu_len
,
NR_UE_MAC_INST_t
*
mac
,
uint8_t
gNB_index
,
frame_t
frameP
,
int
slot
)
{
// TS 38.321 - Figure 6.1.5a-1: BI MAC subheader
// TS 38.321 - Figure 6.1.5a-3: SuccessRAR MAC subheader
...
...
@@ -3426,6 +3445,7 @@ static int nr_ue_validate_successrar(uint8_t *pduP,
uint8_t
E
=
1
;
uint8_t
cont_res_id
[
6
];
RA_config_t
*
ra
=
&
mac
->
ra
;
ra
->
RA_backoff_limit
=
0
;
while
(
n
<
pdu_len
&&
E
)
{
E
=
(
pduP
[
n
]
>>
7
)
&
0x1
;
...
...
@@ -3433,7 +3453,9 @@ static int nr_ue_validate_successrar(uint8_t *pduP,
if
(
SUCESS_RAR_header_T1
==
0
)
{
// T2 exist
int
SUCESS_RAR_header_T2
=
(
pduP
[
n
]
>>
5
)
&
0x1
;
if
(
SUCESS_RAR_header_T2
==
0
)
{
// BI
ra
->
RA_backoff_indicator
=
pduP
[
n
]
&
0x0F
;
int
bi_ms
=
table_7_2_1
[(
pduP
[
n
]
&
0x0F
)]
*
ra
->
scaling_factor_bi
;
int
slots_per_ms
=
mac
->
frame_structure
.
numb_slots_frame
/
10
;
ra
->
RA_backoff_limit
=
bi_ms
*
slots_per_ms
;
n
++
;
}
else
{
// S
n
++
;
...
...
@@ -3476,6 +3498,7 @@ static int nr_ue_validate_successrar(uint8_t *pduP,
bool
ra_success
=
check_ra_contention_resolution
(
cont_res_id
,
ra
->
cont_res_id
);
if
(
ra
->
RA_active
&&
ra_success
)
{
nr_timer_stop
(
&
ra
->
response_window_timer
);
nr_ra_succeeded
(
mac
,
gNB_index
,
frameP
,
slot
);
}
else
if
(
!
ra_success
)
{
// nr_ra_failed(mac, CC_id, &ra->prach_resources, frameP, slot);
...
...
@@ -3841,6 +3864,115 @@ int nr_write_ce_ulsch_pdu(uint8_t *mac_ce,
return
mac_ce
-
pdu
;
}
static
void
handle_rar_reception
(
NR_UE_MAC_INST_t
*
mac
,
nr_downlink_indication_t
*
dlinfo
,
NR_MAC_RAR
*
rar
,
frame_t
frame
,
int
slot
)
{
RAR_grant_t
rar_grant
;
RA_config_t
*
ra
=
&
mac
->
ra
;
#ifdef DEBUG_RAR
// CSI
unsigned
char
csi_req
=
(
unsigned
char
)(
rar
->
UL_GRANT_4
&
0x01
);
#endif
// TPC
unsigned
char
tpc_command
=
(
unsigned
char
)((
rar
->
UL_GRANT_4
>>
1
)
&
0x07
);
ra
->
Msg3_TPC
=
(
tpc_command
<<
1
)
-
6
;
// MCS
rar_grant
.
mcs
=
(
unsigned
char
)(
rar
->
UL_GRANT_4
>>
4
);
// time alloc
rar_grant
.
Msg3_t_alloc
=
(
unsigned
char
)(
rar
->
UL_GRANT_3
&
0x0f
);
// frequency alloc
rar_grant
.
Msg3_f_alloc
=
(
uint16_t
)((
rar
->
UL_GRANT_3
>>
4
)
|
(
rar
->
UL_GRANT_2
<<
4
)
|
((
rar
->
UL_GRANT_1
&
0x03
)
<<
12
));
// frequency hopping
rar_grant
.
freq_hopping
=
(
unsigned
char
)(
rar
->
UL_GRANT_1
>>
2
);
// Schedule Msg3
const
NR_UE_UL_BWP_t
*
current_UL_BWP
=
mac
->
current_UL_BWP
;
const
NR_UE_DL_BWP_t
*
current_DL_BWP
=
mac
->
current_DL_BWP
;
const
NR_BWP_PDCCH_t
*
pdcch_config
=
&
mac
->
config_BWP_PDCCH
[
current_DL_BWP
->
bwp_id
];
NR_tda_info_t
tda_info
=
get_ul_tda_info
(
current_UL_BWP
,
*
pdcch_config
->
ra_SS
->
controlResourceSetId
,
pdcch_config
->
ra_SS
->
searchSpaceType
->
present
,
TYPE_RA_RNTI_
,
rar_grant
.
Msg3_t_alloc
);
if
(
!
tda_info
.
valid_tda
||
tda_info
.
nrOfSymbols
==
0
)
{
LOG_E
(
MAC
,
"Cannot schedule Msg3. Something wrong in TDA information
\n
"
);
return
;
}
frame_t
frame_tx
=
0
;
int
slot_tx
=
0
;
const
int
ntn_ue_koffset
=
GET_NTN_UE_K_OFFSET
(
&
mac
->
ntn_ta
,
mac
->
current_UL_BWP
->
scs
);
int
ret
=
nr_ue_pusch_scheduler
(
mac
,
1
,
frame
,
slot
,
&
frame_tx
,
&
slot_tx
,
tda_info
.
k2
+
ntn_ue_koffset
);
// TA command
// if the timeAlignmentTimer associated with this TAG is not running
if
(
!
nr_timer_is_active
(
&
mac
->
time_alignment_timer
))
{
const
int
ta
=
rar
->
TA2
+
(
rar
->
TA1
<<
5
);
set_time_alignment
(
mac
,
ta
,
rar_ta
,
frame_tx
,
slot_tx
);
LOG_W
(
MAC
,
"received TA command %d
\n
"
,
31
+
ta
);
}
// else ignore the received Timing Advance Command
#ifdef DEBUG_RAR
LOG_I
(
NR_MAC
,
"rarh->E = 0x%x
\n
"
,
rarh
->
E
);
LOG_I
(
NR_MAC
,
"rarh->T = 0x%x
\n
"
,
rarh
->
T
);
LOG_I
(
NR_MAC
,
"rarh->RAPID = 0x%x (%i)
\n
"
,
rarh
->
RAPID
,
rarh
->
RAPID
);
LOG_I
(
NR_MAC
,
"rar->R = 0x%x
\n
"
,
rar
->
R
);
LOG_I
(
NR_MAC
,
"rar->TA1 = 0x%x
\n
"
,
rar
->
TA1
);
LOG_I
(
NR_MAC
,
"rar->TA2 = 0x%x
\n
"
,
rar
->
TA2
);
LOG_I
(
NR_MAC
,
"rar->UL_GRANT_1 = 0x%x
\n
"
,
rar
->
UL_GRANT_1
);
LOG_I
(
NR_MAC
,
"rar->UL_GRANT_2 = 0x%x
\n
"
,
rar
->
UL_GRANT_2
);
LOG_I
(
NR_MAC
,
"rar->UL_GRANT_3 = 0x%x
\n
"
,
rar
->
UL_GRANT_3
);
LOG_I
(
NR_MAC
,
"rar->UL_GRANT_4 = 0x%x
\n
"
,
rar
->
UL_GRANT_4
);
LOG_I
(
NR_MAC
,
"rar->TCRNTI_1 = 0x%x
\n
"
,
rar
->
TCRNTI_1
);
LOG_I
(
NR_MAC
,
"rar->TCRNTI_2 = 0x%x
\n
"
,
rar
->
TCRNTI_2
);
LOG_I
(
NR_MAC
,
"[%d.%d]: [UE %d] Received RAR with t_alloc %d f_alloc %d ta_command %d mcs %d freq_hopping %d tpc_command %d
\n
"
,
frame
,
slot
,
mac
->
ue_id
,
rar_grant
.
Msg3_t_alloc
,
rar_grant
.
Msg3_f_alloc
,
ta_command
,
rar_grant
.
mcs
,
rar_grant
.
freq_hopping
,
tpc_command
);
#endif
if
(
ret
!=
-
1
)
{
uint16_t
rnti
=
mac
->
crnti
;
// Upon successful reception, set the T-CRNTI to the RAR value
// if the RA preamble is selected among the contention-based RA Preambles
if
(
!
ra
->
cfra
)
{
ra
->
t_crnti
=
rar
->
TCRNTI_2
+
(
rar
->
TCRNTI_1
<<
8
);
rnti
=
ra
->
t_crnti
;
if
(
!
ra
->
msg3_C_RNTI
)
nr_mac_rrc_msg3_ind
(
mac
->
ue_id
,
rnti
,
dlinfo
->
gNB_index
);
}
fapi_nr_ul_config_request_pdu_t
*
pdu
=
lockGet_ul_config
(
mac
,
frame_tx
,
slot_tx
,
FAPI_NR_UL_CONFIG_TYPE_PUSCH
);
if
(
!
pdu
)
return
;
// Config Msg3 PDU
int
ret
=
nr_config_pusch_pdu
(
mac
,
&
tda_info
,
&
pdu
->
pusch_config_pdu
,
NULL
,
NULL
,
&
rar_grant
,
rnti
,
NR_SearchSpace__searchSpaceType_PR_common
,
NR_DCI_NONE
);
if
(
ret
!=
0
)
remove_ul_config_last_item
(
pdu
);
release_ul_config
(
pdu
,
false
);
}
}
/////////////////////////////////////
// Random Access Response PDU //
// TS 38.213 ch 8.2 //
...
...
@@ -3885,13 +4017,10 @@ static void nr_ue_process_rar(NR_UE_MAC_INST_t *mac, nr_downlink_indication_t *d
}
RA_config_t
*
ra
=
&
mac
->
ra
;
ra
->
t_crnti
=
0
;
uint8_t
n_subPDUs
=
0
;
// number of RAR payloads
uint8_t
n_subheaders
=
0
;
// number of MAC RAR subheaders
uint8_t
*
dlsch_buffer
=
dl_info
->
rx_ind
->
rx_indication_body
[
pdu_id
].
pdsch_pdu
.
pdu
;
uint8_t
is_Msg3
=
1
;
frame_t
frame_tx
=
0
;
int
slot_tx
=
0
;
int
ret
=
0
;
NR_RA_HEADER_RAPID
*
rarh
=
(
NR_RA_HEADER_RAPID
*
)
dlsch_buffer
;
// RAR subheader pointer
NR_MAC_RAR
*
rar
=
(
NR_MAC_RAR
*
)
(
dlsch_buffer
+
1
);
// RAR subPDU pointer
uint8_t
preamble_index
=
ra
->
ra_PreambleIndex
;
...
...
@@ -3900,7 +4029,8 @@ static void nr_ue_process_rar(NR_UE_MAC_INST_t *mac, nr_downlink_indication_t *d
T
(
T_NRUE_MAC_DL_RAR_PDU_WITH_DATA
,
T_INT
(
rnti
),
T_INT
(
frame
),
T_INT
(
slot
),
T_BUFFER
(
dlsch_buffer
,
dl_info
->
rx_ind
->
rx_indication_body
[
pdu_id
].
pdsch_pdu
.
pdu_length
));
LOG_D
(
NR_MAC
,
"[%d.%d]: [UE %d][RAPROC] invoking MAC for received RAR (current preamble %d)
\n
"
,
frame
,
slot
,
mac
->
ue_id
,
preamble_index
);
ra
->
RA_backoff_limit
=
0
;
LOG_D
(
NR_MAC
,
"[%d.%d]: [UE %d][RAPROC] MAC received RAR (current preamble %d)
\n
"
,
frame
,
slot
,
mac
->
ue_id
,
preamble_index
);
while
(
1
)
{
n_subheaders
++
;
...
...
@@ -3908,10 +4038,11 @@ static void nr_ue_process_rar(NR_UE_MAC_INST_t *mac, nr_downlink_indication_t *d
n_subPDUs
++
;
LOG_I
(
NR_MAC
,
"[UE %d][RAPROC][RA-RNTI %04x] Got RAPID RAR subPDU
\n
"
,
mac
->
ue_id
,
rnti
);
}
else
{
ra
->
RA_backoff_indicator
=
get_backoff_indicator
(((
NR_RA_HEADER_BI
*
)
rarh
)
->
BI
);
ra
->
RA_BI_found
=
1
;
LOG_I
(
NR_MAC
,
"[UE %d][RAPROC][RA-RNTI %04x] Got BI RAR subPDU %d ms
\n
"
,
mac
->
ue_id
,
ra
->
RA_backoff_indicator
,
rnti
);
if
(
((
NR_RA_HEADER_BI
*
)
rarh
)
->
E
==
1
)
{
int
bi_ms
=
table_7_2_1
[((
NR_RA_HEADER_BI
*
)
rarh
)
->
BI
]
*
ra
->
scaling_factor_bi
;
int
slots_per_ms
=
mac
->
frame_structure
.
numb_slots_frame
/
10
;
ra
->
RA_backoff_limit
=
bi_ms
*
slots_per_ms
;
LOG_I
(
NR_MAC
,
"[UE %d][RAPROC][RA-RNTI %04x] Got BI RAR subPDU %d ms
\n
"
,
mac
->
ue_id
,
rnti
,
bi_ms
);
if
(((
NR_RA_HEADER_BI
*
)
rarh
)
->
E
==
1
)
{
rarh
+=
sizeof
(
NR_RA_HEADER_BI
);
continue
;
}
else
{
...
...
@@ -3919,9 +4050,15 @@ static void nr_ue_process_rar(NR_UE_MAC_INST_t *mac, nr_downlink_indication_t *d
}
}
if
(
rarh
->
RAPID
==
preamble_index
)
{
// The MAC entity may stop ra-ResponseWindow (and hence monitoring for Random Access Response(s)) after
// successful reception of a Random Access Response containing Random Access Preamble identifiers
// that matches the transmitted PREAMBLE_INDEX.
nr_timer_stop
(
&
ra
->
response_window_timer
);
LOG_A
(
NR_MAC
,
"[UE %d][RAPROC][%d.%d] Found RAR with the intended RAPID %d
\n
"
,
mac
->
ue_id
,
frame
,
slot
,
rarh
->
RAPID
);
rar
=
(
NR_MAC_RAR
*
)
(
dlsch_buffer
+
n_subheaders
+
(
n_subPDUs
-
1
)
*
sizeof
(
NR_MAC_RAR
));
ra
->
RA_RAPID_found
=
1
;
handle_rar_reception
(
mac
,
dl_info
,
rar
,
frame
,
slot
);
if
(
ra
->
cfra
)
nr_ra_succeeded
(
mac
,
dl_info
->
gNB_index
,
frame
,
slot
);
if
(
get_softmodem_params
()
->
emulate_l1
)
{
/* When we are emulating L1 with multiple UEs, the rx_indication will have
multiple RAR PDUs. The code would previously handle each of these PDUs,
...
...
@@ -3971,142 +4108,6 @@ static void nr_ue_process_rar(NR_UE_MAC_INST_t *mac, nr_downlink_indication_t *d
rarh
->
RAPID
,
preamble_index
);
#endif
if
(
ra
->
RA_RAPID_found
)
{
RAR_grant_t
rar_grant
;
#ifdef DEBUG_RAR
// CSI
unsigned
char
csi_req
=
(
unsigned
char
)
(
rar
->
UL_GRANT_4
&
0x01
);
#endif
// TPC
unsigned
char
tpc_command
=
(
unsigned
char
)
((
rar
->
UL_GRANT_4
>>
1
)
&
0x07
);
switch
(
tpc_command
){
case
0
:
ra
->
Msg3_TPC
=
-
6
;
break
;
case
1
:
ra
->
Msg3_TPC
=
-
4
;
break
;
case
2
:
ra
->
Msg3_TPC
=
-
2
;
break
;
case
3
:
ra
->
Msg3_TPC
=
0
;
break
;
case
4
:
ra
->
Msg3_TPC
=
2
;
break
;
case
5
:
ra
->
Msg3_TPC
=
4
;
break
;
case
6
:
ra
->
Msg3_TPC
=
6
;
break
;
case
7
:
ra
->
Msg3_TPC
=
8
;
break
;
default:
LOG_E
(
NR_PHY
,
"RAR impossible msg3 TPC
\n
"
);
}
// MCS
rar_grant
.
mcs
=
(
unsigned
char
)
(
rar
->
UL_GRANT_4
>>
4
);
// time alloc
rar_grant
.
Msg3_t_alloc
=
(
unsigned
char
)
(
rar
->
UL_GRANT_3
&
0x0f
);
// frequency alloc
rar_grant
.
Msg3_f_alloc
=
(
uint16_t
)
((
rar
->
UL_GRANT_3
>>
4
)
|
(
rar
->
UL_GRANT_2
<<
4
)
|
((
rar
->
UL_GRANT_1
&
0x03
)
<<
12
));
// frequency hopping
rar_grant
.
freq_hopping
=
(
unsigned
char
)
(
rar
->
UL_GRANT_1
>>
2
);
// Schedule Msg3
const
NR_UE_UL_BWP_t
*
current_UL_BWP
=
mac
->
current_UL_BWP
;
const
NR_UE_DL_BWP_t
*
current_DL_BWP
=
mac
->
current_DL_BWP
;
const
NR_BWP_PDCCH_t
*
pdcch_config
=
&
mac
->
config_BWP_PDCCH
[
current_DL_BWP
->
bwp_id
];
NR_tda_info_t
tda_info
=
get_ul_tda_info
(
current_UL_BWP
,
*
pdcch_config
->
ra_SS
->
controlResourceSetId
,
pdcch_config
->
ra_SS
->
searchSpaceType
->
present
,
TYPE_RA_RNTI_
,
rar_grant
.
Msg3_t_alloc
);
if
(
!
tda_info
.
valid_tda
||
tda_info
.
nrOfSymbols
==
0
)
{
LOG_E
(
MAC
,
"Cannot schedule Msg3. Something wrong in TDA information
\n
"
);
return
;
}
const
int
ntn_ue_koffset
=
GET_NTN_UE_K_OFFSET
(
&
mac
->
ntn_ta
,
mac
->
current_UL_BWP
->
scs
);
ret
=
nr_ue_pusch_scheduler
(
mac
,
is_Msg3
,
frame
,
slot
,
&
frame_tx
,
&
slot_tx
,
tda_info
.
k2
+
ntn_ue_koffset
);
// TA command
// if the timeAlignmentTimer associated with this TAG is not running
if
(
!
nr_timer_is_active
(
&
mac
->
time_alignment_timer
))
{
const
int
ta
=
rar
->
TA2
+
(
rar
->
TA1
<<
5
);
set_time_alignment
(
mac
,
ta
,
rar_ta
,
frame_tx
,
slot_tx
);
LOG_W
(
MAC
,
"received TA command %d
\n
"
,
31
+
ta
);
}
// else ignore the received Timing Advance Command
#ifdef DEBUG_RAR
LOG_I
(
NR_MAC
,
"rarh->E = 0x%x
\n
"
,
rarh
->
E
);
LOG_I
(
NR_MAC
,
"rarh->T = 0x%x
\n
"
,
rarh
->
T
);
LOG_I
(
NR_MAC
,
"rarh->RAPID = 0x%x (%i)
\n
"
,
rarh
->
RAPID
,
rarh
->
RAPID
);
LOG_I
(
NR_MAC
,
"rar->R = 0x%x
\n
"
,
rar
->
R
);
LOG_I
(
NR_MAC
,
"rar->TA1 = 0x%x
\n
"
,
rar
->
TA1
);
LOG_I
(
NR_MAC
,
"rar->TA2 = 0x%x
\n
"
,
rar
->
TA2
);
LOG_I
(
NR_MAC
,
"rar->UL_GRANT_1 = 0x%x
\n
"
,
rar
->
UL_GRANT_1
);
LOG_I
(
NR_MAC
,
"rar->UL_GRANT_2 = 0x%x
\n
"
,
rar
->
UL_GRANT_2
);
LOG_I
(
NR_MAC
,
"rar->UL_GRANT_3 = 0x%x
\n
"
,
rar
->
UL_GRANT_3
);
LOG_I
(
NR_MAC
,
"rar->UL_GRANT_4 = 0x%x
\n
"
,
rar
->
UL_GRANT_4
);
LOG_I
(
NR_MAC
,
"rar->TCRNTI_1 = 0x%x
\n
"
,
rar
->
TCRNTI_1
);
LOG_I
(
NR_MAC
,
"rar->TCRNTI_2 = 0x%x
\n
"
,
rar
->
TCRNTI_2
);
LOG_I
(
NR_MAC
,
"[%d.%d]: [UE %d] Received RAR with t_alloc %d f_alloc %d ta_command %d mcs %d freq_hopping %d tpc_command %d
\n
"
,
frame
,
slot
,
mac
->
ue_id
,
rar_grant
.
Msg3_t_alloc
,
rar_grant
.
Msg3_f_alloc
,
ta_command
,
rar_grant
.
mcs
,
rar_grant
.
freq_hopping
,
tpc_command
);
#endif
if
(
ret
!=
-
1
)
{
uint16_t
rnti
=
mac
->
crnti
;
// Upon successful reception, set the T-CRNTI to the RAR value if the RA preamble is selected among the contention-based RA Preambles
if
(
!
ra
->
cfra
)
{
ra
->
t_crnti
=
rar
->
TCRNTI_2
+
(
rar
->
TCRNTI_1
<<
8
);
rnti
=
ra
->
t_crnti
;
if
(
!
ra
->
msg3_C_RNTI
)
nr_mac_rrc_msg3_ind
(
mac
->
ue_id
,
rnti
,
dl_info
->
gNB_index
);
}
fapi_nr_ul_config_request_pdu_t
*
pdu
=
lockGet_ul_config
(
mac
,
frame_tx
,
slot_tx
,
FAPI_NR_UL_CONFIG_TYPE_PUSCH
);
if
(
!
pdu
)
return
;
// Config Msg3 PDU
int
ret
=
nr_config_pusch_pdu
(
mac
,
&
tda_info
,
&
pdu
->
pusch_config_pdu
,
NULL
,
NULL
,
&
rar_grant
,
rnti
,
NR_SearchSpace__searchSpaceType_PR_common
,
NR_DCI_NONE
);
if
(
ret
!=
0
)
remove_ul_config_last_item
(
pdu
);
release_ul_config
(
pdu
,
false
);
}
}
else
{
ra
->
t_crnti
=
0
;
// TODO if the Random Access Preamble was not selected by the MAC entity
// among the contention-based Random Access Preamble
// apply the Timing Advance Command and start or restart the timeAlignmentTimer
}
return
;
}
openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c
View file @
cc154da5
...
...
@@ -236,6 +236,15 @@ void update_mac_timers(NR_UE_MAC_INST_t *mac)
phr_info
->
phr_reporting
|=
(
1
<<
phr_cause_periodic_timer
);
}
}
bool
ra_window_expired
=
nr_timer_tick
(
&
mac
->
ra
.
response_window_timer
);
if
(
ra_window_expired
)
// consider the Random Access Response reception not successful
nr_rar_not_successful
(
mac
);
bool
ra_backoff_expired
=
nr_timer_tick
(
&
mac
->
ra
.
RA_backoff_timer
);
if
(
ra_backoff_expired
)
{
// perform the Random Access Resource selection procedure after the backoff time
mac
->
ra
.
ra_state
=
nrRA_GENERATE_PREAMBLE
;
ra_resource_selection
(
mac
);
}
}
void
remove_ul_config_last_item
(
fapi_nr_ul_config_request_pdu_t
*
pdu
)
...
...
@@ -2064,7 +2073,6 @@ static bool is_prach_frame(frame_t frame, prach_occasion_info_t *prach_occasion_
static
void
nr_ue_prach_scheduler
(
NR_UE_MAC_INST_t
*
mac
,
frame_t
frameP
,
slot_t
slotP
)
{
RA_config_t
*
ra
=
&
mac
->
ra
;
ra
->
RA_offset
=
2
;
// to compensate the rx frame offset at the gNB
if
(
ra
->
ra_state
!=
nrRA_GENERATE_PREAMBLE
)
return
;
...
...
@@ -2076,7 +2084,6 @@ static void nr_ue_prach_scheduler(NR_UE_MAC_INST_t *mac, frame_t frameP, slot_t
if
(
is_ul_slot
(
slotP
,
&
mac
->
frame_structure
))
{
if
(
slotP
==
prach_occasion_info
->
slot
)
{
nr_get_RA_window
(
mac
);
fapi_nr_ul_config_request_pdu_t
*
pdu
=
lockGet_ul_config
(
mac
,
frameP
,
slotP
,
FAPI_NR_UL_CONFIG_TYPE_PRACH
);
if
(
!
pdu
)
{
LOG_E
(
NR_MAC
,
"Error in PRACH allocation
\n
"
);
...
...
@@ -2156,6 +2163,7 @@ static void nr_ue_prach_scheduler(NR_UE_MAC_INST_t *mac, frame_t frameP, slot_t
if
(
ra
->
ra_type
==
RA_4_STEP
)
{
ra
->
ra_state
=
nrRA_WAIT_RAR
;
ra
->
start_response_window
=
true
;
}
else
if
(
ra
->
ra_type
==
RA_2_STEP
)
{
NR_MsgA_PUSCH_Resource_r16_t
*
msgA_PUSCH_Resource
=
mac
->
current_UL_BWP
->
msgA_ConfigCommon_r16
->
msgA_PUSCH_Config_r16
->
msgA_PUSCH_ResourceGroupA_r16
;
...
...
openair2/LAYER2/NR_MAC_UE/tests/test_nr_ue_power_procedures.cpp
View file @
cc154da5
...
...
@@ -192,8 +192,6 @@ TEST(pusch_power_control, pusch_power_control_msg3)
current_UL_BWP
.
BWPSize
=
106
;
current_UL_BWP
.
channel_bandwidth
=
40
;
mac
.
current_UL_BWP
=
&
current_UL_BWP
;
NR_RACH_ConfigCommon_t
nr_rach_ConfigCommon
=
{
0
};
current_UL_BWP
.
rach_ConfigCommon
=
&
nr_rach_ConfigCommon
;
mac
.
nr_band
=
78
;
NR_PUSCH_Config_t
pusch_Config
=
{
0
};
current_UL_BWP
.
pusch_Config
=
&
pusch_Config
;
...
...
@@ -229,8 +227,8 @@ TEST(pusch_power_control, pusch_power_control_msg3)
num_rb
,
start_prb
);
long
preambleReceivedTargetPower
=
-
96
;
nr_rach_ConfigCommon
.
rach_ConfigGeneric
.
preambleReceivedTargetP
ower
=
preambleReceivedTargetPower
;
int
preambleReceivedTargetPower
=
-
96
;
mac
.
ra
.
prach_resources
.
ra_preamble_rx_target_p
ower
=
preambleReceivedTargetPower
;
int
power
=
get_pusch_tx_power_ue
(
&
mac
,
num_rb
,
...
...
@@ -247,7 +245,7 @@ TEST(pusch_power_control, pusch_power_control_msg3)
false
);
EXPECT_EQ
(
power
,
-
84
);
EXPECT_LT
(
power
,
P_CMAX
);
nr_rach_ConfigCommon
.
rach_ConfigGeneric
.
preambleReceivedTargetP
ower
-=
2
;
mac
.
ra
.
prach_resources
.
ra_preamble_rx_target_p
ower
-=
2
;
int
reduced_power
=
get_pusch_tx_power_ue
(
&
mac
,
num_rb
,
...
...
@@ -372,8 +370,6 @@ TEST(pusch_power_control, pusch_power_control_state_initialization)
current_UL_BWP
.
BWPSize
=
106
;
current_UL_BWP
.
channel_bandwidth
=
40
;
mac
.
current_UL_BWP
=
&
current_UL_BWP
;
NR_RACH_ConfigCommon_t
nr_rach_ConfigCommon
=
{
0
};
current_UL_BWP
.
rach_ConfigCommon
=
&
nr_rach_ConfigCommon
;
mac
.
nr_band
=
78
;
NR_PUSCH_Config_t
pusch_Config
=
{
0
};
current_UL_BWP
.
pusch_Config
=
&
pusch_Config
;
...
...
@@ -393,8 +389,8 @@ TEST(pusch_power_control, pusch_power_control_state_initialization)
uint32_t
sum_bits_in_codeblocks
=
56
;
int
delta_pusch
=
0
;
bool
is_rar_tx_retx
=
true
;
long
preambleReceivedTargetPower
=
-
96
;
nr_rach_ConfigCommon
.
rach_ConfigGeneric
.
preambleReceivedTargetP
ower
=
preambleReceivedTargetPower
;
int
preambleReceivedTargetPower
=
-
96
;
mac
.
ra
.
prach_resources
.
ra_preamble_rx_target_p
ower
=
preambleReceivedTargetPower
;
get_pusch_tx_power_ue
(
&
mac
,
num_rb
,
...
...
openair2/LAYER2/NR_MAC_UE/tests/test_nr_ue_ra_procedures.cpp
View file @
cc154da5
...
...
@@ -101,6 +101,7 @@ TEST(test_init_ra, four_step_cbra)
mac
.
p_Max
=
23
;
mac
.
nr_band
=
78
;
mac
.
frame_structure
.
frame_type
=
TDD
;
mac
.
frame_structure
.
numb_slots_frame
=
20
;
mac
.
frequency_range
=
FR1
;
mac
.
first_sync_frame
=
0
;
int
frame
=
151
;
...
...
@@ -135,6 +136,7 @@ TEST(test_init_ra, four_step_cfra)
mac
.
p_Max
=
23
;
mac
.
nr_band
=
78
;
mac
.
frame_structure
.
frame_type
=
TDD
;
mac
.
frame_structure
.
numb_slots_frame
=
20
;
mac
.
frequency_range
=
FR1
;
mac
.
first_sync_frame
=
0
;
int
frame
=
151
;
...
...
openair2/NR_UE_PHY_INTERFACE/NR_IF_Module.c
View file @
cc154da5
...
...
@@ -390,8 +390,7 @@ static bool is_my_dci(NR_UE_MAC_INST_t *mac, nfapi_nr_dl_dci_pdu_t *received_pdu
already. Only once the RA procedure succeeds is the CRNTI value updated
to the TC_RNTI. */
if
(
get_softmodem_params
()
->
nsa
)
{
if
(
received_pdu
->
RNTI
!=
mac
->
crnti
&&
(
received_pdu
->
RNTI
!=
mac
->
ra
.
ra_rnti
||
mac
->
ra
.
RA_RAPID_found
))
if
(
received_pdu
->
RNTI
!=
mac
->
crnti
&&
(
received_pdu
->
RNTI
!=
mac
->
ra
.
ra_rnti
))
return
false
;
}
if
(
IS_SA_MODE
(
get_softmodem_params
()))
{
...
...
@@ -1292,11 +1291,11 @@ static uint32_t nr_ue_dl_processing(NR_UE_MAC_INST_t *mac, nr_downlink_indicatio
ret_mask
|=
(
handle_dlsch
(
mac
,
dl_info
,
i
))
<<
FAPI_NR_RX_PDU_TYPE_DLSCH
;
break
;
case
FAPI_NR_RX_PDU_TYPE_RAR
:
ret_mask
|=
(
handle_dlsch
(
mac
,
dl_info
,
i
))
<<
FAPI_NR_RX_PDU_TYPE_RAR
;
if
(
!
dl_info
->
rx_ind
->
rx_indication_body
[
i
].
pdsch_pdu
.
ack_nack
)
LOG_W
(
PHY
,
"Received a RAR-Msg2 but LDPC decode failed
\n
"
);
else
LOG_I
(
PHY
,
"RAR-Msg2 decoded
\n
"
);
ret_mask
|=
(
handle_dlsch
(
mac
,
dl_info
,
i
))
<<
FAPI_NR_RX_PDU_TYPE_RAR
;
break
;
case
FAPI_NR_CSIRS_IND
:
ret_mask
|=
(
handle_csirs_measurements
(
mac
,
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment