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
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
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
wangjie
OpenXG-RAN
Commits
ba0d2dae
Commit
ba0d2dae
authored
Jul 16, 2021
by
yihongzheng
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
fpga_ldpc both decode and encode are OK
parent
3289c89f
Changes
5
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
715 additions
and
1 deletion
+715
-1
openair1/PHY/NR_TRANSPORT/nr_dlsch.c
openair1/PHY/NR_TRANSPORT/nr_dlsch.c
+487
-0
openair1/PHY/NR_TRANSPORT/nr_dlsch.h
openair1/PHY/NR_TRANSPORT/nr_dlsch.h
+30
-0
openair1/PHY/NR_TRANSPORT/nr_dlsch_coding.c
openair1/PHY/NR_TRANSPORT/nr_dlsch_coding.c
+194
-0
openair1/PHY/NR_TRANSPORT/nr_ulsch_decoding.c
openair1/PHY/NR_TRANSPORT/nr_ulsch_decoding.c
+2
-0
openair1/SCHED_NR/phy_procedures_nr_gNB.c
openair1/SCHED_NR/phy_procedures_nr_gNB.c
+2
-1
No files found.
openair1/PHY/NR_TRANSPORT/nr_dlsch.c
View file @
ba0d2dae
This diff is collapsed.
Click to expand it.
openair1/PHY/NR_TRANSPORT/nr_dlsch.h
View file @
ba0d2dae
...
...
@@ -102,4 +102,34 @@ void dump_pdsch_stats(PHY_VARS_gNB *gNB);
void
clear_pdsch_stats
(
PHY_VARS_gNB
*
gNB
);
int
nr_dlsch_encoding_fpga_ldpc
(
PHY_VARS_gNB
*
gNB
,
unsigned
char
*
a
,
int
frame
,
uint8_t
slot
,
NR_gNB_DLSCH_t
*
dlsch
,
NR_DL_FRAME_PARMS
*
frame_parms
,
time_stats_t
*
tinput
,
time_stats_t
*
tprep
,
time_stats_t
*
tparity
,
time_stats_t
*
toutput
,
time_stats_t
*
dlsch_rate_matching_stats
,
time_stats_t
*
dlsch_interleaving_stats
,
time_stats_t
*
dlsch_segmentation_stats
);
void
dl_find_iLS_lsIndex
(
unsigned
int
*
LDPC_lifting_size
,
uint32_t
*
iLS_out
,
uint32_t
*
lsIndex_out
);
void
nr_pdsch_codeword_scrambling_optim_fpga_ldpc
(
uint8_t
*
in
,
uint32_t
size
,
uint8_t
q
,
uint32_t
Nid
,
uint32_t
n_RNTI
,
uint32_t
*
out
);
unsigned
char
Reverse8U
(
unsigned
char
x
);
void
Byte_Reverse_11
(
unsigned
char
*
Src
,
unsigned
char
*
Dest
,
int
Length
);
uint8_t
nr_generate_pdsch_fpga_ldpc
(
PHY_VARS_gNB
*
gNB
,
int
frame
,
int
slot
);
#endif
openair1/PHY/NR_TRANSPORT/nr_dlsch_coding.c
View file @
ba0d2dae
...
...
@@ -462,3 +462,197 @@ int nr_dlsch_encoding(PHY_VARS_gNB *gNB,
return
0
;
}
//FPGA加速,删除了部分OAI中的encode函数
int
nr_dlsch_encoding_fpga_ldpc
(
PHY_VARS_gNB
*
gNB
,
unsigned
char
*
a
,
int
frame
,
uint8_t
slot
,
NR_gNB_DLSCH_t
*
dlsch
,
NR_DL_FRAME_PARMS
*
frame_parms
,
time_stats_t
*
tinput
,
time_stats_t
*
tprep
,
time_stats_t
*
tparity
,
time_stats_t
*
toutput
,
time_stats_t
*
dlsch_rate_matching_stats
,
time_stats_t
*
dlsch_interleaving_stats
,
time_stats_t
*
dlsch_segmentation_stats
)
{
unsigned
int
G
;
NR_DL_gNB_HARQ_t
*
harq
=
&
dlsch
->
harq_process
;
nfapi_nr_dl_tti_pdsch_pdu_rel15_t
*
rel15
=
&
harq
->
pdsch_pdu
.
pdsch_pdu_rel15
;
uint16_t
nb_rb
=
rel15
->
rbSize
;
uint8_t
nb_symb_sch
=
rel15
->
NrOfSymbols
;
uint32_t
A
=
0
;
uint32_t
*
Zc
=
&
dlsch
->
harq_process
.
Z
;
uint8_t
mod_order
=
rel15
->
qamModOrder
[
0
];
uint16_t
r
=
0
;
uint8_t
nb_re_dmrs
=
0
;
if
(
rel15
->
dmrsConfigType
==
NFAPI_NR_DMRS_TYPE1
)
nb_re_dmrs
=
6
*
rel15
->
numDmrsCdmGrpsNoData
;
else
nb_re_dmrs
=
4
*
rel15
->
numDmrsCdmGrpsNoData
;
uint16_t
length_dmrs
=
get_num_dmrs
(
rel15
->
dlDmrsSymbPos
);
uint16_t
R
=
rel15
->
targetCodeRate
[
0
];
float
Coderate
=
0
.
0
;
EncodeInHeadStruct
EncodeHead
;
uint8_t
*
pEnDataIn
=
NULL
;
uint8_t
*
pEnDataOut
=
NULL
;
uint32_t
iLS
=
0
;
uint32_t
lsIndex
=
0
;
uint32_t
dl_E0
=
0
,
dl_E1
=
0
;
pEnDataIn
=
a
;
pEnDataOut
=
harq
->
f
;
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME
(
VCD_SIGNAL_DUMPER_FUNCTIONS_gNB_DLSCH_ENCODING
,
VCD_FUNCTION_IN
);
A
=
rel15
->
TBSize
[
0
]
<<
3
;
NR_gNB_SCH_STATS_t
*
stats
=
NULL
;
int
first_free
=-
1
;
for
(
int
i
=
0
;
i
<
NUMBER_OF_NR_SCH_STATS_MAX
;
i
++
)
{
if
(
gNB
->
dlsch_stats
[
i
].
rnti
==
0
&&
first_free
==
-
1
)
{
first_free
=
i
;
stats
=&
gNB
->
dlsch_stats
[
i
];
}
if
(
gNB
->
dlsch_stats
[
i
].
rnti
==
dlsch
->
rnti
)
{
stats
=&
gNB
->
dlsch_stats
[
i
];
break
;
}
}
if
(
stats
)
{
stats
->
rnti
=
dlsch
->
rnti
;
stats
->
total_bytes_tx
+=
rel15
->
TBSize
[
0
];
stats
->
current_RI
=
rel15
->
nrOfLayers
;
stats
->
current_Qm
=
rel15
->
qamModOrder
[
0
];
}
G
=
nr_get_G
(
nb_rb
,
nb_symb_sch
,
nb_re_dmrs
,
length_dmrs
,
mod_order
,
rel15
->
nrOfLayers
);
LOG_D
(
PHY
,
"dlsch coding A %d G %d (nb_rb %d, nb_symb_sch %d, nb_re_dmrs %d, length_dmrs %d, mod_order %d)
\n
"
,
A
,
G
,
nb_rb
,
nb_symb_sch
,
nb_re_dmrs
,
length_dmrs
,
mod_order
);
if
(
A
>
3824
)
{
harq
->
B
=
A
+
24
;
}
else
{
harq
->
B
=
A
+
16
;
}
if
(
R
<
1000
)
Coderate
=
(
float
)
R
/
(
float
)
1024
;
else
// to scale for mcs 20 and 26 in table 5.1.3.1-2 which are decimal and input 2* in nr_tbs_tools
Coderate
=
(
float
)
R
/
(
float
)
2048
;
if
((
A
<=
292
)
||
((
A
<=
3824
)
&&
(
Coderate
<=
0
.
6667
))
||
Coderate
<=
0
.
25
)
harq
->
BG
=
2
;
else
harq
->
BG
=
1
;
start_meas
(
dlsch_segmentation_stats
);
nr_segmentation
(
NULL
,
NULL
,
harq
->
B
,
&
harq
->
C
,
&
harq
->
K
,
Zc
,
&
harq
->
F
,
harq
->
BG
);
stop_meas
(
dlsch_segmentation_stats
);
//FPGA加速的头部
//word 0
EncodeHead
.
pktType
=
0x12
;
EncodeHead
.
rsv0
=
0x00
;
EncodeHead
.
chkCode
=
0xFAFA
;
//word 1
EncodeHead
.
rsv1
=
0x0000
;
//word 2
EncodeHead
.
rsv2
=
0x0
;
EncodeHead
.
sectorId
=
0x0
;
//=0表示单小区
EncodeHead
.
rsv3
=
0x0
;
//word 3
EncodeHead
.
sfn
=
frame
;
EncodeHead
.
rsv4
=
0x0
;
EncodeHead
.
slotNum
=
slot
;
EncodeHead
.
subfn
=
EncodeHead
.
slotNum
/
2
;
EncodeHead
.
pduIdx
=
0x0
;
//=0表示第一个码字,总共一个码字
EncodeHead
.
rev5
=
0x0
;
//word 4
EncodeHead
.
tbSizeB
=
rel15
->
TBSize
[
0
];
EncodeHead
.
pktLen
=
32
+
((
EncodeHead
.
tbSizeB
+
32
-
1
)
/
32
)
*
32
;
//Byte,pktLen=encoder header(32byte)+ tbszie (byte),并且32Byte对齐,是32的整数倍
EncodeHead
.
rev6
=
0x0
;
EncodeHead
.
lastTb
=
0x1
;
EncodeHead
.
firstTb
=
0x1
;
//=1表示本slot只有一个TB
EncodeHead
.
rev7
=
0x0
;
EncodeHead
.
cbNum
=
harq
->
C
;
//word 5
EncodeHead
.
qm
=
rel15
->
qamModOrder
[
0
]
/
2
;
//规定是BPSK qm=0,QPSK qm=1,其他floor(调制阶数/2);OAI的Qm为2/4/6/8
EncodeHead
.
rev8
=
0x0
;
EncodeHead
.
fillbit
=
harq
->
F
;
EncodeHead
.
rev9
=
0x0
;
if
(
EncodeHead
.
cbNum
==
1
){
EncodeHead
.
kpInByte
=
((
harq
->
B
)
/
EncodeHead
.
cbNum
)
>>
3
;
}
else
{
EncodeHead
.
kpInByte
=
((
harq
->
B
+
((
EncodeHead
.
cbNum
)
*
24
))
/
EncodeHead
.
cbNum
)
>>
3
;
}
EncodeHead
.
rev10
=
0x0
;
//word 6
EncodeHead
.
gamma
=
EncodeHead
.
cbNum
-
(
G
/
(
rel15
->
nrOfLayers
*
(
2
*
EncodeHead
.
qm
)))
%
EncodeHead
.
cbNum
;
//=1表示本slot只有一个TB
EncodeHead
.
rev11
=
0x0
;
EncodeHead
.
rvIdx
=
rel15
->
rvIndex
[
0
];
EncodeHead
.
rev12
=
0x0
;
//查找iLS和lfSizeIx
dl_find_iLS_lsIndex
(
Zc
,
&
iLS
,
&
lsIndex
);
EncodeHead
.
iLs
=
iLS
;
EncodeHead
.
lfSizeIx
=
lsIndex
;
EncodeHead
.
rev13
=
0x0
;
// EncodeHead.iLs = *iLS_out;
EncodeHead
.
bg
=
harq
->
BG
-
1
;
//规定选择协议base grape1 bg=0; base grape2 bg=1;OAI的BG大了1
if
(
EncodeHead
.
bg
==
0
){
EncodeHead
.
codeRate
=
46
;
}
else
{
EncodeHead
.
codeRate
=
42
;
}
//word 7
//计算并获得e0和e1
nr_get_E0_E1
(
G
,
harq
->
C
,
mod_order
,
rel15
->
nrOfLayers
,
r
,
&
dl_E0
,
&
dl_E1
);
EncodeHead
.
e0
=
dl_E0
;
EncodeHead
.
e1
=
dl_E1
;
//调用FPGA的.so中的编码函数
encoder_load
(
&
EncodeHead
,
pEnDataIn
,
pEnDataOut
);
LOG_D
(
PHY
,
"encoder_load_OK!
\n
"
);
//LOG_M("pEnDataOut.m","pEnDataOut", pEnDataOut, G+32, 1, 9);
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME
(
VCD_SIGNAL_DUMPER_FUNCTIONS_gNB_DLSCH_ENCODING
,
VCD_FUNCTION_OUT
);
return
0
;
}
void
dl_find_iLS_lsIndex
(
unsigned
int
*
LDPC_lifting_size
,
uint32_t
*
iLS_out
,
uint32_t
*
lsIndex_out
)
{
unsigned
int
Set_of_LDPC_lifting_size
[
8
][
8
]
=
{
{
2
,
4
,
8
,
16
,
32
,
64
,
128
,
256
},
{
3
,
6
,
12
,
24
,
48
,
96
,
192
,
384
},
{
5
,
10
,
20
,
40
,
80
,
160
,
320
},
{
7
,
14
,
28
,
56
,
112
,
224
},
{
9
,
18
,
36
,
72
,
144
,
288
},
{
11
,
22
,
44
,
88
,
176
,
352
},
{
13
,
26
,
52
,
104
,
208
},
{
15
,
30
,
60
,
120
,
240
}};
uint32_t
iLS
,
lsIndex
;
for
(
iLS
=
0
;
iLS
<
8
;
iLS
++
)
{
for
(
lsIndex
=
0
;
lsIndex
<
8
;
lsIndex
++
){
if
(
*
LDPC_lifting_size
==
Set_of_LDPC_lifting_size
[
iLS
][
lsIndex
]){
*
iLS_out
=
iLS
;
*
lsIndex_out
=
lsIndex
;
}
}
}
}
\ No newline at end of file
openair1/PHY/NR_TRANSPORT/nr_ulsch_decoding.c
View file @
ba0d2dae
...
...
@@ -815,6 +815,7 @@ uint32_t nr_ulsch_decoding_fpga_ldpc(PHY_VARS_gNB *phy_vars_gNB,
//调用FPGA的decode,并输出CRC
// clock_gettime( CLOCK_REALTIME, &decode_start );
decoder_load
(
&
DecodeHead
,
pDeDataIn
,
pDeDataOut
,
pcrc
);
LOG_D
(
PHY
,
" decoder_load_OK
\n
"
);
// clock_gettime( CLOCK_REALTIME, &decode_stop );
if
(
*
pcrc
==
1
)
{
LOG_D
(
PHY
,
"[gNB %d] ULSCH: Setting ACK for slot %d TBS %d
\n
"
,
...
...
@@ -825,6 +826,7 @@ uint32_t nr_ulsch_decoding_fpga_ldpc(PHY_VARS_gNB *phy_vars_gNB,
LOG_D
(
PHY
,
"ULSCH received ok
\n
"
);
nr_fill_indication
(
phy_vars_gNB
,
harq_process
->
frame
,
harq_process
->
slot
,
ULSCH_id
,
harq_pid
,
0
);
LOG_D
(
PHY
,
"crc = 1!
\n
"
);
}
else
{
LOG_D
(
PHY
,
"[gNB %d] ULSCH: Setting NAK for SFN/SF %d/%d (pid %d, status %d, round %d, TBS %d) r %d
\n
"
,
...
...
openair1/SCHED_NR/phy_procedures_nr_gNB.c
View file @
ba0d2dae
...
...
@@ -194,6 +194,7 @@ void phy_procedures_gNB_TX(PHY_VARS_gNB *gNB,
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME
(
VCD_SIGNAL_DUMPER_FUNCTIONS_GENERATE_DLSCH
,
1
);
LOG_D
(
PHY
,
"PDSCH generation started (%d) in frame %d.%d
\n
"
,
gNB
->
num_pdsch_rnti
[
slot
],
frame
,
slot
);
nr_generate_pdsch
(
gNB
,
frame
,
slot
);
// nr_generate_pdsch_fpga_ldpc(gNB,frame, slot); //上面是OAI的代码,fpga_ldpc的encode切换到该行即可
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME
(
VCD_SIGNAL_DUMPER_FUNCTIONS_GENERATE_DLSCH
,
0
);
}
...
...
@@ -699,7 +700,7 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) {
//LOG_M("rxdataF_ext.m","rxF_ext",gNB->pusch_vars[0]->rxdataF_ext[0],6900,1,1);
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME
(
VCD_SIGNAL_DUMPER_FUNCTIONS_NR_ULSCH_PROCEDURES_RX
,
1
);
nr_ulsch_procedures
(
gNB
,
frame_rx
,
slot_rx
,
ULSCH_id
,
harq_pid
);
// nr_ulsch_procedures_fpga_ldpc(gNB, frame_rx, slot_rx, ULSCH_id, harq_pid); //上面是OAI的代码,pga_ldpc的decode切换到该行即可
// nr_ulsch_procedures_fpga_ldpc(gNB, frame_rx, slot_rx, ULSCH_id, harq_pid); //上面是OAI的代码,
f
pga_ldpc的decode切换到该行即可
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME
(
VCD_SIGNAL_DUMPER_FUNCTIONS_NR_ULSCH_PROCEDURES_RX
,
0
);
break
;
}
...
...
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