Merge remote-tracking branch 'origin/develop' into develop-SRS-MIMO

# Conflicts:
#	openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c
#	openair1/SCHED_NR/phy_procedures_nr_gNB.c
This commit is contained in:
Roberto Louro Magueta
2022-08-08 11:54:43 +01:00
124 changed files with 3860 additions and 122058 deletions
+1 -1
View File
@@ -66,7 +66,7 @@ pipeline {
withCredentials([
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.DH_Credentials}", usernameVariable: 'DH_Username', passwordVariable: 'DH_Password']
]) {
def listOfImages = ["oai-enb", "oai-gnb", "oai-lte-ue", "oai-nr-ue"]
def listOfImages = ["oai-enb", "oai-gnb", "oai-lte-ue", "oai-nr-ue", "proxy"]
sh "docker login -u ${DH_Username} -p ${DH_Password} > /dev/null 2>&1"
listOfImages.eachWithIndex { item, iindex ->
sh "docker image tag ${item}:develop ${DH_Account}/${item}:develop"
+185 -2
View File
@@ -36,6 +36,9 @@ def testStageName = params.pipelineTestStageName
// Name of the phone resource
def ciSmartPhoneResource = params.smartphonesResource
// Name of the phone resource
def ciEpcResource = params.epcResource
// Global Parameters. Normally they should be populated when the master job
// triggers the slave job with parameters
def eNB_Repository
@@ -51,7 +54,7 @@ pipeline {
options {
disableConcurrentBuilds()
ansiColor('xterm')
lock (ciSmartPhoneResource)
lock(extra: [[resource: ciEpcResource]], resource: ciSmartPhoneResource)
}
stages {
stage ("Verify Parameters") {
@@ -216,6 +219,76 @@ pipeline {
}
}
}
stage ("Terminate") {
parallel {
stage('Terminate UE') {
// Bypassing this stage if there are no abd server defined
when {
expression { params.ADB_IPAddress != "none" }
}
steps {
echo '\u2705 \u001B[32mTerminate UE\u001B[0m'
withCredentials([
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.ADB_Credentials}", usernameVariable: 'ADB_Username', passwordVariable: 'ADB_Password']
]) {
sh "python3 ci-scripts/main.py --mode=TerminateUE --ADBIPAddress=${params.ADB_IPAddress} --ADBUserName=${ADB_Username} --ADBPassword=${ADB_Password}"
}
}
}
stage('Terminate eNB') {
steps {
echo '\u2705 \u001B[32mTerminate eNB\u001B[0m'
withCredentials([
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.eNB_Credentials}", usernameVariable: 'eNB_Username', passwordVariable: 'eNB_Password']
]) {
sh "python3 ci-scripts/main.py --mode=TerminateeNB --eNBIPAddress=${params.eNB_IPAddress} --eNBUserName=${eNB_Username} --eNBPassword=${eNB_Password}"
}
}
}
stage('Terminate SPGW') {
// Bypassing this stage if EPC server is not defined
when {
expression { params.EPC_IPAddress != "none" }
}
steps {
echo '\u2705 \u001B[32mTerminate SPGW\u001B[0m'
withCredentials([
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.EPC_Credentials}", usernameVariable: 'EPC_Username', passwordVariable: 'EPC_Password']
]) {
sh "python3 ci-scripts/main.py --mode=TerminateSPGW --EPCIPAddress=${params.EPC_IPAddress} --EPCUserName=${EPC_Username} --EPCPassword=${EPC_Password} --EPCType=${params.EPC_Type} --EPCSourceCodePath=${params.EPC_SourceCodePath}"
}
}
}
stage('Terminate MME') {
// Bypassing this stage if EPC server is not defined
when {
expression { params.EPC_IPAddress != "none" }
}
steps {
echo '\u2705 \u001B[32mTerminate MME\u001B[0m'
withCredentials([
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.EPC_Credentials}", usernameVariable: 'EPC_Username', passwordVariable: 'EPC_Password']
]) {
sh "python3 ci-scripts/main.py --mode=TerminateMME --EPCIPAddress=${params.EPC_IPAddress} --EPCUserName=${EPC_Username} --EPCPassword=${EPC_Password} --EPCType=${params.EPC_Type} --EPCSourceCodePath=${params.EPC_SourceCodePath}"
}
}
}
stage('Terminate HSS') {
// Bypassing this stage if EPC server is not defined
when {
expression { params.EPC_IPAddress != "none" }
}
steps {
echo '\u2705 \u001B[32mTerminate HSS\u001B[0m'
withCredentials([
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.EPC_Credentials}", usernameVariable: 'EPC_Username', passwordVariable: 'EPC_Password']
]) {
sh "python3 ci-scripts/main.py --mode=TerminateHSS --EPCIPAddress=${params.EPC_IPAddress} --EPCUserName=${EPC_Username} --EPCPassword=${EPC_Password} --EPCType=${params.EPC_Type} --EPCSourceCodePath=${params.EPC_SourceCodePath}"
}
}
}
}
}
stage('Log Collection') {
parallel {
stage('Log Collection (eNB - Build)') {
@@ -242,7 +315,7 @@ pipeline {
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.eNB_Credentials}", usernameVariable: 'eNB_Username', passwordVariable: 'eNB_Password']
]) {
echo '\u2705 \u001B[32mLog Collection (eNB - Run)\u001B[0m'
sh "python3 ci-scripts/main.py --mode=LogCollecteNB --eNBIPAddress=${params.eNB_IPAddress} --eNBUserName=${eNB_Username} --eNBPassword=${eNB_Password} --eNBSourceCodePath=${params.eNB_SourceCodePath}"
sh "python3 ci-scripts/main.py --mode=LogCollecteNB --eNBIPAddress=${params.eNB_IPAddress} --eNBUserName=${eNB_Username} --eNBPassword=${eNB_Password} --eNBSourceCodePath=${params.eNB_SourceCodePath} --BuildId=${env.BUILD_ID}"
echo '\u2705 \u001B[32mLog Transfer (eNB - Run)\u001B[0m'
sh "sshpass -p \'${eNB_Password}\' scp -o 'StrictHostKeyChecking no' -o 'ConnectTimeout 10' ${eNB_Username}@${params.eNB_IPAddress}:${eNB_SourceCodePath}/cmake_targets/enb.log.zip ./enb.log.${env.BUILD_ID}.zip || true"
@@ -259,6 +332,116 @@ pipeline {
}
}
}
stage('Log Collection (SPGW)') {
// Bypassing this stage if EPC server is not defined
when {
expression { params.EPC_IPAddress != "none" }
}
steps {
withCredentials([
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.EPC_Credentials}", usernameVariable: 'EPC_Username', passwordVariable: 'EPC_Password']
]) {
echo '\u2705 \u001B[32mLog Collection (SPGW)\u001B[0m'
sh "python3 ci-scripts/main.py --mode=LogCollectSPGW --EPCIPAddress=${params.EPC_IPAddress} --EPCUserName=${EPC_Username} --EPCPassword=${EPC_Password} --EPCSourceCodePath=${params.EPC_SourceCodePath} --EPCType=${params.EPC_Type}"
echo '\u2705 \u001B[32mLog Transfer (SPGW)\u001B[0m'
sh "sshpass -p \'${EPC_Password}\' scp -o 'StrictHostKeyChecking no' -o 'ConnectTimeout 10' ${EPC_Username}@${params.EPC_IPAddress}:${EPC_SourceCodePath}/scripts/spgw.log.zip ./spgw.log.${env.BUILD_ID}.zip || true"
}
script {
if(fileExists("spgw.log.${env.BUILD_ID}.zip")) {
archiveArtifacts "spgw.log.${env.BUILD_ID}.zip"
}
}
}
}
stage('Log Collection (MME)') {
// Bypassing this stage if EPC server is not defined
when {
expression { params.EPC_IPAddress != "none" }
}
steps {
withCredentials([
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.EPC_Credentials}", usernameVariable: 'EPC_Username', passwordVariable: 'EPC_Password']
]) {
echo '\u2705 \u001B[32mLog Collection (MME)\u001B[0m'
sh "python3 ci-scripts/main.py --mode=LogCollectMME --EPCIPAddress=${params.EPC_IPAddress} --EPCUserName=${EPC_Username} --EPCPassword=${EPC_Password} --EPCSourceCodePath=${params.EPC_SourceCodePath} --EPCType=${params.EPC_Type}"
echo '\u2705 \u001B[32mLog Transfer (MME)\u001B[0m'
sh "sshpass -p \'${EPC_Password}\' scp -o 'StrictHostKeyChecking no' -o 'ConnectTimeout 10' ${EPC_Username}@${params.EPC_IPAddress}:${EPC_SourceCodePath}/scripts/mme.log.zip ./mme.log.${env.BUILD_ID}.zip || true"
}
script {
if(fileExists("mme.log.${env.BUILD_ID}.zip")) {
archiveArtifacts "mme.log.${env.BUILD_ID}.zip"
}
}
}
}
stage('Log Collection (HSS)') {
// Bypassing this stage if EPC server is not defined
when {
expression { params.EPC_IPAddress != "none" }
}
steps {
withCredentials([
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.EPC_Credentials}", usernameVariable: 'EPC_Username', passwordVariable: 'EPC_Password']
]) {
echo '\u2705 \u001B[32mLog Collection (HSS)\u001B[0m'
sh "python3 ci-scripts/main.py --mode=LogCollectHSS --EPCIPAddress=${params.EPC_IPAddress} --EPCUserName=${EPC_Username} --EPCPassword=${EPC_Password} --EPCSourceCodePath=${params.EPC_SourceCodePath} --EPCType=${params.EPC_Type}"
echo '\u2705 \u001B[32mLog Transfer (HSS)\u001B[0m'
sh "sshpass -p \'${EPC_Password}\' scp -o 'StrictHostKeyChecking no' -o 'ConnectTimeout 10' ${EPC_Username}@${params.EPC_IPAddress}:${EPC_SourceCodePath}/scripts/hss.log.zip ./hss.log.${env.BUILD_ID}.zip || true"
}
script {
if(fileExists("hss.log.${env.BUILD_ID}.zip")) {
archiveArtifacts "hss.log.${env.BUILD_ID}.zip"
}
}
}
}
stage('Log Collection (Ping)') {
// Bypassing this stage if EPC server is not defined
when {
expression { params.EPC_IPAddress != "none" }
}
steps {
withCredentials([
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.EPC_Credentials}", usernameVariable: 'EPC_Username', passwordVariable: 'EPC_Password']
]) {
echo '\u2705 \u001B[32mLog Collection (Ping)\u001B[0m'
sh "python3 ci-scripts/main.py --mode=LogCollectPing --EPCIPAddress=${params.EPC_IPAddress} --EPCUserName=${EPC_Username} --EPCPassword=${EPC_Password} --EPCSourceCodePath=${params.EPC_SourceCodePath} --EPCType=${params.EPC_Type}"
echo '\u2705 \u001B[32mLog Transfer (Ping)\u001B[0m'
sh "sshpass -p \'${EPC_Password}\' scp -o 'StrictHostKeyChecking no' -o 'ConnectTimeout 10' ${EPC_Username}@${params.EPC_IPAddress}:${EPC_SourceCodePath}/scripts/ping.log.zip ./ping.log.${env.BUILD_ID}.zip || true"
}
script {
if(fileExists("ping.log.${env.BUILD_ID}.zip")) {
archiveArtifacts "ping.log.${env.BUILD_ID}.zip"
}
}
}
}
stage('Log Collection (Iperf)') {
// Bypassing this stage if EPC server is not defined
when {
expression { params.EPC_IPAddress != "none" }
}
steps {
withCredentials([
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.EPC_Credentials}", usernameVariable: 'EPC_Username', passwordVariable: 'EPC_Password']
]) {
echo '\u2705 \u001B[32mLog Collection (Iperf)\u001B[0m'
sh "python3 ci-scripts/main.py --mode=LogCollectIperf --EPCIPAddress=${params.EPC_IPAddress} --EPCUserName=${EPC_Username} --EPCPassword=${EPC_Password} --EPCSourceCodePath=${params.EPC_SourceCodePath} --EPCType=${params.EPC_Type}"
echo '\u2705 \u001B[32mLog Transfer (Iperf)\u001B[0m'
sh "sshpass -p \'${EPC_Password}\' scp -o 'StrictHostKeyChecking no' -o 'ConnectTimeout 10' ${EPC_Username}@${params.EPC_IPAddress}:${EPC_SourceCodePath}/scripts/iperf.log.zip ./iperf.log.${env.BUILD_ID}.zip || true"
}
script {
if(fileExists("iperf.log.${env.BUILD_ID}.zip")) {
archiveArtifacts "iperf.log.${env.BUILD_ID}.zip"
}
}
}
}
}
}
}
+9 -6
View File
@@ -20,6 +20,9 @@
* contact@openairinterface.org
*/
// necessary for reading JSON
import groovy.json.JsonSlurper
// Template Jenkins Declarative Pipeline script to run Test w/ RF HW
// Location of the python executor node shall be in the same subnet as the others servers
@@ -37,12 +40,12 @@ pipeline {
stages {
stage ("Launcher") {
steps {
script {
//retrieve MR that are opened nd with tag NSA
MR_LIST= sh returnStdout: true, script: 'curl --silent "https://gitlab.eurecom.fr/api/v4/projects/oai%2Fopenairinterface5g/merge_requests?state=opened&per_page=100&labels=NSA" | jq ".[].iid" || true '
echo "List of selected MR:\n${MR_LIST}"
def MR_ARRAY = MR_LIST.split('\n')
//for every selected MR, retrieve the branch name and the latest commit
script {
// retrieve MR that are opened nd with tag NSA
MR_LIST = sh returnStdout: true, script: 'curl --silent "https://gitlab.eurecom.fr/api/v4/projects/oai%2Fopenairinterface5g/merge_requests?state=opened&per_page=100&labels=NSA" | jq -cj "[.[].iid]"'
echo "List of selected MRs: ${MR_LIST.trim()}"
def MR_ARRAY = new JsonSlurper().parseText(MR_LIST.trim())
// for every selected MR, retrieve the branch name and the latest commit
for (MR in MR_ARRAY) {
SRC_BRANCH=sh returnStdout: true, script: """curl --silent "https://gitlab.eurecom.fr/api/v4/projects/oai%2Fopenairinterface5g/merge_requests/${MR}" | jq ".source_branch" || true """
SRC_BRANCH=SRC_BRANCH.trim()
+2 -2
View File
@@ -50,7 +50,7 @@ amarisoft_ue_1:
WakeupScript : none
DetachScript : none
#end
Cmd : /root/NV17-12-21/ue/lteue
Cmd : /root/NV18-06-2022/ue/lteue
Config : /root/NV17-12-21/ue/config/oaicicd-ue-Ping-SATest.cfg
Duration : 60
Ping : /tmp/test_ue1.log
@@ -71,7 +71,7 @@ amarisoft_ue_2:
WakeupScript : none
DetachScript : none
#end
Cmd : /root/NV17-12-21/ue/lteue
Cmd : /root/NV18-06-2022/ue/lteue
Config : /root/NV17-12-21/ue/config/xxxxxxx.cfg #to be updated for an other scenario
Duration : 60
Ping :
+119
View File
@@ -74,6 +74,7 @@ class Containerize():
self.eNB2SourceCodePath = ''
self.forcedWorkspaceCleanup = False
self.imageKind = ''
self.proxyCommit = None
self.eNB_instance = 0
self.eNB_serverId = ['', '', '']
self.yamlPath = ['', '', '']
@@ -421,6 +422,124 @@ class Containerize():
HTML.CreateHtmlTabFooter(False)
sys.exit(1)
def BuildProxy(self, HTML):
if self.ranRepository == '' or self.ranBranch == '' or self.ranCommitID == '':
HELP.GenericHelp(CONST.Version)
sys.exit('Insufficient Parameter')
if self.eNB_serverId[self.eNB_instance] == '0':
lIpAddr = self.eNBIPAddress
lUserName = self.eNBUserName
lPassWord = self.eNBPassword
lSourcePath = self.eNBSourceCodePath
elif self.eNB_serverId[self.eNB_instance] == '1':
lIpAddr = self.eNB1IPAddress
lUserName = self.eNB1UserName
lPassWord = self.eNB1Password
lSourcePath = self.eNB1SourceCodePath
elif self.eNB_serverId[self.eNB_instance] == '2':
lIpAddr = self.eNB2IPAddress
lUserName = self.eNB2UserName
lPassWord = self.eNB2Password
lSourcePath = self.eNB2SourceCodePath
if lIpAddr == '' or lUserName == '' or lPassWord == '' or lSourcePath == '':
HELP.GenericHelp(CONST.Version)
sys.exit('Insufficient Parameter')
if self.proxyCommit is None:
HELP.GenericHelp(CONST.Version)
sys.exit('Insufficient Parameter (need proxyCommit for proxy build)')
logging.debug('Building on server: ' + lIpAddr)
mySSH = SSH.SSHConnection()
mySSH.open(lIpAddr, lUserName, lPassWord)
# Check that we are on Ubuntu
mySSH.command('hostnamectl', '\$', 5)
result = re.search('Ubuntu', mySSH.getBefore())
self.host = result.group(0)
if self.host != 'Ubuntu':
logging.error('\u001B[1m Can build proxy only on Ubuntu server\u001B[0m')
mySSH.close()
sys.exit(1)
self.cli = 'docker'
self.cliBuildOptions = '--no-cache'
# Workaround for some servers, we need to erase completely the workspace
if self.forcedWorkspaceCleanup:
mySSH.command('echo ' + lPassWord + ' | sudo -S rm -Rf ' + lSourcePath, '\$', 15)
oldRanCommidID = self.ranCommitID
oldRanRepository = self.ranRepository
oldRanAllowMerge = self.ranAllowMerge
self.ranCommitID = self.proxyCommit
self.ranRepository = 'https://github.com/EpiSci/oai-lte-5g-multi-ue-proxy.git'
self.ranAllowMerge = False
self._createWorkspace(mySSH, lPassWord, lSourcePath)
# to prevent accidentally overwriting data that might be used later
self.ranCommitID = oldRanCommidID
self.ranRepository = oldRanRepository
self.ranAllowMerge = oldRanAllowMerge
# Let's remove any previous run artifacts if still there
mySSH.command(self.cli + ' image prune --force', '\$', 30)
# Remove any previous proxy image
mySSH.command(self.cli + ' image rm oai-lte-multi-ue-proxy:latest || true', '\$', 30)
tag = self.proxyCommit
logging.debug('building L2sim proxy image for tag ' + tag)
# check if the corresponding proxy image with tag exists. If not, build it
mySSH.command(self.cli + ' image inspect --format=\'Size = {{.Size}} bytes\' proxy:' + tag, '\$', 5)
buildProxy = mySSH.getBefore().count('o such image') != 0
if buildProxy:
mySSH.command(self.cli + ' build ' + self.cliBuildOptions + ' --target oai-lte-multi-ue-proxy --tag proxy:' + tag + ' --file docker/Dockerfile.ubuntu18.04 . > cmake_targets/log/proxy-build.log 2>&1', '\$', 180)
# Note: at this point, OAI images are flattened, but we cannot do this
# here, as the flatten script is not in the proxy repo
mySSH.command(self.cli + ' image inspect --format=\'Size = {{.Size}} bytes\' proxy:' + tag, '\$', 5)
if mySSH.getBefore().count('o such image') != 0:
logging.error('\u001B[1m Build of L2sim proxy failed\u001B[0m')
mySSH.close()
HTML.CreateHtmlTestRow('commit ' + tag, 'KO', CONST.ALL_PROCESSES_OK)
HTML.CreateHtmlTabFooter(False)
sys.exit(1)
else:
logging.debug('L2sim proxy image for tag ' + tag + ' already exists, skipping build')
# retag the build images to that we pick it up later
mySSH.command('docker image tag proxy:' + tag + ' oai-lte-multi-ue-proxy:latest', '\$', 5)
# no merge: is a push to develop, tag the image so we can push it to the registry
if not self.ranAllowMerge:
mySSH.command('docker image tag proxy:' + tag + ' proxy:develop', '\$', 5)
# we assume that the host on which this is built will also run the proxy. The proxy
# currently requires the following command, and the docker-compose up mechanism of
# the CI does not allow to run arbitrary commands. Note that the following actually
# belongs to the deployment, not the build of the proxy...
logging.warning('the following command belongs to deployment, but no mechanism exists to exec it there!')
mySSH.command('sudo ifconfig lo: 127.0.0.2 netmask 255.0.0.0 up', '\$', 5)
# Analyzing the logs
if buildProxy:
self.testCase_id = HTML.testCase_id
mySSH.command('cd ' + lSourcePath + '/cmake_targets', '\$', 5)
mySSH.command('mkdir -p proxy_build_log_' + self.testCase_id, '\$', 5)
mySSH.command('mv log/* ' + 'proxy_build_log_' + self.testCase_id, '\$', 5)
if (os.path.isfile('./proxy_build_log_' + self.testCase_id + '.zip')):
os.remove('./proxy_build_log_' + self.testCase_id + '.zip')
if (os.path.isdir('./proxy_build_log_' + self.testCase_id)):
shutil.rmtree('./proxy_build_log_' + self.testCase_id)
mySSH.command('zip -r -qq proxy_build_log_' + self.testCase_id + '.zip proxy_build_log_' + self.testCase_id, '\$', 5)
mySSH.copyin(lIpAddr, lUserName, lPassWord, lSourcePath + '/cmake_targets/build_log_' + self.testCase_id + '.zip', '.')
# don't delete such that we might recover the zips
#mySSH.command('rm -f build_log_' + self.testCase_id + '.zip','\$', 5)
# Cleaning any created tmp volume
mySSH.command(self.cli + ' volume prune --force || true','\$', 15)
mySSH.close()
logging.info('\u001B[1m Building L2sim Proxy Image Pass\u001B[0m')
HTML.CreateHtmlTestRow('commit ' + tag, 'OK', CONST.ALL_PROCESSES_OK)
HTML.CreateHtmlNextTabHeaderTestRow(self.collectInfo, self.allImagesSize)
def Copy_Image_to_Test_Server(self, HTML):
imageTag = 'develop'
if (self.ranAllowMerge):
+6 -1
View File
@@ -102,7 +102,7 @@ def AssignParams(params_dict):
def GetParametersFromXML(action):
if action == 'Build_eNB' or action == 'Build_Image':
if action == 'Build_eNB' or action == 'Build_Image' or action == 'Build_Proxy':
RAN.Build_eNB_args=test.findtext('Build_eNB_args')
CONTAINERS.imageKind=test.findtext('kind')
forced_workspace_cleanup = test.findtext('forced_workspace_cleanup')
@@ -138,6 +138,9 @@ def GetParametersFromXML(action):
RAN.backgroundBuild=True
else:
RAN.backgroundBuild=False
proxy_commit = test.findtext('proxy_commit')
if proxy_commit is not None:
CONTAINERS.proxyCommit = proxy_commit
elif action == 'WaitEndBuild_eNB':
RAN.Build_eNB_args=test.findtext('Build_eNB_args')
@@ -915,6 +918,8 @@ elif re.match('^TesteNB$', mode, re.IGNORECASE) or re.match('^TestUE$', mode, re
HTML=ldpc.Run_PhySim(HTML,CONST,id)
elif action == 'Build_Image':
CONTAINERS.BuildImage(HTML)
elif action == 'Build_Proxy':
CONTAINERS.BuildProxy(HTML)
elif action == 'Copy_Image_to_Test':
CONTAINERS.Copy_Image_to_Test_Server(HTML)
elif action == 'Deploy_Object':
+1
View File
@@ -1,3 +1,4 @@
- Build_Proxy
- Build_PhySim
- Run_PhySim
- Build_eNB
@@ -0,0 +1,42 @@
<!--
Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
contributor license agreements. See the NOTICE file distributed with
this work for additional information regarding copyright ownership.
The OpenAirInterface Software Alliance licenses this file to You under
the OAI Public License, Version 1.1 (the "License"); you may not use this file
except in compliance with the License.
You may obtain a copy of the License at
http://www.openairinterface.org/?page_id=698
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
For more information about the OpenAirInterface (OAI) Software Alliance:
contact@openairinterface.org
-->
<testCaseList>
<htmlTabRef>l2sim-5gnr-proxy-build</htmlTabRef>
<htmlTabName>Build L2sim proxy image</htmlTabName>
<htmlTabIcon>wrench</htmlTabIcon>
<repeatCount>1</repeatCount>
<TestCaseRequestedList>
000001
</TestCaseRequestedList>
<TestCaseExclusionList></TestCaseExclusionList>
<testCase id="000001">
<class>Build_Proxy</class>
<desc>Build L2sim Proxy Image</desc>
<eNB_instance>1</eNB_instance>
<eNB_serverId>1</eNB_serverId>
<forced_workspace_cleanup>True</forced_workspace_cleanup>
<proxy_commit>56cfdc0</proxy_commit>
</testCase>
</testCaseList>
+14
View File
@@ -271,6 +271,12 @@ if (SANITIZE_ADDRESS)
# wrong in the pthread library, or something subtly wrong in this CMakeLists.txt. Use Ubuntu 20.04 instead.
endif ()
add_boolean_option(SANITIZE_UNDEFINED False "enable the undefined behavior sanitizer (UBSan)")
if (SANITIZE_UNDEFINED)
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fsanitize=undefined -fno-sanitize-recover=all")
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fsanitize=undefined -fno-sanitize-recover=all")
endif ()
add_definitions("-DASN_DISABLE_OER_SUPPORT")
#########################
@@ -1804,7 +1810,15 @@ set(NR_PDCP_SRC
${OPENAIR2_DIR}/LAYER2/nr_pdcp/nr_pdcp_timer_thread.c
${OPENAIR2_DIR}/LAYER2/nr_pdcp/nr_pdcp_security_nea2.c
${OPENAIR2_DIR}/LAYER2/nr_pdcp/nr_pdcp_integrity_nia2.c
${OPENAIR2_DIR}/LAYER2/nr_pdcp/nr_pdcp_integrity_nia1.c
${OPENAIR2_DIR}/LAYER2/nr_pdcp/asn1_utils.c
#hack: include these files to compile the nr phy simulators
#these files should not be here, will be removed at some point when the
#computation is done directly inside nr_pdcp_integrity_nia1.c instead
#of reusing code of osa_stream_eia.c
${OPENAIR2_DIR}/UTIL/OSA/osa_stream_eia.c
${OPENAIR2_DIR}/UTIL/OSA/osa_snow3g.c
${OPENAIR2_DIR}/UTIL/OSA/osa_rijndael.c
)
set(NR_SDAP_SRC
+11 -1
View File
@@ -171,8 +171,12 @@ Options:
Skip build for shared libraries to reduce compilation time when building frequently for debugging purposes
--ninja
Tell cmake to use the Ninja build system. Without, will generate make files
--sanitize
Shortcut for usage of --sanitize-address --sanitize-undefined
--sanitize-address | -fsanitize=address
Enable the address sanitizer on all targets
Enable the address sanitizer on all targets
--sanitize-undefined | -fsanitize=undefined
Enable the undefined behavior sanitizer on all targets
--ittiSIM
Makes the itti simulator
-h | --help
@@ -451,10 +455,16 @@ function main() {
CMAKE_CMD="$CMAKE_CMD -GNinja"
MAKE_CMD=ninja
shift;;
--sanitize)
CMAKE_CMD="$CMAKE_CMD -DSANITIZE_ADDRESS=True -DSANITIZE_UNDEFINED=True"
shift;;
--sanitize-address | -fsanitize=address)
grep -sq "Ubuntu 18.04" /etc/os-release && echo_error "Bug in OS with this option, see CMakeLists.txt"
CMAKE_CMD="$CMAKE_CMD -DSANITIZE_ADDRESS=True"
shift;;
--sanitize-undefined | -fundefined=address)
CMAKE_CMD="$CMAKE_CMD -DSANITIZE_UNDEFINED=True"
shift;;
--ittiSIM)
ittiSIM=1
CMAKE_CMD="$CMAKE_CMD -DITTI_SIM=True"
+2 -2
View File
@@ -62,7 +62,7 @@ typedef struct time_stats {
oai_cputime_t in; /*!< \brief time at measure starting point */
oai_cputime_t diff; /*!< \brief average difference between time at starting point and time at endpoint*/
oai_cputime_t p_time; /*!< \brief absolute process duration */
oai_cputime_t diff_square; /*!< \brief process duration square */
double diff_square; /*!< \brief process duration square */
oai_cputime_t max; /*!< \brief maximum difference between time at starting point and time at endpoint*/
int trials; /*!< \brief number of start point - end point iterations */
int meas_flag; /*!< \brief 1: stop_meas not called (consecutive calls of start_meas) */
@@ -156,7 +156,7 @@ static inline void stop_meas(time_stats_t *ts) {
ts->diff += (out-ts->in);
/// process duration is the difference between two clock points
ts->p_time = (out-ts->in);
ts->diff_square += (out-ts->in)*(out-ts->in);
ts->diff_square += ((double)out-ts->in)*((double)out-ts->in);
if ((out-ts->in) > ts->max)
ts->max = out-ts->in;
+9 -2
View File
@@ -440,6 +440,10 @@ The following features are valid for the gNB and the 5G-NR UE.
- PTRS support
- Support for 1, 2 and 4 RX antennas
- Support for up to 2 layers (currently limited to DMRS configuration type 2)
* Measurements based on NR-CSIRS
- RI, PMI and CQI computation
- Support for 1 and 2 RX antennas
- Support for up to 2 layers
* NR-PUSCH (including Segmentation, LDPC encoding, rate matching, scrambling, modulation, RB mapping, etc).
- PUSCH mapping type A and B
- DMRS configuration type 1 and 2
@@ -488,12 +492,15 @@ The following features are valid for the gNB and the 5G-NR UE.
* UCI processing
- ACK/NACK processing
- Triggering periodic SR
- CSI measurement reporting (SSB RSRP only)
* DLSH scheduler
- CSI measurement reporting
* DLSCH scheduler
- Configuration of fapi PDU according to DCI
- HARQ procedures
* ULSCH scheduler
- Configuration of fapi PDU according to DCI
* NR-CSIRS scheduler
- Scheduling of NR-CSIRS reception
- Fill UCI for CSI measurement reporting
* Scheduler procedures for SRS transmission
- Periodic SRS transmission
* Bandwidth part (BWP) operation
+9 -16
View File
@@ -71,10 +71,6 @@ reboot
# https://docs.docker.com/compose/install/
sudo curl -L "https://github.com/docker/compose/releases/download/1.29.2/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose
docker network create --driver=bridge --subnet=192.168.70.128/26 -o "com.docker.network.bridge.name"="demo-oai" demo-oai-public-net
sudo service docker restart
```
## 2.2 OAI CN5G Setup
@@ -82,39 +78,36 @@ sudo service docker restart
```bash
# Git oai-cn5g-fed repository
git clone https://gitlab.eurecom.fr/oai/cn5g/oai-cn5g-fed.git ~/oai-cn5g-fed
cd ~/oai-cn5g-fed
git checkout master
./scripts/syncComponents.sh --nrf-branch develop --amf-branch develop --smf-branch develop --spgwu-tiny-branch develop --ausf-branch develop --udm-branch develop --udr-branch develop --upf-vpp-branch develop --nssf-branch develop
# Pull docker images
docker pull oaisoftwarealliance/oai-amf:develop
docker pull oaisoftwarealliance/oai-nrf:develop
docker pull oaisoftwarealliance/oai-smf:develop
docker pull oaisoftwarealliance/oai-udr:develop
docker pull oaisoftwarealliance/oai-udm:develop
docker pull oaisoftwarealliance/oai-ausf:develop
docker pull oaisoftwarealliance/oai-upf-vpp:develop
docker pull oaisoftwarealliance/oai-spgwu-tiny:develop
docker pull oaisoftwarealliance/oai-nssf:develop
docker pull oaisoftwarealliance/trf-gen-cn5g:latest
# Tag docker images
docker image tag oaisoftwarealliance/oai-amf:develop oai-amf:develop
docker image tag oaisoftwarealliance/oai-nrf:develop oai-nrf:develop
docker image tag oaisoftwarealliance/oai-smf:develop oai-smf:develop
docker image tag oaisoftwarealliance/oai-udr:develop oai-udr:develop
docker image tag oaisoftwarealliance/oai-udm:develop oai-udm:develop
docker image tag oaisoftwarealliance/oai-ausf:develop oai-ausf:develop
docker image tag oaisoftwarealliance/oai-upf-vpp:develop oai-upf-vpp:develop
docker image tag oaisoftwarealliance/oai-spgwu-tiny:develop oai-spgwu-tiny:develop
docker image tag oaisoftwarealliance/oai-nssf:develop oai-nssf:develop
docker image tag oaisoftwarealliance/trf-gen-cn5g:latest trf-gen-cn5g:latest
```
## 2.3 OAI CN5G Configuration files
Download and copy the configuration files to ~/oai-cn5g-fed/docker-compose:
- [docker-compose-basic-nrf.yaml](tutorial_resources/docker-compose-basic-nrf.yaml)
- [oai_db.sql](tutorial_resources/oai_db.sql)
Download and copy configuration files:
- Copy [docker-compose-basic-nrf.yaml](tutorial_resources/docker-compose-basic-nrf.yaml) to `~/oai-cn5g-fed/docker-compose`
- Copy [oai_db.sql](tutorial_resources/oai_db.sql) to `~/oai-cn5g-fed/docker-compose/database`
Change permissions on oai_db.sql to prevent mysql permission denied error:
```bash
chmod 644 ~/oai-cn5g-fed/docker-compose/oai_db.sql
chmod 644 ~/oai-cn5g-fed/docker-compose/database/oai_db.sql
```
## 2.4 SIM Card
@@ -175,7 +168,7 @@ cd cmake_targets
```bash
cd ~/oai-cn5g-fed/docker-compose
python3 core-network.py --type start-basic --fqdn yes --scenario 1
python3 core-network.py --type start-basic --scenario 1
```
## 4.2 Run OAI gNB
+9 -16
View File
@@ -72,10 +72,6 @@ reboot
# https://docs.docker.com/compose/install/
sudo curl -L "https://github.com/docker/compose/releases/download/1.29.2/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose
docker network create --driver=bridge --subnet=192.168.70.128/26 -o "com.docker.network.bridge.name"="demo-oai" demo-oai-public-net
sudo service docker restart
```
## 2.2 OAI CN5G Setup
@@ -83,39 +79,36 @@ sudo service docker restart
```bash
# Git oai-cn5g-fed repository
git clone https://gitlab.eurecom.fr/oai/cn5g/oai-cn5g-fed.git ~/oai-cn5g-fed
cd ~/oai-cn5g-fed
git checkout master
./scripts/syncComponents.sh --nrf-branch develop --amf-branch develop --smf-branch develop --spgwu-tiny-branch develop --ausf-branch develop --udm-branch develop --udr-branch develop --upf-vpp-branch develop --nssf-branch develop
# Pull docker images
docker pull oaisoftwarealliance/oai-amf:develop
docker pull oaisoftwarealliance/oai-nrf:develop
docker pull oaisoftwarealliance/oai-smf:develop
docker pull oaisoftwarealliance/oai-udr:develop
docker pull oaisoftwarealliance/oai-udm:develop
docker pull oaisoftwarealliance/oai-ausf:develop
docker pull oaisoftwarealliance/oai-upf-vpp:develop
docker pull oaisoftwarealliance/oai-spgwu-tiny:develop
docker pull oaisoftwarealliance/oai-nssf:develop
docker pull oaisoftwarealliance/trf-gen-cn5g:latest
# Tag docker images
docker image tag oaisoftwarealliance/oai-amf:develop oai-amf:develop
docker image tag oaisoftwarealliance/oai-nrf:develop oai-nrf:develop
docker image tag oaisoftwarealliance/oai-smf:develop oai-smf:develop
docker image tag oaisoftwarealliance/oai-udr:develop oai-udr:develop
docker image tag oaisoftwarealliance/oai-udm:develop oai-udm:develop
docker image tag oaisoftwarealliance/oai-ausf:develop oai-ausf:develop
docker image tag oaisoftwarealliance/oai-upf-vpp:develop oai-upf-vpp:develop
docker image tag oaisoftwarealliance/oai-spgwu-tiny:develop oai-spgwu-tiny:develop
docker image tag oaisoftwarealliance/oai-nssf:develop oai-nssf:develop
docker image tag oaisoftwarealliance/trf-gen-cn5g:latest trf-gen-cn5g:latest
```
## 2.3 OAI CN5G Configuration files
Download and copy the configuration files to ~/oai-cn5g-fed/docker-compose:
- [docker-compose-basic-nrf.yaml](tutorial_resources/docker-compose-basic-nrf.yaml)
- [oai_db.sql](tutorial_resources/oai_db.sql)
Download and copy configuration files:
- Copy [docker-compose-basic-nrf.yaml](tutorial_resources/docker-compose-basic-nrf.yaml) to `~/oai-cn5g-fed/docker-compose`
- Copy [oai_db.sql](tutorial_resources/oai_db.sql) to `~/oai-cn5g-fed/docker-compose/database`
Change permissions on oai_db.sql to prevent mysql permission denied error:
```bash
chmod 644 ~/oai-cn5g-fed/docker-compose/oai_db.sql
chmod 644 ~/oai-cn5g-fed/docker-compose/database/oai_db.sql
```
## 2.4 SIM Card
@@ -193,7 +186,7 @@ The following steps are recommended. Please change the network interface(s) as r
```bash
cd ~/oai-cn5g-fed/docker-compose
python3 core-network.py --type start-basic --fqdn yes --scenario 1
python3 core-network.py --type start-basic --scenario 1
```
## 4.2 Run OAI gNB
@@ -4,8 +4,8 @@ services:
container_name: "mysql"
image: mysql:5.7
volumes:
- ./oai_db.sql:/docker-entrypoint-initdb.d/oai_db.sql
- ./mysql-healthcheck2.sh:/tmp/mysql-healthcheck.sh
- ./database/oai_db.sql:/docker-entrypoint-initdb.d/oai_db.sql
- ./healthscripts/mysql-healthcheck2.sh:/tmp/mysql-healthcheck.sh
environment:
- TZ=Europe/Paris
- MYSQL_DATABASE=oai_db
@@ -21,35 +21,45 @@ services:
public_net:
ipv4_address: 192.168.70.131
oai-udr:
container_name: oai-udr
container_name: "oai-udr"
image: oai-udr:develop
environment:
- TZ=Europe/Paris
- INSTANCE=0
- PID_DIRECTORY=/var/run
- UDR_NAME=OAI_UDR
- UDR_INTERFACE_NAME_FOR_NUDR=eth0
- UDR_INTERFACE_PORT_FOR_NUDR=80
- UDR_INTERFACE_HTTP2_PORT_FOR_NUDR=8080
- USE_HTTP2=no
- UDR_API_VERSION=v1
- MYSQL_IPV4_ADDRESS=192.168.70.131
- MYSQL_USER=test
- MYSQL_PASS=test
- DB_CONNECTION_TIMEOUT=300 # Reset the connection to the DB after expiring the timeout (in second) currently can't be changed
- MYSQL_DB=oai_db
- WAIT_MYSQL=120
- USE_FQDN_DNS=yes
- REGISTER_NRF=yes
- NRF_IPV4_ADDRESS=192.168.70.130
- NRF_PORT=80
- NRF_API_VERSION=v1
- NRF_FQDN=oai-nrf
depends_on:
- mysql
- oai-nrf
networks:
public_net:
ipv4_address: 192.168.70.136
volumes:
- ./udr-healthcheck.sh:/openair-udr/bin/udr-healthcheck.sh
- ./healthscripts/udr-healthcheck.sh:/openair-udr/bin/udr-healthcheck.sh
healthcheck:
test: /bin/bash -c "/openair-udr/bin/udr-healthcheck.sh"
interval: 10s
timeout: 5s
retries: 5
oai-udm:
container_name: oai-udm
container_name: "oai-udm"
image: oai-udm:develop
environment:
- TZ=Europe/Paris
@@ -58,26 +68,33 @@ services:
- UDM_NAME=OAI_UDM
- SBI_IF_NAME=eth0
- SBI_PORT=80
- SBI_HTTP2_PORT=8080
- USE_HTTP2=no
- UDM_VERSION_NB=v1
- USE_FQDN_DNS=yes
- UDR_IP_ADDRESS=192.168.70.136
- UDR_PORT=80
- UDR_VERSION_NB=v1
- UDR_FQDN=oai-udr
- REGISTER_NRF=yes
- NRF_IPV4_ADDRESS=192.168.70.130
- NRF_PORT=80
- NRF_API_VERSION=v1
- NRF_FQDN=oai-nrf
depends_on:
- oai-udr
networks:
public_net:
ipv4_address: 192.168.70.137
volumes:
- ./udm-healthcheck.sh:/openair-udm/bin/udm-healthcheck.sh
- ./healthscripts/udm-healthcheck.sh:/openair-udm/bin/udm-healthcheck.sh
healthcheck:
test: /bin/bash -c "/openair-udm/bin/udm-healthcheck.sh"
interval: 10s
timeout: 5s
retries: 5
oai-ausf:
container_name: oai-ausf
container_name: "oai-ausf"
image: oai-ausf:develop
environment:
- TZ=Europe/Paris
@@ -86,18 +103,25 @@ services:
- AUSF_NAME=OAI_AUSF
- SBI_IF_NAME=eth0
- SBI_PORT=80
- USE_HTTP2
- SBI_HTTP2_PORT
- USE_FQDN_DNS=yes
- UDM_IP_ADDRESS=192.168.70.137
- UDM_PORT=80
- UDM_VERSION_NB=v1
- UDM_FQDN=oai-udm
- REGISTER_NRF=yes
- NRF_IPV4_ADDRESS=192.168.70.130
- NRF_PORT=80
- NRF_API_VERSION=v1
- NRF_FQDN=oai-nrf
depends_on:
- oai-udm
networks:
public_net:
ipv4_address: 192.168.70.138
volumes:
- ./ausf-healthcheck.sh:/openair-ausf/bin/ausf-healthcheck.sh
- ./healthscripts/ausf-healthcheck.sh:/openair-ausf/bin/ausf-healthcheck.sh
healthcheck:
test: /bin/bash -c "/openair-ausf/bin/ausf-healthcheck.sh"
interval: 10s
@@ -107,9 +131,10 @@ services:
container_name: "oai-nrf"
image: oai-nrf:develop
environment:
- TZ=Europe/Paris
- NRF_INTERFACE_NAME_FOR_SBI=eth0
- NRF_INTERFACE_PORT_FOR_SBI=80
- NRF_INTERFACE_HTTP2_PORT_FOR_SBI=9090
- NRF_INTERFACE_HTTP2_PORT_FOR_SBI=8080
- NRF_API_VERSION=v1
- INSTANCE=0
- PID_DIRECTORY=/var/run
@@ -117,7 +142,7 @@ services:
public_net:
ipv4_address: 192.168.70.130
volumes:
- ./nrf-healthcheck.sh:/openair-nrf/bin/nrf-healthcheck.sh
- ./healthscripts/nrf-healthcheck.sh:/openair-nrf/bin/nrf-healthcheck.sh
healthcheck:
test: /bin/bash -c "/openair-nrf/bin/nrf-healthcheck.sh"
interval: 10s
@@ -146,9 +171,7 @@ services:
- PLMN_SUPPORT_MNC=99
- PLMN_SUPPORT_TAC=0x0001
- SST_0=1
- SD_0=1
- SST_1=1
- SD_1=12
- SD_0=0x1
- AMF_INTERFACE_NAME_FOR_NGAP=eth0
- AMF_INTERFACE_NAME_FOR_N11=eth0
- SMF_INSTANCE_ID_0=1
@@ -168,22 +191,30 @@ services:
- OPERATOR_KEY=1006020f0a478bf6b699f15c062e42b3
- NRF_IPV4_ADDRESS=192.168.70.130
- NRF_PORT=80
- EXTERNAL_NRF=no
- NF_REGISTRATION=yes
- SMF_SELECTION=yes
- USE_FQDN_DNS=yes
- EXTERNAL_AUSF=yes
- EXTERNAL_UDM=no
- EXTERNAL_NSSF=no
- USE_HTTP2=no
- NRF_API_VERSION=v1
- NRF_FQDN=oai-nrf
- AUSF_IPV4_ADDRESS=192.168.70.138
- AUSF_PORT=80
- AUSF_API_VERSION=v1
- AUSF_FQDN=oai-ausf
- UDM_IPV4_ADDRESS=192.168.70.137
- UDM_PORT=80
- UDM_API_VERSION=v2
- UDM_FQDN=oai-udm
depends_on:
- mysql
- oai-nrf
- oai-ausf
volumes:
- ./amf-healthcheck.sh:/openair-amf/bin/amf-healthcheck.sh
- ./healthscripts/amf-healthcheck.sh:/openair-amf/bin/amf-healthcheck.sh
healthcheck:
test: /bin/bash -c "/openair-amf/bin/amf-healthcheck.sh"
interval: 10s
@@ -212,26 +243,35 @@ services:
- AMF_FQDN=oai-amf
- UDM_IPV4_ADDRESS=192.168.70.137
- UDM_PORT=80
- UDM_API_VERSION=v1
- UDM_API_VERSION=v2
- UDM_FQDN=oai-udm
- UPF_IPV4_ADDRESS=192.168.70.134
- UPF_FQDN_0=oai-spgwu
- NRF_IPV4_ADDRESS=192.168.70.130
- NRF_PORT=80
- NRF_API_VERSION=v1
- USE_LOCAL_SUBSCRIPTION_INFO=yes
- USE_LOCAL_SUBSCRIPTION_INFO=yes #Set to yes if SMF uses local subscription information instead of from an UDM
- USE_NETWORK_INSTANCE=no #Set yes if network instance is to be used for given UPF
- NRF_FQDN=oai-nrf
- REGISTER_NRF=yes
- DISCOVER_UPF=yes
- USE_FQDN_DNS=yes
- DNN_RANGE1=12.1.1.2 - 12.1.1.128
- DNN_RANGE0=12.2.1.2 - 12.2.1.128
- DNN_NI1=oai
- HTTP_VERSION=1 # Default: 1
- UE_MTU=1500
- DNN_NI0=oai
- TYPE0=IPv4
- DNN_RANGE0=12.1.1.2 - 12.1.1.253
- NSSAI_SST0=1
- NSSAI_SD0=0x1
- SESSION_AMBR_UL0=1000Mbps
- SESSION_AMBR_DL0=1000Mbps
- DEFAULT_CSCF_IPV4_ADDRESS=127.0.0.1 # only needed when ims is being used
- ENABLE_USAGE_REPORTING=no # Set yes if UE USAGE REPORTING is to be done at UPF
depends_on:
- oai-nrf
- oai-amf
volumes:
- ./smf-healthcheck.sh:/openair-smf/bin/smf-healthcheck.sh
- ./healthscripts/smf-healthcheck.sh:/openair-smf/bin/smf-healthcheck.sh
healthcheck:
test: /bin/bash -c "/openair-smf/bin/smf-healthcheck.sh"
interval: 10s
@@ -258,17 +298,23 @@ services:
- MNC03=099
- TAC=1
- GW_ID=1
- THREAD_S1U_PRIO=80
- S1U_THREADS=8
- THREAD_SX_PRIO=81
- SX_THREADS=1
- THREAD_SGI_PRIO=80
- SGI_THREADS=8
- REALM=openairinterface.org
- ENABLE_5G_FEATURES=yes
- REGISTER_NRF=yes
- USE_FQDN_NRF=no
- USE_FQDN_NRF=yes
- UPF_FQDN_5G=oai-spgwu
- NRF_IPV4_ADDRESS=192.168.70.130
- NRF_PORT=80
- NRF_API_VERSION=v1
- NRF_FQDN=oai-nrf
- NSSAI_SST_0=1
- NSSAI_SD_0=1
- NSSAI_SD_0=0x1
- DNN_0=oai
depends_on:
- oai-nrf
@@ -280,7 +326,7 @@ services:
- ALL
privileged: true
volumes:
- ./spgwu-healthcheck.sh:/openair-spgwu-tiny/bin/spgwu-healthcheck.sh
- ./healthscripts/spgwu-healthcheck.sh:/openair-spgwu-tiny/bin/spgwu-healthcheck.sh
healthcheck:
test: /bin/bash -c "/openair-spgwu-tiny/bin/spgwu-healthcheck.sh"
interval: 10s
@@ -290,12 +336,10 @@ services:
public_net:
ipv4_address: 192.168.70.134
oai-ext-dn:
image: ubuntu:bionic
image: trf-gen-cn5g:latest
privileged: true
container_name: oai-ext-dn
entrypoint: /bin/bash -c \
"apt update; apt install -y iptables iproute2 iperf iperf3 iputils-ping;"\
"iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE;"\
"ip route add 12.1.1.0/24 via 192.168.70.134 dev eth0; sleep infinity"
depends_on:
- oai-spgwu
@@ -303,14 +347,14 @@ services:
public_net:
ipv4_address: 192.168.70.135
networks:
# public_net:
# external:
# name: demo-oai-public-net
public_net:
external:
name: demo-oai-public-net
# public_net:
# driver: bridge
# name: demo-oai-public-net
# ipam:
# config:
# - subnet: 192.168.70.128/26
# driver_opts:
# com.docker.network.bridge.name: "demo-oai"
driver: bridge
name: demo-oai-public-net
ipam:
config:
- subnet: 192.168.70.128/26
driver_opts:
com.docker.network.bridge.name: "demo-oai"
+19 -3
View File
@@ -151,10 +151,13 @@ CREATE TABLE `AuthenticationSubscription` (
--
INSERT INTO `AuthenticationSubscription` (`ueid`, `authenticationMethod`, `encPermanentKey`, `protectionParameterId`, `sequenceNumber`, `authenticationManagementField`, `algorithmId`, `encOpcKey`, `encTopcKey`, `vectorGenerationInHss`, `n5gcAuthMethod`, `rgAuthenticationInd`, `supi`) VALUES
('208950000000031', '5G_AKA', '0C0A34601D4F07677303652C0462535B', '0C0A34601D4F07677303652C0462535B', '{\"sqn\": \"000000000020\", \"sqnScheme\": \"NON_TIME_BASED\", \"lastIndexes\": {\"ausf\": 0}}', '8000', 'milenage', '63bfa50ee6523365ff14c1f45f88737d', NULL, NULL, NULL, NULL, '208950000000031');
('2089900007487', '5G_AKA', 'fec86ba6eb707ed08905757b1bb44b8f', 'fec86ba6eb707ed08905757b1bb44b8f', '{\"sqn\": \"000000000000\", \"sqnScheme\": \"NON_TIME_BASED\", \"lastIndexes\": {\"ausf\": 0}}', '8000', 'milenage', 'C42449363BBAD02B66D16BC975D77CC1', NULL, NULL, NULL, NULL, '2089900007487');
INSERT INTO `AuthenticationSubscription` (`ueid`, `authenticationMethod`, `encPermanentKey`, `protectionParameterId`, `sequenceNumber`, `authenticationManagementField`, `algorithmId`, `encOpcKey`, `encTopcKey`, `vectorGenerationInHss`, `n5gcAuthMethod`, `rgAuthenticationInd`, `supi`) VALUES
('208990000000001', '5G_AKA', 'fec86ba6eb707ed08905757b1bb44b8f', 'fec86ba6eb707ed08905757b1bb44b8f', '{\"sqn\": \"000000000020\", \"sqnScheme\": \"NON_TIME_BASED\", \"lastIndexes\": {\"ausf\": 0}}', '8000', 'milenage', 'C42449363BBAD02B66D16BC975D77CC1', NULL, NULL, NULL, NULL, '208990000000001');
('208990000000001', '5G_AKA', 'fec86ba6eb707ed08905757b1bb44b8f', 'fec86ba6eb707ed08905757b1bb44b8f', '{\"sqn\": \"000000000000\", \"sqnScheme\": \"NON_TIME_BASED\", \"lastIndexes\": {\"ausf\": 0}}', '8000', 'milenage', 'C42449363BBAD02B66D16BC975D77CC1', NULL, NULL, NULL, NULL, '208990000000001');
INSERT INTO `AuthenticationSubscription` (`ueid`, `authenticationMethod`, `encPermanentKey`, `protectionParameterId`, `sequenceNumber`, `authenticationManagementField`, `algorithmId`, `encOpcKey`, `encTopcKey`, `vectorGenerationInHss`, `n5gcAuthMethod`, `rgAuthenticationInd`, `supi`) VALUES
('208990000000002', '5G_AKA', 'fec86ba6eb707ed08905757b1bb44b8f', 'fec86ba6eb707ed08905757b1bb44b8f', '{\"sqn\": \"000000000000\", \"sqnScheme\": \"NON_TIME_BASED\", \"lastIndexes\": {\"ausf\": 0}}', '8000', 'milenage', 'C42449363BBAD02B66D16BC975D77CC1', NULL, NULL, NULL, NULL, '208990000000002');
INSERT INTO `AuthenticationSubscription` (`ueid`, `authenticationMethod`, `encPermanentKey`, `protectionParameterId`, `sequenceNumber`, `authenticationManagementField`, `algorithmId`, `encOpcKey`, `encTopcKey`, `vectorGenerationInHss`, `n5gcAuthMethod`, `rgAuthenticationInd`, `supi`) VALUES
('208990000000003', '5G_AKA', 'fec86ba6eb707ed08905757b1bb44b8f', 'fec86ba6eb707ed08905757b1bb44b8f', '{\"sqn\": \"000000000000\", \"sqnScheme\": \"NON_TIME_BASED\", \"lastIndexes\": {\"ausf\": 0}}', '8000', 'milenage', 'C42449363BBAD02B66D16BC975D77CC1', NULL, NULL, NULL, NULL, '208990000000003');
-- --------------------------------------------------------
@@ -203,6 +206,19 @@ CREATE TABLE `SessionManagementSubscriptionData` (
`3gppChargingCharacteristics` varchar(50) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
--
-- Dumping data for table `SessionManagementSubscriptionData`
--
INSERT INTO `SessionManagementSubscriptionData` (`ueid`, `servingPlmnid`, `singleNssai`, `dnnConfigurations`) VALUES
('2089900007487', '20899', '{\"sst\": 1, \"sd\": \"1\"}','{\"oai\":{\"pduSessionTypes\":{ \"defaultSessionType\": \"IPV4\"},\"sscModes\": {\"defaultSscMode\": \"SSC_MODE_1\"},\"5gQosProfile\": {\"5qi\": 6,\"arp\":{\"priorityLevel\": 1,\"preemptCap\": \"NOT_PREEMPT\",\"preemptVuln\":\"NOT_PREEMPTABLE\"},\"priorityLevel\":1},\"sessionAmbr\":{\"uplink\":\"1000Mbps\", \"downlink\":\"1000Mbps\"},\"staticIpAddress\":[{\"ipv4Addr\": \"12.1.1.2\"}]}}');
INSERT INTO `SessionManagementSubscriptionData` (`ueid`, `servingPlmnid`, `singleNssai`, `dnnConfigurations`) VALUES
('208990000000001', '20899', '{\"sst\": 1, \"sd\": \"1\"}','{\"oai\":{\"pduSessionTypes\":{ \"defaultSessionType\": \"IPV4\"},\"sscModes\": {\"defaultSscMode\": \"SSC_MODE_1\"},\"5gQosProfile\": {\"5qi\": 6,\"arp\":{\"priorityLevel\": 1,\"preemptCap\": \"NOT_PREEMPT\",\"preemptVuln\":\"NOT_PREEMPTABLE\"},\"priorityLevel\":1},\"sessionAmbr\":{\"uplink\":\"1000Mbps\", \"downlink\":\"1000Mbps\"},\"staticIpAddress\":[{\"ipv4Addr\": \"12.1.1.2\"}]}}');
INSERT INTO `SessionManagementSubscriptionData` (`ueid`, `servingPlmnid`, `singleNssai`, `dnnConfigurations`) VALUES
('208990000000002', '20899', '{\"sst\": 1, \"sd\": \"1\"}','{\"oai\":{\"pduSessionTypes\":{ \"defaultSessionType\": \"IPV4\"},\"sscModes\": {\"defaultSscMode\": \"SSC_MODE_1\"},\"5gQosProfile\": {\"5qi\": 6,\"arp\":{\"priorityLevel\": 1,\"preemptCap\": \"NOT_PREEMPT\",\"preemptVuln\":\"NOT_PREEMPTABLE\"},\"priorityLevel\":1},\"sessionAmbr\":{\"uplink\":\"1000Mbps\", \"downlink\":\"1000Mbps\"},\"staticIpAddress\":[{\"ipv4Addr\": \"12.1.1.3\"}]}}');
INSERT INTO `SessionManagementSubscriptionData` (`ueid`, `servingPlmnid`, `singleNssai`, `dnnConfigurations`) VALUES
('208990000000003', '20899', '{\"sst\": 1, \"sd\": \"1\"}','{\"oai\":{\"pduSessionTypes\":{ \"defaultSessionType\": \"IPV4\"},\"sscModes\": {\"defaultSscMode\": \"SSC_MODE_1\"},\"5gQosProfile\": {\"5qi\": 6,\"arp\":{\"priorityLevel\": 1,\"preemptCap\": \"NOT_PREEMPT\",\"preemptVuln\":\"NOT_PREEMPTABLE\"},\"priorityLevel\":1},\"sessionAmbr\":{\"uplink\":\"1000Mbps\", \"downlink\":\"1000Mbps\"},\"staticIpAddress\":[{\"ipv4Addr\": \"12.1.1.4\"}]}}');
-- --------------------------------------------------------
--
+4
View File
@@ -18,6 +18,10 @@ if [[ -v USE_SA_NFAPI_VNF ]]; then cp $PREFIX/etc/gnb.sa.nfapi.vnf.conf $PREFIX/
# Sometimes, the templates are not enough. We mount a conf file on $PREFIX/etc. It can be a template itself.
if [[ -v USE_VOLUMED_CONF ]]; then cp $PREFIX/etc/mounted.conf $PREFIX/etc/gnb.conf; fi
# Resolve AMF FQDN
AMF_FQDN=${AMF_FQDN:-oai-amf-svc}
if ($USE_FQDN); then AMF_IP_ADDRESS=(`getent hosts $AMF_FQDN | awk '{print $1}'`); fi
# Only this template will be manipulated
CONFIG_FILES=`ls $PREFIX/etc/gnb.conf || true`
-3
View File
@@ -59,9 +59,6 @@ extern void set_function_spec_param(RU_t *ru);
extern void reset_opp_meas(void);
extern void print_opp_meas(void);
extern void init_fep_thread(PHY_VARS_gNB *);
void init_gNB_afterRU(void);
extern int stop_L1L2(module_id_t gnb_id);
@@ -1,64 +0,0 @@
SNR BLER BER UNCODED_BER ENCODER_MEAN ENCODER_STD ENCODER_MAX DECODER_TIME_MEAN DECODER_TIME_STD DECODER_TIME_MAX DECODER_ITER_MEAN DECODER_ITER_STD DECODER_ITER_MAX
-2.000000 1.000000 0.346185 0.258473 44.551218 31.688925 357.883903 217.655668 12.810778 326.852166 5.000000 0.000000 5
-1.900000 1.000000 0.345395 0.256275 40.787109 4.190954 65.926488 215.687102 4.300128 230.585721 5.000000 0.000000 5
-1.800000 1.000000 0.343100 0.253634 40.748628 3.912915 56.669470 215.314020 4.139156 227.806468 5.000000 0.000000 5
-1.700000 1.000000 0.341806 0.250634 40.550845 3.347808 56.032851 216.839001 5.959734 244.483352 5.000000 0.000000 5
-1.600000 1.000000 0.339245 0.248129 40.457158 3.735092 56.853508 215.747244 4.995522 242.867659 5.000000 0.000000 5
-1.500000 1.000000 0.337230 0.245763 41.178595 4.297429 56.265874 215.785600 4.151781 227.795995 5.000000 0.000000 5
-1.400000 1.000000 0.335131 0.243311 39.915221 2.739586 55.454917 216.866764 6.547848 251.528327 5.000000 0.000000 5
-1.300000 1.000000 0.333085 0.240664 40.119215 3.044973 55.978253 216.208443 4.459816 228.810686 5.000000 0.000000 5
-1.200000 1.000000 0.330664 0.238769 40.507713 2.998241 55.701876 215.868796 3.778455 226.049304 5.000000 0.000000 5
-1.100000 1.000000 0.329130 0.235812 41.038895 4.522472 56.760814 215.654663 4.746822 236.021980 5.000000 0.000000 5
-1.000000 1.000000 0.325980 0.233534 41.067622 4.626711 57.444142 215.260535 3.481966 225.512853 5.000000 0.000000 5
-0.900000 1.000000 0.323823 0.230863 40.683316 3.689159 56.208182 215.560917 5.180017 243.603452 5.000000 0.000000 5
-0.800000 1.000000 0.321004 0.228222 41.643513 4.717568 58.502452 215.630891 4.283475 238.574145 5.000000 0.000000 5
-0.700000 1.000000 0.317983 0.225520 41.214547 3.941824 56.054211 215.910346 4.375081 227.444626 5.000000 0.000000 5
-0.600000 1.000000 0.316243 0.222903 40.834442 4.370416 56.765508 215.153296 3.617927 226.280086 5.000000 0.000000 5
-0.500000 1.000000 0.312886 0.220473 40.178174 4.185502 64.657291 219.647151 4.454154 236.473446 5.000000 0.000000 5
-0.400000 1.000000 0.309757 0.217536 40.240385 3.172484 55.751563 217.761119 3.900779 228.757195 5.000000 0.000000 5
-0.300000 1.000000 0.305464 0.215229 40.852271 3.761739 56.158869 217.830497 4.087453 230.237764 5.000000 0.000000 5
-0.200000 1.000000 0.302919 0.212364 40.531166 3.688281 56.426841 217.657657 5.498697 253.516146 5.000000 0.000000 5
-0.100000 1.000000 0.298246 0.209310 41.058364 4.140510 59.959571 217.519279 4.087389 228.768313 5.000000 0.000000 5
0.000000 1.000000 0.294110 0.207107 40.436486 3.604369 55.788895 217.853044 4.012624 236.118036 5.000000 0.000000 5
0.100000 1.000000 0.288139 0.204033 40.603738 4.045866 57.560760 217.046816 4.583841 244.429411 5.000000 0.000000 5
0.200000 1.000000 0.285604 0.201954 40.494607 3.886199 59.431970 217.322824 4.080988 233.317513 5.000000 0.000000 5
0.300000 1.000000 0.278478 0.198929 40.311327 3.452837 56.124657 217.319394 4.434358 232.534720 5.000000 0.000000 5
0.400000 1.000000 0.270992 0.196299 40.649243 3.415612 56.204178 218.079445 4.990947 245.055337 5.000000 0.000000 5
0.500000 1.000000 0.263944 0.193661 40.464299 3.622703 56.602842 218.555364 3.936432 229.481159 5.000000 0.000000 5
0.600000 1.000000 0.256340 0.191194 40.200314 2.474984 53.432412 216.547260 3.695211 227.198078 5.000000 0.000000 5
0.700000 1.000000 0.251578 0.188606 40.111945 3.029821 54.900896 216.581752 4.247622 237.358365 5.000000 0.000000 5
0.800000 1.000000 0.234558 0.184742 39.533282 1.182169 42.753097 215.462335 2.960246 226.716604 5.000000 0.000000 5
0.900000 1.000000 0.225915 0.182691 39.851294 1.108193 42.180342 216.404194 4.450720 228.482353 5.000000 0.000000 5
1.000000 1.000000 0.216180 0.179994 40.721936 3.302539 56.032206 217.082196 4.599188 227.979232 5.000000 0.000000 5
1.100000 1.000000 0.203481 0.177332 41.006217 3.798207 56.014901 216.204345 4.292145 227.297386 5.000000 0.000000 5
1.200000 1.000000 0.188297 0.174121 40.739289 3.269948 56.653507 216.585873 6.250858 251.207034 5.000000 0.000000 5
1.300000 1.000000 0.172624 0.171622 41.215540 4.783342 55.692883 215.885639 3.629370 226.473280 5.000000 0.000000 5
1.400000 1.000000 0.156483 0.169110 40.289903 3.749338 56.290861 215.663761 4.176366 225.824735 5.000000 0.000000 5
1.500000 1.000000 0.136293 0.165692 42.208932 6.070189 69.182665 216.390504 4.816283 235.417446 5.000000 0.000000 5
1.600000 1.000000 0.125127 0.163325 40.890581 3.941185 56.491504 215.752348 4.426511 226.425984 5.000000 0.000000 5
1.700000 1.000000 0.104593 0.159971 41.263557 4.128935 57.062514 217.284932 5.311288 249.647163 5.000000 0.000000 5
1.800000 1.000000 0.091397 0.157460 40.273078 3.062810 55.546913 217.252505 6.331426 251.175692 5.000000 0.000000 5
1.900000 1.000000 0.078256 0.154628 40.407489 3.419342 56.316166 216.967648 4.712664 245.093313 5.000000 0.000000 5
2.000000 1.000000 0.065221 0.152571 40.660365 4.317854 57.537407 216.198346 4.991856 245.173269 5.000000 0.000000 5
2.100000 1.000000 0.053694 0.148885 40.355654 4.062614 60.051963 215.797667 4.447252 236.221454 5.000000 0.000000 5
2.200000 1.000000 0.042182 0.146229 40.613562 4.124655 56.201536 216.117304 4.060825 227.115987 5.000000 0.000000 5
2.300000 1.000000 0.034334 0.143612 40.465884 3.541452 55.067611 215.575953 4.891719 244.546802 5.000000 0.000000 5
2.400000 1.000000 0.026641 0.140869 41.074690 4.697458 61.619188 216.069185 4.700827 233.830937 5.000000 0.000000 5
2.500000 1.000000 0.019976 0.138112 40.766971 4.274128 58.871741 215.761570 5.633731 249.753931 5.000000 0.000000 5
2.600000 1.000000 0.012826 0.135122 40.559343 2.952804 54.017706 215.835161 4.039993 226.822103 5.000000 0.000000 5
2.700000 1.000000 0.010550 0.132915 40.985193 3.330639 55.013950 215.975836 4.240744 227.040703 5.000000 0.000000 5
2.800000 1.000000 0.007327 0.130133 39.778804 3.002485 56.610555 216.462786 7.082268 265.051418 5.000000 0.000000 5
2.900000 1.000000 0.004038 0.126763 40.327795 3.934211 55.515352 215.982666 4.626198 230.696124 5.000000 0.000000 5
3.000000 1.000000 0.003087 0.124336 40.337807 3.537021 55.101627 215.468662 4.177203 230.789145 5.000000 0.000000 5
3.100000 1.000000 0.001576 0.121689 39.812195 3.116738 55.422687 215.797778 4.091192 225.897780 5.000000 0.000000 5
3.200000 0.980000 0.001000 0.118928 39.853764 2.871322 56.405555 215.562722 4.187466 232.598421 5.000000 0.000000 5
3.300000 0.960000 0.000623 0.116065 40.440328 3.580650 56.738889 216.165848 4.735158 240.329999 5.000000 0.000000 5
3.400000 0.850000 0.000303 0.113505 40.974107 4.291544 56.280236 215.889562 4.448049 237.556780 5.000000 0.000000 5
3.500000 0.690000 0.000152 0.111010 41.508631 4.251791 56.198873 216.740295 4.889693 242.922934 5.000000 0.000000 5
3.600000 0.530000 0.000102 0.108493 40.065231 3.643794 57.120823 216.887338 5.242621 250.003843 5.000000 0.000000 5
3.700000 0.320000 0.000043 0.105612 40.462159 4.162383 56.782173 216.465615 3.846314 227.022697 5.000000 0.000000 5
3.800000 0.210000 0.000032 0.103084 42.192455 6.207380 64.648964 217.030913 4.482820 228.095918 5.000000 0.000000 5
3.900000 0.110000 0.000013 0.100391 40.640286 3.715782 55.922914 217.726055 4.553212 236.362804 5.000000 0.000000 5
4.000000 0.050000 0.000006 0.097518 40.437760 2.838308 54.764308 218.230040 4.309275 237.932625 5.000000 0.000000 5
4.100000 0.020000 0.000002 0.095436 41.347934 4.608500 64.182062 217.408836 4.385757 228.219627 5.000000 0.000000 5
4.200000 0.000000 0.000000 0.092396 40.782371 3.621708 55.984245 217.579878 4.102149 228.145363 5.000000 0.000000 5
@@ -20,6 +20,7 @@
#define FAPI_NR_RX_PDU_TYPE_DLSCH 0x03
#define FAPI_NR_DCI_IND 0x04
#define FAPI_NR_RX_PDU_TYPE_RAR 0x05
#define FAPI_NR_CSIRS_IND 0x06
#define FAPI_NR_SIBS_MASK_SIB1 0x1
@@ -36,9 +36,6 @@
*/
typedef struct {
uint8_t uci_format;
uint8_t uci_channel;
@@ -50,7 +47,14 @@ typedef struct {
uint32_t sr;
} fapi_nr_uci_pdu_rel15_t;
typedef struct {
uint32_t rsrp;
int rsrp_dBm;
uint8_t rank_indicator;
uint8_t i1;
uint8_t i2;
uint8_t cqi;
} fapi_nr_csirs_measurements_t;
typedef struct {
/// frequency_domain_resource;
@@ -87,7 +91,7 @@ typedef struct {
// N_CCE is L, or number of CCEs for DCI
int N_CCE;
uint8_t payloadSize;
uint8_t payloadBits[16];
uint8_t payloadBits[16] __attribute__((aligned(16))); // will be cast as uint64
//fapi_nr_dci_pdu_rel15_t dci;
} fapi_nr_dci_indication_pdu_t;
@@ -130,6 +134,7 @@ typedef struct {
fapi_nr_pdsch_pdu_t pdsch_pdu;
fapi_nr_ssb_pdu_t ssb_pdu;
fapi_nr_sib_pdu_t sib_pdu;
fapi_nr_csirs_measurements_t csirs_measurements;
};
} fapi_nr_rx_indication_body_t;
@@ -738,7 +738,7 @@ typedef struct {
// The total DCI length (in bits) including padding bits [TS38.212 sec 7.3.1] Range 0->DCI_PAYLOAD_BYTE_LEN*8
uint16_t PayloadSizeBits;
// DCI payload, where the actual size is defined by PayloadSizeBits. The bit order is as following bit0-bit7 are mapped to first byte of MSB - LSB
uint8_t Payload[DCI_PAYLOAD_BYTE_LEN];
uint8_t Payload[DCI_PAYLOAD_BYTE_LEN] __attribute__((aligned(32)));
} nfapi_nr_dl_dci_pdu_t;
@@ -814,7 +814,7 @@ uint8_t phy_threegpplte_turbo_decoder8(int16_t *y,
llr_t *s1,*s2,*yp1,*yp2,*yp;
unsigned int i,j,iind;//,pi;
unsigned char iteration_cnt=0;
unsigned int crc,oldcrc,crc_len;
unsigned int crc, crc_len;
uint8_t temp;
#if defined(__x86_64__) || defined(__i386__)
__m128i *yp128;
@@ -1233,8 +1233,8 @@ uint8_t phy_threegpplte_turbo_decoder8(int16_t *y,
}
// check the CRC
oldcrc= *((unsigned int *)(&decoded_bytes[(n>>3)-crc_len]));
uint32_t oldcrc;
memcpy(&oldcrc, &decoded_bytes[(n >> 3) - crc_len], crc_len);
switch (crc_type) {
case CRC24_A:
oldcrc&=0x00ffffff;
+2 -2
View File
@@ -244,11 +244,11 @@ crc16 (unsigned char * inptr, int bitlen)
while (octetlen-- > 0) {
crc = (crc << 8) ^ (crc16Table[(*inptr++) ^ (crc >> 24)] << 16);
crc = (crc << 8) ^ (((uint32_t)crc16Table[(*inptr++) ^ (crc >> 24)]) << 16);
}
if (resbit > 0)
crc = (crc << resbit) ^ (crc16Table[((*inptr) >> (8 - resbit)) ^ (crc >> (32 - resbit))] << 16);
crc = (crc << resbit) ^ (((uint32_t)crc16Table[(*inptr) >> (8 - resbit) ^ (crc >> (32 - resbit))]) << 16);
return crc;
}
@@ -961,7 +961,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG1(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1028,7 +1029,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG1(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1096,7 +1098,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG1(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1163,7 +1166,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG1(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1230,7 +1234,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG1(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1297,7 +1302,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG1(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1364,7 +1370,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG1(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1431,7 +1438,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG1(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1498,7 +1506,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG1(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1593,7 +1602,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG2(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1660,7 +1670,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG2(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1727,7 +1738,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG2(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1794,7 +1806,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG2(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1861,7 +1874,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG2(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
@@ -1928,7 +1942,8 @@ static inline uint32_t nrLDPC_cnProcPc_BG2(t_nrLDPC_lut* p_lut, int8_t* cnProcBu
// If no error pcRes should be 0
// Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here
if (pcResSum > 0)
+11 -11
View File
@@ -596,20 +596,20 @@ int phy_init_nr_gNB(PHY_VARS_gNB *gNB,
// CSI RS init
// ceil((NB_RB*8(max allocation per RB)*2(QPSK))/32)
int csi_dmrs_init_length = ((fp->N_RB_DL<<4)>>5)+1;
gNB->nr_csi_rs_info = (nr_csi_rs_info_t *)malloc16_clear(sizeof(nr_csi_rs_info_t));
gNB->nr_csi_rs_info->nr_gold_csi_rs = (uint32_t ***)malloc16(fp->slots_per_frame*sizeof(uint32_t **));
AssertFatal(gNB->nr_csi_rs_info->nr_gold_csi_rs!=NULL, "NR init: csi reference signal malloc failed\n");
gNB->nr_csi_info = (nr_csi_info_t *)malloc16_clear(sizeof(nr_csi_info_t));
gNB->nr_csi_info->nr_gold_csi_rs = (uint32_t ***)malloc16(fp->slots_per_frame * sizeof(uint32_t **));
AssertFatal(gNB->nr_csi_info->nr_gold_csi_rs != NULL, "NR init: csi reference signal malloc failed\n");
for (int slot=0; slot<fp->slots_per_frame; slot++) {
gNB->nr_csi_rs_info->nr_gold_csi_rs[slot] = (uint32_t **)malloc16(fp->symbols_per_slot*sizeof(uint32_t *));
AssertFatal(gNB->nr_csi_rs_info->nr_gold_csi_rs[slot]!=NULL, "NR init: csi reference signal for slot %d - malloc failed\n", slot);
gNB->nr_csi_info->nr_gold_csi_rs[slot] = (uint32_t **)malloc16(fp->symbols_per_slot * sizeof(uint32_t *));
AssertFatal(gNB->nr_csi_info->nr_gold_csi_rs[slot] != NULL, "NR init: csi reference signal for slot %d - malloc failed\n", slot);
for (int symb=0; symb<fp->symbols_per_slot; symb++) {
gNB->nr_csi_rs_info->nr_gold_csi_rs[slot][symb] = (uint32_t *)malloc16(csi_dmrs_init_length*sizeof(uint32_t));
AssertFatal(gNB->nr_csi_rs_info->nr_gold_csi_rs[slot][symb]!=NULL, "NR init: csi reference signal for slot %d symbol %d - malloc failed\n", slot, symb);
gNB->nr_csi_info->nr_gold_csi_rs[slot][symb] = (uint32_t *)malloc16(csi_dmrs_init_length * sizeof(uint32_t));
AssertFatal(gNB->nr_csi_info->nr_gold_csi_rs[slot][symb] != NULL, "NR init: csi reference signal for slot %d symbol %d - malloc failed\n", slot, symb);
}
}
gNB->nr_csi_rs_info->csi_gold_init = cfg->cell_config.phy_cell_id.value;
nr_init_csi_rs(&gNB->frame_parms, gNB->nr_csi_rs_info->nr_gold_csi_rs, cfg->cell_config.phy_cell_id.value);
gNB->nr_csi_info->csi_gold_init = cfg->cell_config.phy_cell_id.value;
nr_init_csi_rs(&gNB->frame_parms, gNB->nr_csi_info->nr_gold_csi_rs, cfg->cell_config.phy_cell_id.value);
for (int id=0; id<NUMBER_OF_NR_SRS_MAX; id++) {
gNB->nr_srs_info[id] = (nr_srs_info_t *)malloc16_clear(sizeof(nr_srs_info_t));
@@ -764,14 +764,14 @@ void phy_free_nr_gNB(PHY_VARS_gNB *gNB)
}
free_and_zero(pusch_dmrs);
uint32_t ***nr_gold_csi_rs = gNB->nr_csi_rs_info->nr_gold_csi_rs;
uint32_t ***nr_gold_csi_rs = gNB->nr_csi_info->nr_gold_csi_rs;
for (int slot = 0; slot < fp->slots_per_frame; slot++) {
for (int symb = 0; symb < fp->symbols_per_slot; symb++)
free_and_zero(nr_gold_csi_rs[slot][symb]);
free_and_zero(nr_gold_csi_rs[slot]);
}
free_and_zero(nr_gold_csi_rs);
free_and_zero(gNB->nr_csi_rs_info);
free_and_zero(gNB->nr_csi_info);
for (int id = 0; id < NUMBER_OF_NR_SRS_MAX; id++) {
for(int i=0; i<MAX_NUM_NR_SRS_AP; i++) {
+17 -56
View File
@@ -34,19 +34,6 @@
#include "PHY/NR_REFSIG/nr_refsig.h"
#include "PHY/MODULATION/nr_modulation.h"
#if 0
void phy_config_harq_ue(module_id_t Mod_id,
int CC_id,
uint8_t gNB_id,
uint16_t max_harq_tx) {
int num_of_threads,num_of_code_words;
PHY_VARS_NR_UE *phy_vars_ue = PHY_vars_UE_g[Mod_id][CC_id];
for (num_of_threads=0; num_of_threads<RX_NB_TH_MAX; num_of_threads++)
for (num_of_code_words=0; num_of_code_words<NR_MAX_NB_CODEWORDS; num_of_code_words++)
phy_vars_ue->ulsch[num_of_threads][gNB_id][num_of_code_words]->Mlimit = max_harq_tx;
}
#endif
extern uint16_t beta_cqi[16];
@@ -159,7 +146,7 @@ int init_nr_ue_signal(PHY_VARS_NR_UE *ue, int nb_connected_gNB)
NR_UE_CSI_RS **const csirs_vars = ue->csirs_vars;
NR_UE_SRS **const srs_vars = ue->srs_vars;
int i, j, slot, symb, gNB_id, th_id;
int i, slot, symb, gNB_id, th_id;
LOG_I(PHY, "Initializing UE vars for gNB TXant %u, UE RXant %u\n", fp->nb_antennas_tx, fp->nb_antennas_rx);
@@ -347,33 +334,20 @@ int init_nr_ue_signal(PHY_VARS_NR_UE *ue, int nb_connected_gNB)
// ceil((NB_RB*8(max allocation per RB)*2(QPSK))/32)
int csi_dmrs_init_length = ((fp->N_RB_DL<<4)>>5)+1;
ue->nr_csi_rs_info = (nr_csi_rs_info_t *)malloc16_clear(sizeof(nr_csi_rs_info_t));
ue->nr_csi_rs_info->nr_gold_csi_rs = (uint32_t ***)malloc16(fp->slots_per_frame*sizeof(uint32_t **));
AssertFatal(ue->nr_csi_rs_info->nr_gold_csi_rs!=NULL, "NR init: csi reference signal malloc failed\n");
ue->nr_csi_info = (nr_csi_info_t *)malloc16_clear(sizeof(nr_csi_info_t));
ue->nr_csi_info->nr_gold_csi_rs = (uint32_t ***)malloc16(fp->slots_per_frame * sizeof(uint32_t **));
AssertFatal(ue->nr_csi_info->nr_gold_csi_rs != NULL, "NR init: csi reference signal malloc failed\n");
for (int slot=0; slot<fp->slots_per_frame; slot++) {
ue->nr_csi_rs_info->nr_gold_csi_rs[slot] = (uint32_t **)malloc16(fp->symbols_per_slot*sizeof(uint32_t *));
AssertFatal(ue->nr_csi_rs_info->nr_gold_csi_rs[slot]!=NULL, "NR init: csi reference signal for slot %d - malloc failed\n", slot);
ue->nr_csi_info->nr_gold_csi_rs[slot] = (uint32_t **)malloc16(fp->symbols_per_slot * sizeof(uint32_t *));
AssertFatal(ue->nr_csi_info->nr_gold_csi_rs[slot] != NULL, "NR init: csi reference signal for slot %d - malloc failed\n", slot);
for (int symb=0; symb<fp->symbols_per_slot; symb++) {
ue->nr_csi_rs_info->nr_gold_csi_rs[slot][symb] = (uint32_t *)malloc16(csi_dmrs_init_length*sizeof(uint32_t));
AssertFatal(ue->nr_csi_rs_info->nr_gold_csi_rs[slot][symb]!=NULL, "NR init: csi reference signal for slot %d symbol %d - malloc failed\n", slot, symb);
ue->nr_csi_info->nr_gold_csi_rs[slot][symb] = (uint32_t *)malloc16(csi_dmrs_init_length * sizeof(uint32_t));
AssertFatal(ue->nr_csi_info->nr_gold_csi_rs[slot][symb] != NULL, "NR init: csi reference signal for slot %d symbol %d - malloc failed\n", slot, symb);
}
}
ue->nr_csi_rs_info->noise_power = (uint32_t*)malloc16_clear(sizeof(uint32_t));
ue->nr_csi_rs_info->csi_rs_generated_signal = (int32_t **)malloc16(NR_MAX_NB_PORTS * sizeof(int32_t *) );
ue->nr_csi_info->csi_rs_generated_signal = (int32_t **)malloc16(NR_MAX_NB_PORTS * sizeof(int32_t *) );
for (i=0; i<NR_MAX_NB_PORTS; i++) {
ue->nr_csi_rs_info->csi_rs_generated_signal[i] = (int32_t *) malloc16_clear(fp->samples_per_frame_wCP * sizeof(int32_t));
}
ue->nr_csi_rs_info->csi_rs_received_signal = (int32_t **)malloc16(fp->nb_antennas_rx * sizeof(int32_t *) );
ue->nr_csi_rs_info->csi_rs_ls_estimated_channel = (int32_t ***)malloc16(fp->nb_antennas_rx * sizeof(int32_t **) );
ue->nr_csi_rs_info->csi_rs_estimated_channel_freq = (int32_t ***)malloc16(fp->nb_antennas_rx * sizeof(int32_t **) );
for (i=0; i<fp->nb_antennas_rx; i++) {
ue->nr_csi_rs_info->csi_rs_received_signal[i] = (int32_t *) malloc16_clear(fp->samples_per_frame_wCP * sizeof(int32_t));
ue->nr_csi_rs_info->csi_rs_ls_estimated_channel[i] = (int32_t **) malloc16_clear(NR_MAX_NB_PORTS * sizeof(int32_t *));
ue->nr_csi_rs_info->csi_rs_estimated_channel_freq[i] = (int32_t **) malloc16_clear(NR_MAX_NB_PORTS * sizeof(int32_t *));
for (j=0; j<NR_MAX_NB_PORTS; j++) {
ue->nr_csi_rs_info->csi_rs_ls_estimated_channel[i][j] = (int32_t *) malloc16_clear(fp->ofdm_symbol_size * sizeof(int32_t));
ue->nr_csi_rs_info->csi_rs_estimated_channel_freq[i][j] = (int32_t *) malloc16_clear(fp->ofdm_symbol_size * sizeof(int32_t));
}
ue->nr_csi_info->csi_rs_generated_signal[i] = (int32_t *) malloc16_clear(fp->samples_per_frame_wCP * sizeof(int32_t));
}
ue->nr_srs_info = (nr_srs_info_t *)malloc16_clear(sizeof(nr_srs_info_t));
@@ -470,7 +444,7 @@ void term_nr_ue_signal(PHY_VARS_NR_UE *ue, int nb_connected_gNB)
free_and_zero(ue->pdsch_vars[th_id][gNB_id]);
}
}
for (int gNB_id = 0; gNB_id < ue->n_connected_gNB; gNB_id++) {
for (int th_id = 0; th_id < RX_NB_TH_MAX; th_id++) {
@@ -478,30 +452,17 @@ void term_nr_ue_signal(PHY_VARS_NR_UE *ue, int nb_connected_gNB)
}
for (int i=0; i<NR_MAX_NB_PORTS; i++) {
free_and_zero(ue->nr_csi_rs_info->csi_rs_generated_signal[i]);
}
for (int i = 0; i < fp->nb_antennas_rx; i++) {
free_and_zero(ue->nr_csi_rs_info->csi_rs_received_signal[i]);
for (int j=0; j<NR_MAX_NB_PORTS; j++) {
free_and_zero(ue->nr_csi_rs_info->csi_rs_ls_estimated_channel[i][j]);
free_and_zero(ue->nr_csi_rs_info->csi_rs_estimated_channel_freq[i][j]);
}
free_and_zero(ue->nr_csi_rs_info->csi_rs_ls_estimated_channel[i]);
free_and_zero(ue->nr_csi_rs_info->csi_rs_estimated_channel_freq[i]);
free_and_zero(ue->nr_csi_info->csi_rs_generated_signal[i]);
}
free_and_zero(ue->nr_csi_info->csi_rs_generated_signal);
for (int slot=0; slot<fp->slots_per_frame; slot++) {
for (int symb=0; symb<fp->symbols_per_slot; symb++) {
free_and_zero(ue->nr_csi_rs_info->nr_gold_csi_rs[slot][symb]);
free_and_zero(ue->nr_csi_info->nr_gold_csi_rs[slot][symb]);
}
free_and_zero(ue->nr_csi_rs_info->nr_gold_csi_rs[slot]);
free_and_zero(ue->nr_csi_info->nr_gold_csi_rs[slot]);
}
free_and_zero(ue->nr_csi_rs_info->noise_power);
free_and_zero(ue->nr_csi_rs_info->nr_gold_csi_rs);
free_and_zero(ue->nr_csi_rs_info->csi_rs_generated_signal);
free_and_zero(ue->nr_csi_rs_info->csi_rs_received_signal);
free_and_zero(ue->nr_csi_rs_info->csi_rs_ls_estimated_channel);
free_and_zero(ue->nr_csi_rs_info->csi_rs_estimated_channel_freq);
free_and_zero(ue->nr_csi_rs_info);
free_and_zero(ue->nr_csi_info->nr_gold_csi_rs);
free_and_zero(ue->nr_csi_info);
free_and_zero(ue->nr_srs_info);
+74 -72
View File
@@ -532,9 +532,12 @@ uint32_t conv_1C_RIV(int32_t rballoc,uint32_t N_RB_DL) {
}
// FIXME: this function is compting PRB outside the range, so I FORCED in the range
// I can't understand the 3GPP spec, see below note
uint32_t get_prb(int N_RB_DL,int odd_slot,int vrb,int Ngap) {
int offset;
int ret=-1;
switch (N_RB_DL) {
@@ -545,16 +548,16 @@ uint32_t get_prb(int N_RB_DL,int odd_slot,int vrb,int Ngap) {
switch (vrb) {
case 0: // even: 0->0, 1->2, odd: 0->3, 1->5
case 1:
return ((3*odd_slot) + 2*(vrb&3))%6;
ret= ((3*odd_slot) + 2*(vrb&3))%6;
break;
case 2: // even: 2->3, 3->5, odd: 2->0, 3->2
case 3:
return ((3*odd_slot) + 2*(vrb&3) + 5)%6;
ret= ((3*odd_slot) + 2*(vrb&3) + 5)%6;
break;
case 4: // even: 4->1, odd: 4->4
return ((3*odd_slot) + 1)%6;
ret= ((3*odd_slot) + 1)%6;
case 5: // even: 5->4, odd: 5->1
return ((3*odd_slot) + 4)%6;
ret= ((3*odd_slot) + 4)%6;
break;
}
break;
@@ -562,88 +565,90 @@ uint32_t get_prb(int N_RB_DL,int odd_slot,int vrb,int Ngap) {
case 15:
if (vrb<12) {
if ((vrb&3) < 2) // even: 0->0, 1->4, 4->1, 5->5, 8->2, 9->6 odd: 0->7, 1->11
return(((7*odd_slot) + 4*(vrb&3) + (vrb>>2))%14) + 14*(vrb/14);
ret= (((7*odd_slot) + 4*(vrb&3) + (vrb>>2))%14) + 14*(vrb/14);
else if (vrb < 12) // even: 2->7, 3->11, 6->8, 7->12, 10->9, 11->13
return (((7*odd_slot) + 4*(vrb&3) + (vrb>>2) +13 )%14) + 14*(vrb/14);
ret= (((7*odd_slot) + 4*(vrb&3) + (vrb>>2) +13 )%14) + 14*(vrb/14);
}
if (vrb==12)
return (3+(7*odd_slot)) % 14;
ret= (3+(7*odd_slot)) % 14;
if (vrb==13)
return (10+(7*odd_slot)) % 14;
return 14;
ret= (10+(7*odd_slot)) % 14;
ret= 14;
break;
// Formula in TS 36.211, chap 6.2.3.2
// Fix me: returns a PRB number > 24 when vrb is 24
case 25:
return (((12*odd_slot) + 6*(vrb&3) + (vrb>>2))%24) + 24*(vrb/24);
ret= (((12*odd_slot) + 6*(vrb&3) + (vrb>>2))%24) + 24*(vrb/24);
break;
case 50: // P=3
if (Ngap==0) {
// Nrow=12,Nnull=2,NVRBDL=46,Ngap1= 27
if (vrb>=23)
offset=4;
offset=4;
else
offset=0;
offset=0;
if (vrb<44) {
if ((vrb&3)>=2)
return offset+((23*odd_slot) + 12*(vrb&3) + (vrb>>2) + 45)%46;
else
return offset+((23*odd_slot) + 12*(vrb&3) + (vrb>>2))%46;
if ((vrb&3)>=2)
ret= offset+((23*odd_slot) + 12*(vrb&3) + (vrb>>2) + 45)%46;
else
ret= offset+((23*odd_slot) + 12*(vrb&3) + (vrb>>2))%46;
}
if (vrb==44) // even: 44->11, odd: 45->34
return offset+((23*odd_slot) + 22-12+1);
ret= offset+((23*odd_slot) + 22-12+1);
if (vrb==45) // even: 45->10, odd: 45->33
return offset+((23*odd_slot) + 22+12);
ret= offset+((23*odd_slot) + 22+12);
if (vrb==46)
return offset+46+((23*odd_slot) + 23-12+1) % 46;
ret= offset+46+((23*odd_slot) + 23-12+1) % 46;
if (vrb==47)
return offset+46+((23*odd_slot) + 23+12) % 46;
ret= offset+46+((23*odd_slot) + 23+12) % 46;
if (vrb==48)
return offset+46+((23*odd_slot) + 23-12+1) % 46;
ret= offset+46+((23*odd_slot) + 23-12+1) % 46;
if (vrb==49)
return offset+46+((23*odd_slot) + 23+12) % 46;
ret= offset+46+((23*odd_slot) + 23+12) % 46;
}
else {
// Nrow=6,Nnull=6,NVRBDL=18,Ngap1= 27
if (vrb>=9)
offset=18;
offset=18;
else
offset=0;
offset=0;
if (vrb<12) {
if ((vrb&3)>=2)
return offset+((9*odd_slot) + 6*(vrb&3) + (vrb>>2) + 17)%18;
else
return offset+((9*odd_slot) + 6*(vrb&3) + (vrb>>2))%18;
if ((vrb&3)>=2)
ret= offset+((9*odd_slot) + 6*(vrb&3) + (vrb>>2) + 17)%18;
else
ret= offset+((9*odd_slot) + 6*(vrb&3) + (vrb>>2))%18;
}
else {
return offset+((9*odd_slot) + 12*(vrb&1)+(vrb>>1) )%18 + 18*(vrb/18);
ret= offset+((9*odd_slot) + 12*(vrb&1)+(vrb>>1) )%18 + 18*(vrb/18);
}
}
break;
case 75:
// Ngap1 = 32, NVRBRL=64, P=4, Nrow= 16, Nnull=0
if (Ngap ==0) {
return ((32*odd_slot) + 16*(vrb&3) + (vrb>>2))%64 + (vrb/64);
ret= ((32*odd_slot) + 16*(vrb&3) + (vrb>>2))%64 + (vrb/64);
} else {
// Ngap2 = 16, NVRBDL=32, Nrow=8, Nnull=0
return ((16*odd_slot) + 8*(vrb&3) + (vrb>>2))%32 + (vrb/32);
ret= ((16*odd_slot) + 8*(vrb&3) + (vrb>>2))%32 + (vrb/32);
}
break;
case 100:
// Ngap1 = 48, NVRBDL=96, Nrow=24, Nnull=0
if (Ngap ==0) {
return ((48*odd_slot) + 24*(vrb&3) + (vrb>>2))%96 + (vrb/96);
ret= ((48*odd_slot) + 24*(vrb&3) + (vrb>>2))%96 + (vrb/96);
} else {
// Ngap2 = 16, NVRBDL=32, Nrow=8, Nnull=0
return ((16*odd_slot) + 8*(vrb&3) + (vrb>>2))%32 + (vrb/32);
ret= ((16*odd_slot) + 8*(vrb&3) + (vrb>>2))%32 + (vrb/32);
}
break;
default:
LOG_E(PHY,"Unknown N_RB_DL %d\n",N_RB_DL);
return 0;
ret= 0;
}
return 0;
return ret%N_RB_DL;
}
@@ -677,7 +682,7 @@ void generate_RIV_tables(void)
// printf("RIV %d (%d) : first_rb %d NBRB %d\n",RIV,localRIV2alloc_LUT25[RIV],RBstart,Lcrbs);
localRIV2alloc_LUT6[RIV] = alloc0;
distRIV2alloc_even_LUT6[RIV] = allocdist0_0_even;
distRIV2alloc_even_LUT6[RIV] = allocdist0_0_even;
distRIV2alloc_odd_LUT6[RIV] = allocdist0_0_odd;
RIV2nb_rb_LUT6[RIV] = Lcrbs;
RIV2first_rb_LUT6[RIV] = RBstart;
@@ -693,15 +698,14 @@ void generate_RIV_tables(void)
nVRB = Lcrbs-1+RBstart;
//printf("RBstart %d, len %d --> ",RBstart,Lcrbs);
alloc0 |= (1<<nVRB);
allocdist0_0_even |= (1<<get_prb(25,0,nVRB,0));
allocdist0_0_odd |= (1<<get_prb(25,1,nVRB,0));
allocdist0_0_even |= 1U << get_prb(25, 0, nVRB, 0);
allocdist0_0_odd |= 1U << get_prb(25, 1, nVRB, 0);
//printf("alloc 0 %x, allocdist0_even %x, allocdist0_odd %x\n",alloc0,allocdist0_0_even,allocdist0_0_odd);
RIV=computeRIV(25,RBstart,Lcrbs);
if (RIV>RIV_max25)
RIV_max25 = RIV;;
RIV_max25 = RIV;
localRIV2alloc_LUT25[RIV] = alloc0;
distRIV2alloc_even_LUT25[RIV] = allocdist0_0_even;
@@ -730,37 +734,37 @@ void generate_RIV_tables(void)
if (nVRB<32)
alloc0 |= (1<<nVRB);
alloc0 |= 1U << nVRB;
else
alloc1 |= (1<<(nVRB-32));
alloc1 |= 1U << (nVRB - 32);
// Distributed Gap1, even slot
nVRB_even_dist = get_prb(50,0,nVRB,0);
if (nVRB_even_dist<32)
allocdist0_0_even |= (1<<nVRB_even_dist);
allocdist0_0_even |= 1U << nVRB_even_dist;
else
allocdist1_0_even |= (1<<(nVRB_even_dist-32));
allocdist1_0_even |= 1U << (nVRB_even_dist - 32);
// Distributed Gap1, odd slot
nVRB_odd_dist = get_prb(50,1,nVRB,0);
if (nVRB_odd_dist<32)
allocdist0_0_odd |= (1<<nVRB_odd_dist);
allocdist0_0_odd |= (1U <<nVRB_odd_dist);
else
allocdist1_0_odd |= (1<<(nVRB_odd_dist-32));
allocdist1_0_odd |= (1U <<(nVRB_odd_dist-32));
// Distributed Gap2, even slot
nVRB_even_dist = get_prb(50,0,nVRB,1);
if (nVRB_even_dist<32)
allocdist0_1_even |= (1<<nVRB_even_dist);
allocdist0_1_even |= 1U << nVRB_even_dist;
else
allocdist1_1_even |= (1<<(nVRB_even_dist-32));
allocdist1_1_even |= 1U << (nVRB_even_dist - 32);
// Distributed Gap2, odd slot
nVRB_odd_dist = get_prb(50,1,nVRB,1);
if (nVRB_odd_dist<32)
allocdist0_1_odd |= (1<<nVRB_odd_dist);
allocdist0_1_odd |= 1U << nVRB_odd_dist;
else
allocdist1_1_odd |= (1<<(nVRB_odd_dist-32));
allocdist1_1_odd |= 1U << (nVRB_odd_dist - 32);
RIV=computeRIV(50,RBstart,Lcrbs);
@@ -811,13 +815,13 @@ void generate_RIV_tables(void)
nVRB = Lcrbs-1+RBstart;
if (nVRB<32)
alloc0 |= (1<<nVRB);
alloc0 |= 1U << nVRB;
else if (nVRB<64)
alloc1 |= (1<<(nVRB-32));
alloc1 |= 1U << (nVRB - 32);
else if (nVRB<96)
alloc2 |= (1<<(nVRB-64));
alloc2 |= 1U << (nVRB - 64);
else
alloc3 |= (1<<(nVRB-96));
alloc3 |= 1U << (nVRB - 96);
// Distributed Gap1, even slot
nVRB_even_dist = get_prb(100,0,nVRB,0);
@@ -825,15 +829,14 @@ void generate_RIV_tables(void)
// if ((RBstart==0) && (Lcrbs<=8))
// printf("nVRB %d => nVRB_even_dist %d\n",nVRB,nVRB_even_dist);
if (nVRB_even_dist<32)
allocdist0_0_even |= (1<<nVRB_even_dist);
allocdist0_0_even |= 1U << nVRB_even_dist;
else if (nVRB_even_dist<64)
allocdist1_0_even |= (1<<(nVRB_even_dist-32));
allocdist1_0_even |= 1U << (nVRB_even_dist - 32);
else if (nVRB_even_dist<96)
allocdist2_0_even |= (1<<(nVRB_even_dist-64));
allocdist2_0_even |= 1U << (nVRB_even_dist - 64);
else
allocdist3_0_even |= (1<<(nVRB_even_dist-96));
allocdist3_0_even |= 1U << (nVRB_even_dist - 96);
/* if ((RBstart==0) && (Lcrbs<=8))
printf("rballoc =>(%08x.%08x.%08x.%08x)\n",
allocdist0_0_even,
@@ -845,38 +848,37 @@ void generate_RIV_tables(void)
// Distributed Gap1, odd slot
nVRB_odd_dist = get_prb(100,1,nVRB,0);
if (nVRB_odd_dist<32)
allocdist0_0_odd |= (1<<nVRB_odd_dist);
allocdist0_0_odd |= 1U << nVRB_odd_dist;
else if (nVRB_odd_dist<64)
allocdist1_0_odd |= (1<<(nVRB_odd_dist-32));
allocdist1_0_odd |= 1U << (nVRB_odd_dist - 32);
else if (nVRB_odd_dist<96)
allocdist2_0_odd |= (1<<(nVRB_odd_dist-64));
allocdist2_0_odd |= 1U << (nVRB_odd_dist - 64);
else
allocdist3_0_odd |= (1<<(nVRB_odd_dist-96));
allocdist3_0_odd |= 1U << (nVRB_odd_dist - 96);
// Distributed Gap2, even slot
nVRB_even_dist = get_prb(100,0,nVRB,1);
if (nVRB_even_dist<32)
allocdist0_1_even |= (1<<nVRB_even_dist);
allocdist0_1_even |= 1U << nVRB_even_dist;
else if (nVRB_even_dist<64)
allocdist1_1_even |= (1<<(nVRB_even_dist-32));
allocdist1_1_even |= 1U << (nVRB_even_dist - 32);
else if (nVRB_even_dist<96)
allocdist2_1_even |= (1<<(nVRB_even_dist-64));
allocdist2_1_even |= 1U << (nVRB_even_dist - 64);
else
allocdist3_1_even |= (1<<(nVRB_even_dist-96));
allocdist3_1_even |= 1U << (nVRB_even_dist - 96);
// Distributed Gap2, odd slot
nVRB_odd_dist = get_prb(100,1,nVRB,1);
if (nVRB_odd_dist<32)
allocdist0_1_odd |= (1<<nVRB_odd_dist);
allocdist0_1_odd |= 1U << nVRB_odd_dist;
else if (nVRB_odd_dist<64)
allocdist1_1_odd |= (1<<(nVRB_odd_dist-32));
allocdist1_1_odd |= 1U << (nVRB_odd_dist - 32);
else if (nVRB_odd_dist<96)
allocdist2_1_odd |= (1<<(nVRB_odd_dist-64));
allocdist2_1_odd |= 1U << (nVRB_odd_dist - 64);
else
allocdist3_1_odd |= (1<<(nVRB_odd_dist-96));
allocdist3_1_odd |= 1U << (nVRB_odd_dist - 96);
RIV=computeRIV(100,RBstart,Lcrbs);
+1 -1
View File
@@ -288,7 +288,7 @@ static void TPencode(void * arg) {
LTE_DL_eNB_HARQ_t *hadlsch=rdata->dlsch->harq_processes[harq_pid];
if ( rdata-> round == 0) {
uint8_t tmp[96+12+3+3*6144];
uint8_t tmp[96+12+3+3*6144] __attribute__((aligned(32)));
memset(tmp,LTE_NULL, TURBO_SIMD_SOFTBITS);
start_meas(rdata->te_stats);
encoder(rdata->input,
+16 -5
View File
@@ -64,6 +64,12 @@ extern uint16_t beta_cqi[16];
extern uint16_t beta_ri[16];
extern uint16_t beta_ack[16];
static int errorRB(int rb, char * table, int line) {
LOG_E(PHY,"Received %d rb, impossble in table %s, at line %d\n", rb, table, line);
return 0;
}
#define rbAllocCheck(RBalL, TabLe) (RBalL) > sizeof(TabLe)/sizeof(*TabLe) ? errorRB(RBalL, #TabLe, __LINE__) : TabLe[RBalL]
void extract_dci1A_info(uint8_t N_RB_DL, frame_type_t frame_type, void *dci_pdu, DCI_INFO_EXTRACTED_t *pdci_info_extarcted)
{
uint8_t harq_pid=0;
@@ -974,28 +980,28 @@ int check_dci_format1_1a_coherency(DCI_format_t dci_format,
{
switch (N_RB_DL) {
case 6:
NPRB = RIV2nb_rb_LUT6[rballoc];//NPRB;
NPRB = rbAllocCheck(rballoc, RIV2nb_rb_LUT6);
if(rah)
RIV_max = RIV_max6;
else
RIV_max = 0x3F;
break;
case 25:
NPRB = RIV2nb_rb_LUT25[rballoc];//NPRB;
NPRB = rbAllocCheck(rballoc,RIV2nb_rb_LUT25);
if(rah)
RIV_max = RIV_max25;
else
RIV_max = 0x1FFF;
break;
case 50:
NPRB = RIV2nb_rb_LUT50[rballoc];//NPRB;
NPRB = rbAllocCheck(rballoc,RIV2nb_rb_LUT50);
if(rah)
RIV_max = RIV_max50;
else
RIV_max = 0x1FFFF;
break;
case 100:
NPRB = RIV2nb_rb_LUT100[rballoc];//NPRB;
NPRB = rbAllocCheck(rballoc,RIV2nb_rb_LUT100);
if(rah)
RIV_max = RIV_max100;
else
@@ -1034,9 +1040,14 @@ int check_dci_format1_1a_coherency(DCI_format_t dci_format,
// this is an eNB issue
// retransmisison but old and new TBS are different !!!
// work around, consider it as a new transmission
LOG_E(PHY,"Format1A Retransmission but TBS are different: consider it as new transmission !!! \n");
LOG_E(PHY,
"Format1A Retransmission but TBS are different: consider it as new transmission !!!, round %d, mcs 1 %d, NPRB %d \n",
pdlsch0_harq->round,
mcs1,
NPRB);
pdlsch0_harq->round = 0;
//return(0); // ?? to cross check
return(0); // ?? to cross check
}
}
@@ -1272,14 +1272,6 @@ uint32_t get_TBS_DL(uint8_t mcs, uint16_t nb_rb);
@return Transport block size */
uint32_t get_TBS_UL(uint8_t mcs, uint16_t nb_rb);
/* \brief Return bit-map of resource allocation for a given DCI rballoc (RIV format) and vrb type
@param N_RB_DL number of PRB on DL
@param indicator for even/odd slot
@param vrb vrb index
@param Ngap Gap indicator
*/
uint32_t get_prb(int N_RB_DL,int odd_slot,int vrb,int Ngap);
/* \brief Return prb for a given vrb index
@param vrb_type VRB type (0=localized,1=distributed)
@param rb_alloc_dci rballoc field from DCI
+1 -1
View File
@@ -90,7 +90,7 @@ typedef struct {
/// Redundancy-version of the current sub-frame
uint8_t rvidx;
/// Turbo-code outputs (36-212 V8.6 2009-03, p.12
uint8_t d[MAX_NUM_ULSCH_SEGMENTS][(96+3+(3*6144))];
uint8_t *d[MAX_NUM_ULSCH_SEGMENTS];
/// Sub-block interleaver outputs (36-212 V8.6 2009-03, p.16-17)
uint8_t w[MAX_NUM_ULSCH_SEGMENTS][3*6144];
/// Number of code segments (for definition see 36-212 V8.6 2009-03, p.9)
+18 -29
View File
@@ -71,6 +71,7 @@ void free_ue_ulsch(LTE_UE_ULSCH_t *ulsch) {
for (r=0; r<MAX_NUM_ULSCH_SEGMENTS; r++) {
if (ulsch->harq_processes[i]->c[r]) {
free16(ulsch->harq_processes[i]->c[r],((r==0)?8:0) + 3+768);
free16(ulsch->harq_processes[i]->d[r],0);
ulsch->harq_processes[i]->c[r] = NULL;
}
}
@@ -86,7 +87,7 @@ void free_ue_ulsch(LTE_UE_ULSCH_t *ulsch) {
LTE_UE_ULSCH_t *new_ue_ulsch(unsigned char N_RB_UL, uint8_t abstraction_flag) {
LTE_UE_ULSCH_t *ulsch;
unsigned char exit_flag = 0,i,j,r;
unsigned char exit_flag = 0;
unsigned char bw_scaling =1;
switch (N_RB_UL) {
@@ -113,7 +114,7 @@ LTE_UE_ULSCH_t *new_ue_ulsch(unsigned char N_RB_UL, uint8_t abstraction_flag) {
memset(ulsch,0,sizeof(LTE_UE_ULSCH_t));
ulsch->Mlimit = 4;
for (i=0; i<8; i++) {
for (int i=0; i<8; i++) {
ulsch->harq_processes[i] = (LTE_UL_UE_HARQ_t *)malloc16(sizeof(LTE_UL_UE_HARQ_t));
// printf("ulsch->harq_processes[%d] %p\n",i,ulsch->harq_processes[i]);
@@ -129,15 +130,11 @@ LTE_UE_ULSCH_t *new_ue_ulsch(unsigned char N_RB_UL, uint8_t abstraction_flag) {
}
if (abstraction_flag==0) {
for (r=0; r<MAX_NUM_ULSCH_SEGMENTS; r++) {
ulsch->harq_processes[i]->c[r] = (unsigned char *)malloc16(((r==0)?8:0) + 3+768); // account for filler in first segment and CRCs for multiple segment case
if (ulsch->harq_processes[i]->c[r])
memset(ulsch->harq_processes[i]->c[r],0,((r==0)?8:0) + 3+768);
else {
LOG_E(PHY,"Can't get c\n");
exit_flag=2;
}
for (int r=0; r<MAX_NUM_ULSCH_SEGMENTS; r++) {
ulsch->harq_processes[i]->c[r] = malloc16_clear(((r==0)?8:0) + 3+768); // account for filler in first segment and CRCs for multiple segment case
AssertFatal(ulsch->harq_processes[i]->c[r], "");
ulsch->harq_processes[i]->d[r] = malloc16_clear(96+3+(3*6144));
AssertFatal(ulsch->harq_processes[i]->d[r], "");
}
}
@@ -148,15 +145,7 @@ LTE_UE_ULSCH_t *new_ue_ulsch(unsigned char N_RB_UL, uint8_t abstraction_flag) {
exit_flag=3;
}
}
if ((abstraction_flag == 0) && (exit_flag==0)) {
for (i=0; i<8; i++)
for (j=0; j<96; j++)
for (r=0; r<MAX_NUM_ULSCH_SEGMENTS; r++)
ulsch->harq_processes[i]->d[r][j] = LTE_NULL;
return(ulsch);
} else if (abstraction_flag==1)
if (!exit_flag)
return(ulsch);
}
@@ -191,7 +180,7 @@ uint32_t ulsch_encoding(uint8_t *a,
uint32_t Qprime_ACK=0,Qprime_CQI=0,Qprime_RI=0,len_ACK=0,len_RI=0;
// uint32_t E;
uint8_t ack_parity;
uint32_t i,q,j,iprime,j2;
uint32_t q,j,iprime,j2;
uint16_t o_RCC;
uint8_t o_flip[8];
uint32_t wACK_idx;
@@ -327,6 +316,8 @@ uint32_t ulsch_encoding(uint8_t *a,
#endif
// offset=0;
start_meas(te_stats);
for (int z=0; z<96; z++)
ulsch->harq_processes[harq_pid]->d[r][z] = LTE_NULL;
encoder(ulsch->harq_processes[harq_pid]->c[r],
Kr>>3,
&ulsch->harq_processes[harq_pid]->d[r][96],
@@ -539,8 +530,6 @@ uint32_t ulsch_encoding(uint8_t *a,
ulsch->q);
}
i=0;
// Do RI coding
if (ulsch->O_RI == 1) {
switch (Q_m) {
@@ -691,7 +680,7 @@ uint32_t ulsch_encoding(uint8_t *a,
j=0;
for (i=0; i<Qprime_RI; i++) {
for (int i=0; i<Qprime_RI; i++) {
r = Rmux_prime - 1 - (i>>2);
for (q=0; q<Q_m; q++) {
@@ -725,7 +714,7 @@ uint32_t ulsch_encoding(uint8_t *a,
}
*/
for (i=0; i<Qprime_CQI; i++) {
for (int i=0; i<Qprime_CQI; i++) {
while (y[Q_m*j] != LTE_NULL) j++;
for (q=0; q<Q_m; q++) {
@@ -788,7 +777,7 @@ uint32_t ulsch_encoding(uint8_t *a,
j=0;
for (i=0; i<Qprime_ACK; i++) {
for (int i=0; i<Qprime_ACK; i++) {
r = Rmux_prime - 1 - (i>>2);
for (q=0; q<Q_m; q++) {
@@ -808,7 +797,7 @@ uint32_t ulsch_encoding(uint8_t *a,
switch (Q_m) {
case 2:
for (i=0; i<Cmux; i++)
for (int i=0; i<Cmux; i++)
for (r=0; r<Rmux_prime; r++) {
yptr=&y[((r*Cmux)+i)<<1];
ulsch->h[j++] = *yptr++;
@@ -818,7 +807,7 @@ uint32_t ulsch_encoding(uint8_t *a,
break;
case 4:
for (i=0; i<Cmux; i++)
for (int i=0; i<Cmux; i++)
for (r=0; r<Rmux_prime; r++) {
yptr = &y[((r*Cmux)+i)<<2];
ulsch->h[j++] = *yptr++;
@@ -830,7 +819,7 @@ uint32_t ulsch_encoding(uint8_t *a,
break;
case 6:
for (i=0; i<Cmux; i++)
for (int i=0; i<Cmux; i++)
for (r=0; r<Rmux_prime; r++) {
yptr = &y[((r*Cmux)+i)*6];
ulsch->h[j++] = *yptr++;
+12 -20
View File
@@ -226,10 +226,11 @@ void nr_modulation(uint32_t *in,
i *= 24;
bit_cnt = i * 8;
while (bit_cnt < length) {
x = *((uint32_t*)(in_bytes+i));
x1 = x&4095;
uint32_t xx;
memcpy(&xx, in_bytes+i, sizeof(xx));
x1 = xx & 4095;
out64[j++] = nr_64qam_mod_table[x1];
x1 = (x>>12)&4095;
x1 = (xx >> 12) & 4095;
out64[j++] = nr_64qam_mod_table[x1];
i += 3;
bit_cnt += 24;
@@ -617,32 +618,23 @@ void init_symbol_rotation(NR_DL_FRAME_PARMS *fp) {
for (uint8_t ll = 0; ll < 2; ll++){
double f0 = f[ll];
double Ncpm1 = Ncp0;
LOG_I(PHY, "Doing symbol rotation calculation for gNB TX/RX, f0 %f Hz, Nsymb %d\n", f0, nsymb);
c16_t *symbol_rotation = fp->symbol_rotation[ll];
double tl = 0;
double poff = 2 * M_PI * ((Ncp0 * Tc)) * f0;
double exp_re = cos(poff);
double exp_im = sin(-poff);
symbol_rotation[0].r = (int16_t)floor(exp_re * 32767);
symbol_rotation[0].i = (int16_t)floor(exp_im * 32767);
LOG_I(PHY, "Doing symbol rotation calculation for gNB TX/RX, f0 %f Hz, Nsymb %d\n", f0, nsymb);
LOG_I(PHY, "Symbol rotation %d/%d => (%d,%d)\n",
0,
nsymb,
symbol_rotation[0].r,
symbol_rotation[0].i);
double tl = 0.0;
double poff = 0.0;
double exp_re = 0.0;
double exp_im = 0.0;
for (int l = 1; l < nsymb; l++) {
for (int l = 0; l < nsymb; l++) {
double Ncp;
if (l == (7 * (1 << fp->numerology_index))) {
if (l == 0 || l == (7 * (1 << fp->numerology_index))) {
Ncp = Ncp0;
} else {
Ncp = Ncp1;
}
tl += (Nu + Ncpm1) * Tc;
poff = 2 * M_PI * (tl + (Ncp * Tc)) * f0;
exp_re = cos(poff);
exp_im = sin(-poff);
@@ -657,7 +649,7 @@ void init_symbol_rotation(NR_DL_FRAME_PARMS *fp) {
symbol_rotation[l].i,
(poff / 2 / M_PI) - floor(poff / 2 / M_PI));
Ncpm1 = Ncp;
tl += (Nu + Ncp) * Tc;
}
}
@@ -151,9 +151,9 @@ void gNB_I0_measurements(PHY_VARS_gNB *gNB,int slot, int first_symb,int num_symb
NR_gNB_COMMON *common_vars = &gNB->common_vars;
PHY_MEASUREMENTS_gNB *measurements = &gNB->measurements;
int rb, nb_symb[275]={0};
memset(measurements->n0_subband_power, 0, sizeof(measurements->n0_subband_power));
for (int s=first_symb;s<(first_symb+num_symb);s++) {
for (rb=0; rb<frame_parms->N_RB_UL; rb++) {
if (s==first_symb /*&& ((gNB->rb_mask_ul[s][rb>>5]&(1<<(rb&31))) == 0)*/) {
@@ -162,13 +162,13 @@ void gNB_I0_measurements(PHY_VARS_gNB *gNB,int slot, int first_symb,int num_symb
measurements->n0_subband_power[aarx][rb]=0;
}
int offset0 = (slot&3)*(frame_parms->symbols_per_slot * frame_parms->ofdm_symbol_size) + (frame_parms->first_carrier_offset + (rb*12))%frame_parms->ofdm_symbol_size;
if ((gNB->rb_mask_ul[s][rb>>5]&(1<<(rb&31))) == 0) { // check that rb was not used in this subframe
if ((gNB->rb_mask_ul[s][rb >> 5] & (1U << (rb & 31))) == 0) { // check that rb was not used in this subframe
nb_symb[rb]++;
for (int aarx=0; aarx<frame_parms->nb_antennas_rx; aarx++) {
int offset = offset0 + (s*frame_parms->ofdm_symbol_size);
int32_t *ul_ch = &common_vars->rxdataF[aarx][offset];
int len = 12;
if (((frame_parms->N_RB_UL&1) == 1) &&
if (((frame_parms->N_RB_UL&1) == 1) &&
(rb==(frame_parms->N_RB_UL>>1))) {
len=6;
}
@@ -874,7 +874,7 @@ void nr_pusch_ptrs_processing(PHY_VARS_gNB *gNB,
c16_t *phase_per_symbol = (c16_t*)gNB->pusch_vars[ulsch_id]->ptrs_phase_per_slot[aarx];
ptrs_re_symbol = &gNB->pusch_vars[ulsch_id]->ptrs_re_per_slot;
*ptrs_re_symbol = 0;
phase_per_symbol[symbol].i = 0;
phase_per_symbol[symbol].i = 0;
/* set DMRS estimates to 0 angle with magnitude 1 */
if(is_dmrs_symbol(symbol,*dmrsSymbPos)) {
/* set DMRS real estimation to 32767 */
@@ -884,7 +884,7 @@ void nr_pusch_ptrs_processing(PHY_VARS_gNB *gNB,
#endif
}
else {// real ptrs value is set to 0
phase_per_symbol[symbol].r = 0;
phase_per_symbol[symbol].r = 0;
}
if(symbol == *startSymbIndex) {
@@ -1198,7 +1198,7 @@ int nr_srs_channel_estimation(const PHY_VARS_gNB *gNB,
const int32_t factor_dB = dB_fixed(1<<factor_bits);
const uint8_t srs_symbols_per_rb = srs_pdu->comb_size == 0 ? 6 : 3;
const uint8_t n_noise_estimates = frame_parms->nb_antennas_rx*N_ap*srs_symbols_per_rb;
const uint8_t n_noise_est = frame_parms->nb_antennas_rx*N_ap*srs_symbols_per_rb;
uint64_t sum_re = 0;
uint64_t sum_re2 = 0;
uint64_t sum_im = 0;
@@ -1223,8 +1223,8 @@ int nr_srs_channel_estimation(const PHY_VARS_gNB *gNB,
} // for (int p_index = 0; p_index < N_ap; p_index++)
} // for (int ant = 0; ant < frame_parms->nb_antennas_rx; ant++)
noise_power_per_rb[rb] = sum_re2/n_noise_estimates - (sum_re/n_noise_estimates)*(sum_re/n_noise_estimates) +
sum_im2/n_noise_estimates - (sum_im/n_noise_estimates)*(sum_im/n_noise_estimates);
noise_power_per_rb[rb] = max(sum_re2 / n_noise_est - (sum_re / n_noise_est) * (sum_re / n_noise_est) +
sum_im2 / n_noise_est - (sum_im / n_noise_est) * (sum_im / n_noise_est), 1);
snr_per_rb[rb] = dB_fixed((int32_t)((*signal_power<<factor_bits)/noise_power_per_rb[rb])) - factor_dB;
#ifdef SRS_DEBUG
+1 -1
View File
@@ -38,7 +38,7 @@ void nr_init_pbch_dmrs(PHY_VARS_gNB* gNB);
*/
void nr_init_pdcch_dmrs(PHY_VARS_gNB* gNB, uint32_t Nid);
void nr_init_pdsch_dmrs(PHY_VARS_gNB* gNB, uint8_t nscid, uint32_t Nid);
void nr_init_csi_rs(NR_DL_FRAME_PARMS *fp, uint32_t ***csi_rs, uint32_t Nid);
void nr_init_csi_rs(const NR_DL_FRAME_PARMS *fp, uint32_t ***csi_rs, uint32_t Nid);
void nr_gold_pusch(PHY_VARS_gNB* gNB, int nscid, uint32_t nid);
+1 -1
View File
@@ -68,6 +68,6 @@ void nr_init_pusch_dmrs(PHY_VARS_NR_UE* ue,
uint16_t N_n_scid,
uint8_t n_scid);
void nr_init_csi_rs(NR_DL_FRAME_PARMS *fp, uint32_t ***csi_rs, uint32_t Nid);
void nr_init_csi_rs(const NR_DL_FRAME_PARMS *fp, uint32_t ***csi_rs, uint32_t Nid);
#endif
+47 -37
View File
@@ -27,7 +27,7 @@
//#define NR_CSIRS_DEBUG
void nr_init_csi_rs(NR_DL_FRAME_PARMS *fp, uint32_t ***csi_rs, uint32_t Nid) {
void nr_init_csi_rs(const NR_DL_FRAME_PARMS *fp, uint32_t ***csi_rs, uint32_t Nid) {
uint32_t x1, x2;
uint8_t reset;
int csi_dmrs_init_length = ((fp->N_RB_DL<<4)>>5)+1;
@@ -43,12 +43,20 @@ void nr_init_csi_rs(NR_DL_FRAME_PARMS *fp, uint32_t ***csi_rs, uint32_t Nid) {
}
}
void nr_generate_csi_rs(NR_DL_FRAME_PARMS frame_parms,
void nr_generate_csi_rs(const NR_DL_FRAME_PARMS *frame_parms,
int32_t **dataF,
int16_t amp,
nr_csi_rs_info_t *nr_csi_rs_info,
nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params,
int slot){
const int16_t amp,
nr_csi_info_t *nr_csi_info,
const nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params,
const int slot,
uint8_t *N_cdm_groups,
uint8_t *CDM_group_size,
uint8_t *k_prime,
uint8_t *l_prime,
uint8_t *N_ports,
uint8_t *j_cdm,
uint8_t *k_overline,
uint8_t *l_overline) {
#ifdef NR_CSIRS_DEBUG
LOG_I(NR_PHY, "csi_params->subcarrier_spacing = %i\n", csi_params->subcarrier_spacing);
@@ -67,11 +75,11 @@ void nr_generate_csi_rs(NR_DL_FRAME_PARMS frame_parms,
LOG_I(NR_PHY, "csi_params->power_control_offset_ss = %i\n", csi_params->power_control_offset_ss);
#endif
int dataF_offset = slot*frame_parms.samples_per_slot_wCP;
uint32_t **nr_gold_csi_rs = nr_csi_rs_info->nr_gold_csi_rs[slot];
int dataF_offset = slot*frame_parms->samples_per_slot_wCP;
uint32_t **nr_gold_csi_rs = nr_csi_info->nr_gold_csi_rs[slot];
//*8(max allocation per RB)*2(QPSK))
int csi_rs_length = frame_parms.N_RB_DL<<4;
int16_t mod_csi[frame_parms.symbols_per_slot][csi_rs_length>>1] __attribute__((aligned(16)));
int csi_rs_length = frame_parms->N_RB_DL<<4;
int16_t mod_csi[frame_parms->symbols_per_slot][csi_rs_length>>1] __attribute__((aligned(16)));
uint16_t b = csi_params->freq_domain;
uint16_t n, p, k, l, mprime, na, kpn;
uint8_t size, ports, kprime, lprime, i, gs;
@@ -81,14 +89,14 @@ void nr_generate_csi_rs(NR_DL_FRAME_PARMS frame_parms,
uint8_t fi = 0;
double rho, alpha;
uint32_t beta = amp;
nr_csi_rs_info->csi_rs_generated_signal_bits = log2_approx(amp);
nr_csi_info->csi_rs_generated_signal_bits = log2_approx(amp);
AssertFatal(b!=0, "Invalid CSI frequency domain mapping: no bit selected in bitmap\n");
// if the scrambling id is not the one previously used to initialize we need to re-initialize the rs
if (csi_params->scramb_id != nr_csi_rs_info->csi_gold_init) {
nr_csi_rs_info->csi_gold_init = csi_params->scramb_id;
nr_init_csi_rs(&frame_parms, nr_csi_rs_info->nr_gold_csi_rs, csi_params->scramb_id);
if (csi_params->scramb_id != nr_csi_info->csi_gold_init) {
nr_csi_info->csi_gold_init = csi_params->scramb_id;
nr_init_csi_rs(frame_parms, nr_csi_info->nr_gold_csi_rs, csi_params->scramb_id);
}
switch (csi_params->row) {
@@ -584,7 +592,7 @@ void nr_generate_csi_rs(NR_DL_FRAME_PARMS frame_parms,
}
}
uint16_t start_sc = frame_parms.first_carrier_offset;
uint16_t start_sc = frame_parms->first_carrier_offset;
// resource mapping according to 38.211 7.4.1.5.3
for (n=csi_params->start_rb; n<(csi_params->start_rb+csi_params->nr_of_rbs); n++) {
@@ -593,7 +601,7 @@ void nr_generate_csi_rs(NR_DL_FRAME_PARMS frame_parms,
for (int s=0 ; s<gs; s++) { // loop over each CDM group size
p = s+j[ji]*gs; // port index
for (kp=0; kp<=kprime; kp++) { // loop over frequency resource elements within a group
k = (start_sc+(n*NR_NB_SC_PER_RB)+koverline[ji]+kp)%(frame_parms.ofdm_symbol_size); // frequency index of current resource element
k = (start_sc+(n*NR_NB_SC_PER_RB)+koverline[ji]+kp)%(frame_parms->ofdm_symbol_size); // frequency index of current resource element
// wf according to tables 7.4.5.3-2 to 7.4.5.3-5
if (kp == 0)
wf = 1;
@@ -620,17 +628,17 @@ void nr_generate_csi_rs(NR_DL_FRAME_PARMS frame_parms,
// ZP CSI RS
if (csi_params->csi_type == 2) {
((int16_t*)dataF[p])[((l*frame_parms.ofdm_symbol_size + k)<<1)+(2*dataF_offset)] = 0;
((int16_t*)dataF[p])[((l*frame_parms.ofdm_symbol_size + k)<<1)+1+(2*dataF_offset)] = 0;
((int16_t*)dataF[p])[((l*frame_parms->ofdm_symbol_size + k)<<1)+(2*dataF_offset)] = 0;
((int16_t*)dataF[p])[((l*frame_parms->ofdm_symbol_size + k)<<1)+1+(2*dataF_offset)] = 0;
}
else {
((int16_t*)dataF[p])[((l*frame_parms.ofdm_symbol_size + k)<<1)+(2*dataF_offset)] = (beta*wt*wf*mod_csi[l][mprime<<1]) >> 15;
((int16_t*)dataF[p])[((l*frame_parms.ofdm_symbol_size + k)<<1)+1+(2*dataF_offset)] = (beta*wt*wf*mod_csi[l][(mprime<<1) + 1]) >> 15;
((int16_t*)dataF[p])[((l*frame_parms->ofdm_symbol_size + k)<<1)+(2*dataF_offset)] = (beta*wt*wf*mod_csi[l][mprime<<1]) >> 15;
((int16_t*)dataF[p])[((l*frame_parms->ofdm_symbol_size + k)<<1)+1+(2*dataF_offset)] = (beta*wt*wf*mod_csi[l][(mprime<<1) + 1]) >> 15;
}
#ifdef NR_CSIRS_DEBUG
printf("l,k (%d,%d) seq. index %d \t port %d \t (%d,%d)\n",l,k,mprime,p+3000,
((int16_t*)dataF[p])[((l*frame_parms.ofdm_symbol_size + k)<<1)+(2*dataF_offset)],
((int16_t*)dataF[p])[((l*frame_parms.ofdm_symbol_size + k)<<1)+1+(2*dataF_offset)]);
((int16_t*)dataF[p])[((l*frame_parms->ofdm_symbol_size + k)<<1)+(2*dataF_offset)],
((int16_t*)dataF[p])[((l*frame_parms->ofdm_symbol_size + k)<<1)+1+(2*dataF_offset)]);
#endif
}
}
@@ -638,23 +646,25 @@ void nr_generate_csi_rs(NR_DL_FRAME_PARMS frame_parms,
}
}
}
nr_csi_rs_info->N_cdm_groups = size;
nr_csi_rs_info->CDM_group_size = gs;
nr_csi_rs_info->kprime = kprime;
nr_csi_rs_info->lprime = lprime;
nr_csi_rs_info->N_ports = ports;
memcpy(nr_csi_rs_info->j,j,16*sizeof(uint8_t));
memcpy(nr_csi_rs_info->koverline,koverline,16*sizeof(uint8_t));
memcpy(nr_csi_rs_info->loverline,loverline,16*sizeof(uint8_t));
if (N_cdm_groups) *N_cdm_groups = size;
if (CDM_group_size) *CDM_group_size = gs;
if (k_prime) *k_prime = kprime;
if (l_prime) *l_prime = lprime;
if (N_ports) *N_ports = ports;
if (j_cdm) memcpy(j_cdm,j,16*sizeof(uint8_t));
if (k_overline) memcpy(k_overline,koverline,16*sizeof(uint8_t));
if (l_overline) memcpy(l_overline,loverline,16*sizeof(uint8_t));
#ifdef NR_CSIRS_DEBUG
LOG_I(NR_PHY, "nr_csi_rs_info->N_ports = %d\n", nr_csi_rs_info->N_ports);
LOG_I(NR_PHY, "nr_csi_rs_info->N_cdm_groups = %d\n", nr_csi_rs_info->N_cdm_groups);
LOG_I(NR_PHY, "nr_csi_rs_info->CDM_group_size = %d\n", nr_csi_rs_info->CDM_group_size);
LOG_I(NR_PHY, "nr_csi_rs_info->kprime = %d\n", nr_csi_rs_info->kprime);
LOG_I(NR_PHY, "nr_csi_rs_info->lprime = %d\n", nr_csi_rs_info->lprime);
for(int ji=0; ji<nr_csi_rs_info->N_cdm_groups; ji++) {
LOG_I(NR_PHY, "(CDM group %d) j = %d, koverline = %d, loverline = %d\n", ji, nr_csi_rs_info->j[ji], nr_csi_rs_info->koverline[ji], nr_csi_rs_info->loverline[ji]);
if (N_ports) LOG_I(NR_PHY, "nr_csi_info->N_ports = %d\n", *N_ports);
if (N_cdm_groups) LOG_I(NR_PHY, "nr_csi_info->N_cdm_groups = %d\n", *N_cdm_groups);
if (CDM_group_size) LOG_I(NR_PHY, "nr_csi_info->CDM_group_size = %d\n", *CDM_group_size);
if (k_prime) LOG_I(NR_PHY, "nr_csi_info->kprime = %d\n", *k_prime);
if (l_prime) LOG_I(NR_PHY, "nr_csi_info->lprime = %d\n", *l_prime);
if (N_cdm_groups) {
for(int ji=0; ji<*N_cdm_groups; ji++) {
LOG_I(NR_PHY, "(CDM group %d) j = %d, koverline = %d, loverline = %d\n", ji, j[ji], koverline[ji], loverline[ji]);
}
}
#endif
}
+9 -9
View File
@@ -111,9 +111,10 @@ void nr_generate_dci(PHY_VARS_gNB *gNB,
// DMRS length is per OFDM symbol
uint32_t dmrs_length = n_rb*6; //2(QPSK)*3(per RB)*6(REG per CCE)
uint32_t encoded_length = dci_pdu->AggregationLevel*108; //2(QPSK)*9(per RB)*6(REG per CCE)
LOG_D(PHY, "DL_DCI : rb_offset %d, nb_rb %d, DMRS length per symbol %d\t DCI encoded length %d (precoder_granularity %d,reg_mapping %d),Scrambling_Id %d,ScramblingRNTI %x,PayloadSizeBits %d\n",
rb_offset, n_rb,dmrs_length, encoded_length,pdcch_pdu_rel15->precoderGranularity,pdcch_pdu_rel15->CceRegMappingType,
dci_pdu->ScramblingId,dci_pdu->ScramblingRNTI,dci_pdu->PayloadSizeBits);
if (dci_pdu->RNTI != 0xFFFF)
LOG_D(PHY, "DL_DCI : rb_offset %d, nb_rb %d, DMRS length per symbol %d\t DCI encoded length %d (precoder_granularity %d, reg_mapping %d), Scrambling_Id %d, ScramblingRNTI %x, PayloadSizeBits %d\n",
rb_offset, n_rb,dmrs_length, encoded_length,pdcch_pdu_rel15->precoderGranularity,pdcch_pdu_rel15->CceRegMappingType,
dci_pdu->ScramblingId,dci_pdu->ScramblingRNTI,dci_pdu->PayloadSizeBits);
dmrs_length += rb_offset*6; // To accommodate more DMRS symbols in case of rb offset
/// DMRS QPSK modulation
@@ -122,11 +123,11 @@ void nr_generate_dci(PHY_VARS_gNB *gNB,
nr_modulation(gold_pdcch_dmrs[symb], dmrs_length, DMRS_MOD_ORDER, mod_dmrs[symb]); //Qm = 2 as DMRS is QPSK modulated
#ifdef DEBUG_PDCCH_DMRS
if(dci_pdu->RNTI!=0xFFFF) {
for (int i=0; i<dmrs_length>>1; i++)
printf("symb %d i %d %p gold seq 0x%08x mod_dmrs %d %d\n", symb, i,
&gold_pdcch_dmrs[symb][i>>5],gold_pdcch_dmrs[symb][i>>5], mod_dmrs[symb][i<<1], mod_dmrs[symb][(i<<1)+1] );
}
if(dci_pdu->RNTI!=0xFFFF) {
for (int i=0; i<dmrs_length>>1; i++)
printf("symb %d i %d %p gold seq 0x%08x mod_dmrs %d %d\n", symb, i,
&gold_pdcch_dmrs[symb][i>>5],gold_pdcch_dmrs[symb][i>>5], mod_dmrs[symb][i<<1], mod_dmrs[symb][(i<<1)+1]);
}
#endif
}
@@ -265,7 +266,6 @@ void nr_generate_dci_top(processingData_L1tx_t *msgTx,
int16_t amp,
NR_DL_FRAME_PARMS *frame_parms) {
for (int i=0; i<msgTx->num_ul_pdcch; i++)
nr_generate_dci(msgTx->gNB,&msgTx->ul_pdcch_pdu[i].pdcch_pdu.pdcch_pdu_rel15,txdataF,amp,frame_parms,slot);
for (int i=0; i<msgTx->num_dl_pdcch; i++)
+3 -2
View File
@@ -123,7 +123,6 @@ void nr_generate_pdsch(processingData_L1tx_t *msgTx,
rel15->dlDmrsSymbPos);
n_ptrs = (rel15->rbSize + rel15->PTRSFreqDensity - 1)/rel15->PTRSFreqDensity;
}
int16_t mod_ptrs[n_ptrs<<1] __attribute__ ((aligned(16)));
/// CRC, coding, interleaving and rate matching
AssertFatal(harq->pdu!=NULL,"harq->pdu is null\n");
@@ -302,12 +301,14 @@ void nr_generate_pdsch(processingData_L1tx_t *msgTx,
/* calculate if current symbol is PTRS symbols */
ptrs_idx = 0;
int16_t *mod_ptrs = NULL;
if(rel15->pduBitmap & 0x1) {
ptrs_symbol = is_ptrs_symbol(l,dlPtrsSymPos);
if(ptrs_symbol) {
/* PTRS QPSK Modulation for each OFDM symbol in a slot */
LOG_D(PHY,"Doing ptrs modulation for symbol %d, n_ptrs %d\n",l,n_ptrs);
int16_t mod_ptrsBuf[n_ptrs<<1] __attribute__ ((aligned(16)));
mod_ptrs =mod_ptrsBuf;
nr_modulation(pdsch_dmrs[l][rel15->SCID], (n_ptrs<<1), DMRS_MOD_ORDER, mod_ptrs);
}
}
@@ -123,7 +123,6 @@ NR_gNB_DLSCH_t *new_gNB_dlsch(NR_DL_FRAME_PARMS *frame_parms,
bzero(dlsch,sizeof(NR_gNB_DLSCH_t));
dlsch->Kmimo = Kmimo;
dlsch->Mdlharq = Mdlharq;
dlsch->Mlimit = 4;
dlsch->Nsoft = Nsoft;
int txdataf_size = frame_parms->N_RB_DL*NR_SYMBOLS_PER_SLOT*NR_NB_SC_PER_RB*8; // max pdsch encoded length for each layer
+19 -15
View File
@@ -121,11 +121,11 @@ void free_gNB_dlsch(NR_gNB_DLSCH_t **dlschptr, uint16_t N_RB, const NR_DL_FRAME_
@param slot Slot number
@param harq_pid HARQ process ID
*/
int nr_rx_pusch(PHY_VARS_gNB *gNB,
uint8_t UE_id,
uint32_t frame,
uint8_t slot,
unsigned char harq_pid);
void nr_rx_pusch(PHY_VARS_gNB *gNB,
uint8_t UE_id,
uint32_t frame,
uint8_t slot,
unsigned char harq_pid);
/** \brief This function performs RB extraction (signal and channel estimates) (currently signal only until channel estimation and compensation are implemented)
@param rxdataF pointer to the received frequency domain signal
@@ -337,12 +337,20 @@ void init_prach_ru_list(RU_t *ru);
void free_nr_ru_prach_entry(RU_t *ru, int prach_id);
uint8_t get_nr_prach_duration(uint8_t prach_format);
void nr_generate_csi_rs(NR_DL_FRAME_PARMS frame_parms,
void nr_generate_csi_rs(const NR_DL_FRAME_PARMS *frame_parms,
int32_t **dataF,
int16_t amp,
nr_csi_rs_info_t *nr_csi_rs_info,
nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params,
int slot);
const int16_t amp,
nr_csi_info_t *nr_csi_info,
const nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params,
const int slot,
uint8_t *N_cdm_groups,
uint8_t *CDM_group_size,
uint8_t *k_prime,
uint8_t *l_prime,
uint8_t *N_ports,
uint8_t *j_cdm,
uint8_t *k_overline,
uint8_t *l_overline);
void free_nr_prach_entry(PHY_VARS_gNB *gNB, int prach_id);
@@ -362,6 +370,7 @@ void nr_decode_pucch1(int32_t **rxdataF,
uint8_t nr_bit);
void nr_decode_pucch2(PHY_VARS_gNB *gNB,
int frame,
int slot,
nfapi_nr_uci_pucch_pdu_format_2_3_4_t* uci_pdu,
nfapi_nr_pucch_pdu_t* pucch_pdu);
@@ -372,10 +381,5 @@ void nr_decode_pucch0(PHY_VARS_gNB *gNB,
nfapi_nr_uci_pucch_pdu_format_0_1_t* uci_pdu,
nfapi_nr_pucch_pdu_t* pucch_pdu);
void nr_decode_pucch2(PHY_VARS_gNB *gNB,
int slot,
nfapi_nr_uci_pucch_pdu_format_2_3_4_t* uci_pdu,
nfapi_nr_pucch_pdu_t* pucch_pdu);
#endif /*__NR_TRANSPORT__H__*/
+13 -5
View File
@@ -68,12 +68,20 @@ void nr_fill_ulsch(PHY_VARS_gNB *gNB,
ulsch->rnti = ulsch_pdu->rnti;
//ulsch->rnti_type;
ulsch->harq_mask |= 1<<harq_pid;
ulsch->harq_process_id[slot] = harq_pid;
ulsch->harq_processes[harq_pid]->frame=frame;
ulsch->harq_processes[harq_pid]->slot=slot;
ulsch->harq_processes[harq_pid]->handled= 0;
ulsch->harq_processes[harq_pid]->status= NR_ACTIVE;
NR_UL_gNB_HARQ_t *harq = ulsch->harq_processes[harq_pid];
harq->frame=frame;
harq->slot=slot;
harq->handled = 0;
harq->status= NR_ACTIVE;
harq->new_rx = harq->ndi != ulsch_pdu->pusch_data.new_data_indicator;
if (harq->new_rx) {
harq->ndi = ulsch_pdu->pusch_data.new_data_indicator;
harq->round = 0;
} else {
harq->round++;
}
memcpy((void*)&ulsch->harq_processes[harq_pid]->ulsch_pdu, (void*)ulsch_pdu, sizeof(nfapi_nr_pusch_pdu_t));
LOG_D(PHY,"Initializing nFAPI for ULSCH, UE %d, harq_pid %d\n",ulsch_id,harq_pid);
@@ -101,7 +101,6 @@ NR_gNB_ULSCH_t *new_gNB_ulsch(uint8_t max_ldpc_iterations, uint16_t N_RB_UL)
ulsch = (NR_gNB_ULSCH_t *)malloc16_clear(sizeof(NR_gNB_ULSCH_t));
ulsch->max_ldpc_iterations = max_ldpc_iterations;
ulsch->Mlimit = 4;
for (i=0; i<NR_MAX_ULSCH_HARQ_PROCESSES; i++) {
@@ -136,10 +135,8 @@ void clean_gNB_ulsch(NR_gNB_ULSCH_t *ulsch)
ulsch->rnti_type = 0;
ulsch->cyclicShift = 0;
ulsch->cooperation_flag = 0;
ulsch->Mlimit = 0;
ulsch->max_ldpc_iterations = 0;
ulsch->last_iteration_cnt = 0;
for (i=0;i<NR_MAX_SLOTS_PER_FRAME;i++) ulsch->harq_process_id[i] = 0;
for (i=0; i<NR_MAX_ULSCH_HARQ_PROCESSES; i++) {
if (ulsch->harq_processes[i]){
@@ -415,7 +412,7 @@ uint32_t nr_ulsch_decoding(PHY_VARS_gNB *phy_vars_gNB,
uint8_t n_layers = pusch_pdu->nrOfLayers;
// ------------------------------------------------------------------
if (!ulsch_llr) {
if (!ulsch_llr) {
LOG_E(PHY,"ulsch_decoding.c: NULL ulsch_llr pointer\n");
return 1;
}
@@ -1891,11 +1891,11 @@ uint8_t nr_ulsch_zero_forcing_rx_2layers(int **rxdataF_comp,
//==============================================================================================
/* Main Function */
int nr_rx_pusch(PHY_VARS_gNB *gNB,
uint8_t ulsch_id,
uint32_t frame,
uint8_t slot,
unsigned char harq_pid)
void nr_rx_pusch(PHY_VARS_gNB *gNB,
uint8_t ulsch_id,
uint32_t frame,
uint8_t slot,
unsigned char harq_pid)
{
uint8_t aarx, aatx;
@@ -2149,6 +2149,4 @@ int nr_rx_pusch(PHY_VARS_gNB *gNB,
rxdataF_ext_offset += gNB->pusch_vars[ulsch_id]->ul_valid_re_per_slot[symbol];
}
} // symbol loop
return 0;
}
+9 -2
View File
@@ -331,8 +331,8 @@ void nr_decode_pucch0(PHY_VARS_gNB *gNB,
corr[aa][l].r += xr[aa][l][n].r * idft12_re[seq_index][n] + xr[aa][l][n].i * idft12_im[seq_index][n];
corr[aa][l].i += xr[aa][l][n].r * idft12_im[seq_index][n] - xr[aa][l][n].i * idft12_re[seq_index][n];
}
corr[aa][l].r >>= 31;
corr[aa][l].i >>= 31;
corr[aa][l].r >>= 31;
corr[aa][l].i >>= 31;
}
}
LOG_D(PHY,"PUCCH IDFT[%d/%d] = (%ld,%ld)=>%f\n",
@@ -1136,6 +1136,7 @@ void init_pucch2_luts() {
void nr_decode_pucch2(PHY_VARS_gNB *gNB,
int frame,
int slot,
nfapi_nr_uci_pucch_pdu_format_2_3_4_t* uci_pdu,
nfapi_nr_pucch_pdu_t* pucch_pdu) {
@@ -1720,13 +1721,19 @@ void nr_decode_pucch2(PHY_VARS_gNB *gNB,
uci_pdu->pduBitmap|=2;
uci_pdu->harq.harq_payload = (uint8_t*)malloc(harq_bytes);
uci_pdu->harq.harq_crc = decoderState;
LOG_D(PHY,"[DLSCH/PDSCH/PUCCH2] %d.%d HARQ bytes (%d) Decoder state %d\n",
frame,slot,harq_bytes,decoderState);
int i=0;
for (;i<harq_bytes-1;i++) {
uci_pdu->harq.harq_payload[i] = decodedPayload[0] & 255;
LOG_D(PHY,"[DLSCH/PDSCH/PUCCH2] %d.%d HARQ paylod (%d) = %d\n",
frame,slot,i,uci_pdu->harq.harq_payload[i]);
decodedPayload[0]>>=8;
}
bit_left = pucch_pdu->bit_len_harq-((harq_bytes-1)<<3);
uci_pdu->harq.harq_payload[i] = decodedPayload[0] & ((1<<bit_left)-1);
LOG_D(PHY,"[DLSCH/PDSCH/PUCCH2] %d.%d HARQ paylod (%d) = %d\n",
frame,slot,i,uci_pdu->harq.harq_payload[i]);
decodedPayload[0] >>= pucch_pdu->bit_len_harq;
}
+678 -89
View File
@@ -33,16 +33,103 @@
#include <stdlib.h>
#include <string.h>
#include "executables/nr-softmodem-common.h"
#include "nr_transport_proto_ue.h"
#include "PHY/phy_extern_nr_ue.h"
#include "common/utils/nr/nr_common.h"
#include "PHY/NR_TRANSPORT/nr_transport_proto.h"
#include "PHY/NR_UE_ESTIMATION/filt16a_32.h"
// 10*log10(pow(2,30))
#define pow_2_30_dB 90
//#define NR_CSIRS_DEBUG
//#define NR_CSIIM_DEBUG
bool is_csi_rs_in_symbol(fapi_nr_dl_config_csirs_pdu_rel15_t csirs_config_pdu, int symbol) {
void nr_det_A_MF_2x2(int32_t *a_mf_00,
int32_t *a_mf_01,
int32_t *a_mf_10,
int32_t *a_mf_11,
int32_t *det_fin,
const unsigned short nb_rb) {
int16_t nr_conjug2[8]__attribute__((aligned(16))) = {1,-1,1,-1,1,-1,1,-1} ;
__m128i ad_re_128, bc_re_128, det_re_128;
__m128i *a_mf_00_128 = (__m128i *)a_mf_00;
__m128i *a_mf_01_128 = (__m128i *)a_mf_01;
__m128i *a_mf_10_128 = (__m128i *)a_mf_10;
__m128i *a_mf_11_128 = (__m128i *)a_mf_11;
__m128i *det_fin_128 = (__m128i *)det_fin;
for (int rb = 0; rb<3*nb_rb; rb++) {
//complex multiplication (I_a+jQ_a)(I_d+jQ_d) = (I_aI_d - Q_aQ_d) + j(Q_aI_d + I_aQ_d)
//The imag part is often zero, we compute only the real part
ad_re_128 = _mm_sign_epi16(a_mf_00_128[0],*(__m128i*)&nr_conjug2[0]);
ad_re_128 = _mm_madd_epi16(ad_re_128,a_mf_11_128[0]); //Re: I_a0*I_d0 - Q_a1*Q_d1
//complex multiplication (I_b+jQ_b)(I_c+jQ_c) = (I_bI_c - Q_bQ_c) + j(Q_bI_c + I_bQ_c)
//The imag part is often zero, we compute only the real part
bc_re_128 = _mm_sign_epi16(a_mf_01_128[0],*(__m128i*)&nr_conjug2[0]);
bc_re_128 = _mm_madd_epi16(bc_re_128,a_mf_10_128[0]); //Re: I_b0*I_c0 - Q_b1*Q_c1
det_re_128 = _mm_sub_epi32(ad_re_128, bc_re_128);
//det in Q30 format
det_fin_128[0] = _mm_abs_epi32(det_re_128);
det_fin_128+=1;
a_mf_00_128+=1;
a_mf_01_128+=1;
a_mf_10_128+=1;
a_mf_11_128+=1;
}
_mm_empty();
_m_empty();
}
void nr_squared_matrix_element(int32_t *a,
int32_t *a_sq,
const unsigned short nb_rb) {
__m128i *a_128 = (__m128i *)a;
__m128i *a_sq_128 = (__m128i *)a_sq;
for (int rb=0; rb<3*nb_rb; rb++) {
a_sq_128[0] = _mm_madd_epi16(a_128[0], a_128[0]);
a_sq_128+=1;
a_128+=1;
}
_mm_empty();
_m_empty();
}
void nr_numer_2x2(int32_t *a_00_sq,
int32_t *a_01_sq,
int32_t *a_10_sq,
int32_t *a_11_sq,
int32_t *num_fin,
const unsigned short nb_rb) {
__m128i *a_00_sq_128 = (__m128i *)a_00_sq;
__m128i *a_01_sq_128 = (__m128i *)a_01_sq;
__m128i *a_10_sq_128 = (__m128i *)a_10_sq;
__m128i *a_11_sq_128 = (__m128i *)a_11_sq;
__m128i *num_fin_128 = (__m128i *)num_fin;
for (int rb=0; rb<3*nb_rb; rb++) {
__m128i sq_a_plus_sq_d_128 = _mm_add_epi32(a_00_sq_128[0], a_11_sq_128[0]);
__m128i sq_b_plus_sq_c_128 = _mm_add_epi32(a_01_sq_128[0], a_10_sq_128[0]);
num_fin_128[0] = _mm_add_epi32(sq_a_plus_sq_d_128, sq_b_plus_sq_c_128);
num_fin_128+=1;
a_00_sq_128+=1;
a_01_sq_128+=1;
a_10_sq_128+=1;
a_11_sq_128+=1;
}
_mm_empty();
_m_empty();
}
bool is_csi_rs_in_symbol(const fapi_nr_dl_config_csirs_pdu_rel15_t csirs_config_pdu, const int symbol) {
bool ret = false;
@@ -90,17 +177,27 @@ bool is_csi_rs_in_symbol(fapi_nr_dl_config_csirs_pdu_rel15_t csirs_config_pdu, i
return ret;
}
int nr_get_csi_rs_signal(PHY_VARS_NR_UE *ue,
UE_nr_rxtx_proc_t *proc,
fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu,
nr_csi_rs_info_t *nr_csi_rs_info,
int32_t **csi_rs_received_signal) {
int nr_get_csi_rs_signal(const PHY_VARS_NR_UE *ue,
const UE_nr_rxtx_proc_t *proc,
const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu,
const nr_csi_info_t *nr_csi_info,
const uint8_t N_cdm_groups,
const uint8_t CDM_group_size,
const uint8_t k_prime,
const uint8_t l_prime,
const uint8_t *j_cdm,
const uint8_t *k_overline,
const uint8_t *l_overline,
int32_t csi_rs_received_signal[][ue->frame_parms.samples_per_slot_wCP],
uint32_t *rsrp,
int *rsrp_dBm) {
int32_t **rxdataF = ue->common_vars.common_vars_rx_data_per_thread[proc->thread_id].rxdataF;
NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
uint16_t meas_count = 0;
uint32_t rsrp_sum = 0;
for (int ant_rx = 0; ant_rx < frame_parms->nb_antennas_rx; ant_rx++) {
memset(csi_rs_received_signal[ant_rx], 0, frame_parms->samples_per_frame_wCP*sizeof(int32_t));
for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) {
@@ -109,36 +206,41 @@ int nr_get_csi_rs_signal(PHY_VARS_NR_UE *ue,
continue;
}
for (int cdm_id = 0; cdm_id < nr_csi_rs_info->N_cdm_groups; cdm_id++) {
for (int s = 0; s < nr_csi_rs_info->CDM_group_size; s++) {
for (int cdm_id = 0; cdm_id < N_cdm_groups; cdm_id++) {
for (int s = 0; s < CDM_group_size; s++) {
// loop over frequency resource elements within a group
for (int kp = 0; kp <= nr_csi_rs_info->kprime; kp++) {
for (int kp = 0; kp <= k_prime; kp++) {
uint16_t k = (frame_parms->first_carrier_offset + (rb*NR_NB_SC_PER_RB)+nr_csi_rs_info->koverline[cdm_id] + kp) % frame_parms->ofdm_symbol_size;
uint16_t k = (frame_parms->first_carrier_offset + (rb*NR_NB_SC_PER_RB)+k_overline[cdm_id] + kp) % frame_parms->ofdm_symbol_size;
// loop over time resource elements within a group
for (int lp = 0; lp <= nr_csi_rs_info->lprime; lp++) {
uint16_t symb = lp + nr_csi_rs_info->loverline[cdm_id];
for (int lp = 0; lp <= l_prime; lp++) {
uint16_t symb = lp + l_overline[cdm_id];
uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size;
int16_t *rx_signal = (int16_t*)&rxdataF[ant_rx][symbol_offset];
int16_t *rx_csi_rs_signal = (int16_t*)&csi_rs_received_signal[ant_rx][symbol_offset];
rx_csi_rs_signal[k<<1] = rx_signal[k<<1];
rx_csi_rs_signal[(k<<1)+1] = rx_signal[(k<<1)+1];
c16_t *rx_signal = (c16_t*)&rxdataF[ant_rx][symbol_offset];
c16_t *rx_csi_rs_signal = (c16_t*)&csi_rs_received_signal[ant_rx][symbol_offset];
rx_csi_rs_signal[k].r = rx_signal[k].r;
rx_csi_rs_signal[k].i = rx_signal[k].i;
rsrp_sum += (((int32_t)(rx_csi_rs_signal[k].r)*rx_csi_rs_signal[k].r) +
((int32_t)(rx_csi_rs_signal[k].i)*rx_csi_rs_signal[k].i));
meas_count++;
#ifdef NR_CSIRS_DEBUG
int dataF_offset = proc->nr_slot_rx*ue->frame_parms.samples_per_slot_wCP;
uint16_t port_tx = s+nr_csi_rs_info->j[cdm_id]*nr_csi_rs_info->CDM_group_size;
int16_t *tx_csi_rs_signal = (int16_t*)&nr_csi_rs_info->csi_rs_generated_signal[port_tx][symbol_offset+dataF_offset];
uint16_t port_tx = s+j_cdm[cdm_id]*CDM_group_size;
c16_t *tx_csi_rs_signal = (c16_t*)&nr_csi_info->csi_rs_generated_signal[port_tx][symbol_offset+dataF_offset];
LOG_I(NR_PHY, "l,k (%2d,%4d) |\tport_tx %d (%4d,%4d)\tant_rx %d (%4d,%4d)\n",
symb,
k,
port_tx+3000,
tx_csi_rs_signal[k<<1],
tx_csi_rs_signal[(k<<1)+1],
tx_csi_rs_signal[k].r,
tx_csi_rs_signal[k].i,
ant_rx,
rx_csi_rs_signal[k<<1],
rx_csi_rs_signal[(k<<1)+1]);
rx_csi_rs_signal[k].r,
rx_csi_rs_signal[k].i);
#endif
}
}
@@ -147,10 +249,19 @@ int nr_get_csi_rs_signal(PHY_VARS_NR_UE *ue,
}
}
*rsrp = rsrp_sum/meas_count;
*rsrp_dBm = dB_fixed(*rsrp) + 30 - pow_2_30_dB
- ((int)openair0_cfg[0].rx_gain[0] - (int)openair0_cfg[0].rx_gain_offset[0]) - dB_fixed(ue->frame_parms.ofdm_symbol_size);
#ifdef NR_CSIRS_DEBUG
LOG_I(NR_PHY, "RSRP = %i (%i dBm)\n", *rsrp, *rsrp_dBm);
#endif
return 0;
}
uint32_t calc_power_csirs(uint16_t *x, fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu) {
uint32_t calc_power_csirs(const uint16_t *x, const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu) {
uint64_t sum_x = 0;
uint64_t sum_x2 = 0;
uint16_t size = 0;
@@ -165,25 +276,38 @@ uint32_t calc_power_csirs(uint16_t *x, fapi_nr_dl_config_csirs_pdu_rel15_t *csir
return sum_x2/size - (sum_x/size)*(sum_x/size);
}
int nr_csi_rs_channel_estimation(PHY_VARS_NR_UE *ue,
UE_nr_rxtx_proc_t *proc,
fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu,
nr_csi_rs_info_t *nr_csi_rs_info,
int32_t **csi_rs_generated_signal,
int32_t **csi_rs_received_signal,
int32_t ***csi_rs_estimated_channel_freq,
int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue,
const UE_nr_rxtx_proc_t *proc,
const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu,
const nr_csi_info_t *nr_csi_info,
const int32_t **csi_rs_generated_signal,
const int32_t csi_rs_received_signal[][ue->frame_parms.samples_per_slot_wCP],
const uint8_t N_cdm_groups,
const uint8_t CDM_group_size,
const uint8_t k_prime,
const uint8_t l_prime,
const uint8_t N_ports,
const uint8_t *j_cdm,
const uint8_t *k_overline,
const uint8_t *l_overline,
int32_t csi_rs_ls_estimated_channel[][N_ports][ue->frame_parms.ofdm_symbol_size],
int32_t csi_rs_estimated_channel_freq[][N_ports][ue->frame_parms.ofdm_symbol_size],
int16_t *log2_re,
int16_t *log2_maxh,
uint32_t *noise_power) {
NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
int dataF_offset = proc->nr_slot_rx*ue->frame_parms.samples_per_slot_wCP;
const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
const int dataF_offset = proc->nr_slot_rx*ue->frame_parms.samples_per_slot_wCP;
*noise_power = 0;
int maxh = 0;
int count = 0;
for (int ant_rx = 0; ant_rx < frame_parms->nb_antennas_rx; ant_rx++) {
/// LS channel estimation
for(uint16_t port_tx = 0; port_tx<nr_csi_rs_info->N_ports; port_tx++) {
memset(nr_csi_rs_info->csi_rs_ls_estimated_channel[ant_rx][port_tx], 0, frame_parms->ofdm_symbol_size*sizeof(int32_t));
for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) {
memset(csi_rs_ls_estimated_channel[ant_rx][port_tx], 0, frame_parms->ofdm_symbol_size*sizeof(int32_t));
}
for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) {
@@ -193,32 +317,32 @@ int nr_csi_rs_channel_estimation(PHY_VARS_NR_UE *ue,
continue;
}
for (int cdm_id = 0; cdm_id < nr_csi_rs_info->N_cdm_groups; cdm_id++) {
for (int s = 0; s < nr_csi_rs_info->CDM_group_size; s++) {
for (int cdm_id = 0; cdm_id < N_cdm_groups; cdm_id++) {
for (int s = 0; s < CDM_group_size; s++) {
uint16_t port_tx = s+nr_csi_rs_info->j[cdm_id]*nr_csi_rs_info->CDM_group_size;
uint16_t port_tx = s+j_cdm[cdm_id]*CDM_group_size;
// loop over frequency resource elements within a group
for (int kp = 0; kp <= nr_csi_rs_info->kprime; kp++) {
for (int kp = 0; kp <= k_prime; kp++) {
uint16_t kinit = (frame_parms->first_carrier_offset + rb*NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size;
uint16_t k = kinit + nr_csi_rs_info->koverline[cdm_id] + kp;
uint16_t k = kinit + k_overline[cdm_id] + kp;
// loop over time resource elements within a group
for (int lp = 0; lp <= nr_csi_rs_info->lprime; lp++) {
uint16_t symb = lp + nr_csi_rs_info->loverline[cdm_id];
for (int lp = 0; lp <= l_prime; lp++) {
uint16_t symb = lp + l_overline[cdm_id];
uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size;
int16_t *tx_csi_rs_signal = (int16_t*)&csi_rs_generated_signal[port_tx][symbol_offset+dataF_offset];
int16_t *rx_csi_rs_signal = (int16_t*)&csi_rs_received_signal[ant_rx][symbol_offset];
int16_t *csi_rs_ls_estimated_channel = (int16_t*)&nr_csi_rs_info->csi_rs_ls_estimated_channel[ant_rx][port_tx][0];
c16_t *tx_csi_rs_signal = (c16_t*)&csi_rs_generated_signal[port_tx][symbol_offset+dataF_offset];
c16_t *rx_csi_rs_signal = (c16_t*)&csi_rs_received_signal[ant_rx][symbol_offset];
c16_t *csi_rs_ls_estimated_channel16 = (c16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][0];
int16_t csi_rs_ls_estimated_channel_re = (int16_t)(((int32_t)tx_csi_rs_signal[k<<1]*rx_csi_rs_signal[k<<1] + (int32_t)tx_csi_rs_signal[(k<<1)+1]*rx_csi_rs_signal[(k<<1)+1])>>nr_csi_rs_info->csi_rs_generated_signal_bits);
int16_t csi_rs_ls_estimated_channel_im = (int16_t)(((int32_t)tx_csi_rs_signal[k<<1]*rx_csi_rs_signal[(k<<1)+1] - (int32_t)tx_csi_rs_signal[(k<<1)+1]*rx_csi_rs_signal[k<<1])>>nr_csi_rs_info->csi_rs_generated_signal_bits);
int16_t csi_rs_ls_estimated_channel_re = (int16_t)(((int32_t)tx_csi_rs_signal[k].r*rx_csi_rs_signal[k].r + (int32_t)tx_csi_rs_signal[k].i*rx_csi_rs_signal[k].i)>>nr_csi_info->csi_rs_generated_signal_bits);
int16_t csi_rs_ls_estimated_channel_im = (int16_t)(((int32_t)tx_csi_rs_signal[k].r*rx_csi_rs_signal[k].i - (int32_t)tx_csi_rs_signal[k].i*rx_csi_rs_signal[k].r)>>nr_csi_info->csi_rs_generated_signal_bits);
// This is not just the LS estimation for each (k,l), but also the sum of the different contributions
// for the sake of optimizing the memory used.
csi_rs_ls_estimated_channel[kinit<<1] += csi_rs_ls_estimated_channel_re;
csi_rs_ls_estimated_channel[(kinit<<1)+1] += csi_rs_ls_estimated_channel_im;
csi_rs_ls_estimated_channel16[kinit].r += csi_rs_ls_estimated_channel_re;
csi_rs_ls_estimated_channel16[kinit].i += csi_rs_ls_estimated_channel_im;
}
}
}
@@ -232,16 +356,16 @@ int nr_csi_rs_channel_estimation(PHY_VARS_NR_UE *ue,
}
for(int k = 0; k<frame_parms->ofdm_symbol_size; k++) {
LOG_I(NR_PHY, "l,k (%2d,%4d) | ", symb, k);
for(uint16_t port_tx = 0; port_tx<nr_csi_rs_info->N_ports; port_tx++) {
for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) {
uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size;
int16_t *tx_csi_rs_signal = (int16_t*)&csi_rs_generated_signal[port_tx][symbol_offset+dataF_offset];
int16_t *rx_csi_rs_signal = (int16_t*)&csi_rs_received_signal[ant_rx][symbol_offset];
int16_t *csi_rs_ls_estimated_channel = (int16_t*)&nr_csi_rs_info->csi_rs_ls_estimated_channel[ant_rx][port_tx][0];
c16_t *tx_csi_rs_signal = (c16_t*)&csi_rs_generated_signal[port_tx][symbol_offset+dataF_offset];
c16_t *rx_csi_rs_signal = (c16_t*)&csi_rs_received_signal[ant_rx][symbol_offset];
c16_t *csi_rs_ls_estimated_channel16 = (c16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][0];
printf("port_tx %d --> ant_rx %d, tx (%4d,%4d), rx (%4d,%4d), ls (%4d,%4d) | ",
port_tx+3000, ant_rx,
tx_csi_rs_signal[k<<1], tx_csi_rs_signal[(k<<1)+1],
rx_csi_rs_signal[k<<1], rx_csi_rs_signal[(k<<1)+1],
csi_rs_ls_estimated_channel[k<<1], csi_rs_ls_estimated_channel[(k<<1)+1]);
tx_csi_rs_signal[k].r, tx_csi_rs_signal[k].i,
rx_csi_rs_signal[k].r, rx_csi_rs_signal[k].i,
csi_rs_ls_estimated_channel16[k].r, csi_rs_ls_estimated_channel16[k].i);
}
printf("\n");
}
@@ -250,7 +374,7 @@ int nr_csi_rs_channel_estimation(PHY_VARS_NR_UE *ue,
/// Channel interpolation
for(uint16_t port_tx = 0; port_tx<nr_csi_rs_info->N_ports; port_tx++) {
for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) {
memset(csi_rs_estimated_channel_freq[ant_rx][port_tx], 0, frame_parms->ofdm_symbol_size*sizeof(int32_t));
}
@@ -261,37 +385,40 @@ int nr_csi_rs_channel_estimation(PHY_VARS_NR_UE *ue,
continue;
}
count++;
uint16_t k = (frame_parms->first_carrier_offset + rb*NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size;
for(uint16_t port_tx = 0; port_tx<nr_csi_rs_info->N_ports; port_tx++) {
int16_t *csi_rs_ls_estimated_channel = (int16_t*)&nr_csi_rs_info->csi_rs_ls_estimated_channel[ant_rx][port_tx][k];
for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) {
int16_t *csi_rs_ls_estimated_channel16 = (int16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][k];
int16_t *csi_rs_estimated_channel16 = (int16_t *)&csi_rs_estimated_channel_freq[ant_rx][port_tx][k];
if( (k == 0) || (k == frame_parms->first_carrier_offset) ) { // Start of OFDM symbol case or first occupied subcarrier case
multadd_real_vector_complex_scalar(filt24_start, csi_rs_ls_estimated_channel, csi_rs_estimated_channel16, 24);
multadd_real_vector_complex_scalar(filt24_start, csi_rs_ls_estimated_channel16, csi_rs_estimated_channel16, 24);
} else if( ( (k + NR_NB_SC_PER_RB) >= frame_parms->ofdm_symbol_size) ||
(rb == (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs-1)) ) { // End of OFDM symbol case or Last occupied subcarrier case
multadd_real_vector_complex_scalar(filt24_end, csi_rs_ls_estimated_channel, csi_rs_estimated_channel16 - 3*sizeof(uint64_t), 24);
multadd_real_vector_complex_scalar(filt24_end, csi_rs_ls_estimated_channel16, csi_rs_estimated_channel16 - 3*sizeof(uint64_t), 24);
} else { // Middle case
multadd_real_vector_complex_scalar(filt24_middle, csi_rs_ls_estimated_channel, csi_rs_estimated_channel16 - 3*sizeof(uint64_t), 24);
multadd_real_vector_complex_scalar(filt24_middle, csi_rs_ls_estimated_channel16, csi_rs_estimated_channel16 - 3*sizeof(uint64_t), 24);
}
}
}
/// Power noise estimation
uint16_t noise_real[frame_parms->nb_antennas_rx][nr_csi_rs_info->N_ports][csirs_config_pdu->nr_of_rbs];
uint16_t noise_imag[frame_parms->nb_antennas_rx][nr_csi_rs_info->N_ports][csirs_config_pdu->nr_of_rbs];
uint16_t noise_real[frame_parms->nb_antennas_rx][N_ports][csirs_config_pdu->nr_of_rbs];
uint16_t noise_imag[frame_parms->nb_antennas_rx][N_ports][csirs_config_pdu->nr_of_rbs];
for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) {
if (csirs_config_pdu->freq_density <= 1 && csirs_config_pdu->freq_density != (rb % 2)) {
continue;
}
uint16_t k = (frame_parms->first_carrier_offset + rb*NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size;
for(uint16_t port_tx = 0; port_tx<nr_csi_rs_info->N_ports; port_tx++) {
int16_t *csi_rs_ls_estimated_channel = (int16_t*)&nr_csi_rs_info->csi_rs_ls_estimated_channel[ant_rx][port_tx][k];
int16_t *csi_rs_estimated_channel16 = (int16_t *)&csi_rs_estimated_channel_freq[ant_rx][port_tx][k];
noise_real[ant_rx][port_tx][rb-csirs_config_pdu->start_rb] = abs(csi_rs_ls_estimated_channel[0]-csi_rs_estimated_channel16[0]);
noise_imag[ant_rx][port_tx][rb-csirs_config_pdu->start_rb] = abs(csi_rs_ls_estimated_channel[1]-csi_rs_estimated_channel16[1]);
for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) {
c16_t *csi_rs_ls_estimated_channel16 = (c16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][k];
c16_t *csi_rs_estimated_channel16 = (c16_t *)&csi_rs_estimated_channel_freq[ant_rx][port_tx][k];
noise_real[ant_rx][port_tx][rb-csirs_config_pdu->start_rb] = abs(csi_rs_ls_estimated_channel16->r-csi_rs_estimated_channel16->r);
noise_imag[ant_rx][port_tx][rb-csirs_config_pdu->start_rb] = abs(csi_rs_ls_estimated_channel16->i-csi_rs_estimated_channel16->i);
maxh = cmax3(maxh, abs(csi_rs_estimated_channel16->r), abs(csi_rs_estimated_channel16->i));
}
}
for(uint16_t port_tx = 0; port_tx<nr_csi_rs_info->N_ports; port_tx++) {
for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) {
*noise_power += (calc_power_csirs(noise_real[ant_rx][port_tx], csirs_config_pdu) + calc_power_csirs(noise_imag[ant_rx][port_tx],csirs_config_pdu));
}
@@ -301,13 +428,13 @@ int nr_csi_rs_channel_estimation(PHY_VARS_NR_UE *ue,
(k - frame_parms->first_carrier_offset)/NR_NB_SC_PER_RB :
(k + frame_parms->ofdm_symbol_size - frame_parms->first_carrier_offset)/NR_NB_SC_PER_RB;
LOG_I(NR_PHY, "(k = %4d) |\t", k);
for(uint16_t port_tx = 0; port_tx<nr_csi_rs_info->N_ports; port_tx++) {
int16_t *csi_rs_ls_estimated_channel = (int16_t*)&nr_csi_rs_info->csi_rs_ls_estimated_channel[ant_rx][port_tx][0];
int16_t *csi_rs_estimated_channel16 = (int16_t *)&csi_rs_estimated_channel_freq[ant_rx][port_tx][0];
for(uint16_t port_tx = 0; port_tx<N_ports; port_tx++) {
c16_t *csi_rs_ls_estimated_channel16 = (c16_t*)&csi_rs_ls_estimated_channel[ant_rx][port_tx][0];
c16_t *csi_rs_estimated_channel16 = (c16_t *)&csi_rs_estimated_channel_freq[ant_rx][port_tx][0];
printf("Channel port_tx %d --> ant_rx %d : ls (%4d,%4d), int (%4d,%4d), noise (%4d,%4d) | ",
port_tx+3000, ant_rx,
csi_rs_ls_estimated_channel[k<<1], csi_rs_ls_estimated_channel[(k<<1)+1],
csi_rs_estimated_channel16[k<<1], csi_rs_estimated_channel16[(k<<1)+1],
csi_rs_ls_estimated_channel16[k].r, csi_rs_ls_estimated_channel16[k].i,
csi_rs_estimated_channel16[k].r, csi_rs_estimated_channel16[k].i,
rb >= csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs ? 0 : noise_real[ant_rx][port_tx][rb-csirs_config_pdu->start_rb],
rb >= csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs ? 0 : noise_imag[ant_rx][port_tx][rb-csirs_config_pdu->start_rb]);
}
@@ -317,7 +444,9 @@ int nr_csi_rs_channel_estimation(PHY_VARS_NR_UE *ue,
}
*noise_power /= (frame_parms->nb_antennas_rx*nr_csi_rs_info->N_ports);
*noise_power /= (frame_parms->nb_antennas_rx*N_ports);
*log2_maxh = log2_approx(maxh-1);
*log2_re = log2_approx(count-1);
#ifdef NR_CSIRS_DEBUG
LOG_I(NR_PHY, "Noise power estimation based on CSI-RS: %i\n", *noise_power);
@@ -326,7 +455,371 @@ int nr_csi_rs_channel_estimation(PHY_VARS_NR_UE *ue,
return 0;
}
int nr_csi_rs_ri_estimation(const PHY_VARS_NR_UE *ue,
const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu,
const nr_csi_info_t *nr_csi_info,
const uint8_t N_ports,
int32_t csi_rs_estimated_channel_freq[][N_ports][ue->frame_parms.ofdm_symbol_size],
const int16_t log2_maxh,
uint8_t *rank_indicator) {
const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
const int16_t cond_dB_threshold = 5;
int count = 0;
*rank_indicator = 0;
if (ue->frame_parms.nb_antennas_rx == 1 || N_ports == 1) {
return 0;
} else if( !(ue->frame_parms.nb_antennas_rx == 2 && N_ports == 2) ) {
LOG_W(NR_PHY, "Rank indicator computation is not implemented for %i x %i system\n",
ue->frame_parms.nb_antennas_rx, N_ports);
return -1;
}
/* Example 2x2: Hh x H =
* | conjch00 conjch10 | x | ch00 ch01 | = | conjch00*ch00+conjch10*ch10 conjch00*ch01+conjch10*ch11 |
* | conjch01 conjch11 | | ch10 ch11 | | conjch01*ch00+conjch11*ch10 conjch01*ch01+conjch11*ch11 |
*/
int32_t csi_rs_estimated_conjch_ch[frame_parms->nb_antennas_rx][N_ports][frame_parms->nb_antennas_rx][N_ports][frame_parms->ofdm_symbol_size] __attribute__((aligned(32)));
int32_t csi_rs_estimated_A_MF[N_ports][N_ports][frame_parms->ofdm_symbol_size] __attribute__((aligned(32)));
int32_t csi_rs_estimated_A_MF_sq[N_ports][N_ports][frame_parms->ofdm_symbol_size] __attribute__((aligned(32)));
int32_t csi_rs_estimated_determ_fin[frame_parms->ofdm_symbol_size] __attribute__((aligned(32)));
int32_t csi_rs_estimated_numer_fin[frame_parms->ofdm_symbol_size] __attribute__((aligned(32)));
const uint8_t sum_shift = 1; // log2(2x2) = 2, which is a shift of 1 bit
for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) {
if (csirs_config_pdu->freq_density <= 1 && csirs_config_pdu->freq_density != (rb % 2)) {
continue;
}
uint16_t k = (frame_parms->first_carrier_offset + rb*NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size;
for (int ant_rx_conjch = 0; ant_rx_conjch < frame_parms->nb_antennas_rx; ant_rx_conjch++) {
for(uint16_t port_tx_conjch = 0; port_tx_conjch < N_ports; port_tx_conjch++) {
for (int ant_rx_ch = 0; ant_rx_ch < frame_parms->nb_antennas_rx; ant_rx_ch++) {
for(uint16_t port_tx_ch = 0; port_tx_ch < N_ports; port_tx_ch++) {
// conjch x ch computation
nr_conjch0_mult_ch1(&csi_rs_estimated_channel_freq[ant_rx_conjch][port_tx_conjch][k],
&csi_rs_estimated_channel_freq[ant_rx_ch][port_tx_ch][k],
&csi_rs_estimated_conjch_ch[ant_rx_conjch][port_tx_conjch][ant_rx_ch][port_tx_ch][k],
1,
log2_maxh);
// construct Hh x H elements
if(ant_rx_conjch == ant_rx_ch) {
nr_a_sum_b((__m128i *)&csi_rs_estimated_A_MF[port_tx_conjch][port_tx_ch][k],
(__m128i *)&csi_rs_estimated_conjch_ch[ant_rx_conjch][port_tx_conjch][ant_rx_ch][port_tx_ch][k],
1);
}
}
}
}
}
// compute the determinant of A_MF (denominator)
nr_det_A_MF_2x2(&csi_rs_estimated_A_MF[0][0][k],
&csi_rs_estimated_A_MF[0][1][k],
&csi_rs_estimated_A_MF[1][0][k],
&csi_rs_estimated_A_MF[1][1][k],
&csi_rs_estimated_determ_fin[k],
1);
// compute the square of A_MF (numerator)
nr_squared_matrix_element(&csi_rs_estimated_A_MF[0][0][k], &csi_rs_estimated_A_MF_sq[0][0][k], 1);
nr_squared_matrix_element(&csi_rs_estimated_A_MF[0][1][k], &csi_rs_estimated_A_MF_sq[0][1][k], 1);
nr_squared_matrix_element(&csi_rs_estimated_A_MF[1][0][k], &csi_rs_estimated_A_MF_sq[1][0][k], 1);
nr_squared_matrix_element(&csi_rs_estimated_A_MF[1][1][k], &csi_rs_estimated_A_MF_sq[1][1][k], 1);
nr_numer_2x2(&csi_rs_estimated_A_MF_sq[0][0][k],
&csi_rs_estimated_A_MF_sq[0][1][k],
&csi_rs_estimated_A_MF_sq[1][0][k],
&csi_rs_estimated_A_MF_sq[1][1][k],
&csi_rs_estimated_numer_fin[k],
1);
#ifdef NR_CSIRS_DEBUG
for(uint16_t port_tx_conjch = 0; port_tx_conjch < N_ports; port_tx_conjch++) {
for(uint16_t port_tx_ch = 0; port_tx_ch < N_ports; port_tx_ch++) {
c16_t *csi_rs_estimated_A_MF_k = (c16_t *) &csi_rs_estimated_A_MF[port_tx_conjch][port_tx_ch][k];
LOG_I(NR_PHY, "(%i) csi_rs_estimated_A_MF[%i][%i] = (%i, %i)\n",
k, port_tx_conjch, port_tx_ch, csi_rs_estimated_A_MF_k->r, csi_rs_estimated_A_MF_k->i);
c16_t *csi_rs_estimated_A_MF_sq_k = (c16_t *) &csi_rs_estimated_A_MF_sq[port_tx_conjch][port_tx_ch][k];
LOG_I(NR_PHY, "(%i) csi_rs_estimated_A_MF_sq[%i][%i] = (%i, %i)\n",
k, port_tx_conjch, port_tx_ch, csi_rs_estimated_A_MF_sq_k->r, csi_rs_estimated_A_MF_sq_k->i);
}
}
LOG_I(NR_PHY, "(%i) csi_rs_estimated_determ_fin = %i\n", k, csi_rs_estimated_determ_fin[k]);
LOG_I(NR_PHY, "(%i) csi_rs_estimated_numer_fin = %i\n", k, csi_rs_estimated_numer_fin[k]>>sum_shift);
#endif
// compute the conditional number
for (int sc_idx=0; sc_idx < NR_NB_SC_PER_RB; sc_idx++) {
int8_t csi_rs_estimated_denum_db = dB_fixed(csi_rs_estimated_determ_fin[k + sc_idx]);
int8_t csi_rs_estimated_numer_db = dB_fixed(csi_rs_estimated_numer_fin[k + sc_idx]>>sum_shift);
int8_t cond_db = csi_rs_estimated_numer_db - csi_rs_estimated_denum_db;
#ifdef NR_CSIRS_DEBUG
LOG_I(NR_PHY, "csi_rs_estimated_denum_db = %i\n", csi_rs_estimated_denum_db);
LOG_I(NR_PHY, "csi_rs_estimated_numer_db = %i\n", csi_rs_estimated_numer_db);
LOG_I(NR_PHY, "cond_db = %i\n", cond_db);
#endif
if (cond_db < cond_dB_threshold) {
count++;
} else {
count--;
}
}
}
// conditional number is lower than cond_dB_threshold in half on more REs
if (count > 0) {
*rank_indicator = 1;
}
#ifdef NR_CSIRS_DEBUG
LOG_I(NR_PHY, "count = %i\n", count);
LOG_I(NR_PHY, "rank = %i\n", (*rank_indicator)+1);
#endif
return 0;
}
int nr_csi_rs_pmi_estimation(const PHY_VARS_NR_UE *ue,
const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu,
const nr_csi_info_t *nr_csi_info,
const uint8_t N_ports,
const int32_t csi_rs_estimated_channel_freq[][N_ports][ue->frame_parms.ofdm_symbol_size],
const uint32_t interference_plus_noise_power,
const uint8_t rank_indicator,
const int16_t log2_re,
uint8_t *i1,
uint8_t *i2,
uint32_t *precoded_sinr_dB) {
const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
memset(i1,0,3*sizeof(uint8_t));
i2[0] = 0;
// i1 is a three-element vector in the form of [i11 i12 i13], when CodebookType is specified as 'Type1SinglePanel'.
// Note that i13 is not applicable when the number of transmission layers is one of {1, 5, 6, 7, 8}.
// i2, for 'Type1SinglePanel' codebook type, it is a scalar when PMIMode is specified as 'wideband', and when PMIMode
// is specified as 'subband' or when PRGSize, the length of the i2 vector equals to the number of subbands or PRGs.
// Note that when the number of CSI-RS ports is 2, the applicable codebook type is 'Type1SinglePanel'. In this case,
// the precoding matrix is obtained by a single index (i2 field here) based on TS 38.214 Table 5.2.2.2.1-1.
// The first column is applicable if the UE is reporting a Rank = 1, whereas the second column is applicable if the
// UE is reporting a Rank = 2.
if(N_ports == 1 || interference_plus_noise_power == 0) {
return 0;
}
if(rank_indicator == 0 || rank_indicator == 1) {
int32_t sum_re[4] = {0};
int32_t sum_im[4] = {0};
int32_t sum2_re[4] = {0};
int32_t sum2_im[4] = {0};
int32_t tested_precoded_sinr[4] = {0};
for (int rb = csirs_config_pdu->start_rb; rb < (csirs_config_pdu->start_rb+csirs_config_pdu->nr_of_rbs); rb++) {
if (csirs_config_pdu->freq_density <= 1 && csirs_config_pdu->freq_density != (rb % 2)) {
continue;
}
uint16_t k = (frame_parms->first_carrier_offset + rb * NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size;
for (int ant_rx = 0; ant_rx < frame_parms->nb_antennas_rx; ant_rx++) {
c16_t *csi_rs_estimated_channel_p0 = (c16_t *) &csi_rs_estimated_channel_freq[ant_rx][0][k];
c16_t *csi_rs_estimated_channel_p1 = (c16_t *) &csi_rs_estimated_channel_freq[ant_rx][1][k];
// H_p0 + 1*H_p1 = (H_p0_re + H_p1_re) + 1j*(H_p0_im + H_p1_im)
sum_re[0] += (csi_rs_estimated_channel_p0->r+csi_rs_estimated_channel_p1->r);
sum_im[0] += (csi_rs_estimated_channel_p0->i+csi_rs_estimated_channel_p1->i);
sum2_re[0] += ((csi_rs_estimated_channel_p0->r+csi_rs_estimated_channel_p1->r)*(csi_rs_estimated_channel_p0->r+csi_rs_estimated_channel_p1->r))>>log2_re;
sum2_im[0] += ((csi_rs_estimated_channel_p0->i+csi_rs_estimated_channel_p1->i)*(csi_rs_estimated_channel_p0->i+csi_rs_estimated_channel_p1->i))>>log2_re;
// H_p0 + 1j*H_p1 = (H_p0_re - H_p1_im) + 1j*(H_p0_im + H_p1_re)
sum_re[1] += (csi_rs_estimated_channel_p0->r-csi_rs_estimated_channel_p1->i);
sum_im[1] += (csi_rs_estimated_channel_p0->i+csi_rs_estimated_channel_p1->r);
sum2_re[1] += ((csi_rs_estimated_channel_p0->r-csi_rs_estimated_channel_p1->i)*(csi_rs_estimated_channel_p0->r-csi_rs_estimated_channel_p1->i))>>log2_re;
sum2_im[1] += ((csi_rs_estimated_channel_p0->i+csi_rs_estimated_channel_p1->r)*(csi_rs_estimated_channel_p0->i+csi_rs_estimated_channel_p1->r))>>log2_re;
// H_p0 - 1*H_p1 = (H_p0_re - H_p1_re) + 1j*(H_p0_im - H_p1_im)
sum_re[2] += (csi_rs_estimated_channel_p0->r-csi_rs_estimated_channel_p1->r);
sum_im[2] += (csi_rs_estimated_channel_p0->i-csi_rs_estimated_channel_p1->i);
sum2_re[2] += ((csi_rs_estimated_channel_p0->r-csi_rs_estimated_channel_p1->r)*(csi_rs_estimated_channel_p0->r-csi_rs_estimated_channel_p1->r))>>log2_re;
sum2_im[2] += ((csi_rs_estimated_channel_p0->i-csi_rs_estimated_channel_p1->i)*(csi_rs_estimated_channel_p0->i-csi_rs_estimated_channel_p1->i))>>log2_re;
// H_p0 - 1j*H_p1 = (H_p0_re + H_p1_im) + 1j*(H_p0_im - H_p1_re)
sum_re[3] += (csi_rs_estimated_channel_p0->r+csi_rs_estimated_channel_p1->i);
sum_im[3] += (csi_rs_estimated_channel_p0->i-csi_rs_estimated_channel_p1->r);
sum2_re[3] += ((csi_rs_estimated_channel_p0->r+csi_rs_estimated_channel_p1->i)*(csi_rs_estimated_channel_p0->r+csi_rs_estimated_channel_p1->i))>>log2_re;
sum2_im[3] += ((csi_rs_estimated_channel_p0->i-csi_rs_estimated_channel_p1->r)*(csi_rs_estimated_channel_p0->i-csi_rs_estimated_channel_p1->r))>>log2_re;
}
}
// We should perform >>nr_csi_info->log2_re here for all terms, but since sum2_re and sum2_im can be high values,
// we performed this above.
for(int p = 0; p<4; p++) {
int32_t power_re = sum2_re[p] - (sum_re[p]>>log2_re)*(sum_re[p]>>log2_re);
int32_t power_im = sum2_im[p] - (sum_im[p]>>log2_re)*(sum_im[p]>>log2_re);
tested_precoded_sinr[p] = (power_re+power_im)/(int32_t)interference_plus_noise_power;
}
if(rank_indicator == 0) {
for(int tested_i2 = 0; tested_i2 < 4; tested_i2++) {
if(tested_precoded_sinr[tested_i2] > tested_precoded_sinr[i2[0]]) {
i2[0] = tested_i2;
}
}
*precoded_sinr_dB = dB_fixed(tested_precoded_sinr[i2[0]]);
} else {
i2[0] = tested_precoded_sinr[0]+tested_precoded_sinr[2] > tested_precoded_sinr[1]+tested_precoded_sinr[3] ? 0 : 1;
*precoded_sinr_dB = dB_fixed((tested_precoded_sinr[i2[0]] + tested_precoded_sinr[i2[0]+2])>>1);
}
} else {
LOG_W(NR_PHY, "PMI computation is not implemented for rank indicator %i\n", rank_indicator+1);
return -1;
}
return 0;
}
int nr_csi_rs_cqi_estimation(const uint32_t precoded_sinr,
uint8_t *cqi) {
*cqi = 0;
// Default SINR table for an AWGN channel for SISO scenario, considering 0.1 BLER condition and TS 38.214 Table 5.2.2.1-2
if(precoded_sinr>0 && precoded_sinr<=2) {
*cqi = 4;
} else if(precoded_sinr==3) {
*cqi = 5;
} else if(precoded_sinr>3 && precoded_sinr<=5) {
*cqi = 6;
} else if(precoded_sinr>5 && precoded_sinr<=7) {
*cqi = 7;
} else if(precoded_sinr>7 && precoded_sinr<=9) {
*cqi = 8;
} else if(precoded_sinr==10) {
*cqi = 9;
} else if(precoded_sinr>10 && precoded_sinr<=12) {
*cqi = 10;
} else if(precoded_sinr>12 && precoded_sinr<=15) {
*cqi = 11;
} else if(precoded_sinr==16) {
*cqi = 12;
} else if(precoded_sinr>16 && precoded_sinr<=18) {
*cqi = 13;
} else if(precoded_sinr==19) {
*cqi = 14;
} else if(precoded_sinr>19) {
*cqi = 15;
}
return 0;
}
int nr_csi_im_power_estimation(const PHY_VARS_NR_UE *ue,
const UE_nr_rxtx_proc_t *proc,
const fapi_nr_dl_config_csiim_pdu_rel15_t *csiim_config_pdu,
uint32_t *interference_plus_noise_power) {
int32_t **rxdataF = ue->common_vars.common_vars_rx_data_per_thread[proc->thread_id].rxdataF;
const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
const uint16_t end_rb = csiim_config_pdu->start_rb + csiim_config_pdu->nr_of_rbs > csiim_config_pdu->bwp_size ?
csiim_config_pdu->bwp_size : csiim_config_pdu->start_rb + csiim_config_pdu->nr_of_rbs;
int32_t count = 0;
int32_t sum_re = 0;
int32_t sum_im = 0;
int32_t sum2_re = 0;
int32_t sum2_im = 0;
int l_csiim[4] = {-1, -1, -1, -1};
for(int symb_idx = 0; symb_idx < 4; symb_idx++) {
uint8_t symb = csiim_config_pdu->l_csiim[symb_idx];
bool done = false;
for (int symb_idx2 = 0; symb_idx2 < symb_idx; symb_idx2++) {
if (l_csiim[symb_idx2] == symb) {
done = true;
}
}
if (done) {
continue;
}
l_csiim[symb_idx] = symb;
uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size;
for (int ant_rx = 0; ant_rx < frame_parms->nb_antennas_rx; ant_rx++) {
c16_t *rx_signal = (c16_t*)&rxdataF[ant_rx][symbol_offset];
for (int rb = csiim_config_pdu->start_rb; rb < end_rb; rb++) {
uint16_t sc0_offset = (frame_parms->first_carrier_offset + rb*NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size;
for (int sc_idx = 0; sc_idx<4; sc_idx++) {
uint16_t sc = sc0_offset + csiim_config_pdu->k_csiim[sc_idx];
#ifdef NR_CSIIM_DEBUG
LOG_I(NR_PHY, "(ant_rx %i, sc %i) real %i, imag %i\n", ant_rx, rb, rx_signal[sc].r, rx_signal[sc].i);
#endif
sum_re += rx_signal[sc].r;
sum_im += rx_signal[sc].i;
sum2_re += rx_signal[sc].r*rx_signal[sc].r;
sum2_im += rx_signal[sc].i*rx_signal[sc].i;
count++;
}
}
}
}
int32_t power_re = sum2_re/count - (sum_re/count)*(sum_re/count);
int32_t power_im = sum2_im/count - (sum_im/count)*(sum_im/count);
*interference_plus_noise_power = power_re + power_im;
#ifdef NR_CSIIM_DEBUG
LOG_I(NR_PHY, "interference_plus_noise_power based on CSI-IM = %i\n", *interference_plus_noise_power);
#endif
return 0;
}
int nr_ue_csi_im_procedures(PHY_VARS_NR_UE *ue, UE_nr_rxtx_proc_t *proc, uint8_t gNB_id) {
if(!ue->csiim_vars[gNB_id]->active) {
return -1;
}
const fapi_nr_dl_config_csiim_pdu_rel15_t *csiim_config_pdu = (fapi_nr_dl_config_csiim_pdu_rel15_t*)&ue->csiim_vars[gNB_id]->csiim_config_pdu;
#ifdef NR_CSIIM_DEBUG
LOG_I(NR_PHY, "csiim_config_pdu->bwp_size = %i\n", csiim_config_pdu->bwp_size);
LOG_I(NR_PHY, "csiim_config_pdu->bwp_start = %i\n", csiim_config_pdu->bwp_start);
LOG_I(NR_PHY, "csiim_config_pdu->subcarrier_spacing = %i\n", csiim_config_pdu->subcarrier_spacing);
LOG_I(NR_PHY, "csiim_config_pdu->start_rb = %i\n", csiim_config_pdu->start_rb);
LOG_I(NR_PHY, "csiim_config_pdu->nr_of_rbs = %i\n", csiim_config_pdu->nr_of_rbs);
LOG_I(NR_PHY, "csiim_config_pdu->k_csiim = %i.%i.%i.%i\n", csiim_config_pdu->k_csiim[0], csiim_config_pdu->k_csiim[1], csiim_config_pdu->k_csiim[2], csiim_config_pdu->k_csiim[3]);
LOG_I(NR_PHY, "csiim_config_pdu->l_csiim = %i.%i.%i.%i\n", csiim_config_pdu->l_csiim[0], csiim_config_pdu->l_csiim[1], csiim_config_pdu->l_csiim[2], csiim_config_pdu->l_csiim[3]);
#endif
nr_csi_im_power_estimation(ue, proc, csiim_config_pdu, &ue->nr_csi_info->interference_plus_noise_power);
ue->nr_csi_info->csi_im_meas_computed = true;
return 0;
}
@@ -336,7 +829,7 @@ int nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue, UE_nr_rxtx_proc_t *proc, uint8_t
return -1;
}
fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu = (fapi_nr_dl_config_csirs_pdu_rel15_t*)&ue->csirs_vars[gNB_id]->csirs_config_pdu;
const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu = (fapi_nr_dl_config_csirs_pdu_rel15_t*)&ue->csirs_vars[gNB_id]->csirs_config_pdu;
#ifdef NR_CSIRS_DEBUG
LOG_I(NR_PHY, "csirs_config_pdu->subcarrier_spacing = %i\n", csirs_config_pdu->subcarrier_spacing);
@@ -355,26 +848,122 @@ int nr_ue_csi_rs_procedures(PHY_VARS_NR_UE *ue, UE_nr_rxtx_proc_t *proc, uint8_t
LOG_I(NR_PHY, "csirs_config_pdu->power_control_offset_ss = %i\n", csirs_config_pdu->power_control_offset_ss);
#endif
nr_generate_csi_rs(ue->frame_parms,
ue->nr_csi_rs_info->csi_rs_generated_signal,
const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
int32_t csi_rs_received_signal[frame_parms->nb_antennas_rx][frame_parms->samples_per_slot_wCP];
uint8_t N_cdm_groups = 0;
uint8_t CDM_group_size = 0;
uint8_t k_prime = 0;
uint8_t l_prime = 0;
uint8_t N_ports = 0;
uint8_t j_cdm[16];
uint8_t k_overline[16];
uint8_t l_overline[16];
int16_t log2_re = 0;
int16_t log2_maxh = 0;
uint32_t rsrp = 0;
int rsrp_dBm = 0;
uint32_t noise_power = 0;
uint8_t rank_indicator = 0;
uint32_t precoded_sinr_dB = 0;
uint8_t cqi = 0;
uint8_t i1[3];
uint8_t i2[1];
nr_generate_csi_rs(frame_parms,
ue->nr_csi_info->csi_rs_generated_signal,
AMP,
ue->nr_csi_rs_info,
ue->nr_csi_info,
(nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *) csirs_config_pdu,
proc->nr_slot_rx);
proc->nr_slot_rx,
&N_cdm_groups,
&CDM_group_size,
&k_prime,
&l_prime,
&N_ports,
j_cdm,
k_overline,
l_overline);
int32_t csi_rs_ls_estimated_channel[frame_parms->nb_antennas_rx][N_ports][frame_parms->ofdm_symbol_size];
int32_t csi_rs_estimated_channel_freq[frame_parms->nb_antennas_rx][N_ports][frame_parms->ofdm_symbol_size];
nr_get_csi_rs_signal(ue,
proc,
csirs_config_pdu,
ue->nr_csi_rs_info,
ue->nr_csi_rs_info->csi_rs_received_signal);
ue->nr_csi_info,
N_cdm_groups,
CDM_group_size,
k_prime,
l_prime,
j_cdm,
k_overline,
l_overline,
csi_rs_received_signal,
&rsrp,
&rsrp_dBm);
nr_csi_rs_channel_estimation(ue,
proc,
csirs_config_pdu,
ue->nr_csi_rs_info,
ue->nr_csi_rs_info->csi_rs_generated_signal,
ue->nr_csi_rs_info->csi_rs_received_signal,
ue->nr_csi_rs_info->csi_rs_estimated_channel_freq,
ue->nr_csi_rs_info->noise_power);
ue->nr_csi_info,
(const int32_t **) ue->nr_csi_info->csi_rs_generated_signal,
csi_rs_received_signal,
N_cdm_groups,
CDM_group_size,
k_prime,
l_prime,
N_ports,
j_cdm,
k_overline,
l_overline,
csi_rs_ls_estimated_channel,
csi_rs_estimated_channel_freq,
&log2_re,
&log2_maxh,
&noise_power);
nr_csi_rs_ri_estimation(ue,
csirs_config_pdu,
ue->nr_csi_info,
N_ports,
csi_rs_estimated_channel_freq,
log2_maxh,
&rank_indicator);
nr_csi_rs_pmi_estimation(ue,
csirs_config_pdu,
ue->nr_csi_info,
N_ports,
csi_rs_estimated_channel_freq,
ue->nr_csi_info->csi_im_meas_computed ? ue->nr_csi_info->interference_plus_noise_power : noise_power,
rank_indicator,
log2_re,
i1,
i2,
&precoded_sinr_dB);
nr_csi_rs_cqi_estimation(precoded_sinr_dB, &cqi);
LOG_I(NR_PHY, "RSRP = %i dBm, RI = %i, i1 = %i.%i.%i, i2 = %i, SINR = %i dB, CQI = %i\n",
rsrp_dBm, rank_indicator+1, i1[0], i1[1], i1[2], i2[0], precoded_sinr_dB, cqi);
// Send CSI measurements to MAC
fapi_nr_csirs_measurements_t csirs_measurements;
csirs_measurements.rsrp = rsrp;
csirs_measurements.rsrp_dBm = rsrp_dBm;
csirs_measurements.rank_indicator = rank_indicator;
csirs_measurements.i1 = *i1;
csirs_measurements.i2 = *i2;
csirs_measurements.cqi = cqi;
nr_downlink_indication_t dl_indication;
fapi_nr_rx_indication_t *rx_ind = calloc(sizeof(*rx_ind),1);
nr_fill_dl_indication(&dl_indication, NULL, rx_ind, proc, ue, gNB_id, NULL);
nr_fill_rx_indication(rx_ind, FAPI_NR_CSIRS_IND, gNB_id, ue, NULL, NULL, 1, proc, (void *)&csirs_measurements);
if (ue->if_inst && ue->if_inst->dl_indication) {
ue->if_inst->dl_indication(&dl_indication, NULL);
} else {
free(rx_ind);
}
return 0;
}
@@ -140,7 +140,6 @@ NR_UE_DLSCH_t *new_nr_ue_dlsch(uint8_t Kmimo,uint8_t Mdlharq,uint32_t Nsoft,uint
dlsch->Mdlharq = Mdlharq;
dlsch->number_harq_processes_for_pdsch = Mdlharq;
dlsch->Nsoft = Nsoft;
dlsch->Mlimit = 4;
dlsch->max_ldpc_iterations = max_ldpc_iterations;
for (int i=0; i<Mdlharq; i++) {
@@ -222,7 +221,6 @@ bool nr_ue_postDecode(PHY_VARS_NR_UE *phy_vars_ue, notifiedFIFO_elt_t *req, bool
//LOG_D(PHY,"[UE %d] DLSCH: Setting ACK for nr_slot_rx %d TBS %d mcs %d nb_rb %d harq_process->round %d\n",
// phy_vars_ue->Mod_id,nr_slot_rx,harq_process->TBS,harq_process->mcs,harq_process->nb_rb, harq_process->round);
harq_process->status = SCH_IDLE;
harq_process->DLround = 0;
harq_process->ack = 1;
//LOG_D(PHY,"[UE %d] DLSCH: Setting ACK for SFN/SF %d/%d (pid %d, status %d, round %d, TBS %d, mcs %d)\n",
@@ -237,11 +235,6 @@ bool nr_ue_postDecode(PHY_VARS_NR_UE *phy_vars_ue, notifiedFIFO_elt_t *req, bool
//LOG_D(PHY,"[UE %d] DLSCH: Setting NAK for SFN/SF %d/%d (pid %d, status %d, round %d, TBS %d, mcs %d) Kr %d r %d harq_process->round %d\n",
// phy_vars_ue->Mod_id, frame, nr_slot_rx, harq_pid,harq_process->status, harq_process->round,harq_process->TBS,harq_process->mcs,Kr,r,harq_process->round);
harq_process->ack = 0;
if (harq_process->DLround >= dlsch->Mlimit) {
harq_process->status = SCH_IDLE;
harq_process->DLround = 0;
phy_vars_ue->dl_stats[4]++;
}
//if(is_crnti) {
// LOG_D(PHY,"[UE %d] DLSCH: Setting NACK for nr_slot_rx %d (pid %d, pid status %d, round %d/Max %d, TBS %d)\n",
@@ -496,8 +489,6 @@ uint32_t nr_dlsch_decoding(PHY_VARS_NR_UE *phy_vars_ue,
}
*/
nb_rb = harq_process->nb_rb;
harq_process->trials[harq_process->DLround]++;
A = harq_process->TBS;
ret = dlsch->max_ldpc_iterations + 1;
dlsch->last_iteration_cnt = ret;
@@ -466,88 +466,87 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
if (cpumeas(CPUMEAS_GETSTATE))
LOG_D(PHY, "[AbsSFN %u.%d] Slot%d Symbol %d: Channel Combine and zero forcing %5.2f \n",frame,nr_slot_rx,slot,symbol,ue->generic_stat_bis[proc->thread_id][slot].p_time/(cpuf*1000.0));
start_meas(&ue->generic_stat_bis[proc->thread_id][slot]);
start_meas(&ue->generic_stat_bis[proc->thread_id][slot]);
/* Store the valid DL RE's */
pdsch_vars[gNB_id]->dl_valid_re[symbol-1] = nb_re_pdsch;
pdsch_vars[gNB_id]->dl_valid_re[symbol-1] = nb_re_pdsch;
if(dlsch0_harq->status == ACTIVE) {
startSymbIdx = dlsch0_harq->start_symbol;
nbSymb = dlsch0_harq->nb_symbols;
pduBitmap = dlsch0_harq->pduBitmap;
}
if(dlsch1_harq) {
startSymbIdx = dlsch1_harq->start_symbol;
nbSymb = dlsch1_harq->nb_symbols;
pduBitmap = dlsch1_harq->pduBitmap;
}
if(dlsch0_harq->status == ACTIVE) {
startSymbIdx = dlsch0_harq->start_symbol;
nbSymb = dlsch0_harq->nb_symbols;
pduBitmap = dlsch0_harq->pduBitmap;
}
if(dlsch1_harq) {
startSymbIdx = dlsch1_harq->start_symbol;
nbSymb = dlsch1_harq->nb_symbols;
pduBitmap = dlsch1_harq->pduBitmap;
}
/* Check for PTRS bitmap and process it respectively */
if((pduBitmap & 0x1) && (type == PDSCH)) {
nr_pdsch_ptrs_processing(ue,
pdsch_vars,
frame_parms,
dlsch0_harq,
dlsch1_harq,
gNB_id,
nr_slot_rx,
symbol,
(nb_rb_pdsch*12),
dlsch[0]->rnti,rx_type);
pdsch_vars[gNB_id]->dl_valid_re[symbol-1] -= pdsch_vars[gNB_id]->ptrs_re_per_slot[0][symbol];
}
/* Check for PTRS bitmap and process it respectively */
if((pduBitmap & 0x1) && (type == PDSCH)) {
nr_pdsch_ptrs_processing(ue,
pdsch_vars,
frame_parms,
dlsch0_harq,
dlsch1_harq,
gNB_id,
nr_slot_rx,
symbol,
(nb_rb_pdsch*12),
dlsch[0]->rnti,rx_type);
pdsch_vars[gNB_id]->dl_valid_re[symbol-1] -= pdsch_vars[gNB_id]->ptrs_re_per_slot[0][symbol];
}
/* at last symbol in a slot calculate LLR's for whole slot */
if(symbol == (startSymbIdx + nbSymb -1)) {
for(uint8_t i =startSymbIdx; i < (startSymbIdx+nbSymb);i++) {
/* re evaluating the first symbol flag as LLR's are done in symbol loop */
if(i == startSymbIdx && i < 3) {
first_symbol_flag =1;
}
else {
first_symbol_flag=0;
}
/* Calculate LLR's for each symbol */
nr_dlsch_llr(pdsch_vars, frame_parms,
rxdataF_comp_ptr, dl_ch_mag_ptr,
dlsch0_harq, dlsch1_harq,
rx_type, harq_pid,
gNB_id, gNB_id_i,
first_symbol_flag,
i, nb_rb_pdsch,
codeword_TB0, codeword_TB1,
pdsch_vars[gNB_id]->dl_valid_re[i-1],
nr_slot_rx, beamforming_mode);
/* at last symbol in a slot calculate LLR's for whole slot */
if(symbol == (startSymbIdx + nbSymb -1)) {
for(uint8_t i =startSymbIdx; i < (startSymbIdx+nbSymb);i++) {
/* re evaluating the first symbol flag as LLR's are done in symbol loop */
if(i == startSymbIdx && i < 3) {
first_symbol_flag =1;
}
int dmrs_type = dlsch[0]->harq_processes[harq_pid]->dmrsConfigType;
uint8_t nb_re_dmrs;
uint16_t dmrs_len = get_num_dmrs(dlsch[0]->harq_processes[harq_pid]->dlDmrsSymbPos);
if (dmrs_type==NFAPI_NR_DMRS_TYPE1) {
nb_re_dmrs = 6*dlsch[0]->harq_processes[harq_pid]->n_dmrs_cdm_groups;
} else {
nb_re_dmrs = 4*dlsch[0]->harq_processes[harq_pid]->n_dmrs_cdm_groups;
else {
first_symbol_flag=0;
}
dlsch[0]->harq_processes[harq_pid]->G = nr_get_G(dlsch[0]->harq_processes[harq_pid]->nb_rb,
dlsch[0]->harq_processes[harq_pid]->nb_symbols,
nb_re_dmrs,
dmrs_len,
dlsch[0]->harq_processes[harq_pid]->Qm,
dlsch[0]->harq_processes[harq_pid]->Nl);
nr_dlsch_layer_demapping(pdsch_vars[gNB_id]->llr,
dlsch[0]->harq_processes[harq_pid]->Nl,
dlsch[0]->harq_processes[harq_pid]->Qm,
dlsch[0]->harq_processes[harq_pid]->G,
codeword_TB0,
codeword_TB1,
pdsch_vars[gNB_id]->layer_llr);
/* Calculate LLR's for each symbol */
nr_dlsch_llr(pdsch_vars, frame_parms,
rxdataF_comp_ptr, dl_ch_mag_ptr,
dlsch0_harq, dlsch1_harq,
rx_type, harq_pid,
gNB_id, gNB_id_i,
first_symbol_flag,
i, nb_rb_pdsch,
codeword_TB0, codeword_TB1,
pdsch_vars[gNB_id]->dl_valid_re[i-1],
nr_slot_rx, beamforming_mode);
}
stop_meas(&ue->generic_stat_bis[proc->thread_id][slot]);
if (cpumeas(CPUMEAS_GETSTATE))
LOG_D(PHY, "[AbsSFN %u.%d] Slot%d Symbol %d: LLR Computation %5.2f \n",frame,nr_slot_rx,slot,symbol,ue->generic_stat_bis[proc->thread_id][slot].p_time/(cpuf*1000.0));
int dmrs_type = dlsch[0]->harq_processes[harq_pid]->dmrsConfigType;
uint8_t nb_re_dmrs;
uint16_t dmrs_len = get_num_dmrs(dlsch[0]->harq_processes[harq_pid]->dlDmrsSymbPos);
if (dmrs_type==NFAPI_NR_DMRS_TYPE1) {
nb_re_dmrs = 6*dlsch[0]->harq_processes[harq_pid]->n_dmrs_cdm_groups;
} else {
nb_re_dmrs = 4*dlsch[0]->harq_processes[harq_pid]->n_dmrs_cdm_groups;
}
dlsch[0]->harq_processes[harq_pid]->G = nr_get_G(dlsch[0]->harq_processes[harq_pid]->nb_rb,
dlsch[0]->harq_processes[harq_pid]->nb_symbols,
nb_re_dmrs,
dmrs_len,
dlsch[0]->harq_processes[harq_pid]->Qm,
dlsch[0]->harq_processes[harq_pid]->Nl);
nr_dlsch_layer_demapping(pdsch_vars[gNB_id]->llr,
dlsch[0]->harq_processes[harq_pid]->Nl,
dlsch[0]->harq_processes[harq_pid]->Qm,
dlsch[0]->harq_processes[harq_pid]->G,
codeword_TB0,
codeword_TB1,
pdsch_vars[gNB_id]->layer_llr);
}
// Please keep it: useful for debugging
stop_meas(&ue->generic_stat_bis[proc->thread_id][slot]);
if (cpumeas(CPUMEAS_GETSTATE))
LOG_D(PHY, "[AbsSFN %u.%d] Slot%d Symbol %d: LLR Computation %5.2f \n",frame,nr_slot_rx,slot,symbol,ue->generic_stat_bis[proc->thread_id][slot].p_time/(cpuf*1000.0));
// Please keep it: useful for debugging
#ifdef DEBUG_PDSCH_RX
char filename[50];
uint8_t aa = 0;
@@ -362,7 +362,7 @@ int nr_initial_sync(UE_nr_rxtx_proc_t *proc,
nr_gold_pdsch(ue, i, ue->scramblingID_dlsch[i]);
}
nr_init_csi_rs(fp, ue->nr_csi_rs_info->nr_gold_csi_rs, fp->Nid_cell);
nr_init_csi_rs(fp, ue->nr_csi_info->nr_gold_csi_rs, fp->Nid_cell);
// initialize the pusch dmrs
for (int i=0; i<NR_NB_NSCID; i++) {
@@ -855,10 +855,6 @@ void construct_HhH_elements(int *ch0conj_ch0,
int32_t *after_mf_11,
unsigned short nb_rb);
void squared_matrix_element(int32_t *Hh_h_00,
int32_t *Hh_h_00_sq,
unsigned short nb_rb);
void dlsch_channel_level_TM34_meas(int *ch00,
int *ch01,
int *ch10,
@@ -885,19 +881,15 @@ void nr_dlsch_detection_mrc(int **rxdataF_comp,
unsigned short nb_rb,
int length);
void det_HhH(int32_t *after_mf_00,
int32_t *after_mf_01,
int32_t *after_mf_10,
int32_t *after_mf_11,
int32_t *det_fin_128,
unsigned short nb_rb);
void nr_conjch0_mult_ch1(int *ch0,
int *ch1,
int32_t *ch0conj_ch1,
unsigned short nb_rb,
unsigned char output_shift0);
void numer(int32_t *Hh_h_00_sq,
int32_t *Hh_h_01_sq,
int32_t *Hh_h_10_sq,
int32_t *Hh_h_11_sq,
int32_t *num_fin,
unsigned short nb_rb);
void nr_a_sum_b(__m128i *input_x,
__m128i *input_y,
unsigned short nb_rb);
uint8_t rank_estimation_tm3_tm4(int *dl_ch_estimates_00,
int *dl_ch_estimates_01,
+2 -10
View File
@@ -161,15 +161,13 @@ typedef struct {
//uint8_t num_cba_dci[10];
/// allocated CBA RNTI
//uint16_t cba_rnti[4];//NUM_MAX_CBA_GROUP];
/// UL max-harq-retransmission
uint16_t Mlimit;
} NR_UE_ULSCH_t;
typedef struct {
/// Indicator of first reception
uint8_t first_rx;
/// Last Ndi received for this process on DCI (used for C-RNTI only)
uint8_t DCINdi;
uint8_t Ndi;
/// DLSCH status flag indicating
SCH_status_t status;
/// Transport block size
@@ -241,10 +239,6 @@ typedef struct {
vrb_t vrb_type;
/// downlink power offset field
uint8_t dl_power_off;
/// trials per round statistics
uint32_t trials[8];
/// error statistics per round
uint32_t errors[8];
/// codeword this transport block is mapped to
uint8_t codeword;
/// HARQ-ACKs
@@ -311,9 +305,7 @@ typedef struct {
/// Maximum number of LDPC iterations
uint8_t max_ldpc_iterations;
/// number of iterations used in last turbo decoding
uint8_t last_iteration_cnt;
/// Maximum number of HARQ rounds
uint8_t Mlimit;
uint8_t last_iteration_cnt;
} NR_UE_DLSCH_t;
typedef enum {format0_0,
@@ -130,10 +130,6 @@ NR_UE_ULSCH_t *new_nr_ue_ulsch(uint16_t N_RB_UL, int number_of_harq_pids, NR_DL_
memset(ulsch, 0, sizeof(*ulsch));
ulsch->number_harq_processes_for_pusch = NR_MAX_ULSCH_HARQ_PROCESSES;
ulsch->Mlimit = 4; // maximum harq retransmissions
//for (i=0; i<10; i++)
//ulsch->harq_ids[i] = 0;
for (int i = 0; i < number_of_harq_pids; i++) {
+2 -8
View File
@@ -188,8 +188,6 @@ typedef struct {
uint8_t codebook_index;
/// Maximum number of HARQ processes
uint8_t Mdlharq;
/// Maximum number of HARQ rounds
uint8_t Mlimit;
/// MIMO transmission mode indicator for this sub-frame
uint8_t Kmimo;
/// Nsoft parameter related to UE Category
@@ -345,8 +343,6 @@ typedef struct {
typedef struct {
/// Pointers to 16 HARQ processes for the ULSCH
NR_UL_gNB_HARQ_t *harq_processes[NR_MAX_ULSCH_HARQ_PROCESSES];
/// Current HARQ process id
int harq_process_id[NR_MAX_SLOTS_PER_FRAME];
/// HARQ process mask, indicates which processes are currently active
uint16_t harq_mask;
/// ACK/NAK Bundling flag
@@ -373,8 +369,6 @@ typedef struct {
uint8_t cyclicShift;
/// for cooperative communication
uint8_t cooperation_flag;
/// Maximum number of HARQ rounds
uint8_t Mlimit;
/// Maximum number of LDPC iterations
uint8_t max_ldpc_iterations;
/// number of iterations used in last LDPC decoding
@@ -765,8 +759,8 @@ typedef struct PHY_VARS_gNB_s {
/// SRS variables
nr_srs_info_t *nr_srs_info[NUMBER_OF_NR_SRS_MAX];
/// CSI-RS variables
nr_csi_rs_info_t *nr_csi_rs_info;
/// CSI variables
nr_csi_info_t *nr_csi_info;
uint8_t pbch_configured;
char gNB_generate_rar;
+4 -4
View File
@@ -878,8 +878,8 @@ typedef struct {
/// SRS variables
nr_srs_info_t *nr_srs_info;
/// CSI-RS variables
nr_csi_rs_info_t *nr_csi_rs_info;
/// CSI variables
nr_csi_info_t *nr_csi_info;
//#if defined(UPGRADE_RAT_NR)
#if 1
@@ -978,8 +978,8 @@ typedef struct {
SLIST_HEAD(ral_thresholds_gen_poll_s, ral_threshold_phy_t) ral_thresholds_gen_polled[RAL_LINK_PARAM_GEN_MAX];
SLIST_HEAD(ral_thresholds_lte_poll_s, ral_threshold_phy_t) ral_thresholds_lte_polled[RAL_LINK_PARAM_LTE_MAX];
#endif
int dl_stats[5];
int dl_errors;
int dl_stats[8];
void* scopeData;
} PHY_VARS_NR_UE;
+4 -13
View File
@@ -43,6 +43,7 @@
#define nr_slot_t lte_subframe_t
#define MAX_NUM_SUBCARRIER_SPACING 5
#define NR_MAX_OFDM_SYMBOL_SIZE 4096
#define NR_NB_SC_PER_RB 12
#define NR_NB_REG_PER_CCE 6
@@ -247,23 +248,13 @@ typedef struct {
} nr_srs_info_t;
typedef struct {
uint8_t N_cdm_groups;
uint8_t CDM_group_size;
uint8_t kprime;
uint8_t lprime;
uint8_t N_ports;
uint8_t j[16];
uint8_t koverline[16];
uint8_t loverline[16];
uint16_t csi_gold_init;
uint32_t ***nr_gold_csi_rs;
uint8_t csi_rs_generated_signal_bits;
int32_t **csi_rs_generated_signal;
int32_t **csi_rs_received_signal;
int32_t ***csi_rs_ls_estimated_channel;
int32_t ***csi_rs_estimated_channel_freq;
uint32_t *noise_power;
} nr_csi_rs_info_t;
bool csi_im_meas_computed;
uint32_t interference_plus_noise_power;
} nr_csi_info_t;
typedef struct NR_DL_FRAME_PARMS NR_DL_FRAME_PARMS;
+9 -5
View File
@@ -71,9 +71,9 @@
#include "common/utils/system.h"
#include <time.h>
extern int oai_exit;
#include "openair1/SCHED/sched_common_extern.h"
#include "targets/RT/USER/lte-softmodem.h"
#include "common/ran_context.h"
void feptx0(RU_t *ru,
int slot)
@@ -616,9 +616,11 @@ void init_fep_thread(RU_t *ru,
}
extern void kill_fep_thread(RU_t *ru)
void kill_fep_thread(RU_t *ru)
{
RU_proc_t *proc = &ru->proc;
if (proc->pthread_fep == 0)
return;
pthread_mutex_lock( &proc->mutex_fep );
proc->instance_cnt_fep = 0;
pthread_cond_signal(&proc->cond_fep);
@@ -630,9 +632,11 @@ extern void kill_fep_thread(RU_t *ru)
}
extern void kill_feptx_thread(RU_t *ru)
void kill_feptx_thread(RU_t *ru)
{
RU_proc_t *proc = &ru->proc;
if (proc->pthread_feptx == 0)
return;
pthread_mutex_lock( &proc->mutex_feptx );
proc->instance_cnt_feptx = 0;
pthread_cond_signal(&proc->cond_feptx);
+2
View File
@@ -29,4 +29,6 @@
extern int16_t hundred_times_delta_TF[100];
extern uint16_t hundred_times_log10_NPRB[100];
void kill_fep_thread(RU_t *ru);
#endif /*__SCHED_EXTERN_H__ */
+9 -34
View File
@@ -172,7 +172,7 @@ void phy_procedures_gNB_TX(processingData_L1tx_t *msgTx,
if (csirs->active == 1) {
LOG_D(PHY, "CSI-RS generation started in frame %d.%d\n",frame,slot);
nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params = &csirs->csirs_pdu.csi_rs_pdu_rel15;
nr_generate_csi_rs(gNB->frame_parms, gNB->common_vars.txdataF, AMP, gNB->nr_csi_rs_info, csi_params, slot);
nr_generate_csi_rs(&gNB->frame_parms, gNB->common_vars.txdataF, AMP, gNB->nr_csi_info, csi_params, slot, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL);
csirs->active = 0;
}
}
@@ -193,14 +193,12 @@ void nr_postDecode(PHY_VARS_gNB *gNB, notifiedFIFO_elt_t *req) {
NR_gNB_ULSCH_t *ulsch = rdata->ulsch;
int r = rdata->segment_r;
nfapi_nr_pusch_pdu_t *pusch_pdu = &gNB->ulsch[rdata->ulsch_id]->harq_processes[rdata->harq_pid]->ulsch_pdu;
bool decodeSuccess = (rdata->decodeIterations <= rdata->decoderParms.numMaxIter);
ulsch_harq->processedSegments++;
LOG_D(PHY, "processing result of segment: %d, processed %d/%d\n",
rdata->segment_r, ulsch_harq->processedSegments, rdata->nbSegments);
gNB->nbDecode--;
LOG_D(PHY,"remain to decoded in subframe: %d\n", gNB->nbDecode);
if (decodeSuccess) {
memcpy(ulsch_harq->b+rdata->offset,
ulsch_harq->c[r],
@@ -222,7 +220,7 @@ void nr_postDecode(PHY_VARS_gNB *gNB, notifiedFIFO_elt_t *req) {
//int dumpsig=0;
// if all segments are done
if (rdata->nbSegments == ulsch_harq->processedSegments) {
if (decodeSuccess) {
if (decodeSuccess && !gNB->pusch_vars[rdata->ulsch_id]->DTX) {
LOG_D(PHY,"[gNB %d] ULSCH: Setting ACK for SFN/SF %d.%d (pid %d, ndi %d, status %d, round %d, TBS %d, Max interation (all seg) %d)\n",
gNB->Mod_id,ulsch_harq->frame,ulsch_harq->slot,rdata->harq_pid,pusch_pdu->pusch_data.new_data_indicator,ulsch_harq->status,ulsch_harq->round,ulsch_harq->TBS,rdata->decodeIterations);
ulsch_harq->status = SCH_IDLE;
@@ -242,13 +240,6 @@ void nr_postDecode(PHY_VARS_gNB *gNB, notifiedFIFO_elt_t *req) {
ulsch_harq->ulsch_pdu.rb_size,
ulsch_harq->TBS,
r);
ulsch_harq->round++;
if (ulsch_harq->round >= ulsch->Mlimit) {
ulsch_harq->status = SCH_IDLE;
ulsch_harq->round = 0;
ulsch_harq->handled = 0;
ulsch->harq_mask &= ~(1 << rdata->harq_pid);
}
ulsch_harq->handled = 1;
LOG_D(PHY, "ULSCH %d in error\n",rdata->ulsch_id);
@@ -413,17 +404,8 @@ void nr_fill_indication(PHY_VARS_gNB *gNB, int frame, int slot_rx, int ULSCH_id,
if (timing_advance_update > 63) timing_advance_update = 63;
if (crc_flag == 0) LOG_D(PHY, "%d.%d : Received PUSCH : Estimated timing advance PUSCH is = %d, timing_advance_update is %d \n", frame,slot_rx,sync_pos,timing_advance_update);
else if (harq_process->round>0 || dtx_flag == 0) { // increment round if crc_flag == 1 and not(dtx_flag ==1 and round==0)
harq_process->round++;
if (harq_process->round >= ulsch->Mlimit) {
harq_process->status = SCH_IDLE;
harq_process->round = 0;
harq_process->handled = 0;
ulsch->harq_mask &= ~(1 << harq_pid);
}
}
// estimate UL_CQI for MAC
// estimate UL_CQI for MAC
int SNRtimes10 = dB_fixed_x10(gNB->pusch_vars[ULSCH_id]->ulsch_power_tot) -
dB_fixed_x10(gNB->pusch_vars[ULSCH_id]->ulsch_noise_power_tot);
@@ -573,7 +555,7 @@ void fill_ul_rb_mask(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) {
LOG_D(PHY,"symbol %d Filling rb_mask_ul rb_size %d\n",symbol,ulsch_harq->ulsch_pdu.rb_size);
for (rb=0; rb<ulsch_harq->ulsch_pdu.rb_size; rb++) {
rb2 = rb+ulsch_harq->ulsch_pdu.rb_start+ulsch_harq->ulsch_pdu.bwp_start;
gNB->rb_mask_ul[symbol][rb2>>5] |= (1<<(rb2&31));
gNB->rb_mask_ul[symbol][rb2 >> 5] |= 1U << (rb2 & 31);
}
}
}
@@ -727,6 +709,7 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) {
LOG_D(PHY,"%d.%d Calling nr_decode_pucch2\n",frame_rx,slot_rx);
nr_decode_pucch2(gNB,
frame_rx,
slot_rx,
uci_pdu_format2,
pucch_pdu);
@@ -743,14 +726,12 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) {
for (int ULSCH_id=0;ULSCH_id<gNB->number_of_nr_ulsch_max;ULSCH_id++) {
NR_gNB_ULSCH_t *ulsch = gNB->ulsch[ULSCH_id];
int harq_pid;
int no_sig;
NR_UL_gNB_HARQ_t *ulsch_harq;
if ((ulsch) &&
(ulsch->rnti > 0)) {
// for for an active HARQ process
for (harq_pid=0;harq_pid<NR_MAX_ULSCH_HARQ_PROCESSES;harq_pid++) {
for (int harq_pid=0;harq_pid<NR_MAX_ULSCH_HARQ_PROCESSES;harq_pid++) {
ulsch_harq = ulsch->harq_processes[harq_pid];
AssertFatal(ulsch_harq!=NULL,"harq_pid %d is not allocated\n",harq_pid);
if ((ulsch_harq->status == NR_ACTIVE) &&
@@ -792,13 +773,7 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) {
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_NR_RX_PUSCH,1);
start_meas(&gNB->rx_pusch_stats);
no_sig = nr_rx_pusch(gNB, ULSCH_id, frame_rx, slot_rx, harq_pid);
if (no_sig) {
LOG_D(PHY, "PUSCH not detected in frame %d, slot %d\n", frame_rx, slot_rx);
nr_fill_indication(gNB, frame_rx, slot_rx, ULSCH_id, harq_pid, 1,1);
pusch_DTX++;
continue;
}
nr_rx_pusch(gNB, ULSCH_id, frame_rx, slot_rx, harq_pid);
gNB->pusch_vars[ULSCH_id]->ulsch_power_tot=0;
gNB->pusch_vars[ULSCH_id]->ulsch_noise_power_tot=0;
for (int aarx=0;aarx<gNB->frame_parms.nb_antennas_rx;aarx++) {
@@ -858,8 +833,8 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) {
uint8_t N_symb_SRS = 1<<srs_pdu->num_symbols;
int32_t srs_received_signal[frame_parms->nb_antennas_rx][frame_parms->ofdm_symbol_size*N_symb_SRS];
int32_t srs_ls_estimated_channel[frame_parms->nb_antennas_rx][MAX_NUM_NR_SRS_AP][frame_parms->ofdm_symbol_size*N_symb_SRS];
int32_t srs_estimated_channel_freq[frame_parms->nb_antennas_rx][MAX_NUM_NR_SRS_AP][frame_parms->ofdm_symbol_size*N_symb_SRS];
int32_t srs_estimated_channel_time[frame_parms->nb_antennas_rx][MAX_NUM_NR_SRS_AP][frame_parms->ofdm_symbol_size];
int32_t srs_estimated_channel_freq[frame_parms->nb_antennas_rx][MAX_NUM_NR_SRS_AP][frame_parms->ofdm_symbol_size*N_symb_SRS] __attribute__ ((aligned(32)));
int32_t srs_estimated_channel_time[frame_parms->nb_antennas_rx][MAX_NUM_NR_SRS_AP][frame_parms->ofdm_symbol_size] __attribute__ ((aligned(32)));
int32_t srs_estimated_channel_time_shifted[frame_parms->nb_antennas_rx][MAX_NUM_NR_SRS_AP][frame_parms->ofdm_symbol_size];
uint32_t noise_power_per_rb[srs_pdu->bwp_size];
int8_t snr_per_rb[srs_pdu->bwp_size];
+1 -1
View File
@@ -405,7 +405,7 @@ void nr_fill_rx_indication(fapi_nr_rx_indication_t *rx_ind,
NR_UE_DLSCH_t *dlsch1,
uint16_t n_pdus,
UE_nr_rxtx_proc_t *proc,
void * typeSpecific);
void *typeSpecific);
bool nr_ue_dlsch_procedures(PHY_VARS_NR_UE *ue,
UE_nr_rxtx_proc_t *proc,
+1 -1
View File
@@ -393,7 +393,7 @@ int8_t nr_ue_scheduled_response(nr_scheduled_response_t *scheduled_response){
case FAPI_NR_DL_CONFIG_TYPE_CSI_IM:
csiim_config_pdu = &dl_config->dl_config_list[i].csiim_config_pdu.csiim_config_rel15;
memcpy((void*)&(csiim_vars->csiim_config_pdu), (void*)csiim_config_pdu, sizeof(fapi_nr_dl_config_csiim_pdu_rel15_t));
csirs_vars->active = true;
csiim_vars->active = true;
break;
case FAPI_NR_DL_CONFIG_TYPE_CSI_RS:
csirs_config_pdu = &dl_config->dl_config_list[i].csirs_config_pdu.csirs_config_rel15;
+6 -7
View File
@@ -308,7 +308,7 @@ void init_downlink_harq_status(NR_DL_UE_HARQ_t *dl_harq)
dl_harq->status = SCH_IDLE;
dl_harq->first_rx = 1;
dl_harq->DLround = 0;
dl_harq->DCINdi = 1;
dl_harq->Ndi = 1;
dl_harq->ack = DL_ACKNACK_NO_SET;
}
@@ -329,7 +329,7 @@ void init_downlink_harq_status(NR_DL_UE_HARQ_t *dl_harq)
*
*********************************************************************/
void downlink_harq_process(NR_DL_UE_HARQ_t *dl_harq, int harq_pid, int ndi, int rv, uint8_t rnti_type) {
void downlink_harq_process(NR_DL_UE_HARQ_t *dl_harq, int harq_pid, int dci_ndi, int rv, uint8_t rnti_type) {
if (rnti_type == _SI_RNTI_ ||
rnti_type == _P_RNTI_ ||
@@ -339,10 +339,9 @@ void downlink_harq_process(NR_DL_UE_HARQ_t *dl_harq, int harq_pid, int ndi, int
dl_harq->first_rx = 1;
} else {
LOG_D(PHY,"receive harq process: %p harqPid=%d, rv=%d, ndi=%d, rntiType=%d new transmission= %s\n",
dl_harq, harq_pid, rv, ndi, rnti_type, dl_harq->DCINdi != ndi ? "yes":"no");
dl_harq, harq_pid, rv, dci_ndi, rnti_type, dl_harq->Ndi != dci_ndi ? "yes":"no");
AssertFatal(rv<4 && rv>=0, "invalid redondancy version %d\n", rv);
if (ndi!=dl_harq->DCINdi) {
if (dci_ndi!=dl_harq->Ndi) {
if (dl_harq->ack == DL_NACK)
LOG_D(PHY,"New transmission on a harq pid (%d) never acknowledged\n", harq_pid);
else
@@ -354,7 +353,7 @@ void downlink_harq_process(NR_DL_UE_HARQ_t *dl_harq, int harq_pid, int ndi, int
LOG_D(PHY,"Starting retransmission on a harq pid (%d), rv (%d)\n", harq_pid, rv);
}
if (ndi!=dl_harq->DCINdi) {
if (dci_ndi!=dl_harq->Ndi) {
dl_harq->first_rx = true;
dl_harq->DLround = 0;
} else {
@@ -364,7 +363,7 @@ void downlink_harq_process(NR_DL_UE_HARQ_t *dl_harq, int harq_pid, int ndi, int
dl_harq->status = ACTIVE;
dl_harq->DCINdi = ndi;
dl_harq->Ndi = dci_ndi;
//dl_harq->status = SCH_IDLE;
}
}
+32 -6
View File
@@ -121,9 +121,8 @@ void nr_fill_rx_indication(fapi_nr_rx_indication_t *rx_ind,
NR_UE_DLSCH_t *dlsch0,
NR_UE_DLSCH_t *dlsch1,
uint16_t n_pdus,
UE_nr_rxtx_proc_t *proc,
void * typeSpecific){
UE_nr_rxtx_proc_t *proc,
void *typeSpecific){
NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
@@ -176,6 +175,11 @@ void nr_fill_rx_indication(fapi_nr_rx_indication_t *rx_ind,
rx_ind->rx_indication_body[n_pdus - 1].ssb_pdu.ssb_start_subcarrier = frame_parms->ssb_start_subcarrier;
rx_ind->rx_indication_body[n_pdus - 1].ssb_pdu.rsrp_dBm = ue->measurements.rsrp_dBm[gNB_id];
break;
case FAPI_NR_CSIRS_IND:
memcpy(&rx_ind->rx_indication_body[n_pdus - 1].csirs_measurements,
(fapi_nr_csirs_measurements_t*)typeSpecific,
sizeof(*(fapi_nr_csirs_measurements_t*)typeSpecific));
break;
default:
break;
}
@@ -1321,8 +1325,7 @@ int is_ssb_in_slot(fapi_nr_config_request_t *config, int frame, int slot, NR_DL_
//uint8_t half_frame_index = fp->half_frame_bit;
//uint8_t i_ssb = fp->ssb_index;
uint8_t Lmax = fp->Lmax;
if (!(frame%(1<<(config->ssb_table.ssb_period-1)))){
if ((config->ssb_table.ssb_period > 0) && !(frame % (1 << (config->ssb_table.ssb_period - 1)))) {
if(Lmax <= 8) {
if(slot <=3 && (((config->ssb_table.ssb_mask_list[0].ssb_mask << 2*slot)&0x80000000) == 0x80000000 || ((config->ssb_table.ssb_mask_list[0].ssb_mask << (2*slot +1))&0x80000000) == 0x80000000))
@@ -1477,7 +1480,17 @@ int phy_procedures_nrUE_RX(PHY_VARS_NR_UE *ue,
if ((frame_rx%64 == 0) && (nr_slot_rx==0)) {
LOG_I(NR_PHY,"============================================\n");
LOG_I(NR_PHY,"Harq round stats for Downlink: %d/%d/%d/%d DLSCH errors: %d\n",ue->dl_stats[0],ue->dl_stats[1],ue->dl_stats[2],ue->dl_stats[3],ue->dl_stats[4]);
// fixed text + 8 HARQs rounds à 10 ("999999999/") + NULL
// if we use 999999999 HARQs, that should be sufficient for at least 138 hours
const size_t harq_output_len = 31 + 10 * 8 + 1;
char output[harq_output_len];
char *p = output;
const char *end = output + harq_output_len;
p += snprintf(p, end - p, "Harq round stats for Downlink: %d", ue->dl_stats[0]);
for (int round = 1; round < 16 && (round < 3 || ue->dl_stats[round] != 0); ++round)
p += snprintf(p, end - p,"/%d", ue->dl_stats[round]);
LOG_I(NR_PHY,"%s/0\n", output);
LOG_I(NR_PHY,"============================================\n");
}
@@ -1692,6 +1705,19 @@ int phy_procedures_nrUE_RX(PHY_VARS_NR_UE *ue,
// do procedures for CSI-IM
if ((ue->csiim_vars[gNB_id]) && (ue->csiim_vars[gNB_id]->active == 1)) {
int l_csiim[4] = {-1, -1, -1, -1};
for(int symb_idx = 0; symb_idx < 4; symb_idx++) {
bool nr_slot_fep_done = false;
for (int symb_idx2 = 0; symb_idx2 < symb_idx; symb_idx2++) {
if (l_csiim[symb_idx2] == ue->csiim_vars[gNB_id]->csiim_config_pdu.l_csiim[symb_idx]) {
nr_slot_fep_done = true;
}
}
l_csiim[symb_idx] = ue->csiim_vars[gNB_id]->csiim_config_pdu.l_csiim[symb_idx];
if(nr_slot_fep_done == false) {
nr_slot_fep(ue, proc, ue->csiim_vars[gNB_id]->csiim_config_pdu.l_csiim[symb_idx], nr_slot_rx);
}
}
nr_ue_csi_im_procedures(ue, proc, gNB_id);
ue->csiim_vars[gNB_id]->active = 0;
}
+10 -6
View File
@@ -512,12 +512,16 @@ int main(int argc, char **argv) {
int re;
int s,Kr,Kr_bytes;
LTE_DL_FRAME_PARMS *frame_parms;
double s_re0[30720*2],s_im0[30720*2],r_re0[30720*2],r_im0[30720*2];
double s_re1[30720*2],s_im1[30720*2],r_re1[30720*2],r_im1[30720*2];
double *s_re[2]= {s_re0,s_re1};
double *s_im[2]= {s_im0,s_im1};
double *r_re[2]= {r_re0,r_re1};
double *r_im[2]= {r_im0,r_im1};
double *tmpTX[4], *tmpRX[4] ;
for (int i = 0; i < 4; i++) {
tmpTX[i] = malloc(30720 * NB_ANTENNAS_TX * sizeof(*tmpTX));
tmpRX[i] = malloc(30720 * NB_ANTENNAS_RX * sizeof(*tmpRX));
}
double *s_re[NB_ANTENNAS_TX] = {tmpTX[0], tmpTX[1]};
double *s_im[NB_ANTENNAS_TX] = {tmpTX[2], tmpTX[3]};
double *r_re[NB_ANTENNAS_RX] = {tmpRX[0], tmpRX[1]};
double *r_im[NB_ANTENNAS_RX] = {tmpRX[2], tmpRX[3]};
uint8_t transmission_mode=1,n_tx_port=1,n_tx_phy=1,n_rx=2;
int eNB_id = 0;
unsigned char round;
+7 -7
View File
@@ -358,7 +358,7 @@ int main(int argc, char **argv) {
unsigned short input_buffer_length;
unsigned int ret;
unsigned int coded_bits_per_codeword,nsymb;
unsigned int tx_lev=0,tx_lev_dB=0,trials,errs[5]= {0,0,0,0,0},round_trials[4]= {0,0,0,0};
unsigned int tx_lev = 0, tx_lev_dB = 0, trials, errs[6] = {0}, round_trials[4] = {0};
FILE *bler_fd=NULL;
char bler_fname[512];
FILE *time_meas_fd=NULL;
@@ -387,7 +387,6 @@ int main(int argc, char **argv) {
double cpu_freq_GHz;
int iter_trials;
uint32_t UL_alloc_pdu;
int s,Kr,Kr_bytes;
int dump_perf=0;
static int dump_table =0;
double effective_rate=0.0;
@@ -1233,20 +1232,21 @@ int main(int argc, char **argv) {
if (n_frames==1) {
printf("ULSCH errors found o_ACK[0]= %d\n",eNB->ulsch[0]->harq_processes[harq_pid]->o_ACK[0]);
#ifdef DUMP_EACH_VALUE
int Kr_bytes;
for (s=0; s<eNB->ulsch[0]->harq_processes[harq_pid]->C; s++) {
if (s<eNB->ulsch[0]->harq_processes[harq_pid]->Cminus)
Kr = eNB->ulsch[0]->harq_processes[harq_pid]->Kminus;
Kr_bytes = eNB->ulsch[0]->harq_processes[harq_pid]->Kminus;
else
Kr = eNB->ulsch[0]->harq_processes[harq_pid]->Kplus;
Kr_bytes = Kr>>3;
Kr_bytes = eNB->ulsch[0]->harq_processes[harq_pid]->Kplus;
Kr_bytes = Kr_bytes >> 3;
printf("Decoded_output (Segment %d):\n",s);
for (i=0; i<Kr_bytes; i++)
printf("%d : %x (%x)\n",i,eNB->ulsch[0]->harq_processes[harq_pid]->c[s][i],
eNB->ulsch[0]->harq_processes[harq_pid]->c[s][i]^UE->ulsch[0]->harq_processes[harq_pid]->c[s][i]);
}
#endif
dump_ulsch(eNB,eNB->proc.frame_rx,subframe,0,round);
round=5;
+11 -11
View File
@@ -114,16 +114,16 @@ int main(int argc, char **argv)
//int run_initial_sync=0;
int loglvl = OAILOG_WARNING;
uint8_t dlsch_threads = 0;
float target_error_rate = 0.01;
uint64_t SSB_positions=0x01;
uint16_t nb_symb_sch = 12;
uint16_t nb_rb = 50;
uint8_t Imcs = 9;
uint8_t mcs_table = 0;
double DS_TDL = .03;
cpuf = get_cpu_freq_GHz();
char gNBthreads[128]="n";
int Tbslbrm = 950984;
float target_error_rate = 0.01;
uint64_t SSB_positions=0x01;
uint16_t nb_symb_sch = 12;
uint16_t nb_rb = 50;
uint8_t Imcs = 9;
uint8_t mcs_table = 0;
double DS_TDL = .03;
cpuf = get_cpu_freq_GHz();
char gNBthreads[128]="n";
int Tbslbrm = 950984;
if (load_configmodule(argc, argv, CONFIG_ENABLECMDLINEONLY) == 0) {
exit_fun("[NR_DLSCHSIM] Error, configuration module init failed\n");
@@ -299,7 +299,7 @@ int main(int argc, char **argv)
break;
case 'X':
strncpy(gNBthreads, optarg, sizeof(gNBthreads));
strncpy(gNBthreads, optarg, sizeof(gNBthreads)-1);
gNBthreads[sizeof(gNBthreads)-1]=0;
break;
+23 -16
View File
@@ -100,9 +100,17 @@ nfapi_ue_release_request_body_t release_rntis;
//Fixme: Uniq dirty DU instance, by global var, datamodel need better management
instance_t DUuniqInstance=0;
instance_t CUuniqInstance=0;
teid_t newGtpuCreateTunnel(instance_t instance, rnti_t rnti, int incoming_bearer_id, int outgoing_bearer_id, teid_t outgoing_teid,
transport_layer_addr_t remoteAddr, int port, gtpCallback callBack) {
return 0;
teid_t newGtpuCreateTunnel(instance_t instance,
rnti_t rnti,
int incoming_bearer_id,
int outgoing_bearer_id,
teid_t outgoing_teid,
int qfi,
transport_layer_addr_t remoteAddr,
int port,
gtpCallback callBack,
gtpCallbackSDAP callBackSDAP) {
return 0;
}
int newGtpuDeleteAllTunnels(instance_t instance, rnti_t rnti) {
@@ -272,10 +280,9 @@ void nr_dlsim_preprocessor(module_id_t module_id,
NR_UE_info_t *UE_info = RC.nrmac[module_id]->UE_info.list[0];
AssertFatal(RC.nrmac[module_id]->UE_info.list[1]==NULL, "can have only a single UE\n");
NR_UE_sched_ctrl_t *sched_ctrl = &UE_info->UE_sched_ctrl;
NR_UE_DL_BWP_t *current_BWP = &UE_info->current_DL_BWP;
NR_ServingCellConfigCommon_t *scc = RC.nrmac[0]->common_channels[0].ServingCellConfigCommon;
const int target_ss = NR_SearchSpace__searchSpaceType_PR_ue_Specific;
sched_ctrl->search_space = get_searchspace(NULL, scc, sched_ctrl->active_bwp ? sched_ctrl->active_bwp->bwp_Dedicated : NULL, target_ss);
uint8_t nr_of_candidates = 0;
if (g_mcsIndex < 4) {
find_aggregation_candidates(&sched_ctrl->aggregation_level,
@@ -287,7 +294,6 @@ void nr_dlsim_preprocessor(module_id_t module_id,
&nr_of_candidates,
sched_ctrl->search_space,4);
}
sched_ctrl->coreset = get_coreset(RC.nrmac[module_id], scc, sched_ctrl->active_bwp->bwp_Dedicated, sched_ctrl->search_space, target_ss);
uint32_t Y = get_Y(sched_ctrl->search_space, slot, UE_info->rnti);
int CCEIndex = find_pdcch_candidate(RC.nrmac[module_id],
/* CC_id = */ 0,
@@ -301,11 +307,8 @@ void nr_dlsim_preprocessor(module_id_t module_id,
NR_pdsch_semi_static_t *ps = &sched_ctrl->pdsch_semi_static;
nr_set_pdsch_semi_static(NULL,
nr_set_pdsch_semi_static(current_BWP,
scc,
UE_info->CellGroup,
sched_ctrl->active_bwp,
NULL,
/* tda = */ 0,
g_nrOfLayers,
sched_ctrl,
@@ -317,10 +320,10 @@ void nr_dlsim_preprocessor(module_id_t module_id,
sched_pdsch->mcs = g_mcsIndex;
/* the following might override the table that is mandated by RRC
* configuration */
ps->mcsTableIdx = g_mcsTableIdx;
current_BWP->mcsTableIdx = g_mcsTableIdx;
sched_pdsch->Qm = nr_get_Qm_dl(sched_pdsch->mcs, ps->mcsTableIdx);
sched_pdsch->R = nr_get_code_rate_dl(sched_pdsch->mcs, ps->mcsTableIdx);
sched_pdsch->Qm = nr_get_Qm_dl(sched_pdsch->mcs, current_BWP->mcsTableIdx);
sched_pdsch->R = nr_get_code_rate_dl(sched_pdsch->mcs, current_BWP->mcsTableIdx);
sched_pdsch->tb_size = nr_compute_tbs(sched_pdsch->Qm,
sched_pdsch->R,
sched_pdsch->rbSize,
@@ -348,7 +351,7 @@ void nr_dlsim_preprocessor(module_id_t module_id,
AssertFatal(sched_pdsch->rbStart >= 0, "invalid rbStart %d\n", sched_pdsch->rbStart);
AssertFatal(sched_pdsch->rbSize > 0, "invalid rbSize %d\n", sched_pdsch->rbSize);
AssertFatal(sched_pdsch->mcs >= 0, "invalid mcs %d\n", sched_pdsch->mcs);
AssertFatal(ps->mcsTableIdx >= 0 && ps->mcsTableIdx <= 2, "invalid mcsTableIdx %d\n", ps->mcsTableIdx);
AssertFatal(current_BWP->mcsTableIdx >= 0 && current_BWP->mcsTableIdx <= 2, "invalid mcsTableIdx %d\n", current_BWP->mcsTableIdx);
}
typedef struct {
@@ -670,7 +673,7 @@ int main(int argc, char **argv)
break;
case 'X':
strncpy(gNBthreads, optarg, sizeof(gNBthreads));
strncpy(gNBthreads, optarg, sizeof(gNBthreads)-1);
gNBthreads[sizeof(gNBthreads)-1]=0;
break;
@@ -761,6 +764,8 @@ int main(int argc, char **argv)
gNB_RRC_INST rrc;
memset((void*)&rrc,0,sizeof(rrc));
gNB_mac->dl_bler.harq_round_max = num_rounds;
/*
// read in SCGroupConfig
AssertFatal(scg_fd != NULL,"no reconfig.raw file\n");
@@ -866,6 +871,8 @@ int main(int argc, char **argv)
N_RB_DL = gNB->frame_parms.N_RB_DL;
NR_UE_info_t *UE_info = RC.nrmac[0]->UE_info.list[0];
configure_UE_BWP(RC.nrmac[0], scc, &UE_info->UE_sched_ctrl, NULL, UE_info);
// stub to configure frame_parms
// nr_phy_config_request_sim(gNB,N_RB_DL,N_RB_DL,mu,Nid_cell,SSB_positions);
// call MAC to configure common parameters
@@ -1142,7 +1149,7 @@ int main(int argc, char **argv)
Sched_INFO.frame = frame;
Sched_INFO.slot = slot;
Sched_INFO.DL_req = &gNB_mac->DL_req[0];
Sched_INFO.UL_tti_req = gNB_mac->UL_tti_req_ahead[slot];
Sched_INFO.UL_tti_req = gNB_mac->UL_tti_req_ahead[0];
Sched_INFO.UL_dci_req = NULL;
Sched_INFO.TX_req = &gNB_mac->TX_req[0];
pushNotifiedFIFO(gNB->L1_tx_free,msgL1Tx);
@@ -40,4 +40,4 @@ void nr_fill_rx_indication(fapi_nr_rx_indication_t *rx_ind,
NR_UE_DLSCH_t *dlsch1,
uint16_t n_pdus,
UE_nr_rxtx_proc_t *proc,
void * typeSpecific ) {}
void *typeSpecific ) {}
+11 -3
View File
@@ -92,9 +92,17 @@ int oai_nfapi_nr_rach_indication(nfapi_nr_rach_indication_t *ind) { return(0);
//Fixme: Uniq dirty DU instance, by global var, datamodel need better management
instance_t DUuniqInstance=0;
instance_t CUuniqInstance=0;
teid_t newGtpuCreateTunnel(instance_t instance, rnti_t rnti, int incoming_bearer_id, int outgoing_bearer_id, teid_t outgoing_teid,
transport_layer_addr_t remoteAddr, int port, gtpCallback callBack) {
return 0;
teid_t newGtpuCreateTunnel(instance_t instance,
rnti_t rnti,
int incoming_bearer_id,
int outgoing_bearer_id,
teid_t outgoing_teid,
int qfi,
transport_layer_addr_t remoteAddr,
int port,
gtpCallback callBack,
gtpCallbackSDAP callBackSDAP) {
return 0;
}
int newGtpuDeleteAllTunnels(instance_t instance, rnti_t rnti) {
+1 -1
View File
@@ -705,7 +705,7 @@ int main(int argc, char **argv)
pucch_pdu.second_hop_prb = N_RB_DL-1;
}
else pucch_pdu.freq_hop_flag = 0;
nr_decode_pucch2(gNB,nr_slot_tx,&uci_pdu,&pucch_pdu);
nr_decode_pucch2(gNB,nr_frame_tx,nr_slot_tx,&uci_pdu,&pucch_pdu);
int csi_part1_bytes=pucch_pdu.bit_len_csi_part1>>3;
if ((pucch_pdu.bit_len_csi_part1&7) > 0) csi_part1_bytes++;
for (int i=0;i<csi_part1_bytes;i++) {
+11 -3
View File
@@ -95,9 +95,17 @@ nfapi_ue_release_request_body_t release_rntis;
//Fixme: Uniq dirty DU instance, by global var, datamodel need better management
instance_t DUuniqInstance=0;
instance_t CUuniqInstance=0;
teid_t newGtpuCreateTunnel(instance_t instance, rnti_t rnti, int incoming_bearer_id, int outgoing_bearer_id, teid_t outgoing_teid,
transport_layer_addr_t remoteAddr, int port, gtpCallback callBack) {
return 0;
teid_t newGtpuCreateTunnel(instance_t instance,
rnti_t rnti,
int incoming_bearer_id,
int outgoing_bearer_id,
teid_t outgoing_teid,
int qfi,
transport_layer_addr_t remoteAddr,
int port,
gtpCallback callBack,
gtpCallbackSDAP callBackSDAP) {
return 0;
}
int newGtpuDeleteAllTunnels(instance_t instance, rnti_t rnti) {
+1
View File
@@ -181,6 +181,7 @@ typedef struct gtpv1u_gnb_create_tunnel_req_s {
int num_tunnels;
//teid_t upf_NGu_teid[NR_GTPV1U_MAX_BEARERS_PER_UE]; ///< Tunnel Endpoint Identifier
teid_t outgoing_teid[NR_GTPV1U_MAX_BEARERS_PER_UE];
int outgoing_qfi[NR_GTPV1U_MAX_BEARERS_PER_UE];
pdusessionid_t pdusession_id[NR_GTPV1U_MAX_BEARERS_PER_UE];
ebi_t incoming_rb_id[NR_GTPV1U_MAX_BEARERS_PER_UE];
//ebi_t outgoing_rb_id[NR_GTPV1U_MAX_BEARERS_PER_UE];
+20 -18
View File
@@ -515,15 +515,16 @@ int CU_send_UE_CONTEXT_SETUP_REQUEST(instance_t instance,
int sz=sizeof(f1ap_ue_context_setup_req->drbs_to_be_setup[i].up_dl_tnl[0].tl_address);
memcpy(addr.buffer,&f1ap_ue_context_setup_req->drbs_to_be_setup[i].up_dl_tnl[0].tl_address, sz);
addr.length = sz*8;
f1ap_ue_context_setup_req->drbs_to_be_setup[i].up_ul_tnl[j].teid=
newGtpuCreateTunnel(getCxt(CUtype, instance)->gtpInst,
f1ap_ue_context_setup_req->rnti,
f1ap_ue_context_setup_req->drbs_to_be_setup[i].drb_id,
f1ap_ue_context_setup_req->drbs_to_be_setup[i].drb_id,
0xFFFF, // We will set the right value from DU answer
addr,
f1ap_ue_context_setup_req->drbs_to_be_setup[i].up_dl_tnl[0].port,
cu_f1u_data_req);
f1ap_ue_context_setup_req->drbs_to_be_setup[i].up_ul_tnl[j].teid = newGtpuCreateTunnel(getCxt(CUtype, instance)->gtpInst,
f1ap_ue_context_setup_req->rnti,
f1ap_ue_context_setup_req->drbs_to_be_setup[i].drb_id,
f1ap_ue_context_setup_req->drbs_to_be_setup[i].drb_id,
0xFFFF, // We will set the right value from DU answer
-1, // no qfi
addr,
f1ap_ue_context_setup_req->drbs_to_be_setup[i].up_dl_tnl[0].port,
cu_f1u_data_req,
NULL);
/* 12.3.1 ULTunnels_ToBeSetup_Item */
asn1cSequenceAdd(drbs_toBeSetup_item->uLUPTNLInformation_ToBeSetup_List.list,
F1AP_ULUPTNLInformation_ToBeSetup_Item_t, uLUPTNLInformation_ToBeSetup_Item);
@@ -1491,15 +1492,16 @@ int CU_send_UE_CONTEXT_MODIFICATION_REQUEST(instance_t instance, f1ap_ue_context
memcpy(addr.buffer,&f1ap_ue_context_modification_req->drbs_to_be_setup[i].up_dl_tnl[0].tl_address, sz);
addr.length = sz*8;
f1ap_ue_context_modification_req->drbs_to_be_setup[i].up_ul_tnl[j].teid=
newGtpuCreateTunnel(getCxt(CUtype, instance)->gtpInst,
f1ap_ue_context_modification_req->rnti,
f1ap_ue_context_modification_req->drbs_to_be_setup[i].drb_id,
f1ap_ue_context_modification_req->drbs_to_be_setup[i].drb_id,
0xFFFF, // We will set the right value from DU answer
addr,
f1ap_ue_context_modification_req->drbs_to_be_setup[i].up_dl_tnl[0].port,
cu_f1u_data_req);
f1ap_ue_context_modification_req->drbs_to_be_setup[i].up_ul_tnl[j].teid = newGtpuCreateTunnel(getCxt(CUtype, instance)->gtpInst,
f1ap_ue_context_modification_req->rnti,
f1ap_ue_context_modification_req->drbs_to_be_setup[i].drb_id,
f1ap_ue_context_modification_req->drbs_to_be_setup[i].drb_id,
0xFFFF, // We will set the right value from DU answer
-1, // no qfi
addr,
f1ap_ue_context_modification_req->drbs_to_be_setup[i].up_dl_tnl[0].port,
cu_f1u_data_req,
NULL);
/* 12.3.1 ULTunnels_ToBeSetup_Item */
asn1cSequenceAdd(drbs_toBeSetupMod_item->uLUPTNLInformation_ToBeSetup_List.list,
F1AP_ULUPTNLInformation_ToBeSetup_Item_t, uLUPTNLInformation_ToBeSetup_Item);
+20 -16
View File
@@ -187,14 +187,16 @@ int DU_handle_UE_CONTEXT_SETUP_REQUEST(instance_t instance,
transport_layer_addr_t addr;
memcpy(addr.buffer, &drb_p->up_ul_tnl[0].tl_address, sizeof(drb_p->up_ul_tnl[0].tl_address));
addr.length=sizeof(drb_p->up_ul_tnl[0].tl_address)*8;
drb_p->up_dl_tnl[0].teid=newGtpuCreateTunnel(INSTANCE_DEFAULT,
f1ap_ue_context_setup_req->rnti,
drb_p->drb_id,
drb_p->drb_id,
drb_p->up_ul_tnl[0].teid,
addr,
drb_p->up_ul_tnl[0].port,
lteDURecvCb);
drb_p->up_dl_tnl[0].teid = newGtpuCreateTunnel(INSTANCE_DEFAULT,
f1ap_ue_context_setup_req->rnti,
drb_p->drb_id,
drb_p->drb_id,
drb_p->up_ul_tnl[0].teid,
-1, // no qfi
addr,
drb_p->up_ul_tnl[0].port,
lteDURecvCb,
NULL);
drb_p->up_dl_tnl_length++;
}
}
@@ -1171,14 +1173,16 @@ int DU_handle_UE_CONTEXT_MODIFICATION_REQUEST(instance_t instance,
transport_layer_addr_t addr;
memcpy(addr.buffer, &drb_p->up_ul_tnl[0].tl_address, sizeof(drb_p->up_ul_tnl[0].tl_address));
addr.length=sizeof(drb_p->up_ul_tnl[0].tl_address)*8;
drb_p->up_dl_tnl[0].teid=newGtpuCreateTunnel(INSTANCE_DEFAULT,
f1ap_ue_context_modification_req->rnti,
drb_p->drb_id,
drb_p->drb_id,
drb_p->up_ul_tnl[0].teid,
addr,
drb_p->up_ul_tnl[0].port,
lteDURecvCb);
drb_p->up_dl_tnl[0].teid = newGtpuCreateTunnel(INSTANCE_DEFAULT,
f1ap_ue_context_modification_req->rnti,
drb_p->drb_id,
drb_p->drb_id,
drb_p->up_ul_tnl[0].teid,
-1, // no qfi
addr,
drb_p->up_ul_tnl[0].port,
lteDURecvCb,
NULL);
drb_p->up_dl_tnl_length++;
}
}
+46 -7
View File
@@ -67,7 +67,8 @@
#define CONFIG_STRING_MACRLC_UL_BLER_TARGET_UPPER "ul_bler_target_upper"
#define CONFIG_STRING_MACRLC_UL_BLER_TARGET_LOWER "ul_bler_target_lower"
#define CONFIG_STRING_MACRLC_UL_MAX_MCS "ul_max_mcs"
#define CONFIG_STRING_MACRLC_HARQ_ROUND_MAX "harq_round_max"
#define CONFIG_STRING_MACRLC_DL_HARQ_ROUND_MAX "dl_harq_round_max"
#define CONFIG_STRING_MACRLC_UL_HARQ_ROUND_MAX "ul_harq_round_max"
#define CONFIG_STRING_MACRLC_MIN_GRANT_PRB "min_grant_prb"
#define CONFIG_STRING_MACRLC_MIN_GRANT_MCS "min_grant_mcs"
@@ -97,7 +98,7 @@
{CONFIG_STRING_MACRLC_ULSCH_MAX_FRAME_INACTIVITY, NULL, 0, uptr:NULL, defintval:10, TYPE_UINT, 0}, \
{CONFIG_STRING_MACRLC_PUSCHTARGETSNRX10, NULL, 0, iptr:NULL, defintval:200, TYPE_INT, 0}, \
{CONFIG_STRING_MACRLC_PUCCHTARGETSNRX10, NULL, 0, iptr:NULL, defintval:150, TYPE_INT, 0}, \
{CONFIG_STRING_MACRLC_UL_PRBBLACK_SNR_THRESHOLD, "SNR threshold to decide whether a PRB will be blacklisted or not", 0, iptr:NULL, defintval:10, TYPE_INT, 0}, \
{CONFIG_STRING_MACRLC_UL_PRBBLACK_SNR_THRESHOLD, "SNR threshold to decide whether a PRB will be blacklisted or not", 0, iptr:NULL, defintval:10, TYPE_INT, 0}, \
{CONFIG_STRING_MACRLC_PUCCHFAILURETHRES, NULL, 0, iptr:NULL, defintval:10, TYPE_INT, 0}, \
{CONFIG_STRING_MACRLC_PUSCHFAILURETHRES, NULL, 0, iptr:NULL, defintval:10, TYPE_INT, 0}, \
{CONFIG_STRING_MACRLC_DL_BLER_TARGET_UPPER, "Upper threshold of BLER to decrease DL MCS", 0, dblptr:NULL, defdblval:0.15, TYPE_DOUBLE, 0}, \
@@ -106,9 +107,10 @@
{CONFIG_STRING_MACRLC_UL_BLER_TARGET_UPPER, "Upper threshold of BLER to decrease UL MCS", 0, dblptr:NULL, defdblval:0.15, TYPE_DOUBLE, 0}, \
{CONFIG_STRING_MACRLC_UL_BLER_TARGET_LOWER, "Lower threshold of BLER to increase UL MCS", 0, dblptr:NULL, defdblval:0.05, TYPE_DOUBLE, 0}, \
{CONFIG_STRING_MACRLC_UL_MAX_MCS, "Maximum UL MCS that should be used", 0, u8ptr:NULL, defintval:9, TYPE_UINT8, 0}, \
{CONFIG_STRING_MACRLC_HARQ_ROUND_MAX, "Maximum number of HARQ rounds", 0, u8ptr:NULL, defintval:4, TYPE_UINT8, 0}, \
{CONFIG_STRING_MACRLC_DL_HARQ_ROUND_MAX, "Maximum number of DL HARQ rounds", 0, u8ptr:NULL, defintval:4, TYPE_UINT8, 0}, \
{CONFIG_STRING_MACRLC_UL_HARQ_ROUND_MAX, "Maximum number of UL HARQ rounds", 0, u8ptr:NULL, defintval:4, TYPE_UINT8, 0}, \
{CONFIG_STRING_MACRLC_MIN_GRANT_PRB, "Minimal Periodic ULSCH Grant PRBs", 0, u8ptr:NULL, defintval:5, TYPE_UINT8, 0}, \
{CONFIG_STRING_MACRLC_MIN_GRANT_MCS, "Minimal Periodic ULSCH Grant MCS", 0, u8ptr:NULL, defintval:9, TYPE_UINT8, 0} \
{CONFIG_STRING_MACRLC_MIN_GRANT_MCS, "Minimal Periodic ULSCH Grant MCS", 0, u8ptr:NULL, defintval:9, TYPE_UINT8, 0}, \
}
#define MACRLC_CC_IDX 0
#define MACRLC_TRANSPORT_N_PREFERENCE_IDX 1
@@ -139,9 +141,46 @@
#define MACRLC_UL_BLER_TARGET_UPPER_IDX 26
#define MACRLC_UL_BLER_TARGET_LOWER_IDX 27
#define MACRLC_UL_MAX_MCS_IDX 28
#define MACRLC_HARQ_ROUND_MAX_IDX 29
#define MACRLC_MIN_GRANT_PRB_IDX 30
#define MACRLC_MIN_GRANT_MCS_IDX 31
#define MACRLC_DL_HARQ_ROUND_MAX_IDX 29
#define MACRLC_UL_HARQ_ROUND_MAX_IDX 30
#define MACRLC_MIN_GRANT_PRB_IDX 31
#define MACRLC_MIN_GRANT_MCS_IDX 32
#define MACRLCPARAMS_CHECK { \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
{ .s2 = { config_check_intrange, {1, 8} } }, /* DL max HARQ rounds */ \
{ .s2 = { config_check_intrange, {1, 8} } }, /* UL max HARQ rounds */ \
{ .s5 = { NULL } }, \
{ .s5 = { NULL } }, \
}
/*---------------------------------------------------------------------------------------------------------------------------------------------------------*/
#endif
+6 -1
View File
@@ -816,6 +816,10 @@ void RCconfig_nr_macrlc() {
}
paramdef_t MacRLC_Params[] = MACRLCPARAMS_DESC;
paramlist_def_t MacRLC_ParamList = {CONFIG_STRING_MACRLC_LIST,NULL,0};
/* map parameter checking array instances to parameter definition array instances */
checkedparam_t config_check_MacRLCParams [] = MACRLCPARAMS_CHECK;
for (int i = 0; i < sizeof(MacRLC_Params) / sizeof(paramdef_t); ++i)
MacRLC_Params[i].chkPptr = &(config_check_MacRLCParams[i]);
config_getlist( &MacRLC_ParamList,MacRLC_Params,sizeof(MacRLC_Params)/sizeof(paramdef_t), NULL);
if ( MacRLC_ParamList.numelt > 0) {
@@ -887,11 +891,12 @@ void RCconfig_nr_macrlc() {
dl_bler_options->upper = *(MacRLC_ParamList.paramarray[j][MACRLC_DL_BLER_TARGET_UPPER_IDX].dblptr);
dl_bler_options->lower = *(MacRLC_ParamList.paramarray[j][MACRLC_DL_BLER_TARGET_LOWER_IDX].dblptr);
dl_bler_options->max_mcs = *(MacRLC_ParamList.paramarray[j][MACRLC_DL_MAX_MCS_IDX].u8ptr);
dl_bler_options->harq_round_max = *(MacRLC_ParamList.paramarray[j][MACRLC_DL_HARQ_ROUND_MAX_IDX].u8ptr);
NR_bler_options_t *ul_bler_options = &RC.nrmac[j]->ul_bler;
ul_bler_options->upper = *(MacRLC_ParamList.paramarray[j][MACRLC_UL_BLER_TARGET_UPPER_IDX].dblptr);
ul_bler_options->lower = *(MacRLC_ParamList.paramarray[j][MACRLC_UL_BLER_TARGET_LOWER_IDX].dblptr);
ul_bler_options->max_mcs = *(MacRLC_ParamList.paramarray[j][MACRLC_UL_MAX_MCS_IDX].u8ptr);
RC.nrmac[j]->harq_round_max = *(MacRLC_ParamList.paramarray[j][MACRLC_HARQ_ROUND_MAX_IDX].u8ptr);
ul_bler_options->harq_round_max = *(MacRLC_ParamList.paramarray[j][MACRLC_UL_HARQ_ROUND_MAX_IDX].u8ptr);
RC.nrmac[j]->min_grant_prb = *(MacRLC_ParamList.paramarray[j][MACRLC_MIN_GRANT_PRB_IDX].u8ptr);
RC.nrmac[j]->min_grant_mcs = *(MacRLC_ParamList.paramarray[j][MACRLC_MIN_GRANT_MCS_IDX].u8ptr);
RC.nrmac[j]->num_ulprbbl = num_prbbl;
+2 -2
View File
@@ -158,9 +158,9 @@ typedef enum {
{GNB_CONFIG_STRING_NRCELLID, NULL, 0, u64ptr:NULL, defint64val:1, TYPE_UINT64, 0}, \
{GNB_CONFIG_STRING_MINRXTXTIME, NULL, 0, iptr:NULL, defintval:2, TYPE_INT, 0}, \
{GNB_CONFIG_STRING_ULPRBBLACKLIST, NULL, 0, strptr:NULL, defstrval:"", TYPE_STRING, 0}, \
{GNB_CONFIG_STRING_UMONDEFAULTDRB, NULL, 0, uptr:NULL, defuintval:0, TYPE_UINT, 0}, \
{GNB_CONFIG_STRING_UMONDEFAULTDRB, NULL, 0, uptr:NULL, defuintval:0, TYPE_UINT, 0}, \
{GNB_CONFIG_STRING_FORCE256QAMOFF, GNB_CONFIG_HLP_FORCE256QAMOFF, PARAMFLAG_BOOL, iptr:NULL, defintval:0, TYPE_INT, 0}, \
{GNB_CONFIG_STRING_ENABLE_SDAP, GNB_CONFIG_HLP_STRING_ENABLE_SDAP, PARAMFLAG_BOOL, iptr:NULL, defintval:0, TYPE_INT, 0} \
{GNB_CONFIG_STRING_ENABLE_SDAP, GNB_CONFIG_HLP_STRING_ENABLE_SDAP, PARAMFLAG_BOOL, iptr:NULL, defintval:0, TYPE_INT, 0}, \
}
#define GNB_GNB_ID_IDX 0
@@ -2366,22 +2366,6 @@ rrc_mac_remove_ue(module_id_t mod_idP,
return 0;
}
//------------------------------------------------------------------------------
/*
* Returns the previous UE_id in the scheduling list in UL or DL
*/
inline int prev(UE_list_t *listP, int nodeP) {
if (nodeP == listP->head)
return -1; /* there is no previous of the head */
for (int j = listP->head; j >= 0; j = listP->next[j])
if (listP->next[j] == nodeP)
return j;
LOG_E(MAC, "%s(): could not find previous to %d in UE_list\n", __func__, nodeP);
dump_ue_list(listP);
return -1;
}
// This has to be updated to include BSR information
//------------------------------------------------------------------------------
+1 -11
View File
@@ -329,17 +329,7 @@ rx_sdu(const module_id_t enb_mod_idP,
if (ra->msg3_round >= mac->common_channels[CC_idP].radioResourceConfigCommon->rach_ConfigCommon.maxHARQ_Msg3Tx - 1) {
// Release RNTI of LTE PHY when RA does not succeed
UE_free_list_t *free_list = NULL;
pthread_mutex_lock(&lock_ue_freelist);
free_list = &mac->UE_free_list;
free_list->UE_free_ctrl[free_list->tail_freelist].rnti = current_rnti;
free_list->UE_free_ctrl[free_list->tail_freelist].removeContextFlg = 1;
free_list->UE_free_ctrl[free_list->tail_freelist].raFlag = 1;
free_list->num_UEs++;
mac->UE_release_req.ue_release_request_body.ue_release_request_TLVs_list[mac->UE_release_req.ue_release_request_body.number_of_TLVs].rnti = current_rnti;
mac->UE_release_req.ue_release_request_body.number_of_TLVs++;
free_list->tail_freelist = (free_list->tail_freelist + 1) % (NUMBER_OF_UE_MAX+1);
pthread_mutex_unlock(&lock_ue_freelist);
put_UE_in_freelist(enb_mod_idP, current_rnti, true);
cancel_ra_proc(enb_mod_idP, CC_idP, frameP, current_rnti);
nfapi_hi_dci0_request_t *hi_dci0_req = NULL;
+1 -9
View File
@@ -1195,14 +1195,6 @@ typedef struct {
///remove RA flag
bool raFlag;
} UE_free_ctrl_t;
/*! \brief REMOVE UE list used by eNB to order UEs/CC for deleting*/
typedef struct {
/// deleting control info
UE_free_ctrl_t UE_free_ctrl[NUMBER_OF_UE_MAX+1];
int num_UEs;
int head_freelist; ///the head position of the delete list
int tail_freelist; ///the tail position of the delete list
} UE_free_list_t;
/**
* describes contiguous RBs
@@ -1443,7 +1435,7 @@ typedef struct eNB_MAC_INST_s {
/// processing time of eNB PCH scheduler
time_stats_t schedule_pch;
UE_free_list_t UE_free_list;
UE_free_ctrl_t UE_free_ctrl[NUMBER_OF_UE_MAX+1];
/// for scheduling selection
SCHEDULER_MODES scheduler_mode;
/// Default scheduler: Pre-processor implementation. Algorithms for UL/DL
+34
View File
@@ -39,6 +39,7 @@
#include <stdbool.h>
#include "NR_SubcarrierSpacing.h"
#include "NR_CSI-ReportConfig.h"
#include "openair1/SCHED_NR_UE/harq_nr.h"
#define NR_SHORT_BSR_TABLE_SIZE 32
@@ -63,6 +64,7 @@
#define CCCH_PAYLOAD_SIZE_MAX 512
#define RAR_PAYLOAD_SIZE_MAX 128
#define MAX_BWP_SIZE 275
#define MAX_CSI_REPORTCONFIG 48
typedef enum frequency_range_e {
FR1 = 0,
@@ -512,5 +514,37 @@ typedef struct Type0_PDCCH_CSS_config_s {
bool active;
} NR_Type0_PDCCH_CSS_config_t;
typedef struct {
uint8_t nb_ssbri_cri;
uint8_t cri_ssbri_bitlen;
uint8_t rsrp_bitlen;
uint8_t diff_rsrp_bitlen;
} L1_RSRP_bitlen_t;
typedef struct{
uint8_t ri_restriction;
uint8_t cri_bitlen;
uint8_t ri_bitlen;
uint8_t li_bitlen[8];
uint8_t pmi_x1_bitlen[8];
uint8_t pmi_x2_bitlen[8];
uint8_t cqi_bitlen[8];
} CSI_Meas_bitlen_t;
typedef struct nr_csi_report {
NR_CSI_ReportConfig__reportQuantity_PR reportQuantity_type;
long periodicity;
uint16_t offset;
long ** SSB_Index_list;
long ** CSI_Index_list;
// uint8_t nb_of_nzp_csi_report;
uint8_t nb_of_csi_ssb_report;
L1_RSRP_bitlen_t CSI_report_bitlen;
CSI_Meas_bitlen_t csi_meas_bitlen;
int codebook_mode;
int N1;
int N2;
} nr_csi_report_t;
#endif /*__LAYER2_MAC_H__ */
+530 -12
View File
@@ -4128,22 +4128,22 @@ uint16_t compute_pucch_prb_size(uint8_t format,
}
}
int get_bw_tbslbrm(NR_BWP_t *genericParameters,
int get_bw_tbslbrm(int scc_bwpsize,
NR_CellGroupConfig_t *cg) {
int bw = 0;
if (cg && cg->spCellConfig && cg->spCellConfig->spCellConfigDedicated &&
cg->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList) {
struct NR_ServingCellConfig__downlinkBWP_ToAddModList *BWP_list = cg->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList;
for (int i=0; i<BWP_list->list.count; i++) {
genericParameters = &BWP_list->list.array[i]->bwp_Common->genericParameters;
int curr_bw = NRRIV2BW(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
if (curr_bw > bw)
bw = curr_bw;
int bw = scc_bwpsize;
if (cg && cg->spCellConfig && cg->spCellConfig->spCellConfigDedicated) {
const NR_ServingCellConfig_t *servingCellConfig = cg->spCellConfig->spCellConfigDedicated;
if(servingCellConfig->downlinkBWP_ToAddModList) {
struct NR_ServingCellConfig__downlinkBWP_ToAddModList *BWP_list = servingCellConfig->downlinkBWP_ToAddModList;
for (int i=0; i<BWP_list->list.count; i++) {
NR_BWP_t genericParameters = BWP_list->list.array[i]->bwp_Common->genericParameters;
int curr_bw = NRRIV2BW(genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
if (curr_bw > bw)
bw = curr_bw;
}
}
}
else
bw = NRRIV2BW(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
return bw;
}
@@ -4221,3 +4221,521 @@ bool set_ul_ptrs_values(NR_PTRS_UplinkConfig_t *ul_ptrs_config,
}
return valid;
}
//! Calculating number of bits set
uint8_t number_of_bits_set(uint8_t buf) {
uint8_t nb_of_bits_set = 0;
uint8_t mask = 0xff;
uint8_t index = 0;
for (index=7; (buf & mask) && (index>=0) ; index--){
if (buf & (1<<index))
nb_of_bits_set++;
mask>>=1;
}
return nb_of_bits_set;
}
void compute_rsrp_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
uint8_t nb_resources,
nr_csi_report_t *csi_report) {
if (NR_CSI_ReportConfig__groupBasedBeamReporting_PR_disabled == csi_reportconfig->groupBasedBeamReporting.present) {
if (NULL != csi_reportconfig->groupBasedBeamReporting.choice.disabled->nrofReportedRS)
csi_report->CSI_report_bitlen.nb_ssbri_cri = *(csi_reportconfig->groupBasedBeamReporting.choice.disabled->nrofReportedRS)+1;
else
/*! From Spec 38.331
* nrofReportedRS
* The number (N) of measured RS resources to be reported per report setting in a non-group-based report. N <= N_max, where N_max is either 2 or 4 depending on UE
* capability. FFS: The signaling mechanism for the gNB to select a subset of N beams for the UE to measure and report.
* When the field is absent the UE applies the value 1
*/
csi_report->CSI_report_bitlen.nb_ssbri_cri= 1;
} else
csi_report->CSI_report_bitlen.nb_ssbri_cri= 2;
if (nb_resources) {
csi_report->CSI_report_bitlen.cri_ssbri_bitlen =ceil(log2 (nb_resources));
csi_report->CSI_report_bitlen.rsrp_bitlen = 7; //From spec 38.212 Table 6.3.1.1.2-6: CRI, SSBRI, and RSRP
csi_report->CSI_report_bitlen.diff_rsrp_bitlen =4; //From spec 38.212 Table 6.3.1.1.2-6: CRI, SSBRI, and RSRP
} else {
csi_report->CSI_report_bitlen.cri_ssbri_bitlen =0;
csi_report->CSI_report_bitlen.rsrp_bitlen = 0;
csi_report->CSI_report_bitlen.diff_rsrp_bitlen =0;
}
}
uint8_t compute_ri_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
nr_csi_report_t *csi_report) {
struct NR_CodebookConfig *codebookConfig = csi_reportconfig->codebookConfig;
uint8_t nb_allowed_ri, ri_bitlen;
uint8_t ri_restriction = 0;
if (codebookConfig == NULL) {
csi_report->csi_meas_bitlen.ri_bitlen=0;
return ri_restriction;
}
// codebook type1 single panel
if (NR_CodebookConfig__codebookType__type1__subType_PR_typeI_SinglePanel==codebookConfig->codebookType.choice.type1->subType.present){
struct NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel *type1single = codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel;
if (type1single->nrOfAntennaPorts.present == NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts_PR_two){
ri_restriction = csi_reportconfig->codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel->typeI_SinglePanel_ri_Restriction.buf[0];
nb_allowed_ri = number_of_bits_set(ri_restriction);
ri_bitlen = ceil(log2(nb_allowed_ri));
ri_bitlen = ri_bitlen<1?ri_bitlen:1; //from the spec 38.212 and table 6.3.1.1.2-3: RI, LI, CQI, and CRI of codebookType=typeI-SinglePanel
csi_report->csi_meas_bitlen.ri_bitlen=ri_bitlen;
}
if (type1single->nrOfAntennaPorts.present == NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts_PR_moreThanTwo){
if (type1single->nrOfAntennaPorts.choice.moreThanTwo->n1_n2.present ==
NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_two_one_TypeI_SinglePanel_Restriction) {
// 4 ports
ri_restriction = csi_reportconfig->codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel->typeI_SinglePanel_ri_Restriction.buf[0];
nb_allowed_ri = number_of_bits_set(ri_restriction);
ri_bitlen = ceil(log2(nb_allowed_ri));
ri_bitlen = ri_bitlen<2?ri_bitlen:2; //from the spec 38.212 and table 6.3.1.1.2-3: RI, LI, CQI, and CRI of codebookType=typeI-SinglePanel
csi_report->csi_meas_bitlen.ri_bitlen=ri_bitlen;
}
else {
// more than 4 ports
ri_restriction = csi_reportconfig->codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel->typeI_SinglePanel_ri_Restriction.buf[0];
nb_allowed_ri = number_of_bits_set(ri_restriction);
ri_bitlen = ceil(log2(nb_allowed_ri));
csi_report->csi_meas_bitlen.ri_bitlen=ri_bitlen;
}
}
return ri_restriction;
}
else
AssertFatal(1==0,"Other configurations not yet implemented\n");
return -1;
}
void compute_li_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
uint8_t ri_restriction,
nr_csi_report_t *csi_report) {
struct NR_CodebookConfig *codebookConfig = csi_reportconfig->codebookConfig;
for(int i=0; i<8; i++) {
if (codebookConfig == NULL || ((ri_restriction>>i)&0x01) == 0)
csi_report->csi_meas_bitlen.li_bitlen[i]=0;
else {
// codebook type1 single panel
if (NR_CodebookConfig__codebookType__type1__subType_PR_typeI_SinglePanel==codebookConfig->codebookType.choice.type1->subType.present)
csi_report->csi_meas_bitlen.li_bitlen[i]=ceil(log2(i+1))<2?ceil(log2(i+1)):2;
else
AssertFatal(1==0,"Other configurations not yet implemented\n");
}
}
}
void get_n1n2_o1o2_singlepanel(int *n1, int *n2, int *o1, int *o2,
struct NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo *morethantwo) {
// Table 5.2.2.2.1-2 in 38.214 for supported configurations
switch(morethantwo->n1_n2.present){
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_two_one_TypeI_SinglePanel_Restriction):
*n1 = 2;
*n2 = 1;
*o1 = 4;
*o2 = 1;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_two_two_TypeI_SinglePanel_Restriction):
*n1 = 2;
*n2 = 2;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_four_one_TypeI_SinglePanel_Restriction):
*n1 = 4;
*n2 = 1;
*o1 = 4;
*o2 = 1;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_three_two_TypeI_SinglePanel_Restriction):
*n1 = 3;
*n2 = 2;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_six_one_TypeI_SinglePanel_Restriction):
*n1 = 6;
*n2 = 1;
*o1 = 4;
*o2 = 1;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_four_two_TypeI_SinglePanel_Restriction):
*n1 = 4;
*n2 = 2;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_eight_one_TypeI_SinglePanel_Restriction):
*n1 = 8;
*n2 = 1;
*o1 = 4;
*o2 = 1;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_four_three_TypeI_SinglePanel_Restriction):
*n1 = 4;
*n2 = 3;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_six_two_TypeI_SinglePanel_Restriction):
*n1 = 4;
*n2 = 2;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_twelve_one_TypeI_SinglePanel_Restriction):
*n1 = 12;
*n2 = 1;
*o1 = 4;
*o2 = 1;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_four_four_TypeI_SinglePanel_Restriction):
*n1 = 4;
*n2 = 4;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_eight_two_TypeI_SinglePanel_Restriction):
*n1 = 8;
*n2 = 2;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_sixteen_one_TypeI_SinglePanel_Restriction):
*n1 = 16;
*n2 = 1;
*o1 = 4;
*o2 = 1;
break;
default:
AssertFatal(1==0,"Not supported configuration for n1_n2 in codebook configuration");
}
}
void get_x1x2_bitlen_singlepanel(int n1, int n2, int o1, int o2,
int *x1, int *x2, int rank, int codebook_mode) {
// Table 6.3.1.1.2-1 in 38.212
switch(rank){
case 1:
if(n2>1) {
if (codebook_mode == 1) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 2;
}
else {
*x1 = ceil(log2(n1*o1/2)) + ceil(log2(n2*o2/2));
*x2 = 4;
}
}
else{
if (codebook_mode == 1) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 2;
}
else {
*x1 = ceil(log2(n1*o1/2));
*x2 = 4;
}
}
break;
case 2:
if(n1*n2 == 2) {
if (codebook_mode == 1) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 1;
}
else {
*x1 = ceil(log2(n1*o1/2));
*x2 = 3;
}
*x1 += 1;
}
else {
if(n2>1) {
if (codebook_mode == 1) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 3;
}
else {
*x1 = ceil(log2(n1*o1/2)) + ceil(log2(n2*o2/2));
*x2 = 3;
}
}
else{
if (codebook_mode == 1) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 1;
}
else {
*x1 = ceil(log2(n1*o1/2));
*x2 = 3;
}
}
*x1 += 2;
}
break;
case 3:
case 4:
if(n1*n2 == 2) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 1;
}
else {
if(n1*n2 >= 8) {
*x1 = ceil(log2(n1*o1/2)) + ceil(log2(n2*o2)) + 2;
*x2 = 1;
}
else {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2)) + 2;
*x2 = 1;
}
}
break;
case 5:
case 6:
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 1;
break;
case 7:
case 8:
if(n1 == 4 && n2 == 1) {
*x1 = ceil(log2(n1*o1/2)) + ceil(log2(n2*o2));
*x2 = 1;
}
else {
if(n1 > 2 && n2 == 2) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2/2));
*x2 = 1;
}
else {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 1;
}
}
break;
default:
AssertFatal(1==0,"Invalid rank in x1 x2 bit length computation\n");
}
}
void compute_pmi_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
uint8_t ri_restriction,
nr_csi_report_t *csi_report) {
struct NR_CodebookConfig *codebookConfig = csi_reportconfig->codebookConfig;
for(int i=0; i<8; i++) {
csi_report->csi_meas_bitlen.pmi_x1_bitlen[i]=0;
csi_report->csi_meas_bitlen.pmi_x2_bitlen[i]=0;
if (codebookConfig == NULL || ((ri_restriction>>i)&0x01) == 0)
return;
else {
if(codebookConfig->codebookType.present == NR_CodebookConfig__codebookType_PR_type1) {
if(codebookConfig->codebookType.choice.type1->subType.present == NR_CodebookConfig__codebookType__type1__subType_PR_typeI_SinglePanel) {
if(codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel->nrOfAntennaPorts.present ==
NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts_PR_two) {
csi_report->N1 = 1;
csi_report->N2 = 1;
if (i==0)
csi_report->csi_meas_bitlen.pmi_x2_bitlen[i]=2;
if (i==1)
csi_report->csi_meas_bitlen.pmi_x2_bitlen[i]=1;
}
else { // more than two
int n1,n2,o1,o2,x1,x2;
get_n1n2_o1o2_singlepanel(&n1,&n2,&o1,&o2,codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel->nrOfAntennaPorts.choice.moreThanTwo);
get_x1x2_bitlen_singlepanel(n1,n2,o1,o2,&x1,&x2,i+1,codebookConfig->codebookType.choice.type1->codebookMode);
csi_report->N1 = n1;
csi_report->N2 = n2;
csi_report->codebook_mode = codebookConfig->codebookType.choice.type1->codebookMode;
csi_report->csi_meas_bitlen.pmi_x1_bitlen[i]=x1;
csi_report->csi_meas_bitlen.pmi_x2_bitlen[i]=x2;
}
}
else
AssertFatal(1==0,"Type1 Multi-panel Codebook Config not yet implemented\n");
}
else
AssertFatal(1==0,"Type2 Codebook Config not yet implemented\n");
}
}
}
void compute_cqi_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
uint8_t ri_restriction,
nr_csi_report_t *csi_report) {
struct NR_CodebookConfig *codebookConfig = csi_reportconfig->codebookConfig;
struct NR_CSI_ReportConfig__reportFreqConfiguration *freq_config = csi_reportconfig->reportFreqConfiguration;
if (*freq_config->cqi_FormatIndicator == NR_CSI_ReportConfig__reportFreqConfiguration__cqi_FormatIndicator_widebandCQI) {
for(int i=0; i<8; i++) {
if ((ri_restriction>>i)&0x01) {
csi_report->csi_meas_bitlen.cqi_bitlen[i] = 4;
if(codebookConfig != NULL) {
if (NR_CodebookConfig__codebookType__type1__subType_PR_typeI_SinglePanel == codebookConfig->codebookType.choice.type1->subType.present){
struct NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel *type1single = codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel;
if (type1single->nrOfAntennaPorts.present == NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts_PR_moreThanTwo) {
if (type1single->nrOfAntennaPorts.choice.moreThanTwo->n1_n2.present >
NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_two_one_TypeI_SinglePanel_Restriction) {
// more than 4 antenna ports
if (i > 4)
csi_report->csi_meas_bitlen.cqi_bitlen[i] += 4; // CQI for second TB
}
}
}
}
}
else
csi_report->csi_meas_bitlen.cqi_bitlen[i] = 0;
}
}
else
AssertFatal(1==0,"Sub-band CQI reporting not yet supported");
}
//!TODO : same function can be written to handle csi_resources
void compute_csi_bitlen(NR_CSI_MeasConfig_t *csi_MeasConfig, nr_csi_report_t *csi_report_template) {
uint8_t csi_report_id = 0;
uint8_t nb_resources = 0;
NR_CSI_ReportConfig__reportQuantity_PR reportQuantity_type;
NR_CSI_ResourceConfigId_t csi_ResourceConfigId;
struct NR_CSI_ResourceConfig *csi_resourceconfig;
// for each CSI measurement report configuration (list of CSI-ReportConfig)
LOG_D(NR_MAC,"Searching %d csi_reports\n",csi_MeasConfig->csi_ReportConfigToAddModList->list.count);
for (csi_report_id=0; csi_report_id < csi_MeasConfig->csi_ReportConfigToAddModList->list.count; csi_report_id++){
struct NR_CSI_ReportConfig *csi_reportconfig = csi_MeasConfig->csi_ReportConfigToAddModList->list.array[csi_report_id];
// MAC structure for CSI measurement reports (per UE and per report)
nr_csi_report_t *csi_report = &csi_report_template[csi_report_id];
// csi-ResourceConfigId of a CSI-ResourceConfig included in the configuration
// (either CSI-RS or SSB)
csi_ResourceConfigId = csi_reportconfig->resourcesForChannelMeasurement;
// looking for CSI-ResourceConfig
int found_resource = 0;
int csi_resourceidx = 0;
while (found_resource == 0 && csi_resourceidx < csi_MeasConfig->csi_ResourceConfigToAddModList->list.count) {
csi_resourceconfig = csi_MeasConfig->csi_ResourceConfigToAddModList->list.array[csi_resourceidx];
if ( csi_resourceconfig->csi_ResourceConfigId == csi_ResourceConfigId)
found_resource = 1;
csi_resourceidx++;
}
AssertFatal(found_resource==1,"Not able to found any CSI-ResourceConfig with csi-ResourceConfigId %ld\n",
csi_ResourceConfigId);
long resourceType = csi_resourceconfig->resourceType;
reportQuantity_type = csi_reportconfig->reportQuantity.present;
csi_report->reportQuantity_type = reportQuantity_type;
// setting the CSI or SSB index list
if (NR_CSI_ReportConfig__reportQuantity_PR_ssb_Index_RSRP == csi_report->reportQuantity_type) {
for (int csi_idx = 0; csi_idx < csi_MeasConfig->csi_SSB_ResourceSetToAddModList->list.count; csi_idx++) {
if (csi_MeasConfig->csi_SSB_ResourceSetToAddModList->list.array[csi_idx]->csi_SSB_ResourceSetId ==
*(csi_resourceconfig->csi_RS_ResourceSetList.choice.nzp_CSI_RS_SSB->csi_SSB_ResourceSetList->list.array[0])){
//We can configure only one SSB resource set from spec 38.331 IE CSI-ResourceConfig
nb_resources= csi_MeasConfig->csi_SSB_ResourceSetToAddModList->list.array[csi_idx]->csi_SSB_ResourceList.list.count;
csi_report->SSB_Index_list = csi_MeasConfig->csi_SSB_ResourceSetToAddModList->list.array[csi_idx]->csi_SSB_ResourceList.list.array;
csi_report->CSI_Index_list = NULL;
break;
}
}
}
else {
if (resourceType == NR_CSI_ResourceConfig__resourceType_periodic) {
AssertFatal(csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList != NULL,
"Wrong settings! Report quantity requires CSI-RS but csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList is NULL\n");
for (int csi_idx = 0; csi_idx < csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList->list.count; csi_idx++) {
if (csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList->list.array[csi_idx]->nzp_CSI_ResourceSetId ==
*(csi_resourceconfig->csi_RS_ResourceSetList.choice.nzp_CSI_RS_SSB->nzp_CSI_RS_ResourceSetList->list.array[0])) {
//For periodic and semi-persistent CSI Resource Settings, the number of CSI-RS Resource Sets configured is limited to S=1 for spec 38.212
nb_resources = csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList->list.array[csi_idx]->nzp_CSI_RS_Resources.list.count;
csi_report->CSI_Index_list = csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList->list.array[csi_idx]->nzp_CSI_RS_Resources.list.array;
csi_report->SSB_Index_list = NULL;
break;
}
}
}
else AssertFatal(1==0,"Only periodic resource configuration currently supported\n");
}
LOG_D(NR_MAC,"nb_resources %d\n",nb_resources);
// computation of bit length depending on the report type
switch(reportQuantity_type){
case (NR_CSI_ReportConfig__reportQuantity_PR_ssb_Index_RSRP):
compute_rsrp_bitlen(csi_reportconfig, nb_resources, csi_report);
break;
case (NR_CSI_ReportConfig__reportQuantity_PR_cri_RSRP):
compute_rsrp_bitlen(csi_reportconfig, nb_resources, csi_report);
break;
case (NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_CQI):
csi_report->csi_meas_bitlen.cri_bitlen=ceil(log2(nb_resources));
csi_report->csi_meas_bitlen.ri_restriction = compute_ri_bitlen(csi_reportconfig, csi_report);
compute_cqi_bitlen(csi_reportconfig, csi_report->csi_meas_bitlen.ri_restriction, csi_report);
break;
case (NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_PMI_CQI):
csi_report->csi_meas_bitlen.cri_bitlen=ceil(log2(nb_resources));
csi_report->csi_meas_bitlen.ri_restriction = compute_ri_bitlen(csi_reportconfig, csi_report);
compute_cqi_bitlen(csi_reportconfig, csi_report->csi_meas_bitlen.ri_restriction, csi_report);
compute_pmi_bitlen(csi_reportconfig, csi_report->csi_meas_bitlen.ri_restriction, csi_report);
break;
case (NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_LI_PMI_CQI):
csi_report->csi_meas_bitlen.cri_bitlen=ceil(log2(nb_resources));
csi_report->csi_meas_bitlen.ri_restriction = compute_ri_bitlen(csi_reportconfig, csi_report);
compute_li_bitlen(csi_reportconfig, csi_report->csi_meas_bitlen.ri_restriction, csi_report);
compute_cqi_bitlen(csi_reportconfig, csi_report->csi_meas_bitlen.ri_restriction, csi_report);
compute_pmi_bitlen(csi_reportconfig, csi_report->csi_meas_bitlen.ri_restriction, csi_report);
break;
default:
AssertFatal(1==0,"Not yet supported CSI report quantity type");
}
}
}
uint16_t nr_get_csi_bitlen(nr_csi_report_t *csi_report_template, uint8_t csi_report_id) {
uint16_t csi_bitlen = 0;
uint16_t max_bitlen = 0;
L1_RSRP_bitlen_t *CSI_report_bitlen = NULL;
CSI_Meas_bitlen_t *csi_meas_bitlen = NULL;
if (csi_report_template[csi_report_id].reportQuantity_type == NR_CSI_ReportConfig__reportQuantity_PR_ssb_Index_RSRP ||
csi_report_template[csi_report_id].reportQuantity_type == NR_CSI_ReportConfig__reportQuantity_PR_cri_RSRP) {
CSI_report_bitlen = &(csi_report_template[csi_report_id].CSI_report_bitlen); // This might need to be moodif for Aperiodic CSI-RS measurements
csi_bitlen += ((CSI_report_bitlen->cri_ssbri_bitlen * CSI_report_bitlen->nb_ssbri_cri) +
CSI_report_bitlen->rsrp_bitlen +(CSI_report_bitlen->diff_rsrp_bitlen *
(CSI_report_bitlen->nb_ssbri_cri -1 )));
} else {
csi_meas_bitlen = &(csi_report_template[csi_report_id].csi_meas_bitlen); //This might need to be moodif for Aperiodic CSI-RS measurements
uint16_t temp_bitlen;
for (int i=0; i<8; i++) {
temp_bitlen = (csi_meas_bitlen->cri_bitlen+
csi_meas_bitlen->ri_bitlen+
csi_meas_bitlen->li_bitlen[i]+
csi_meas_bitlen->cqi_bitlen[i]+
csi_meas_bitlen->pmi_x1_bitlen[i]+
csi_meas_bitlen->pmi_x2_bitlen[i]);
if(temp_bitlen>max_bitlen)
max_bitlen = temp_bitlen;
}
csi_bitlen += max_bitlen;
}
return csi_bitlen;
}
+34 -2
View File
@@ -105,7 +105,7 @@ uint8_t get_pusch_mcs_table(long *mcs_Table,
uint8_t compute_nr_root_seq(NR_RACH_ConfigCommon_t *rach_config,
uint8_t nb_preambles,
uint8_t unpaired,
frequency_range_t);
frequency_range_t);
int ul_ant_bits(NR_DMRS_UplinkConfig_t *NR_DMRS_UplinkConfig,long transformPrecoder);
@@ -142,7 +142,7 @@ uint32_t nr_get_code_rate_ul(uint8_t Imcs, uint8_t table_idx);
uint16_t get_nr_srs_offset(NR_SRS_PeriodicityAndOffset_t periodicityAndOffset);
int get_bw_tbslbrm(NR_BWP_t *genericParameters,
int get_bw_tbslbrm(int scc_bwpsize,
NR_CellGroupConfig_t *cg);
uint32_t nr_compute_tbslbrm(uint16_t table,
@@ -234,4 +234,36 @@ void nr_mac_gNB_rrc_ul_failure_reset(const module_id_t Mod_instP,
const frame_t frameP,
const sub_frame_t subframeP,
const rnti_t rntiP);
uint8_t number_of_bits_set(uint8_t buf);
void compute_rsrp_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
uint8_t nb_resources,
nr_csi_report_t *csi_report);
uint8_t compute_ri_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
nr_csi_report_t *csi_report);
void compute_li_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
uint8_t ri_restriction,
nr_csi_report_t *csi_report);
void get_n1n2_o1o2_singlepanel(int *n1, int *n2, int *o1, int *o2,
struct NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo *morethantwo);
void get_x1x2_bitlen_singlepanel(int n1, int n2, int o1, int o2,
int *x1, int *x2, int rank, int codebook_mode);
void compute_pmi_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
uint8_t ri_restriction,
nr_csi_report_t *csi_report);
void compute_cqi_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
uint8_t ri_restriction,
nr_csi_report_t *csi_report);
void compute_csi_bitlen(NR_CSI_MeasConfig_t *csi_MeasConfig, nr_csi_report_t *csi_report_template);
uint16_t nr_get_csi_bitlen(nr_csi_report_t *csi_report_template, uint8_t csi_report_id);
#endif
+2 -2
View File
@@ -190,7 +190,7 @@ void config_common_ue_sa(NR_UE_MAC_INST_t *mac,
cfg->ssb_table.ssb_subcarrier_offset = mac->ssb_subcarrier_offset;
if (mac->frequency_range == FR1){
cfg->ssb_table.ssb_mask_list[0].ssb_mask = scc->ssb_PositionsInBurst.inOneGroup.buf[0]<<24;
cfg->ssb_table.ssb_mask_list[0].ssb_mask = ((uint32_t) scc->ssb_PositionsInBurst.inOneGroup.buf[0]) << 24;
cfg->ssb_table.ssb_mask_list[1].ssb_mask = 0;
}
else{
@@ -353,7 +353,7 @@ void config_common_ue(NR_UE_MAC_INST_t *mac,
cfg->ssb_table.ssb_mask_list[1].ssb_mask = 0;
break;
case 2 :
cfg->ssb_table.ssb_mask_list[0].ssb_mask = scc->ssb_PositionsInBurst->choice.mediumBitmap.buf[0]<<24;
cfg->ssb_table.ssb_mask_list[0].ssb_mask = ((uint32_t) scc->ssb_PositionsInBurst->choice.mediumBitmap.buf[0]) << 24;
cfg->ssb_table.ssb_mask_list[1].ssb_mask = 0;
break;
case 3 :
+5
View File
@@ -399,6 +399,11 @@ typedef struct {
/// measured SSB RSRP in dBm
short ssb_rsrp_dBm;
nr_csi_report_t csi_report_template[MAX_CSI_REPORTCONFIG];
/// measurements from CSI-RS
fapi_nr_csirs_measurements_t csirs_measurements;
/// Last NDI of UL HARQ processes
uint8_t UL_ndi[NR_MAX_HARQ_PROCESSES];
/// first ULTX of UL HARQ processes
+13 -7
View File
@@ -194,6 +194,7 @@ int nr_get_sf_retxBSRTimer(uint8_t retxBSR_Timer);
int8_t nr_ue_process_dci(module_id_t module_id, int cc_id, uint8_t gNB_index, frame_t frame, int slot, dci_pdu_rel15_t *dci, fapi_nr_dci_indication_pdu_t *dci_ind);
int nr_ue_process_dci_indication_pdu(module_id_t module_id, int cc_id, int gNB_index, frame_t frame, int slot, fapi_nr_dci_indication_pdu_t *dci);
int8_t nr_ue_process_csirs_measurements(module_id_t module_id, frame_t frame, int slot, fapi_nr_csirs_measurements_t *csirs_measurements);
uint32_t get_ssb_frame(uint32_t test);
@@ -213,6 +214,18 @@ uint8_t get_ssb_rsrp_payload(NR_UE_MAC_INST_t *mac,
NR_CSI_ResourceConfigId_t csi_ResourceConfigId,
NR_CSI_MeasConfig_t *csi_MeasConfig);
uint8_t get_csirs_RI_PMI_CQI_payload(NR_UE_MAC_INST_t *mac,
PUCCH_sched_t *pucch,
struct NR_CSI_ReportConfig *csi_reportconfig,
NR_CSI_ResourceConfigId_t csi_ResourceConfigId,
NR_CSI_MeasConfig_t *csi_MeasConfig);
uint8_t get_csirs_RSRP_payload(NR_UE_MAC_INST_t *mac,
PUCCH_sched_t *pucch,
struct NR_CSI_ReportConfig *csi_reportconfig,
NR_CSI_ResourceConfigId_t csi_ResourceConfigId,
NR_CSI_MeasConfig_t *csi_MeasConfig);
uint8_t nr_get_csi_payload(NR_UE_MAC_INST_t *mac,
PUCCH_sched_t *pucch,
int csi_report_id,
@@ -257,13 +270,6 @@ void get_bwp_info(NR_UE_MAC_INST_t *mac,
NR_BWP_DownlinkCommon_t *get_bwp_downlink_common(NR_UE_MAC_INST_t *mac, NR_BWP_Id_t dl_bwp_id);
uint8_t nr_extract_dci_info(NR_UE_MAC_INST_t *mac,
uint8_t dci_format,
uint8_t dci_length,
uint16_t rnti,
uint64_t *dci_pdu,
dci_pdu_rel15_t *nr_pdci_info_extracted);
NR_PUSCH_TimeDomainResourceAllocationList_t *choose_ul_tda_list(const NR_PUSCH_Config_t *pusch_Config,NR_PUSCH_ConfigCommon_t *pusch_ConfigCommon);
NR_PDSCH_TimeDomainResourceAllocationList_t *choose_dl_tda_list(NR_PDSCH_Config_t *pdsch_Config,NR_PDSCH_ConfigCommon_t *pdsch_ConfigCommon);
+153 -17
View File
@@ -134,6 +134,13 @@ const initial_pucch_resource_t initial_pucch_resource[16] = {
};
static uint8_t nr_extract_dci_info(NR_UE_MAC_INST_t *mac,
uint8_t dci_format,
uint8_t dci_length,
uint16_t rnti,
uint64_t *dci_pdu,
dci_pdu_rel15_t *nr_pdci_info_extracted);
void nr_ue_init_mac(module_id_t module_idP) {
int i;
@@ -957,7 +964,8 @@ int8_t nr_ue_process_dci(module_id_t module_id, int cc_id, uint8_t gNB_index, fr
if (mac->scc || mac->scc_SIB || mac->cg) {
NR_BWP_t genericParameters = mac->scc ? mac->scc->downlinkConfigCommon->initialDownlinkBWP->genericParameters :
mac->scc_SIB->downlinkConfigCommon.initialDownlinkBWP.genericParameters;
bw_tbslbrm = get_bw_tbslbrm(&genericParameters, mac->cg);
int BWPSize = NRRIV2BW(genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
bw_tbslbrm = get_bw_tbslbrm(BWPSize, mac->cg);
}
else
bw_tbslbrm = dlsch_config_pdu_1_0->BWPSize;
@@ -985,7 +993,8 @@ int8_t nr_ue_process_dci(module_id_t module_id, int cc_id, uint8_t gNB_index, fr
if (dci->tpc == 3) dlsch_config_pdu_1_0->accumulated_delta_PUCCH = 3;
// Sanity check for pucch_resource_indicator value received to check for false DCI.
valid = 0;
if (mac->ULbwp[ul_bwp_id-1] &&
if (ul_bwp_id > 0 &&
mac->ULbwp[ul_bwp_id-1] &&
mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated &&
mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pucch_Config &&
mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pucch_Config->choice.setup&&
@@ -1396,7 +1405,8 @@ int8_t nr_ue_process_dci(module_id_t module_id, int cc_id, uint8_t gNB_index, fr
int nl_tbslbrm = *maxMIMO_Layers < 4 ? *maxMIMO_Layers : 4;
NR_BWP_t genericParameters = mac->scc ? mac->scc->downlinkConfigCommon->initialDownlinkBWP->genericParameters :
mac->scc_SIB->downlinkConfigCommon.initialDownlinkBWP.genericParameters;
int bw_tbslbrm = get_bw_tbslbrm(&genericParameters, mac->cg);
int BWPSize = NRRIV2BW(genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
int bw_tbslbrm = get_bw_tbslbrm(BWPSize, mac->cg);
dlsch_config_pdu_1_1->tbslbrm = nr_compute_tbslbrm(dlsch_config_pdu_1_1->mcs_table,
bw_tbslbrm,
nl_tbslbrm);
@@ -1454,6 +1464,16 @@ int8_t nr_ue_process_dci(module_id_t module_id, int cc_id, uint8_t gNB_index, fr
}
int8_t nr_ue_process_csirs_measurements(module_id_t module_id,
frame_t frame,
int slot,
fapi_nr_csirs_measurements_t *csirs_measurements) {
LOG_D(NR_MAC,"(%d.%d) Received CSI-RS measurements\n", frame, slot);
NR_UE_MAC_INST_t *mac = get_mac_inst(module_id);
memcpy(&mac->csirs_measurements, csirs_measurements, sizeof(*csirs_measurements));
return 0;
}
void set_harq_status(NR_UE_MAC_INST_t *mac,
uint8_t pucch_id,
uint8_t harq_id,
@@ -1512,13 +1532,12 @@ void nr_ue_configure_pucch(NR_UE_MAC_INST_t *mac,
NR_BWP_UplinkCommon_t *initialUplinkBWP;
if (mac->scc) initialUplinkBWP = mac->scc->uplinkConfigCommon->initialUplinkBWP;
else initialUplinkBWP = &mac->scc_SIB->uplinkConfigCommon->initialUplinkBWP;
NR_BWP_Uplink_t *ubwp = mac->ULbwp[bwp_id-1];
if (mac->cg && ubwp &&
if (mac->cg && bwp_id > 1 && mac->ULbwp[bwp_id - 1] &&
mac->cg->spCellConfig &&
mac->cg->spCellConfig->spCellConfigDedicated &&
mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig &&
mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP) {
scs = ubwp->bwp_Common->genericParameters.subcarrierSpacing;
scs = mac->ULbwp[bwp_id - 1]->bwp_Common->genericParameters.subcarrierSpacing;
}
else
scs = initialUplinkBWP->genericParameters.subcarrierSpacing;
@@ -1581,7 +1600,6 @@ void nr_ue_configure_pucch(NR_UE_MAC_INST_t *mac,
// TODO verify if SR can be transmitted in this mode
pucch_pdu->payload = (pucch->sr_payload << O_ACK) | pucch->ack_payload;
}
else if (pucch->pucch_resource != NULL) {
@@ -1782,8 +1800,6 @@ void nr_ue_configure_pucch(NR_UE_MAC_INST_t *mac,
default:
AssertFatal(1==0,"Group hopping flag undefined (0,1,2) \n");
}
}
@@ -2178,7 +2194,8 @@ uint8_t get_downlink_ack(NR_UE_MAC_INST_t *mac,
sched_frame = (sched_frame + 1) % 1024;
}
AssertFatal(sched_slot < slots_per_frame, "sched_slot was calculated incorrect %d\n", sched_slot);
LOG_D(PHY,"HARQ pid %d is active for %d.%d (dl_slot %d, feedback_to_ul %d, is_common %d\n",dl_harq_pid, sched_frame,sched_slot,current_harq->dl_slot,current_harq->feedback_to_ul,current_harq->is_common);
LOG_D(PHY,"HARQ pid %d is active for %d.%d (dl_slot %d, feedback_to_ul %d, is_common %d\n",
dl_harq_pid, sched_frame,sched_slot,current_harq->dl_slot,current_harq->feedback_to_ul,current_harq->is_common);
/* check if current tx slot should transmit downlink acknowlegment */
if (sched_frame == frame && sched_slot == slot) {
if (get_softmodem_params()->emulate_l1) {
@@ -2340,17 +2357,16 @@ bool trigger_periodic_scheduling_request(NR_UE_MAC_INST_t *mac,
NR_BWP_Id_t bwp_id = mac->UL_BWP_Id;
NR_PUCCH_Config_t *pucch_Config = NULL;
int scs;
NR_BWP_Uplink_t *ubwp = mac->ULbwp[bwp_id-1];
NR_BWP_UplinkCommon_t *initialUplinkBWP;
if (mac->scc) initialUplinkBWP = mac->scc->uplinkConfigCommon->initialUplinkBWP;
else initialUplinkBWP = &mac->scc_SIB->uplinkConfigCommon->initialUplinkBWP;
if (mac->cg && ubwp &&
if (mac->cg && bwp_id && mac->ULbwp[bwp_id - 1] &&
mac->cg->spCellConfig &&
mac->cg->spCellConfig->spCellConfigDedicated &&
mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig &&
mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP) {
scs = ubwp->bwp_Common->genericParameters.subcarrierSpacing;
scs = mac->ULbwp[bwp_id - 1]->bwp_Common->genericParameters.subcarrierSpacing;
}
else
scs = initialUplinkBWP->genericParameters.subcarrierSpacing;
@@ -2558,13 +2574,17 @@ uint8_t nr_get_csi_payload(NR_UE_MAC_INST_t *mac,
case NR_CSI_ReportConfig__reportQuantity_PR_ssb_Index_RSRP:
n_csi_bits = get_ssb_rsrp_payload(mac,pucch,csi_reportconfig,csi_ResourceConfigId,csi_MeasConfig);
break;
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RSRP:
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_PMI_CQI:
n_csi_bits = get_csirs_RI_PMI_CQI_payload(mac,pucch,csi_reportconfig,csi_ResourceConfigId,csi_MeasConfig);
break;
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RSRP:
n_csi_bits = get_csirs_RSRP_payload(mac,pucch,csi_reportconfig,csi_ResourceConfigId,csi_MeasConfig);
break;
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_i1:
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_i1_CQI:
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_CQI:
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_LI_PMI_CQI:
LOG_E(NR_MAC,"Measurement report based on CSI-RS not available\n");
LOG_E(NR_MAC,"Measurement report %d based on CSI-RS is not available\n", csi_reportconfig->reportQuantity.present);
break;
default:
AssertFatal(1==0,"Invalid CSI report quantity type %d\n",csi_reportconfig->reportQuantity.present);
@@ -2652,6 +2672,122 @@ uint8_t get_ssb_rsrp_payload(NR_UE_MAC_INST_t *mac,
return bits;
}
uint8_t get_csirs_RI_PMI_CQI_payload(NR_UE_MAC_INST_t *mac,
PUCCH_sched_t *pucch,
struct NR_CSI_ReportConfig *csi_reportconfig,
NR_CSI_ResourceConfigId_t csi_ResourceConfigId,
NR_CSI_MeasConfig_t *csi_MeasConfig) {
int n_bits = 0;
uint32_t temp_payload = 0;
for (int csi_resourceidx = 0; csi_resourceidx < csi_MeasConfig->csi_ResourceConfigToAddModList->list.count; csi_resourceidx++) {
struct NR_CSI_ResourceConfig *csi_resourceconfig = csi_MeasConfig->csi_ResourceConfigToAddModList->list.array[csi_resourceidx];
if (csi_resourceconfig->csi_ResourceConfigId == csi_ResourceConfigId) {
for (int csi_idx = 0; csi_idx < csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList->list.count; csi_idx++) {
if (csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList->list.array[csi_idx]->nzp_CSI_ResourceSetId ==
*(csi_resourceconfig->csi_RS_ResourceSetList.choice.nzp_CSI_RS_SSB->nzp_CSI_RS_ResourceSetList->list.array[0])) {
nr_csi_report_t *csi_report = &mac->csi_report_template[csi_reportconfig->reportConfigId];
compute_csi_bitlen(csi_MeasConfig, mac->csi_report_template);
n_bits = nr_get_csi_bitlen(mac->csi_report_template, csi_reportconfig->reportConfigId);
int cri_bitlen = csi_report->csi_meas_bitlen.cri_bitlen;
int ri_bitlen = csi_report->csi_meas_bitlen.ri_bitlen;
int pmi_x1_bitlen = csi_report->csi_meas_bitlen.pmi_x1_bitlen[mac->csirs_measurements.rank_indicator];
int pmi_x2_bitlen = csi_report->csi_meas_bitlen.pmi_x2_bitlen[mac->csirs_measurements.rank_indicator];
int cqi_bitlen = csi_report->csi_meas_bitlen.cqi_bitlen[mac->csirs_measurements.rank_indicator];
int padding_bitlen = n_bits - (cri_bitlen + ri_bitlen + pmi_x1_bitlen + pmi_x2_bitlen + cqi_bitlen);
// TODO: Improvements will be needed to cri_bitlen>0 and pmi_x1_bitlen>0
temp_payload = (mac->csirs_measurements.rank_indicator<<(cri_bitlen+cqi_bitlen+pmi_x2_bitlen+padding_bitlen+pmi_x1_bitlen)) |
(mac->csirs_measurements.i1<<(cri_bitlen+cqi_bitlen+pmi_x2_bitlen)) |
(mac->csirs_measurements.i2<<(cri_bitlen+cqi_bitlen)) |
(mac->csirs_measurements.cqi<<cri_bitlen) |
0;
reverse_n_bits((uint8_t *)&temp_payload, n_bits);
LOG_D(NR_MAC, "cri_bitlen = %d\n", cri_bitlen);
LOG_D(NR_MAC, "ri_bitlen = %d\n", ri_bitlen);
LOG_D(NR_MAC, "pmi_x1_bitlen = %d\n", pmi_x1_bitlen);
LOG_D(NR_MAC, "pmi_x2_bitlen = %d\n", pmi_x2_bitlen);
LOG_D(NR_MAC, "cqi_bitlen = %d\n", cqi_bitlen);
LOG_D(NR_MAC, "csi_part1_payload = 0x%x\n", temp_payload);
LOG_D(NR_MAC, "n_bits = %d\n", n_bits);
LOG_D(NR_MAC, "csi_part1_payload = 0x%x\n", temp_payload);
break;
}
}
}
}
pucch->csi_part1_payload = temp_payload;
return n_bits;
}
uint8_t get_csirs_RSRP_payload(NR_UE_MAC_INST_t *mac,
PUCCH_sched_t *pucch,
struct NR_CSI_ReportConfig *csi_reportconfig,
NR_CSI_ResourceConfigId_t csi_ResourceConfigId,
NR_CSI_MeasConfig_t *csi_MeasConfig) {
int n_bits = 0;
uint32_t temp_payload = 0;
for (int csi_resourceidx = 0; csi_resourceidx < csi_MeasConfig->csi_ResourceConfigToAddModList->list.count; csi_resourceidx++) {
struct NR_CSI_ResourceConfig *csi_resourceconfig = csi_MeasConfig->csi_ResourceConfigToAddModList->list.array[csi_resourceidx];
if (csi_resourceconfig->csi_ResourceConfigId == csi_ResourceConfigId) {
for (int csi_idx = 0; csi_idx < csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList->list.count; csi_idx++) {
if (csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList->list.array[csi_idx]->nzp_CSI_ResourceSetId ==
*(csi_resourceconfig->csi_RS_ResourceSetList.choice.nzp_CSI_RS_SSB->nzp_CSI_RS_ResourceSetList->list.array[0])) {
nr_csi_report_t *csi_report = &mac->csi_report_template[csi_reportconfig->reportConfigId];
compute_csi_bitlen(csi_MeasConfig, mac->csi_report_template);
n_bits = nr_get_csi_bitlen(mac->csi_report_template, csi_reportconfig->reportConfigId);
int cri_ssbri_bitlen = csi_report->CSI_report_bitlen.cri_ssbri_bitlen;
int rsrp_bitlen = csi_report->CSI_report_bitlen.rsrp_bitlen;
int diff_rsrp_bitlen = csi_report->CSI_report_bitlen.diff_rsrp_bitlen;
if (cri_ssbri_bitlen > 0) {
LOG_E(NR_MAC, "Implementation for cri_ssbri_bitlen>0 is not supported yet!\n");;
}
// TODO: Improvements will be needed to cri_ssbri_bitlen>0
// TS 38.133 - Table 10.1.6.1-1
int rsrp_dBm = mac->csirs_measurements.rsrp_dBm;
if (rsrp_dBm < -140) {
temp_payload = 16;
} else if (rsrp_dBm > -44) {
temp_payload = 113;
} else {
temp_payload = mac->csirs_measurements.rsrp_dBm + 157;
}
reverse_n_bits((uint8_t *)&temp_payload, n_bits);
LOG_D(NR_MAC, "cri_ssbri_bitlen = %d\n", cri_ssbri_bitlen);
LOG_D(NR_MAC, "rsrp_bitlen = %d\n", rsrp_bitlen);
LOG_D(NR_MAC, "diff_rsrp_bitlen = %d\n", diff_rsrp_bitlen);
LOG_D(NR_MAC, "n_bits = %d\n", n_bits);
LOG_D(NR_MAC, "csi_part1_payload = 0x%x\n", temp_payload);
break;
}
}
}
}
pucch->csi_part1_payload = temp_payload;
return n_bits;
}
// returns index from RSRP
// according to Table 10.1.6.1-1 in 38.133
@@ -2732,7 +2868,7 @@ int get_n_rb(NR_UE_MAC_INST_t *mac, int rnti_type){
}
uint8_t nr_extract_dci_info(NR_UE_MAC_INST_t *mac,
static uint8_t nr_extract_dci_info(NR_UE_MAC_INST_t *mac,
uint8_t dci_format,
uint8_t dci_size,
uint16_t rnti,
@@ -3580,7 +3716,7 @@ void nr_ue_process_mac_pdu(nr_downlink_indication_t *dl_info,
#endif
*/
LOG_I(NR_MAC, "[%d.%d] Received TA_COMMAND %u TAGID %u CC_id %d\n", frameP, slot, ul_time_alignment->ta_command, ul_time_alignment->tag_id, CC_id);
LOG_I(NR_MAC, "[%d.%d] Received TA_COMMAND %u TAGID %u CC_id %d\n", frameP, slot, ul_time_alignment->ta_command, ul_time_alignment->tag_id, CC_id);
break;
case DL_SCH_LCID_CON_RES_ID:
+25 -19
View File
@@ -118,12 +118,13 @@ long get_k2(NR_UE_MAC_INST_t *mac, uint8_t time_domain_ind) {
NR_BWP_Id_t ul_bwp_id = mac->UL_BWP_Id;
// Get K2 from RRC configuration
NR_PUSCH_Config_t *pusch_config=mac->ULbwp[ul_bwp_id-1] ? mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pusch_Config->choice.setup : NULL;
NR_PUSCH_Config_t *pusch_config= ul_bwp_id > 0 && mac->ULbwp[ul_bwp_id-1] ? mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pusch_Config->choice.setup : NULL;
NR_PUSCH_TimeDomainResourceAllocationList_t *pusch_TimeDomainAllocationList = NULL;
if (pusch_config && pusch_config->pusch_TimeDomainAllocationList) {
pusch_TimeDomainAllocationList = pusch_config->pusch_TimeDomainAllocationList->choice.setup;
}
else if (mac->ULbwp[ul_bwp_id-1] &&
else if (ul_bwp_id > 0 &&
mac->ULbwp[ul_bwp_id-1] &&
mac->ULbwp[ul_bwp_id-1]->bwp_Common&&
mac->ULbwp[ul_bwp_id-1]->bwp_Common->pusch_ConfigCommon&&
mac->ULbwp[ul_bwp_id-1]->bwp_Common->pusch_ConfigCommon->choice.setup &&
@@ -169,7 +170,7 @@ fapi_nr_ul_config_request_t *get_ul_config_request(NR_UE_MAC_INST_t *mac, int sl
// Calculate the index of the UL slot in mac->ul_config_request list. This is
// based on the TDD pattern (slot configuration period) and number of UL+mixed
// slots in the period. TS 38.213 Sec 11.1
int mu = mac->ULbwp[ul_bwp_id-1] ?
int mu = ul_bwp_id > 0 && mac->ULbwp[ul_bwp_id-1] ?
mac->ULbwp[ul_bwp_id-1]->bwp_Common->genericParameters.subcarrierSpacing :
mac->scc_SIB->uplinkConfigCommon->initialUplinkBWP.genericParameters.subcarrierSpacing;
const int n = nr_slots_per_frame[mu];
@@ -205,7 +206,7 @@ void ul_layers_config(NR_UE_MAC_INST_t * mac, nfapi_nr_ue_pusch_pdu_t *pusch_con
srs_config = mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP->srs_Config->choice.setup;
}
NR_PUSCH_Config_t *pusch_Config = mac->ULbwp[ul_bwp_id-1] ?
NR_PUSCH_Config_t *pusch_Config = ul_bwp_id > 0 && mac->ULbwp[ul_bwp_id-1] ?
mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pusch_Config->choice.setup :
(ubwpd?
ubwpd->pusch_Config->choice.setup:
@@ -361,7 +362,7 @@ void ul_ports_config(NR_UE_MAC_INST_t *mac, int *n_front_load_symb, nfapi_nr_ue_
mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP)
ubwpd = mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP;
NR_PUSCH_Config_t *pusch_Config = mac->ULbwp[ul_bwp_id-1] ? mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pusch_Config->choice.setup : (ubwpd?ubwpd->pusch_Config->choice.setup:NULL);
NR_PUSCH_Config_t *pusch_Config = ul_bwp_id > 0 && mac->ULbwp[ul_bwp_id-1] ? mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pusch_Config->choice.setup : (ubwpd?ubwpd->pusch_Config->choice.setup:NULL);
AssertFatal(pusch_Config!=NULL,"pusch_Config shouldn't be null\n");
long transformPrecoder;
@@ -581,7 +582,7 @@ int nr_config_pusch_pdu(NR_UE_MAC_INST_t *mac,
if (rar_grant) {
// Note: for Msg3 or MsgA PUSCH transmission the N_PRB_oh is always set to 0
NR_BWP_Uplink_t *ubwp = mac->ULbwp[ul_bwp_id-1];
NR_BWP_Uplink_t *ubwp = ul_bwp_id > 0 ? mac->ULbwp[ul_bwp_id - 1] : NULL;
NR_BWP_UplinkDedicated_t *ibwp;
int scs,abwp_start,abwp_size,startSymbolAndLength,mappingtype;
NR_PUSCH_Config_t *pusch_Config=NULL;
@@ -839,11 +840,15 @@ int nr_config_pusch_pdu(NR_UE_MAC_INST_t *mac,
mappingtype, add_pos, dmrslength,
pusch_config_pdu->start_symbol_index,
mac->scc ? mac->scc->dmrs_TypeA_Position : mac->mib->dmrs_TypeA_Position);
if (mac->ULbwp[ul_bwp_id-1] && pusch_config_pdu->transform_precoding == NR_PUSCH_Config__transformPrecoder_disabled) {
if (*dci_format != NR_UL_DCI_FORMAT_0_1) {
pusch_config_pdu->num_dmrs_cdm_grps_no_data = 1;
}
} else if (*dci_format == NR_UL_DCI_FORMAT_0_0 || (mac->ULbwp[ul_bwp_id-1] && pusch_config_pdu->transform_precoding == NR_PUSCH_Config__transformPrecoder_enabled)) {
if (ul_bwp_id > 0 &&
mac->ULbwp[ul_bwp_id - 1] &&
pusch_config_pdu->transform_precoding == NR_PUSCH_Config__transformPrecoder_disabled &&
*dci_format != NR_UL_DCI_FORMAT_0_1) {
pusch_config_pdu->num_dmrs_cdm_grps_no_data = 1;
} else if (*dci_format == NR_UL_DCI_FORMAT_0_0 ||
(ul_bwp_id > 0 &&
mac->ULbwp[ul_bwp_id-1] &&
pusch_config_pdu->transform_precoding == NR_PUSCH_Config__transformPrecoder_enabled)) {
pusch_config_pdu->num_dmrs_cdm_grps_no_data = 2;
}
@@ -859,7 +864,8 @@ int nr_config_pusch_pdu(NR_UE_MAC_INST_t *mac,
else N_PRB_oh = 0;
/* PTRS */
if (mac->ULbwp[ul_bwp_id-1] &&
if (ul_bwp_id > 0 &&
mac->ULbwp[ul_bwp_id-1] &&
mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated &&
mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pusch_Config &&
mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pusch_Config->choice.setup &&
@@ -1093,9 +1099,10 @@ NR_UE_L2_STATE_t nr_ue_scheduler(nr_downlink_indication_t *dl_info, nr_uplink_in
dcireq.dl_config_req = mac->dl_config_request;
fill_scheduled_response(&scheduled_response, &dcireq.dl_config_req, NULL, NULL, mod_id, cc_id, rx_frame, rx_slot, dl_info->thread_id, dl_info->phy_data);
if(mac->if_module != NULL && mac->if_module->scheduled_response != NULL)
if(mac->if_module != NULL && mac->if_module->scheduled_response != NULL) {
LOG_D(NR_MAC,"1# scheduled_response transmitted, %d, %d\n", rx_frame, rx_slot);
mac->if_module->scheduled_response(&scheduled_response);
mac->if_module->scheduled_response(&scheduled_response);
}
}
else {
// this is for Msg2/Msg4
@@ -1564,15 +1571,14 @@ int nr_ue_pusch_scheduler(NR_UE_MAC_INST_t *mac,
int delta = 0;
NR_BWP_Id_t ul_bwp_id = mac->UL_BWP_Id;
NR_BWP_Uplink_t *ubwp = mac->ULbwp[ul_bwp_id-1];
// Get the numerology to calculate the Tx frame and slot
int mu = ubwp ?
ubwp->bwp_Common->genericParameters.subcarrierSpacing :
int mu = ul_bwp_id > 0 && mac->ULbwp[ul_bwp_id-1] ?
mac->ULbwp[ul_bwp_id-1]->bwp_Common->genericParameters.subcarrierSpacing :
mac->scc_SIB->uplinkConfigCommon->initialUplinkBWP.genericParameters.subcarrierSpacing;
NR_PUSCH_TimeDomainResourceAllocationList_t *pusch_TimeDomainAllocationList = ubwp ?
ubwp->bwp_Common->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList:
NR_PUSCH_TimeDomainResourceAllocationList_t *pusch_TimeDomainAllocationList = ul_bwp_id > 0 && mac->ULbwp[ul_bwp_id-1] ?
mac->ULbwp[ul_bwp_id-1]->bwp_Common->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList:
mac->scc_SIB->uplinkConfigCommon->initialUplinkBWP.pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList;
// k2 as per 3GPP TS 38.214 version 15.9.0 Release 15 ch 6.1.2.1.1
// PUSCH time domain resource allocation is higher layer configured from uschTimeDomainAllocationList in either pusch-ConfigCommon
+2 -2
View File
@@ -337,7 +337,7 @@ void config_common(int Mod_idP, int pdsch_AntennaPorts, int pusch_AntennaPorts,
// SSB Table Configuration
uint32_t absolute_diff = (*scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencySSB - scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencyPointA);
const int scaling_5khz = scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencyPointA < 600000 ? 3 : 1;
int sco = (absolute_diff*scaling_5khz) % 24;
int sco = (absolute_diff/scaling_5khz) % 24;
if(frequency_range == FR2)
sco >>= 1; // this assumes 120kHz SCS for SSB and subCarrierSpacingCommon (only option supported by OAI for
const int scs_scaling = frequency_range == FR2 ? 1 << (*scc->ssbSubcarrierSpacing - 2) : 1 << *scc->ssbSubcarrierSpacing;
@@ -360,7 +360,7 @@ void config_common(int Mod_idP, int pdsch_AntennaPorts, int pusch_AntennaPorts,
cfg->ssb_table.ssb_mask_list[1].ssb_mask.value = 0;
break;
case 2 :
cfg->ssb_table.ssb_mask_list[0].ssb_mask.value = scc->ssb_PositionsInBurst->choice.mediumBitmap.buf[0]<<24;
cfg->ssb_table.ssb_mask_list[0].ssb_mask.value = ((uint32_t) scc->ssb_PositionsInBurst->choice.mediumBitmap.buf[0]) << 24;
cfg->ssb_table.ssb_mask_list[1].ssb_mask.value = 0;
break;
case 3 :
+83 -224
View File
@@ -398,7 +398,7 @@ void schedule_nr_prach(module_id_t module_idP, frame_t frameP, sub_frame_t slotP
void nr_schedule_msg2(uint16_t rach_frame, uint16_t rach_slot,
uint16_t *msg2_frame, uint16_t *msg2_slot,
NR_ServingCellConfigCommon_t *scc,
int mu, NR_ServingCellConfigCommon_t *scc,
frame_type_t frame_type,
uint16_t monitoring_slot_period,
uint16_t monitoring_offset,uint8_t beam_index,
@@ -407,10 +407,9 @@ void nr_schedule_msg2(uint16_t rach_frame, uint16_t rach_slot,
// preferentially we schedule the msg2 in the mixed slot or in the last dl slot
// if they are allowed by search space configuration
uint8_t mu = *scc->ssbSubcarrierSpacing;
uint8_t response_window = scc->uplinkConfigCommon->initialUplinkBWP->rach_ConfigCommon->choice.setup->rach_ConfigGeneric.ra_ResponseWindow;
uint8_t slot_window;
const int n_slots_frame = nr_slots_per_frame[*scc->ssbSubcarrierSpacing];
const int n_slots_frame = nr_slots_per_frame[mu];
const NR_TDD_UL_DL_Pattern_t *tdd = scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL;
// number of mixed slot or of last dl slot if there is no mixed slot
uint8_t last_dl_slot_period = n_slots_frame-1;
@@ -516,7 +515,6 @@ void nr_initiate_ra_proc(module_id_t module_idP,
int16_t timing_offset){
uint8_t ul_carrier_id = 0; // 0 for NUL 1 for SUL
NR_SearchSpace_t *ss;
uint16_t msg2_frame, msg2_slot,monitoring_slot_period,monitoring_offset;
gNB_MAC_INST *nr_mac = RC.nrmac[module_idP];
@@ -567,20 +565,8 @@ void nr_initiate_ra_proc(module_id_t module_idP,
else
ra_rnti = 1 + symbol + (slotP * 14) + (freq_index * 14 * 80) + (ul_carrier_id * 14 * 80 * 8);
// This should be handled differently when we use the initialBWP for RA
ra->dl_bwp_id = 0;//TODO
ra->ul_bwp_id = 0;
NR_BWP_Downlink_t *bwp=NULL;
if (ra->CellGroup && ra->CellGroup->spCellConfig && ra->CellGroup->spCellConfig->spCellConfigDedicated) {
if (ra->CellGroup->spCellConfig->spCellConfigDedicated->firstActiveDownlinkBWP_Id &&
ra->CellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList) {
ra->dl_bwp_id = *ra->CellGroup->spCellConfig->spCellConfigDedicated->firstActiveDownlinkBWP_Id;
bwp = ra->CellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList->list.array[ra->dl_bwp_id - 1];
}
if (ra->CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig &&
ra->CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->firstActiveUplinkBWP_Id)
ra->ul_bwp_id = *ra->CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->firstActiveUplinkBWP_Id;
}
// Configure RA BWP
configure_UE_BWP(nr_mac, scc, NULL, ra, NULL);
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_INITIATE_RA_PROC, 1);
@@ -611,37 +597,6 @@ void nr_initiate_ra_proc(module_id_t module_idP,
ra->timing_offset = timing_offset;
ra->preamble_slot = slotP;
NR_SearchSpaceId_t ra_SearchSpace = 0;
struct NR_PDCCH_ConfigCommon__commonSearchSpaceList *commonSearchSpaceList = NULL;
NR_BWP_t *genericParameters = NULL;
if(bwp) {
commonSearchSpaceList = bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->commonSearchSpaceList;
ra_SearchSpace = *bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->ra_SearchSpace;
genericParameters = &bwp->bwp_Common->genericParameters;
} else {
commonSearchSpaceList = scc->downlinkConfigCommon->initialDownlinkBWP->pdcch_ConfigCommon->choice.setup->commonSearchSpaceList;
ra_SearchSpace = *scc->downlinkConfigCommon->initialDownlinkBWP->pdcch_ConfigCommon->choice.setup->ra_SearchSpace;
genericParameters = &scc->downlinkConfigCommon->initialDownlinkBWP->genericParameters;
}
AssertFatal(commonSearchSpaceList->list.count > 0, "common SearchSpace list has 0 elements\n");
// Common SearchSpace list
for (int i = 0; i < commonSearchSpaceList->list.count; i++) {
ss = commonSearchSpaceList->list.array[i];
if (ss->searchSpaceId == ra_SearchSpace)
ra->ra_ss = ss;
}
AssertFatal(ra->ra_ss!=NULL,"SearchSpace cannot be null for RA\n");
ra->coreset = get_coreset(nr_mac, scc, bwp, ra->ra_ss, NR_SearchSpace__searchSpaceType_PR_common);
ra->sched_pdcch = set_pdcch_structure(nr_mac,
ra->ra_ss,
ra->coreset,
scc,
genericParameters,
&nr_mac->type0_PDCCH_CSS_config[ra->beam_id]);
// retrieving ra pdcch monitoring period and offset
find_monitoring_periodicity_offset_common(ra->ra_ss, &monitoring_slot_period, &monitoring_offset);
@@ -649,6 +604,7 @@ void nr_initiate_ra_proc(module_id_t module_idP,
slotP,
&msg2_frame,
&msg2_slot,
ra->DL_BWP.scs,
scc,
frame_type,
monitoring_slot_period,
@@ -656,7 +612,7 @@ void nr_initiate_ra_proc(module_id_t module_idP,
beam_index,
cc->num_active_ssb,
nr_mac->tdd_beam_association,
nr_mac->if_inst->sl_ahead);
nr_mac->if_inst->sl_ahead);
ra->Msg2_frame = msg2_frame;
ra->Msg2_slot = msg2_slot;
@@ -738,22 +694,10 @@ void nr_generate_Msg3_retransmission(module_id_t module_idP, int CC_id, frame_t
gNB_MAC_INST *nr_mac = RC.nrmac[module_idP];
NR_COMMON_channels_t *cc = &nr_mac->common_channels[CC_id];
NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon;
NR_UE_UL_BWP_t *ul_bwp = &ra->UL_BWP;
NR_BWP_Uplink_t *ubwp = NULL;
NR_BWP_UplinkDedicated_t *ubwpd = NULL;
NR_PUSCH_TimeDomainResourceAllocationList_t *pusch_TimeDomainAllocationList = NULL;
NR_BWP_t *genericParameters = NULL;
if(ra->CellGroup) {
ubwp = ra->CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->uplinkBWP_ToAddModList->list.array[ra->ul_bwp_id-1];
ubwpd = ra->CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP;
genericParameters = &ubwp->bwp_Common->genericParameters;
pusch_TimeDomainAllocationList = ubwp->bwp_Common->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList;
} else {
genericParameters = &scc->uplinkConfigCommon->initialUplinkBWP->genericParameters;
pusch_TimeDomainAllocationList = scc->uplinkConfigCommon->initialUplinkBWP->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList;
}
int mu = genericParameters->subcarrierSpacing;
NR_PUSCH_TimeDomainResourceAllocationList_t *pusch_TimeDomainAllocationList = ul_bwp->tdaList;
int mu = ul_bwp->scs;
uint8_t K2 = *pusch_TimeDomainAllocationList->list.array[ra->Msg3_tda_id]->k2;
const int sched_frame = frame + (slot + K2 >= nr_slots_per_frame[mu]);
const int sched_slot = (slot + K2) % nr_slots_per_frame[mu];
@@ -763,7 +707,7 @@ void nr_generate_Msg3_retransmission(module_id_t module_idP, int CC_id, frame_t
int16_t *tdd_beam_association = nr_mac->tdd_beam_association;
if (*scc->downlinkConfigCommon->frequencyInfoDL->frequencyBandList.list.array[0] >= 257) {
// FR2
const int n_slots_frame = nr_slots_per_frame[*scc->ssbSubcarrierSpacing];
const int n_slots_frame = nr_slots_per_frame[mu];
const NR_TDD_UL_DL_Pattern_t *tdd = scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL;
AssertFatal(tdd,"Dynamic TDD not handled yet\n");
uint8_t tdd_period_slot = n_slots_frame/get_nb_periods_per_frame(tdd->dl_UL_TransmissionPeriodicity);
@@ -775,12 +719,11 @@ void nr_generate_Msg3_retransmission(module_id_t module_idP, int CC_id, frame_t
tdd_beam_association[num_tdd_period] = ra->beam_id;
}
int scs = scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.subcarrierSpacing;
int fh = 0;
int startSymbolAndLength = scc->uplinkConfigCommon->initialUplinkBWP->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList->list.array[ra->Msg3_tda_id]->startSymbolAndLength;
int startSymbolAndLength = pusch_TimeDomainAllocationList->list.array[ra->Msg3_tda_id]->startSymbolAndLength;
int StartSymbolIndex, NrOfSymbols;
SLIV2SL(startSymbolAndLength, &StartSymbolIndex, &NrOfSymbols);
int mappingtype = scc->uplinkConfigCommon->initialUplinkBWP->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList->list.array[ra->Msg3_tda_id]->mappingType;
int mappingtype = pusch_TimeDomainAllocationList->list.array[ra->Msg3_tda_id]->mappingType;
uint16_t *vrb_map_UL = &RC.nrmac[module_idP]->common_channels[CC_id].vrb_map_UL[sched_slot * MAX_BWP_SIZE];
@@ -821,7 +764,7 @@ void nr_generate_Msg3_retransmission(module_id_t module_idP, int CC_id, frame_t
fill_msg3_pusch_pdu(pusch_pdu, scc,
ra->msg3_round,
startSymbolAndLength,
ra->rnti, scs,
ra->rnti, mu,
BWPSize, BWPStart,
mappingtype, fh,
rbStart, ra->msg3_nb_rb);
@@ -843,7 +786,7 @@ void nr_generate_Msg3_retransmission(module_id_t module_idP, int CC_id, frame_t
ul_dci_request_pdu->PDUSize = (uint8_t)(2+sizeof(nfapi_nr_dl_tti_pdcch_pdu));
pdcch_pdu_rel15 = &ul_dci_request_pdu->pdcch_pdu.pdcch_pdu_rel15;
ul_dci_req->numPdus += 1;
nr_configure_pdcch(pdcch_pdu_rel15, coreset, genericParameters, &ra->sched_pdcch);
nr_configure_pdcch(pdcch_pdu_rel15, coreset, false, &ra->sched_pdcch);
nr_mac->pdcch_pdu_idx[CC_id][coresetid] = pdcch_pdu_rel15;
}
@@ -883,26 +826,23 @@ void nr_generate_Msg3_retransmission(module_id_t module_idP, int CC_id, frame_t
const NR_SIB1_t *sib1 = cc->sib1 ? cc->sib1->message.choice.c1->choice.systemInformationBlockType1 : NULL;
config_uldci(sib1,
ubwp,
ubwpd,
scc,
pusch_pdu,
&uldci_payload,
NR_UL_DCI_FORMAT_0_0,
ra->Msg3_tda_id,
ra->msg3_TPC,
0, // not used in format 0_0
ra->ul_bwp_id);
&ra->UL_BWP);
fill_dci_pdu_rel15(scc,
ra->CellGroup,
&ra->DL_BWP,
dci_pdu,
&uldci_payload,
NR_UL_DCI_FORMAT_0_0,
NR_RNTI_TC,
pusch_pdu->bwp_size,
ra->ul_bwp_id,
coresetid,
ul_bwp->bwp_id,
coreset,
nr_mac->cset0_bwp_size);
// Mark the corresponding RBs as used
@@ -923,13 +863,11 @@ void nr_generate_Msg3_retransmission(module_id_t module_idP, int CC_id, frame_t
ra->Msg3_slot = sched_slot;
}
}
void nr_get_Msg3alloc(module_id_t module_id,
int CC_id,
NR_ServingCellConfigCommon_t *scc,
NR_BWP_Uplink_t *ubwp,
sub_frame_t current_slot,
frame_t current_frame,
NR_RA_t *ra,
@@ -938,21 +876,18 @@ void nr_get_Msg3alloc(module_id_t module_id,
// msg3 is scheduled in mixed slot in the following TDD period
uint16_t msg3_nb_rb = 8; // sdu has 6 or 8 bytes
frame_type_t frame_type = RC.nrmac[module_id]->common_channels->frame_type;
int mu = ubwp ?
ubwp->bwp_Common->genericParameters.subcarrierSpacing :
scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.subcarrierSpacing;
NR_UE_UL_BWP_t *ul_bwp = &ra->UL_BWP;
int mu = ul_bwp->scs;
int StartSymbolIndex = 0;
int NrOfSymbols = 0;
int startSymbolAndLength = 0;
int temp_slot = 0;
ra->Msg3_tda_id = 16; // initialization to a value above limit
NR_PUSCH_TimeDomainResourceAllocationList_t *pusch_TimeDomainAllocationList= ubwp ?
ubwp->bwp_Common->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList:
scc->uplinkConfigCommon->initialUplinkBWP->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList;
NR_PUSCH_TimeDomainResourceAllocationList_t *pusch_TimeDomainAllocationList = ul_bwp->tdaList;
const NR_TDD_UL_DL_Pattern_t *tdd = scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL;
const int n_slots_frame = nr_slots_per_frame[mu];
@@ -1016,10 +951,9 @@ void nr_get_Msg3alloc(module_id_t module_id,
int bwpSize = NRRIV2BW(scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
int bwpStart = NRRIV2PRBOFFSET(scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
if (ra->CellGroup) {
NR_BWP_Uplink_t *ubwp = ra->CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->uplinkBWP_ToAddModList->list.array[ra->ul_bwp_id - 1];
int act_bwp_start = NRRIV2PRBOFFSET(ubwp->bwp_Common->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
int act_bwp_size = NRRIV2BW(ubwp->bwp_Common->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
if (bwpSize != ul_bwp->BWPSize || bwpStart != ul_bwp->BWPStart) {
int act_bwp_start = ul_bwp->BWPStart;
int act_bwp_size = ul_bwp->BWPSize;
if (!((bwpStart >= act_bwp_start) && ((bwpStart+bwpSize) <= (act_bwp_start+act_bwp_size))))
bwpStart = act_bwp_start;
}
@@ -1054,7 +988,6 @@ void fill_msg3_pusch_pdu(nfapi_nr_pusch_pdu_t *pusch_pdu,
int mappingtype, int fh,
int msg3_first_rb, int msg3_nb_rb) {
int start_symbol_index,nr_of_symbols;
SLIV2SL(startSymbolAndLength, &start_symbol_index, &nr_of_symbols);
@@ -1090,13 +1023,16 @@ void fill_msg3_pusch_pdu(nfapi_nr_pusch_pdu_t *pusch_pdu,
pusch_pdu->vrb_to_prb_mapping = 0;
pusch_pdu->frequency_hopping = fh;
//pusch_pdu->tx_direct_current_location;//The uplink Tx Direct Current location for the carrier. Only values in the value range of this field between 0 and 3299, which indicate the subcarrier index within the carrier corresponding 1o the numerology of the corresponding uplink BWP and value 3300, which indicates "Outside the carrier" and value 3301, which indicates "Undetermined position within the carrier" are used. [TS38.331, UplinkTxDirectCurrentBWP IE]
//pusch_pdu->tx_direct_current_location;
//The uplink Tx Direct Current location for the carrier. Only values in the value range of this field between 0 and 3299,
//which indicate the subcarrier index within the carrier corresponding 1o the numerology of the corresponding uplink BWP and value 3300,
//which indicates "Outside the carrier" and value 3301, which indicates "Undetermined position within the carrier" are used. [TS38.331, UplinkTxDirectCurrentBWP IE]
pusch_pdu->uplink_frequency_shift_7p5khz = 0;
//Resource Allocation in time domain
pusch_pdu->start_symbol_index = start_symbol_index;
pusch_pdu->nr_of_symbols = nr_of_symbols;
//Optional Data only included if indicated in pduBitmap
pusch_pdu->pusch_data.rv_index = nr_rv_round_map[round];
pusch_pdu->pusch_data.rv_index = nr_rv_round_map[round%4];
pusch_pdu->pusch_data.harq_process_id = 0;
pusch_pdu->pusch_data.new_data_indicator = 1;
pusch_pdu->pusch_data.num_cb = 0;
@@ -1126,9 +1062,10 @@ void fill_msg3_pusch_pdu(nfapi_nr_pusch_pdu_t *pusch_pdu,
void nr_add_msg3(module_id_t module_idP, int CC_id, frame_t frameP, sub_frame_t slotP, NR_RA_t *ra, uint8_t *RAR_pdu)
{
gNB_MAC_INST *mac = RC.nrmac[module_idP];
NR_COMMON_channels_t *cc = &mac->common_channels[CC_id];
NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon;
gNB_MAC_INST *mac = RC.nrmac[module_idP];
NR_COMMON_channels_t *cc = &mac->common_channels[CC_id];
NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon;
NR_UE_UL_BWP_t *ul_bwp = &ra->UL_BWP;
if (ra->state == RA_IDLE) {
LOG_W(NR_MAC,"RA is not active for RA %X. skipping msg3 scheduling\n", ra->rnti);
@@ -1161,20 +1098,11 @@ void nr_add_msg3(module_id_t module_idP, int CC_id, frame_t frameP, sub_frame_t
nfapi_nr_pusch_pdu_t *pusch_pdu = &future_ul_tti_req->pdus_list[future_ul_tti_req->n_pdus].pusch_pdu;
memset(pusch_pdu, 0, sizeof(nfapi_nr_pusch_pdu_t));
int ibwp_size = NRRIV2BW(scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
int scs = scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.subcarrierSpacing;
int fh = 0;
int startSymbolAndLength = scc->uplinkConfigCommon->initialUplinkBWP->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList->list.array[ra->Msg3_tda_id]->startSymbolAndLength;
int mappingtype = scc->uplinkConfigCommon->initialUplinkBWP->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList->list.array[ra->Msg3_tda_id]->mappingType;
if (ra->CellGroup) {
NR_BWP_Uplink_t *ubwp = ra->CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->uplinkBWP_ToAddModList->list.array[ra->ul_bwp_id - 1];
startSymbolAndLength = ubwp->bwp_Common->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList->list.array[ra->Msg3_tda_id]->startSymbolAndLength;
mappingtype = ubwp->bwp_Common->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList->list.array[ra->Msg3_tda_id]->mappingType;
scs = ubwp->bwp_Common->genericParameters.subcarrierSpacing;
fh = ubwp->bwp_Dedicated->pusch_Config->choice.setup->frequencyHopping ? 1 : 0;
}
const int ibwp_size = NRRIV2BW(scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
const int scs = ul_bwp->scs;
const int fh = (ul_bwp->pusch_Config && ul_bwp->pusch_Config->frequencyHopping) ? 1 : 0;
const int startSymbolAndLength = ul_bwp->tdaList->list.array[ra->Msg3_tda_id]->startSymbolAndLength;
const int mappingtype = ul_bwp->tdaList->list.array[ra->Msg3_tda_id]->mappingType;
LOG_D(NR_MAC, "Frame %d, Slot %d Adding Msg3 UL Config Request for (%d,%d) : (%d,%d,%d) for rnti: %d\n",
frameP,
@@ -1203,6 +1131,7 @@ void nr_generate_Msg2(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
gNB_MAC_INST *nr_mac = RC.nrmac[module_idP];
NR_COMMON_channels_t *cc = &nr_mac->common_channels[CC_id];
NR_UE_DL_BWP_t *dl_bwp = &ra->DL_BWP;
if ((ra->Msg2_frame == frameP) && (ra->Msg2_slot == slotP)) {
@@ -1213,30 +1142,13 @@ void nr_generate_Msg2(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon;
NR_SearchSpace_t *ss = ra->ra_ss;
NR_BWP_Downlink_t *bwp = NULL;
NR_ControlResourceSet_t *coreset = NULL;
NR_BWP_t *genericParameters = NULL;
NR_PDSCH_TimeDomainResourceAllocationList_t *pdsch_TimeDomainAllocationList=NULL;
if (ra->CellGroup &&
ra->CellGroup->spCellConfig &&
ra->CellGroup->spCellConfig->spCellConfigDedicated &&
ra->CellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList &&
ra->CellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList->list.array[ra->dl_bwp_id-1]) {
bwp = ra->CellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList->list.array[ra->dl_bwp_id-1];
genericParameters = &bwp->bwp_Common->genericParameters;
pdsch_TimeDomainAllocationList = bwp->bwp_Common->pdsch_ConfigCommon->choice.setup->pdsch_TimeDomainAllocationList;
}
else {
genericParameters= &scc->downlinkConfigCommon->initialDownlinkBWP->genericParameters;
pdsch_TimeDomainAllocationList = scc->downlinkConfigCommon->initialDownlinkBWP->pdsch_ConfigCommon->choice.setup->pdsch_TimeDomainAllocationList;
}
NR_PDSCH_TimeDomainResourceAllocationList_t *pdsch_TimeDomainAllocationList = dl_bwp->tdaList;
long BWPStart = 0;
long BWPSize = 0;
NR_Type0_PDCCH_CSS_config_t *type0_PDCCH_CSS_config = NULL;
if(*ss->controlResourceSetId!=0) {
BWPStart = NRRIV2PRBOFFSET(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
BWPStart = dl_bwp->BWPStart;
BWPSize = NRRIV2BW(scc->downlinkConfigCommon->initialDownlinkBWP->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
} else {
type0_PDCCH_CSS_config = &nr_mac->type0_PDCCH_CSS_config[ra->beam_id];
@@ -1251,7 +1163,7 @@ void nr_generate_Msg2(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
SLIV2SL(startSymbolAndLength, &startSymbolIndex, &nrOfSymbols);
AssertFatal(startSymbolIndex >= 0, "StartSymbolIndex is negative\n");
coreset = ra->coreset;
NR_ControlResourceSet_t *coreset = ra->coreset;
AssertFatal(coreset!=NULL,"Coreset cannot be null for RA-Msg2\n");
@@ -1303,7 +1215,6 @@ void nr_generate_Msg2(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
// look up the PDCCH PDU for this CC, BWP, and CORESET. If it does not exist, create it. This is especially
// important if we have multiple RAs, and the DLSCH has to reuse them, so we need to mark them
const int bwpid = bwp ? bwp->bwp_Id : 0;
const int coresetid = coreset->controlResourceSetId;
nfapi_nr_dl_tti_pdcch_pdu_rel15_t *pdcch_pdu_rel15 = nr_mac->pdcch_pdu_idx[CC_id][coresetid];
if (!pdcch_pdu_rel15) {
@@ -1313,7 +1224,7 @@ void nr_generate_Msg2(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
dl_tti_pdcch_pdu->PDUSize = (uint8_t)(2 + sizeof(nfapi_nr_dl_tti_pdcch_pdu));
dl_req->nPDUs += 1;
pdcch_pdu_rel15 = &dl_tti_pdcch_pdu->pdcch_pdu.pdcch_pdu_rel15;
nr_configure_pdcch(pdcch_pdu_rel15, coreset, genericParameters, &ra->sched_pdcch);
nr_configure_pdcch(pdcch_pdu_rel15, coreset, false, &ra->sched_pdcch);
nr_mac->pdcch_pdu_idx[CC_id][coresetid] = pdcch_pdu_rel15;
}
@@ -1331,37 +1242,22 @@ void nr_generate_Msg2(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
// information to data and is reset every slot.
const int pduindex = nr_mac->pdu_index[CC_id]++;
uint8_t mcsTableIdx = 0;
if (bwp &&
bwp->bwp_Dedicated &&
bwp->bwp_Dedicated->pdsch_Config &&
bwp->bwp_Dedicated->pdsch_Config->choice.setup &&
bwp->bwp_Dedicated->pdsch_Config->choice.setup->mcs_Table) {
if (*bwp->bwp_Dedicated->pdsch_Config->choice.setup->mcs_Table == 0)
mcsTableIdx = 1;
else
mcsTableIdx = 2;
}
else mcsTableIdx = 0;
NR_PDSCH_Config_t *pdsch_Config = dl_bwp->pdsch_Config;
uint8_t mcsTableIdx = dl_bwp->mcsTableIdx;
int dmrsConfigType=0;
if (bwp &&
bwp->bwp_Dedicated &&
bwp->bwp_Dedicated->pdsch_Config &&
bwp->bwp_Dedicated->pdsch_Config->choice.setup &&
bwp->bwp_Dedicated->pdsch_Config->choice.setup->dmrs_DownlinkForPDSCH_MappingTypeA &&
bwp->bwp_Dedicated->pdsch_Config->choice.setup->dmrs_DownlinkForPDSCH_MappingTypeA->choice.setup &&
bwp->bwp_Dedicated->pdsch_Config->choice.setup->dmrs_DownlinkForPDSCH_MappingTypeA->choice.setup->dmrs_Type)
if (pdsch_Config &&
pdsch_Config->dmrs_DownlinkForPDSCH_MappingTypeA &&
pdsch_Config->dmrs_DownlinkForPDSCH_MappingTypeA->choice.setup &&
pdsch_Config->dmrs_DownlinkForPDSCH_MappingTypeA->choice.setup->dmrs_Type)
dmrsConfigType = 1;
NR_PDSCH_Config_t *pdsch_config = bwp && bwp->bwp_Dedicated && bwp->bwp_Dedicated->pdsch_Config ? bwp->bwp_Dedicated->pdsch_Config->choice.setup : NULL;
pdsch_pdu_rel15->pduBitmap = 0;
pdsch_pdu_rel15->rnti = ra->RA_rnti;
pdsch_pdu_rel15->pduIndex = pduindex;
pdsch_pdu_rel15->BWPSize = BWPSize;
pdsch_pdu_rel15->BWPStart = BWPStart;
pdsch_pdu_rel15->SubcarrierSpacing = genericParameters->subcarrierSpacing;
pdsch_pdu_rel15->SubcarrierSpacing = dl_bwp->scs;
pdsch_pdu_rel15->CyclicPrefix = 0;
pdsch_pdu_rel15->NrOfCodewords = 1;
pdsch_pdu_rel15->mcsTable[0] = mcsTableIdx;
@@ -1381,7 +1277,7 @@ void nr_generate_Msg2(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
pdsch_pdu_rel15->VRBtoPRBMapping = 0;
pdsch_pdu_rel15->StartSymbolIndex = startSymbolIndex;
pdsch_pdu_rel15->NrOfSymbols = nrOfSymbols;
pdsch_pdu_rel15->dlDmrsSymbPos = fill_dmrs_mask(pdsch_config,
pdsch_pdu_rel15->dlDmrsSymbPos = fill_dmrs_mask(pdsch_Config,
nr_mac->common_channels->ServingCellConfigCommon->dmrs_TypeA_Position,
nrOfSymbols,
startSymbolIndex,
@@ -1421,7 +1317,8 @@ void nr_generate_Msg2(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
pdsch_pdu_rel15->TBSize[0] = TBS;
}
int bw_tbslbrm = get_bw_tbslbrm(genericParameters, ra->CellGroup);
int scc_bwpsize = NRRIV2BW(scc->downlinkConfigCommon->initialDownlinkBWP->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
int bw_tbslbrm = get_bw_tbslbrm(scc_bwpsize, ra->CellGroup);
pdsch_pdu_rel15->maintenance_parms_v3.tbSizeLbrmBytes = nr_compute_tbslbrm(mcsTableIdx,
bw_tbslbrm,
1);
@@ -1473,23 +1370,21 @@ void nr_generate_Msg2(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
fill_dci_pdu_rel15(scc,
ra->CellGroup,
dl_bwp,
&pdcch_pdu_rel15->dci_pdu[pdcch_pdu_rel15->numDlDci - 1],
&dci_payload,
NR_DL_DCI_FORMAT_1_0,
NR_RNTI_RA,
BWPSize,
bwpid,
coresetid,
dl_bwp->bwp_id,
coreset,
nr_mac->cset0_bwp_size);
// DL TX request
nfapi_nr_pdu_t *tx_req = &nr_mac->TX_req[CC_id].pdu_list[nr_mac->TX_req[CC_id].Number_of_PDUs];
// Program UL processing for Msg3
NR_BWP_Uplink_t *ubwp = ra->CellGroup ?
ra->CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->uplinkBWP_ToAddModList->list.array[ra->dl_bwp_id-1] :
NULL;
nr_get_Msg3alloc(module_idP, CC_id, scc, ubwp, slotP, frameP, ra, nr_mac->tdd_beam_association);
nr_get_Msg3alloc(module_idP, CC_id, scc, slotP, frameP, ra, nr_mac->tdd_beam_association);
nr_add_msg3(module_idP, CC_id, frameP, slotP, ra, (uint8_t *) &tx_req->TLVs[0].value.direct[0]);
if(ra->cfra) {
@@ -1527,6 +1422,7 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
gNB_MAC_INST *nr_mac = RC.nrmac[module_idP];
NR_COMMON_channels_t *cc = &nr_mac->common_channels[CC_id];
NR_UE_DL_BWP_t *dl_bwp = &ra->DL_BWP;
if (ra->Msg4_frame == frameP && ra->Msg4_slot == slotP ) {
@@ -1536,23 +1432,8 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon;
NR_SearchSpace_t *ss = ra->ra_ss;
NR_BWP_Downlink_t *bwp = NULL;
NR_ControlResourceSet_t *coreset = NULL;
NR_PDSCH_TimeDomainResourceAllocationList_t *pdsch_TimeDomainAllocationList=NULL;
if (ra->CellGroup &&
ra->CellGroup->spCellConfig &&
ra->CellGroup->spCellConfig->spCellConfigDedicated &&
ra->CellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList &&
ra->CellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList->list.array[ra->dl_bwp_id-1]) {
bwp = ra->CellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList->list.array[ra->dl_bwp_id-1];
pdsch_TimeDomainAllocationList = bwp->bwp_Common->pdsch_ConfigCommon->choice.setup->pdsch_TimeDomainAllocationList;
}
else {
pdsch_TimeDomainAllocationList = scc->downlinkConfigCommon->initialDownlinkBWP->pdsch_ConfigCommon->choice.setup->pdsch_TimeDomainAllocationList;
}
coreset = ra->coreset;
NR_ControlResourceSet_t *coreset = ra->coreset;
NR_PDSCH_TimeDomainResourceAllocationList_t *pdsch_TimeDomainAllocationList = dl_bwp->tdaList;
AssertFatal(coreset!=NULL,"Coreset cannot be null for RA-Msg4\n");
@@ -1571,14 +1452,12 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
LOG_I(NR_MAC,"Generate msg4, rnti: %04x\n", ra->rnti);
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_BWP_t *genericParameters = bwp ? & bwp->bwp_Common->genericParameters : &scc->downlinkConfigCommon->initialDownlinkBWP->genericParameters;
long BWPStart = 0;
long BWPSize = 0;
NR_Type0_PDCCH_CSS_config_t *type0_PDCCH_CSS_config = NULL;
if(*ss->controlResourceSetId!=0) {
BWPStart = NRRIV2PRBOFFSET(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
BWPSize = NRRIV2BW(scc->downlinkConfigCommon->initialDownlinkBWP->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
BWPStart = dl_bwp->BWPStart;
BWPSize = dl_bwp->BWPSize;
} else {
type0_PDCCH_CSS_config = &nr_mac->type0_PDCCH_CSS_config[ra->beam_id];
BWPStart = type0_PDCCH_CSS_config->cset_start_rb;
@@ -1629,7 +1508,7 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
}
const int delta_PRI=0;
int r_pucch = nr_get_pucch_resource(coreset, sched_ctrl->active_ubwp, NULL, CCEIndex);
int r_pucch = nr_get_pucch_resource(coreset, ra->UL_BWP.pucch_Config, CCEIndex);
LOG_D(NR_MAC,"[RAPROC] Msg4 r_pucch %d (CCEIndex %d, nb_of_candidates %d, delta_PRI %d)\n", r_pucch, CCEIndex, nr_of_candidates, delta_PRI);
@@ -1688,7 +1567,13 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
uint16_t N_DMRS_SLOT = get_num_dmrs(dlDmrsSymbPos);
long dmrsConfigType = bwp!=NULL ? (bwp->bwp_Dedicated->pdsch_Config->choice.setup->dmrs_DownlinkForPDSCH_MappingTypeA->choice.setup->dmrs_Type == NULL ? 0 : 1) : 0;
NR_PDSCH_Config_t *pdsch_Config = dl_bwp->pdsch_Config;
int dmrsConfigType=0;
if (pdsch_Config &&
pdsch_Config->dmrs_DownlinkForPDSCH_MappingTypeA &&
pdsch_Config->dmrs_DownlinkForPDSCH_MappingTypeA->choice.setup &&
pdsch_Config->dmrs_DownlinkForPDSCH_MappingTypeA->choice.setup->dmrs_Type)
dmrsConfigType = 1;
nr_mac->sched_ctrlCommon->pdsch_semi_static.numDmrsCdmGrpsNoData = 2;
if (nrOfSymbols == 2) {
@@ -1708,18 +1593,7 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
N_PRB_DMRS = nr_mac->sched_ctrlCommon->pdsch_semi_static.numDmrsCdmGrpsNoData * 4;
}
uint8_t mcsTableIdx = 0;
if (bwp &&
bwp->bwp_Dedicated &&
bwp->bwp_Dedicated->pdsch_Config &&
bwp->bwp_Dedicated->pdsch_Config->choice.setup &&
bwp->bwp_Dedicated->pdsch_Config->choice.setup->mcs_Table) {
if (*bwp->bwp_Dedicated->pdsch_Config->choice.setup->mcs_Table == 0)
mcsTableIdx = 1;
else
mcsTableIdx = 2;
}
else mcsTableIdx = 0;
uint8_t mcsTableIdx = dl_bwp->mcsTableIdx;
int rbStart = 0;
int rbSize = 0;
@@ -1764,7 +1638,6 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
// look up the PDCCH PDU for this CC, BWP, and CORESET. If it does not exist, create it. This is especially
// important if we have multiple RAs, and the DLSCH has to reuse them, so we need to mark them
const int bwpid = bwp ? bwp->bwp_Id : 0;
const int coresetid = coreset->controlResourceSetId;
nfapi_nr_dl_tti_pdcch_pdu_rel15_t *pdcch_pdu_rel15 = nr_mac->pdcch_pdu_idx[CC_id][coresetid];
if (!pdcch_pdu_rel15) {
@@ -1774,7 +1647,7 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
dl_tti_pdcch_pdu->PDUSize = (uint8_t)(2 + sizeof(nfapi_nr_dl_tti_pdcch_pdu));
dl_req->nPDUs += 1;
pdcch_pdu_rel15 = &dl_tti_pdcch_pdu->pdcch_pdu.pdcch_pdu_rel15;
nr_configure_pdcch(pdcch_pdu_rel15, coreset, genericParameters, &ra->sched_pdcch);
nr_configure_pdcch(pdcch_pdu_rel15, coreset, false, &ra->sched_pdcch);
nr_mac->pdcch_pdu_idx[CC_id][coresetid] = pdcch_pdu_rel15;
}
@@ -1796,7 +1669,7 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
pdsch_pdu_rel15->pduIndex = pduindex;
pdsch_pdu_rel15->BWPSize = BWPSize;
pdsch_pdu_rel15->BWPStart = BWPStart;
pdsch_pdu_rel15->SubcarrierSpacing = genericParameters->subcarrierSpacing;
pdsch_pdu_rel15->SubcarrierSpacing = dl_bwp->scs;
pdsch_pdu_rel15->CyclicPrefix = 0;
pdsch_pdu_rel15->NrOfCodewords = 1;
int R = nr_get_code_rate_dl(mcsIndex,mcsTableIdx);
@@ -1804,7 +1677,7 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
pdsch_pdu_rel15->qamModOrder[0] = 2;
pdsch_pdu_rel15->mcsIndex[0] = mcsIndex;
pdsch_pdu_rel15->mcsTable[0] = mcsTableIdx;
pdsch_pdu_rel15->rvIndex[0] = nr_rv_round_map[harq->round];
pdsch_pdu_rel15->rvIndex[0] = nr_rv_round_map[harq->round%4];
pdsch_pdu_rel15->dataScramblingId = *scc->physCellId;
pdsch_pdu_rel15->nrOfLayers = 1;
pdsch_pdu_rel15->transmissionScheme = 0;
@@ -1825,7 +1698,8 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
int x_Overhead = 0;
nr_get_tbs_dl(&dl_tti_pdsch_pdu->pdsch_pdu, x_Overhead, pdsch_pdu_rel15->numDmrsCdmGrpsNoData, tb_scaling);
int bw_tbslbrm = get_bw_tbslbrm(genericParameters, ra->CellGroup);
int scc_bwpsize = NRRIV2BW(scc->downlinkConfigCommon->initialDownlinkBWP->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
int bw_tbslbrm = get_bw_tbslbrm(scc_bwpsize, ra->CellGroup);
pdsch_pdu_rel15->maintenance_parms_v3.tbSizeLbrmBytes = nr_compute_tbslbrm(mcsTableIdx,
bw_tbslbrm,
1);
@@ -1890,13 +1764,14 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
fill_dci_pdu_rel15(scc,
ra->CellGroup,
dl_bwp,
&pdcch_pdu_rel15->dci_pdu[pdcch_pdu_rel15->numDlDci - 1],
&dci_payload,
NR_DL_DCI_FORMAT_1_0,
NR_RNTI_TC,
pdsch_pdu_rel15->BWPSize,
bwpid,
coresetid,
dl_bwp->bwp_id,
coreset,
nr_mac->cset0_bwp_size);
// Add padding header and zero rest out if there is space left
@@ -1962,19 +1837,8 @@ void nr_generate_Msg4(module_id_t module_idP, int CC_id, frame_t frameP, sub_fra
harq->round = 0;
harq->ndi ^= 1;
// Pause scheduling according to:
// 3GPP TS 38.331 Section 12 Table 12.1-1: UE performance requirements for RRC procedures for UEs
const NR_COMMON_channels_t *common_channels = &RC.nrmac[module_idP]->common_channels[0];
const NR_SIB1_t *sib1 = common_channels->sib1 ? common_channels->sib1->message.choice.c1->choice.systemInformationBlockType1 : NULL;
const NR_ServingCellConfig_t *servingCellConfig = UE->CellGroup ? UE->CellGroup->spCellConfig->spCellConfigDedicated : NULL;
NR_BWP_t *genericParameters = get_dl_bwp_genericParameters(sched_ctrl->active_bwp,
common_channels->ServingCellConfigCommon,
sib1);
uint32_t delay_ms = servingCellConfig && servingCellConfig->downlinkBWP_ToAddModList ?
NR_RRC_SETUP_DELAY_MS + NR_RRC_BWP_SWITCHING_DELAY_MS : NR_RRC_SETUP_DELAY_MS;
sched_ctrl->rrc_processing_timer = (delay_ms << genericParameters->subcarrierSpacing);
LOG_I(NR_MAC, "(%d.%d) Activating RRC processing timer for UE %04x with %d ms\n", frameP, slotP, UE->rnti, delay_ms);
sched_ctrl->rrc_processing_timer = 1; // No need to wait at this point in time, setting it to 1 just to enter in function nr_mac_update_timers
LOG_I(NR_MAC, "(%d.%d) Activating RRC processing timer for UE %04x with %d ms\n", frameP, slotP, UE->rnti, 1);
// Reset uplink failure flags/counters/timers at MAC so gNB will resume again scheduling resources for this UE
UE->UE_sched_ctrl.pusch_consecutive_dtx_cnt = 0;
@@ -2006,16 +1870,11 @@ void nr_check_Msg4_Ack(module_id_t module_id, int CC_id, frame_t frame, sub_fram
// Pause scheduling according to:
// 3GPP TS 38.331 Section 12 Table 12.1-1: UE performance requirements for RRC procedures for UEs
const NR_COMMON_channels_t *common_channels = &RC.nrmac[module_id]->common_channels[0];
const NR_SIB1_t *sib1 = common_channels->sib1 ? common_channels->sib1->message.choice.c1->choice.systemInformationBlockType1 : NULL;
const NR_ServingCellConfig_t *servingCellConfig = UE->CellGroup ? UE->CellGroup->spCellConfig->spCellConfigDedicated : NULL;
NR_BWP_t *genericParameters = get_dl_bwp_genericParameters(sched_ctrl->active_bwp,
common_channels->ServingCellConfigCommon,
sib1);
uint32_t delay_ms = servingCellConfig && servingCellConfig->downlinkBWP_ToAddModList ?
NR_RRC_SETUP_DELAY_MS + NR_RRC_BWP_SWITCHING_DELAY_MS : NR_RRC_SETUP_DELAY_MS;
sched_ctrl->rrc_processing_timer = (delay_ms << genericParameters->subcarrierSpacing);
sched_ctrl->rrc_processing_timer = (delay_ms << ra->DL_BWP.scs);
LOG_I(NR_MAC, "(%d.%d) Activating RRC processing timer for UE %04x with %d ms\n", frame, slot, UE->rnti, delay_ms);
} else {
LOG_I(NR_MAC, "(ue rnti 0x%04x) RA Procedure failed at Msg4!\n", ra->rnti);
+14 -12
View File
@@ -285,7 +285,7 @@ uint32_t schedule_control_sib1(module_id_t module_id,
int nrOfSymbols,
uint16_t dlDmrsSymbPos,
uint8_t candidate_idx,
int num_total_bytes) {
uint16_t num_total_bytes) {
gNB_MAC_INST *gNB_mac = RC.nrmac[module_id];
NR_COMMON_channels_t *cc = &gNB_mac->common_channels[CC_id];
@@ -310,7 +310,6 @@ uint32_t schedule_control_sib1(module_id_t module_id,
}
gNB_mac->sched_ctrlCommon->pdsch_semi_static.time_domain_allocation = time_domain_allocation;
gNB_mac->sched_ctrlCommon->pdsch_semi_static.mcsTableIdx = 0;
gNB_mac->sched_ctrlCommon->sched_pdsch.mcs = 0; // starting from mcs 0
gNB_mac->sched_ctrlCommon->num_total_bytes = num_total_bytes;
@@ -347,6 +346,7 @@ uint32_t schedule_control_sib1(module_id_t module_id,
uint8_t N_PRB_DMRS = gNB_mac->sched_ctrlCommon->pdsch_semi_static.numDmrsCdmGrpsNoData * 6;
uint16_t dmrs_length = get_num_dmrs(dlDmrsSymbPos);
LOG_D(MAC,"dlDmrsSymbPos %x\n",dlDmrsSymbPos);
int mcsTableIdx = 0;
int rbSize = 0;
uint32_t TBS = 0;
do {
@@ -358,8 +358,8 @@ uint32_t schedule_control_sib1(module_id_t module_id,
else
break;
}
TBS = nr_compute_tbs(nr_get_Qm_dl(gNB_mac->sched_ctrlCommon->sched_pdsch.mcs, gNB_mac->sched_ctrlCommon->pdsch_semi_static.mcsTableIdx),
nr_get_code_rate_dl(gNB_mac->sched_ctrlCommon->sched_pdsch.mcs, gNB_mac->sched_ctrlCommon->pdsch_semi_static.mcsTableIdx),
TBS = nr_compute_tbs(nr_get_Qm_dl(gNB_mac->sched_ctrlCommon->sched_pdsch.mcs, mcsTableIdx),
nr_get_code_rate_dl(gNB_mac->sched_ctrlCommon->sched_pdsch.mcs, mcsTableIdx),
rbSize, nrOfSymbols, N_PRB_DMRS * dmrs_length,0, 0,1) >> 3;
} while (TBS < gNB_mac->sched_ctrlCommon->num_total_bytes);
@@ -401,7 +401,7 @@ void nr_fill_nfapi_dl_sib1_pdu(int Mod_idP,
gNB_MAC_INST *gNB_mac = RC.nrmac[Mod_idP];
NR_COMMON_channels_t *cc = gNB_mac->common_channels;
NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon;
int mcsTableIdx = 0;
nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdcch_pdu = &dl_req->dl_tti_pdu_list[dl_req->nPDUs];
memset((void*)dl_tti_pdcch_pdu,0,sizeof(nfapi_nr_dl_tti_request_pdu_t));
dl_tti_pdcch_pdu->PDUType = NFAPI_NR_DL_TTI_PDCCH_PDU_TYPE;
@@ -410,7 +410,7 @@ void nr_fill_nfapi_dl_sib1_pdu(int Mod_idP,
nfapi_nr_dl_tti_pdcch_pdu_rel15_t *pdcch_pdu_rel15 = &dl_tti_pdcch_pdu->pdcch_pdu.pdcch_pdu_rel15;
nr_configure_pdcch(pdcch_pdu_rel15,
gNB_mac->sched_ctrlCommon->coreset,
NULL,
true, // sib1
&gNB_mac->sched_ctrlCommon->sched_pdcch);
nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdsch_pdu = &dl_req->dl_tti_pdu_list[dl_req->nPDUs];
@@ -437,7 +437,7 @@ void nr_fill_nfapi_dl_sib1_pdu(int Mod_idP,
pdsch_pdu_rel15->qamModOrder[0] = 2;
pdsch_pdu_rel15->mcsIndex[0] = gNB_mac->sched_ctrlCommon->sched_pdsch.mcs;
pdsch_pdu_rel15->mcsTable[0] = 0;
pdsch_pdu_rel15->rvIndex[0] = nr_rv_round_map[0];
pdsch_pdu_rel15->rvIndex[0] = 0;
pdsch_pdu_rel15->dataScramblingId = *scc->physCellId;
pdsch_pdu_rel15->nrOfLayers = 1;
pdsch_pdu_rel15->transmissionScheme = 0;
@@ -452,9 +452,9 @@ void nr_fill_nfapi_dl_sib1_pdu(int Mod_idP,
pdsch_pdu_rel15->rbSize = gNB_mac->sched_ctrlCommon->sched_pdsch.rbSize;
pdsch_pdu_rel15->VRBtoPRBMapping = 0;
pdsch_pdu_rel15->qamModOrder[0] = nr_get_Qm_dl(gNB_mac->sched_ctrlCommon->sched_pdsch.mcs,
gNB_mac->sched_ctrlCommon->pdsch_semi_static.mcsTableIdx);
mcsTableIdx);
pdsch_pdu_rel15->TBSize[0] = TBS;
pdsch_pdu_rel15->mcsTable[0] = gNB_mac->sched_ctrlCommon->pdsch_semi_static.mcsTableIdx;
pdsch_pdu_rel15->mcsTable[0] = mcsTableIdx;
pdsch_pdu_rel15->StartSymbolIndex = StartSymbolIndex;
pdsch_pdu_rel15->NrOfSymbols = NrOfSymbols;
pdsch_pdu_rel15->dlDmrsSymbPos = dlDmrsSymbPos;
@@ -503,6 +503,7 @@ void nr_fill_nfapi_dl_sib1_pdu(int Mod_idP,
int rnti_type = NR_RNTI_SI;
fill_dci_pdu_rel15(scc,
NULL,
NULL,
&pdcch_pdu_rel15->dci_pdu[pdcch_pdu_rel15->numDlDci - 1],
&dci_payload,
@@ -510,7 +511,7 @@ void nr_fill_nfapi_dl_sib1_pdu(int Mod_idP,
rnti_type,
pdsch_pdu_rel15->BWPSize,
0,
0,
gNB_mac->sched_ctrlCommon->coreset,
gNB_mac->cset0_bwp_size);
LOG_D(MAC,"BWPSize: %i\n", pdcch_pdu_rel15->BWPSize);
@@ -570,7 +571,7 @@ void schedule_nr_sib1(module_id_t module_idP, frame_t frameP, sub_frame_t slotP)
// Get SIB1
uint8_t sib1_payload[NR_MAX_SIB_LENGTH/8];
uint8_t sib1_sdu_length = mac_rrc_nr_data_req(module_idP, CC_id, frameP, BCCH, SI_RNTI, 1, sib1_payload);
uint16_t sib1_sdu_length = mac_rrc_nr_data_req(module_idP, CC_id, frameP, BCCH, SI_RNTI, 1, sib1_payload);
LOG_D(NR_MAC,"sib1_sdu_length = %i\n", sib1_sdu_length);
LOG_D(NR_MAC,"SIB1: \n");
for (int k=0;k<sib1_sdu_length;k++)
@@ -598,7 +599,8 @@ void schedule_nr_sib1(module_id_t module_idP, frame_t frameP, sub_frame_t slotP)
startSymbolIndex,
nrOfSymbols,
dlDmrsSymbPos,
candidate_idx, sib1_sdu_length);
candidate_idx,
sib1_sdu_length);
nfapi_nr_dl_tti_request_body_t *dl_req = &gNB_mac->DL_req[CC_id].dl_tti_request_body;
int pdu_index = gNB_mac->pdu_index[0]++;
+57 -134
View File
@@ -388,8 +388,9 @@ bool allocate_dl_retransmission(module_id_t module_id,
gNB_MAC_INST *nr_mac = RC.nrmac[module_id];
const NR_ServingCellConfigCommon_t *scc = nr_mac->common_channels->ServingCellConfigCommon;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_DL_BWP_t *dl_bwp = &UE->current_DL_BWP;
NR_UE_UL_BWP_t *ul_bwp = &UE->current_UL_BWP;
NR_sched_pdsch_t *retInfo = &sched_ctrl->harq_processes[current_harq_pid].sched_pdsch;
NR_CellGroupConfig_t *cg = UE->CellGroup;
NR_pdsch_semi_static_t *ps = &sched_ctrl->pdsch_semi_static;
//TODO remove this and handle retransmission with old nrOfLayers
@@ -402,26 +403,8 @@ bool allocate_dl_retransmission(module_id_t module_id,
return false;
}
NR_BWP_DownlinkDedicated_t *bwpd =
cg &&
cg->spCellConfig &&
cg->spCellConfig->spCellConfigDedicated ?
cg->spCellConfig->spCellConfigDedicated->initialDownlinkBWP : NULL;
NR_BWP_UplinkDedicated_t *ubwpd =
cg &&
cg->spCellConfig &&
cg->spCellConfig->spCellConfigDedicated &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig ?
cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP : NULL;
const NR_SIB1_t *sib1 = RC.nrmac[module_id]->common_channels[0].sib1 ? RC.nrmac[module_id]->common_channels[0].sib1->message.choice.c1->choice.systemInformationBlockType1 : NULL;
NR_BWP_t *genericParameters = get_dl_bwp_genericParameters(sched_ctrl->active_bwp,
RC.nrmac[module_id]->common_channels[0].ServingCellConfigCommon,
sib1);
const int coresetid = (sched_ctrl->active_bwp||bwpd) ? sched_ctrl->coreset->controlResourceSetId : RC.nrmac[module_id]->sched_ctrlCommon->coreset->controlResourceSetId;
const uint16_t bwpSize = coresetid == 0 ? RC.nrmac[module_id]->cset0_bwp_size : NRRIV2BW(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
const int coresetid = sched_ctrl->coreset->controlResourceSetId;
const uint16_t bwpSize = coresetid == 0 ? RC.nrmac[module_id]->cset0_bwp_size : dl_bwp->BWPSize;
int rbStart = 0; // start wrt BWPstart
int rbSize = 0;
@@ -452,11 +435,8 @@ bool allocate_dl_retransmission(module_id_t module_id,
/* check whether we need to switch the TDA allocation since the last
* (re-)transmission */
if (ps->time_domain_allocation != tda) {
nr_set_pdsch_semi_static(sib1,
nr_set_pdsch_semi_static(dl_bwp,
scc,
cg,
sched_ctrl->active_bwp,
bwpd,
tda,
ps->nrOfLayers,
sched_ctrl,
@@ -467,11 +447,8 @@ bool allocate_dl_retransmission(module_id_t module_id,
* that we have enough resources */
NR_pdsch_semi_static_t temp_ps = *ps;
nr_set_pdsch_semi_static(sib1,
nr_set_pdsch_semi_static(dl_bwp,
scc,
cg,
sched_ctrl->active_bwp,
bwpd,
tda,
ps->nrOfLayers,
sched_ctrl,
@@ -542,7 +519,7 @@ bool allocate_dl_retransmission(module_id_t module_id,
/* Find PUCCH occasion: if it fails, undo CCE allocation (undoing PUCCH
* allocation after CCE alloc fail would be more complex) */
int r_pucch = nr_get_pucch_resource(sched_ctrl->coreset, sched_ctrl->active_ubwp, ubwpd, CCEIndex);
int r_pucch = nr_get_pucch_resource(sched_ctrl->coreset, ul_bwp->pucch_Config, CCEIndex);
const int alloc = nr_acknack_scheduling(module_id, UE, frame, slot, r_pucch, 0);
if (alloc<0) {
LOG_D(MAC,
@@ -602,6 +579,7 @@ void pf_dl(module_id_t module_id,
continue;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_DL_BWP_t *current_BWP = &UE->current_DL_BWP;
if (sched_ctrl->ul_failure==1 && get_softmodem_params()->phy_test==0) continue;
@@ -641,12 +619,15 @@ void pf_dl(module_id_t module_id,
/* Calculate coeff */
const NR_bler_options_t *bo = &mac->dl_bler;
const int max_mcs_table = ps->mcsTableIdx == 1 ? 27 : 28;
const int max_mcs_table = current_BWP->mcsTableIdx == 1 ? 27 : 28;
const int max_mcs = min(sched_ctrl->dl_max_mcs, max_mcs_table);
sched_pdsch->mcs = get_mcs_from_bler(bo, stats, &sched_ctrl->dl_bler_stats, max_mcs, frame);
if (bo->harq_round_max == 1)
sched_pdsch->mcs = max_mcs;
else
sched_pdsch->mcs = get_mcs_from_bler(bo, stats, &sched_ctrl->dl_bler_stats, max_mcs, frame);
UE->layers = set_dl_nrOfLayers(sched_ctrl);
const uint8_t Qm = nr_get_Qm_dl(sched_pdsch->mcs, ps->mcsTableIdx);
const uint16_t R = nr_get_code_rate_dl(sched_pdsch->mcs, ps->mcsTableIdx);
const uint8_t Qm = nr_get_Qm_dl(sched_pdsch->mcs, current_BWP->mcsTableIdx);
const uint16_t R = nr_get_code_rate_dl(sched_pdsch->mcs, current_BWP->mcsTableIdx);
uint32_t tbs = nr_compute_tbs(Qm,
R,
1, /* rbSize */
@@ -673,37 +654,16 @@ void pf_dl(module_id_t module_id,
/* Loop UE_sched to find max coeff and allocate transmission */
while (remainUEs> 0 && n_rb_sched >= min_rbSize && iterator->UE != NULL) {
NR_CellGroupConfig_t *cg = iterator->UE->CellGroup;
NR_BWP_DownlinkDedicated_t *bwpd =
cg &&
cg->spCellConfig &&
cg->spCellConfig->spCellConfigDedicated ?
cg->spCellConfig->spCellConfigDedicated->initialDownlinkBWP : NULL;
NR_BWP_UplinkDedicated_t *ubwpd =
cg &&
cg->spCellConfig &&
cg->spCellConfig->spCellConfigDedicated &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig ?
cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP : NULL;
NR_UE_sched_ctrl_t *sched_ctrl = &iterator->UE->UE_sched_ctrl;
const uint16_t rnti = iterator->UE->rnti;
const NR_SIB1_t *sib1 = RC.nrmac[module_id]->common_channels[0].sib1 ?
RC.nrmac[module_id]->common_channels[0].sib1->message.choice.c1->choice.systemInformationBlockType1 :
NULL;
NR_BWP_t *genericParameters = get_dl_bwp_genericParameters(sched_ctrl->active_bwp,
RC.nrmac[module_id]->common_channels[0].ServingCellConfigCommon,
sib1);
NR_UE_DL_BWP_t *dl_bwp = &iterator->UE->current_DL_BWP;
NR_UE_UL_BWP_t *ul_bwp = &iterator->UE->current_UL_BWP;
const int coresetid = (sched_ctrl->active_bwp||bwpd) ?
sched_ctrl->coreset->controlResourceSetId :
RC.nrmac[module_id]->sched_ctrlCommon->coreset->controlResourceSetId;
const int coresetid = sched_ctrl->coreset->controlResourceSetId;
const uint16_t bwpSize = coresetid == 0 ?
RC.nrmac[module_id]->cset0_bwp_size :
NRRIV2BW(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
dl_bwp->BWPSize;
int rbStart = 0; // start wrt BWPstart
if (sched_ctrl->available_dl_harq.head < 0) {
@@ -743,7 +703,7 @@ void pf_dl(module_id_t module_id,
/* Find PUCCH occasion: if it fails, undo CCE allocation (undoing PUCCH
* allocation after CCE alloc fail would be more complex) */
int r_pucch = nr_get_pucch_resource(sched_ctrl->coreset, sched_ctrl->active_ubwp, ubwpd, CCEIndex);
int r_pucch = nr_get_pucch_resource(sched_ctrl->coreset, ul_bwp->pucch_Config, CCEIndex);
const int alloc = nr_acknack_scheduling(module_id, iterator->UE, frame, slot, r_pucch, 0);
if (alloc<0) {
@@ -770,11 +730,8 @@ void pf_dl(module_id_t module_id,
NR_pdsch_semi_static_t *ps = &sched_ctrl->pdsch_semi_static;
if (ps->nrOfLayers != iterator->UE->layers || ps->time_domain_allocation != tda ) {
nr_set_pdsch_semi_static(sib1,
nr_set_pdsch_semi_static(dl_bwp,
scc,
iterator->UE->CellGroup,
sched_ctrl->active_bwp,
bwpd,
tda,
iterator->UE->layers,
sched_ctrl,
@@ -792,8 +749,8 @@ void pf_dl(module_id_t module_id,
while (rbStart + max_rbSize < bwpSize && (rballoc_mask[rbStart + max_rbSize] & slbitmap) == slbitmap)
max_rbSize++;
sched_pdsch->Qm = nr_get_Qm_dl(sched_pdsch->mcs, ps->mcsTableIdx);
sched_pdsch->R = nr_get_code_rate_dl(sched_pdsch->mcs, ps->mcsTableIdx);
sched_pdsch->Qm = nr_get_Qm_dl(sched_pdsch->mcs, dl_bwp->mcsTableIdx);
sched_pdsch->R = nr_get_code_rate_dl(sched_pdsch->mcs, dl_bwp->mcsTableIdx);
sched_pdsch->pucch_allocation = alloc;
uint32_t TBS = 0;
uint16_t rbSize;
@@ -839,30 +796,18 @@ void nr_fr1_dlsch_preprocessor(module_id_t module_id, frame_t frame, sub_frame_t
/* This is temporary and it assumes all UEs have the same BWP and TDA*/
NR_UE_info_t *UE=UE_info->list[0];
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_DL_BWP_t *current_BWP = &UE->current_DL_BWP;
const int tda = get_dl_tda(RC.nrmac[module_id], scc, slot);
int startSymbolIndex, nrOfSymbols;
const struct NR_PDSCH_TimeDomainResourceAllocationList *tdaList = sched_ctrl->active_bwp ?
sched_ctrl->active_bwp->bwp_Common->pdsch_ConfigCommon->choice.setup->pdsch_TimeDomainAllocationList :
scc->downlinkConfigCommon->initialDownlinkBWP->pdsch_ConfigCommon->choice.setup->pdsch_TimeDomainAllocationList;
const struct NR_PDSCH_TimeDomainResourceAllocationList *tdaList = current_BWP->tdaList;
AssertFatal(tda < tdaList->list.count, "time_domain_allocation %d>=%d\n", tda, tdaList->list.count);
const int startSymbolAndLength = tdaList->list.array[tda]->startSymbolAndLength;
SLIV2SL(startSymbolAndLength, &startSymbolIndex, &nrOfSymbols);
const NR_SIB1_t *sib1 = RC.nrmac[module_id]->common_channels[0].sib1 ? RC.nrmac[module_id]->common_channels[0].sib1->message.choice.c1->choice.systemInformationBlockType1 : NULL;
NR_BWP_t *genericParameters = get_dl_bwp_genericParameters(sched_ctrl->active_bwp,
RC.nrmac[module_id]->common_channels[0].ServingCellConfigCommon,
sib1);
const int coresetid = sched_ctrl->coreset->controlResourceSetId;
NR_BWP_DownlinkDedicated_t *bwpd =
UE->CellGroup &&
UE->CellGroup->spCellConfig &&
UE->CellGroup->spCellConfig->spCellConfigDedicated ?
UE->CellGroup->spCellConfig->spCellConfigDedicated->initialDownlinkBWP : NULL;
const int coresetid = (sched_ctrl->active_bwp||bwpd) ? sched_ctrl->coreset->controlResourceSetId : RC.nrmac[module_id]->sched_ctrlCommon->coreset->controlResourceSetId;
const uint16_t bwpSize = coresetid == 0 ? RC.nrmac[module_id]->cset0_bwp_size : NRRIV2BW(genericParameters->locationAndBandwidth,MAX_BWP_SIZE);
const uint16_t BWPStart = coresetid == 0 ? RC.nrmac[module_id]->cset0_bwp_start : NRRIV2PRBOFFSET(genericParameters->locationAndBandwidth,MAX_BWP_SIZE);
const uint16_t bwpSize = coresetid == 0 ? RC.nrmac[module_id]->cset0_bwp_size : current_BWP->BWPSize;
const uint16_t BWPStart = coresetid == 0 ? RC.nrmac[module_id]->cset0_bwp_start : current_BWP->BWPStart;
const uint16_t slbitmap = SL_to_bitmap(startSymbolIndex, nrOfSymbols);
uint16_t *vrb_map = RC.nrmac[module_id]->common_channels[CC_id].vrb_map;
@@ -922,13 +867,12 @@ nr_pp_impl_dl nr_init_fr1_dlsch_preprocessor(module_id_t module_id, int CC_id) {
void nr_schedule_ue_spec(module_id_t module_id,
frame_t frame,
sub_frame_t slot) {
gNB_MAC_INST *gNB_mac = RC.nrmac[module_id];
if (!is_xlsch_in_slot(gNB_mac->dlsch_slot_bitmap[slot / 64], slot))
return;
//if (slot==7 || slot == 17) return;
/* PREPROCESSOR */
gNB_mac->pre_processor_dl(module_id, frame, slot);
const int CC_id = 0;
@@ -938,6 +882,7 @@ void nr_schedule_ue_spec(module_id_t module_id,
UE_iterator(UE_info->list, UE) {
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_DL_BWP_t *current_BWP = &UE->current_DL_BWP;
if (sched_ctrl->ul_failure==1 && get_softmodem_params()->phy_test==0) continue;
@@ -945,12 +890,6 @@ void nr_schedule_ue_spec(module_id_t module_id,
UE->mac_stats.dl.current_bytes = 0;
NR_CellGroupConfig_t *cg = UE->CellGroup;
NR_BWP_DownlinkDedicated_t *bwpd =
cg &&
cg->spCellConfig &&
cg->spCellConfig->spCellConfigDedicated ?
cg->spCellConfig->spCellConfigDedicated->initialDownlinkBWP : NULL;
/* update TA and set ta_apply every 10 frames.
* Possible improvement: take the periodicity from input file.
* If such UE is not scheduled now, it will be by the preprocessor later.
@@ -1017,24 +956,16 @@ void nr_schedule_ue_spec(module_id_t module_id,
TBS,
current_harq_pid,
harq->round,
nr_rv_round_map[harq->round],
nr_rv_round_map[harq->round%4],
harq->ndi,
pucch->timing_indicator,
pucch->frame,
pucch->ul_slot,
sched_pdsch->pucch_allocation,
sched_ctrl->tpc1);
NR_BWP_Downlink_t *bwp = sched_ctrl->active_bwp;
const NR_SIB1_t *sib1 = RC.nrmac[module_id]->common_channels[0].sib1 ? RC.nrmac[module_id]->common_channels[0].sib1->message.choice.c1->choice.systemInformationBlockType1 : NULL;
NR_BWP_t *genericParameters = get_dl_bwp_genericParameters(bwp,
RC.nrmac[module_id]->common_channels[0].ServingCellConfigCommon,
sib1);
NR_SearchSpace_t *ss = (bwp||bwpd) ? sched_ctrl->search_space : gNB_mac->sched_ctrlCommon->search_space;
const int bwp_id = bwp ? bwp->bwp_Id : 0;
const int coresetid = (bwp||bwpd) ? sched_ctrl->coreset->controlResourceSetId : gNB_mac->sched_ctrlCommon->coreset->controlResourceSetId;
const int bwp_id = current_BWP->bwp_id;
const int coresetid = sched_ctrl->coreset->controlResourceSetId;
/* look up the PDCCH PDU for this CC, BWP, and CORESET. If it does not exist, create it */
nfapi_nr_dl_tti_pdcch_pdu_rel15_t *pdcch_pdu = gNB_mac->pdcch_pdu_idx[CC_id][coresetid];
@@ -1048,8 +979,8 @@ void nr_schedule_ue_spec(module_id_t module_id,
dl_req->nPDUs += 1;
pdcch_pdu = &dl_tti_pdcch_pdu->pdcch_pdu.pdcch_pdu_rel15;
LOG_D(NR_MAC,"Trying to configure DL pdcch for UE %04x, bwp %d, cs %d\n", UE->rnti, bwp_id, coresetid);
NR_ControlResourceSet_t *coreset = (bwp||bwpd)? sched_ctrl->coreset:gNB_mac->sched_ctrlCommon->coreset;
nr_configure_pdcch(pdcch_pdu, coreset, genericParameters, &sched_ctrl->sched_pdcch);
NR_ControlResourceSet_t *coreset = sched_ctrl->coreset;
nr_configure_pdcch(pdcch_pdu, coreset, false, &sched_ctrl->sched_pdcch);
gNB_mac->pdcch_pdu_idx[CC_id][coresetid] = pdcch_pdu;
}
@@ -1071,22 +1002,22 @@ void nr_schedule_ue_spec(module_id_t module_id,
pdsch_pdu->BWPSize = gNB_mac->cset0_bwp_size;
pdsch_pdu->BWPStart = gNB_mac->cset0_bwp_start;
} else {
pdsch_pdu->BWPSize = NRRIV2BW(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
pdsch_pdu->BWPStart = NRRIV2PRBOFFSET(genericParameters->locationAndBandwidth,MAX_BWP_SIZE);
pdsch_pdu->BWPSize = current_BWP->BWPSize;
pdsch_pdu->BWPStart = current_BWP->BWPStart;
}
pdsch_pdu->SubcarrierSpacing = genericParameters->subcarrierSpacing;
pdsch_pdu->CyclicPrefix = genericParameters->cyclicPrefix ? *genericParameters->cyclicPrefix : 0;
pdsch_pdu->SubcarrierSpacing = current_BWP->scs;
pdsch_pdu->CyclicPrefix = current_BWP->cyclicprefix ? *current_BWP->cyclicprefix : 0;
// Codeword information
pdsch_pdu->NrOfCodewords = 1;
//number of information bits per 1024 coded bits expressed in 0.1 bit units
pdsch_pdu->targetCodeRate[0] = R;
pdsch_pdu->qamModOrder[0] = Qm;
pdsch_pdu->mcsIndex[0] = sched_pdsch->mcs;
pdsch_pdu->mcsTable[0] = ps->mcsTableIdx;
pdsch_pdu->mcsTable[0] = current_BWP->mcsTableIdx;
AssertFatal(harq!=NULL,"harq is null\n");
AssertFatal(harq->round<4,"%d",harq->round);
pdsch_pdu->rvIndex[0] = nr_rv_round_map[harq->round];
AssertFatal(harq->round<gNB_mac->dl_bler.harq_round_max,"%d",harq->round);
pdsch_pdu->rvIndex[0] = nr_rv_round_map[harq->round%4];
pdsch_pdu->TBSize[0] = TBS;
pdsch_pdu->dataScramblingId = *scc->physCellId;
pdsch_pdu->nrOfLayers = nrOfLayers;
@@ -1120,22 +1051,17 @@ void nr_schedule_ue_spec(module_id_t module_id,
csi_report->codebook_mode);
}
// TBS_LBRM according to section 5.4.2.1 of 38.212
long *maxMIMO_Layers = cg->spCellConfig->spCellConfigDedicated->pdsch_ServingCellConfig->choice.setup->ext1->maxMIMO_Layers;
long *maxMIMO_Layers = current_BWP->pdsch_servingcellconfig->ext1->maxMIMO_Layers;
AssertFatal (maxMIMO_Layers != NULL,"Option with max MIMO layers not configured is not supported\n");
int nl_tbslbrm = *maxMIMO_Layers < 4 ? *maxMIMO_Layers : 4;
// Maximum number of PRBs across all configured DL BWPs
int bw_tbslbrm = get_bw_tbslbrm(genericParameters, cg);
pdsch_pdu->maintenance_parms_v3.tbSizeLbrmBytes = nr_compute_tbslbrm(ps->mcsTableIdx,
int scc_bwpsize = NRRIV2BW(scc->downlinkConfigCommon->initialDownlinkBWP->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
int bw_tbslbrm = get_bw_tbslbrm(scc_bwpsize, cg);
pdsch_pdu->maintenance_parms_v3.tbSizeLbrmBytes = nr_compute_tbslbrm(current_BWP->mcsTableIdx,
bw_tbslbrm,
nl_tbslbrm);
NR_PDSCH_Config_t *pdsch_Config=NULL;
if (bwp &&
bwp->bwp_Dedicated &&
bwp->bwp_Dedicated->pdsch_Config &&
bwp->bwp_Dedicated->pdsch_Config->choice.setup)
pdsch_Config = bwp->bwp_Dedicated->pdsch_Config->choice.setup;
NR_PDSCH_Config_t *pdsch_Config = current_BWP->pdsch_Config;
/* Check and validate PTRS values */
struct NR_SetupRelease_PTRS_DownlinkConfig *phaseTrackingRS =
@@ -1182,14 +1108,11 @@ void nr_schedule_ue_spec(module_id_t module_id,
dci_pdu_rel15_t dci_payload;
memset(&dci_payload, 0, sizeof(dci_pdu_rel15_t));
// bwp indicator
const int n_dl_bwp = bwp ? cg->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList->list.count : 0;
AssertFatal(n_dl_bwp <= NR_MAX_NUM_BWP, "downlinkBWP_ToAddModList has %d BWP!\n", n_dl_bwp);
// as per table 7.3.1.1.2-1 in 38.212
dci_payload.bwp_indicator.val = bwp ? (n_dl_bwp < 4 ? bwp->bwp_Id : bwp->bwp_Id - 1) : 0;
dci_payload.bwp_indicator.val = current_BWP->n_dl_bwp < 4 ? bwp_id : bwp_id - 1;
if (bwp) AssertFatal(bwp->bwp_Dedicated->pdsch_Config->choice.setup->resourceAllocation == NR_PDSCH_Config__resourceAllocation_resourceAllocationType1,
"Only frequency resource allocation type 1 is currently supported\n");
AssertFatal(pdsch_Config->resourceAllocation == NR_PDSCH_Config__resourceAllocation_resourceAllocationType1,
"Only frequency resource allocation type 1 is currently supported\n");
dci_payload.frequency_domain_assignment.val = PRBalloc_to_locationandbandwidth0(pdsch_pdu->rbSize,
pdsch_pdu->rbStart,
@@ -1225,19 +1148,17 @@ void nr_schedule_ue_spec(module_id_t module_id,
dci_payload.tpc,
pucch->timing_indicator);
int dci_format = ss && ss->searchSpaceType && ss->searchSpaceType->present == NR_SearchSpace__searchSpaceType_PR_ue_Specific ?
NR_DL_DCI_FORMAT_1_1 : NR_DL_DCI_FORMAT_1_0;
const int rnti_type = NR_RNTI_C;
fill_dci_pdu_rel15(scc,
cg,
current_BWP,
dci_pdu,
&dci_payload,
dci_format,
current_BWP->dci_format,
rnti_type,
pdsch_pdu->BWPSize,
bwp ? bwp->bwp_Id : 0,
coresetid,
bwp_id,
sched_ctrl->coreset,
gNB_mac->cset0_bwp_size);
LOG_D(NR_MAC,
@@ -1318,7 +1239,7 @@ void nr_schedule_ue_spec(module_id_t module_id,
lcid < 4 ? "DCCH" : "DTCH",
lcid,
ndata,
bufEnd-buf-+sizeof(NR_MAC_SUBHEADER_LONG));
bufEnd-buf-sizeof(NR_MAC_SUBHEADER_LONG));
if (len == 0)
break;
@@ -1349,6 +1270,8 @@ void nr_schedule_ue_spec(module_id_t module_id,
header->L = htons(bufEnd-buf);
dlsch_total_bytes += bufEnd-buf;
for (; ((intptr_t)buf) % 4; buf++)
*buf = lrand48() & 0xff;
for (; buf < bufEnd - 3; buf += 4) {
uint32_t *buf32 = (uint32_t *)buf;
*buf32 = lrand48();
@@ -195,17 +195,18 @@ void nr_preprocessor_phytest(module_id_t module_id,
NR_UE_info_t *UE = RC.nrmac[module_id]->UE_info.list[0];
NR_ServingCellConfigCommon_t *scc = RC.nrmac[module_id]->common_channels[0].ServingCellConfigCommon;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_DL_BWP_t *dl_bwp = &UE->current_DL_BWP;
const int CC_id = 0;
const int tda = get_dl_tda(RC.nrmac[module_id], scc, slot);
NR_pdsch_semi_static_t *ps = &sched_ctrl->pdsch_semi_static;
ps->nrOfLayers = target_dl_Nl;
if (ps->time_domain_allocation != tda || ps->nrOfLayers != target_dl_Nl)
nr_set_pdsch_semi_static(NULL, scc, UE->CellGroup, sched_ctrl->active_bwp, NULL, tda, target_dl_Nl,sched_ctrl , ps);
nr_set_pdsch_semi_static(dl_bwp, scc, tda, target_dl_Nl,sched_ctrl , ps);
/* find largest unallocated chunk */
const int bwpSize = NRRIV2BW(sched_ctrl->active_bwp->bwp_Common->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
const int BWPStart = NRRIV2PRBOFFSET(sched_ctrl->active_bwp->bwp_Common->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
const int bwpSize = dl_bwp->BWPSize;
const int BWPStart = dl_bwp->BWPStart;
int rbStart = 0;
int rbSize = 0;
@@ -278,7 +279,7 @@ void nr_preprocessor_phytest(module_id_t module_id,
__func__,
UE->rnti);
int r_pucch = nr_get_pucch_resource(sched_ctrl->coreset, sched_ctrl->active_ubwp, NULL, CCEIndex);
int r_pucch = nr_get_pucch_resource(sched_ctrl->coreset, UE->current_UL_BWP.pucch_Config, CCEIndex);
const int alloc = nr_acknack_scheduling(module_id, UE, frame, slot, r_pucch, 0);
if (alloc < 0) {
LOG_D(MAC,
@@ -308,9 +309,9 @@ void nr_preprocessor_phytest(module_id_t module_id,
sched_pdsch->rbSize = rbSize;
sched_pdsch->mcs = target_dl_mcs;
sched_pdsch->Qm = nr_get_Qm_dl(sched_pdsch->mcs, dl_bwp->mcsTableIdx);
sched_pdsch->R = nr_get_code_rate_dl(sched_pdsch->mcs, dl_bwp->mcsTableIdx);
sched_ctrl->dl_bler_stats.mcs = target_dl_mcs; /* for logging output */
sched_pdsch->Qm = nr_get_Qm_dl(sched_pdsch->mcs, ps->mcsTableIdx);
sched_pdsch->R = nr_get_code_rate_dl(sched_pdsch->mcs, ps->mcsTableIdx);
sched_pdsch->tb_size = nr_compute_tbs(sched_pdsch->Qm,
sched_pdsch->R,
sched_pdsch->rbSize,
@@ -340,7 +341,6 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, sub_frame_
gNB_MAC_INST *nr_mac = RC.nrmac[module_id];
NR_COMMON_channels_t *cc = nr_mac->common_channels;
NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon;
const int mu = scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.subcarrierSpacing;
NR_UE_info_t *UE = nr_mac->UE_info.list[0];
AssertFatal(nr_mac->UE_info.list[1] == NULL,
@@ -351,9 +351,10 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, sub_frame_
const int CC_id = 0;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_UL_BWP_t *ul_bwp = &UE->current_UL_BWP;
const int mu = ul_bwp->scs;
const struct NR_PUSCH_TimeDomainResourceAllocationList *tdaList =
sched_ctrl->active_ubwp->bwp_Common->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList;
const struct NR_PUSCH_TimeDomainResourceAllocationList *tdaList = ul_bwp->tdaList;
const int temp_tda = get_ul_tda(nr_mac, scc, slot);
if (temp_tda < 0)
return false;
@@ -361,7 +362,7 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, sub_frame_
"time domain assignment %d >= %d\n",
temp_tda,
tdaList->list.count);
int K2 = get_K2(scc,NULL,sched_ctrl->active_ubwp, temp_tda, mu);
int K2 = get_K2(ul_bwp->tdaList, temp_tda, mu);
const int sched_frame = frame + (slot + K2 >= nr_slots_per_frame[mu]);
const int sched_slot = (slot + K2) % nr_slots_per_frame[mu];
const int tda = get_ul_tda(nr_mac, scc, sched_slot);
@@ -377,33 +378,19 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, sub_frame_
if (!is_xlsch_in_slot(ulsch_slot_bitmap, sched_slot))
return false;
const long f = (sched_ctrl->active_bwp && sched_ctrl->search_space &&
sched_ctrl->search_space->searchSpaceType->present == NR_SearchSpace__searchSpaceType_PR_ue_Specific) ?
sched_ctrl->search_space->searchSpaceType->choice.ue_Specific->dci_Formats : 0;
const int dci_format = f ? NR_UL_DCI_FORMAT_0_1 : NR_UL_DCI_FORMAT_0_0;
uint8_t num_dmrs_cdm_grps_no_data = 1;
if ((target_ul_Nl==4)||(target_ul_Nl==3))
num_dmrs_cdm_grps_no_data = 2;
/* we want to avoid a lengthy deduction of DMRS and other parameters in
* every TTI if we can save it, so check whether dci_format, TDA, or
* every TTI if we can save it, so check whether TDA, or
* num_dmrs_cdm_grps_no_data has changed and only then recompute */
NR_pusch_semi_static_t *ps = &sched_ctrl->pusch_semi_static;
if (ps->time_domain_allocation != tda
|| ps->dci_format != dci_format
|| ps->nrOfLayers != target_ul_Nl
|| ps->num_dmrs_cdm_grps_no_data != num_dmrs_cdm_grps_no_data)
nr_set_pusch_semi_static(NULL, scc, sched_ctrl->active_ubwp, NULL,dci_format, tda, num_dmrs_cdm_grps_no_data,target_ul_Nl,ps);
|| ps->nrOfLayers != target_ul_Nl)
nr_set_pusch_semi_static(ul_bwp, scc, tda, target_ul_Nl,ps);
uint16_t rbStart = 0;
uint16_t rbSize;
const int bw = NRRIV2BW(sched_ctrl->active_ubwp ?
sched_ctrl->active_ubwp->bwp_Common->genericParameters.locationAndBandwidth :
scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
const int BWPStart = NRRIV2PRBOFFSET(sched_ctrl->active_ubwp ?
sched_ctrl->active_ubwp->bwp_Common->genericParameters.locationAndBandwidth :
scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.locationAndBandwidth, MAX_BWP_SIZE);
const int bw = ul_bwp->BWPSize;
const int BWPStart = ul_bwp->BWPStart;
if (target_ul_bw>bw)
rbSize = bw;
@@ -466,10 +453,10 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, sub_frame_
/* Calculate TBS from MCS */
ps->nrOfLayers = target_ul_Nl;
sched_pusch->R = nr_get_code_rate_ul(mcs, ps->mcs_table);
sched_pusch->Qm = nr_get_Qm_ul(mcs, ps->mcs_table);
if (ps->pusch_Config->tp_pi2BPSK
&& ((ps->mcs_table == 3 && mcs < 2) || (ps->mcs_table == 4 && mcs < 6))) {
sched_pusch->R = nr_get_code_rate_ul(mcs, ul_bwp->mcs_table);
sched_pusch->Qm = nr_get_Qm_ul(mcs, ul_bwp->mcs_table);
if (ul_bwp->pusch_Config->tp_pi2BPSK
&& ((ul_bwp->mcs_table == 3 && mcs < 2) || (ul_bwp->mcs_table == 4 && mcs < 6))) {
sched_pusch->R >>= 1;
sched_pusch->Qm <<= 1;
}
File diff suppressed because it is too large Load Diff
+8 -36
View File
@@ -36,20 +36,13 @@ extern RAN_CONTEXT_t RC;
void nr_configure_srs(nfapi_nr_srs_pdu_t *srs_pdu, int module_id, int CC_id,NR_UE_info_t* UE, NR_SRS_Resource_t *srs_resource) {
gNB_MAC_INST *nrmac = RC.nrmac[module_id];
NR_ServingCellConfigCommon_t *scc = nrmac->common_channels[CC_id].ServingCellConfigCommon;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
const NR_SIB1_t *sib1 = nrmac->common_channels[0].sib1 ? nrmac->common_channels[0].sib1->message.choice.c1->choice.systemInformationBlockType1 : NULL;
const NR_BWP_t *genericParameters = get_ul_bwp_genericParameters(sched_ctrl->active_ubwp,
scc,
sib1);
NR_UE_UL_BWP_t *current_BWP = &UE->current_UL_BWP;
srs_pdu->rnti = UE->rnti;
srs_pdu->handle = 0;
srs_pdu->bwp_size = NRRIV2BW(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);;
srs_pdu->bwp_start = NRRIV2PRBOFFSET(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);;
srs_pdu->subcarrier_spacing = genericParameters->subcarrierSpacing;
srs_pdu->bwp_size = current_BWP->BWPSize;
srs_pdu->bwp_start = current_BWP->BWPStart;
srs_pdu->subcarrier_spacing = current_BWP->scs;
srs_pdu->cyclic_prefix = 0;
srs_pdu->num_ant_ports = srs_resource->nrofSRS_Ports;
srs_pdu->num_symbols = srs_resource->resourceMapping.nrofSymbols;
@@ -115,9 +108,8 @@ void nr_schedule_srs(int module_id, frame_t frame) {
UE_iterator(UE_info->list, UE) {
const int CC_id = 0;
NR_ServingCellConfigCommon_t *scc = RC.nrmac[module_id]->common_channels[CC_id].ServingCellConfigCommon;
NR_CellGroupConfig_t *cg = UE->CellGroup;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_UL_BWP_t *current_BWP = &UE->current_UL_BWP;
sched_ctrl->sched_srs.frame = -1;
sched_ctrl->sched_srs.slot = -1;
@@ -128,23 +120,9 @@ void nr_schedule_srs(int module_id, frame_t frame) {
continue;
}
NR_SRS_Config_t *srs_config = NULL;
if (sched_ctrl->active_ubwp) {
if (sched_ctrl->active_ubwp->bwp_Dedicated &&
sched_ctrl->active_ubwp->bwp_Dedicated->srs_Config) {
srs_config = sched_ctrl->active_ubwp->bwp_Dedicated->srs_Config->choice.setup;
}
} else if (cg &&
cg->spCellConfig &&
cg->spCellConfig->spCellConfigDedicated &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP) {
srs_config = cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP->srs_Config->choice.setup;
}
if (!srs_config) {
NR_SRS_Config_t *srs_config = current_BWP->srs_Config;
if (!srs_config)
continue;
}
for(int rs = 0; rs < srs_config->srs_ResourceSetToAddModList->list.count; rs++) {
@@ -172,15 +150,9 @@ void nr_schedule_srs(int module_id, frame_t frame) {
continue;
}
const NR_SIB1_t *sib1 = nrmac->common_channels[0].sib1 ? nrmac->common_channels[0].sib1->message.choice.c1->choice.systemInformationBlockType1 : NULL;
const NR_BWP_t *genericParameters = get_ul_bwp_genericParameters(sched_ctrl->active_ubwp,
scc,
sib1);
uint16_t period = srs_period[srs_resource->resourceType.choice.periodic->periodicityAndOffset_p.present];
uint16_t offset = get_nr_srs_offset(srs_resource->resourceType.choice.periodic->periodicityAndOffset_p);
const int n_slots_frame = nr_slots_per_frame[genericParameters->subcarrierSpacing];
int n_slots_frame = nr_slots_per_frame[current_BWP->scs];
// Check if UE will transmit the SRS in this frame
if ( ((frame - offset/n_slots_frame)*n_slots_frame)%period == 0) {
+66 -665
View File
@@ -80,23 +80,13 @@ static void nr_fill_nfapi_pucch(gNB_MAC_INST *nrmac,
pucch->resource_indicator);
NR_COMMON_channels_t * common_ch=nrmac->common_channels;
NR_ServingCellConfigCommon_t *scc = common_ch->ServingCellConfigCommon;
NR_CellGroupConfig_t *cg=UE->CellGroup;
NR_BWP_UplinkDedicated_t *ubwpd = cg && cg->spCellConfig && cg->spCellConfig->spCellConfigDedicated &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig ?
cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP : NULL;
LOG_D(NR_MAC,"%4d.%2d Calling nr_configure_pucch (pucch_Config %p,r_pucch %d) pucch to be scheduled in %4d.%2d\n",
frame,slot,UE->current_UL_BWP.pucch_Config,pucch->r_pucch,pucch->frame,pucch->ul_slot);
LOG_D(NR_MAC,"%4d.%2d Calling nr_configure_pucch (ubwpd %p,r_pucch %d) pucch to be scheduled in %4d.%2d\n",
frame,slot,ubwpd,pucch->r_pucch,pucch->frame,pucch->ul_slot);
const NR_SIB1_t *sib1 = common_ch->sib1 ? common_ch->sib1->message.choice.c1->choice.systemInformationBlockType1 : NULL;
nr_configure_pucch(sib1,
pucch_pdu,
nr_configure_pucch(pucch_pdu,
scc,
UE->CellGroup,
UE->UE_sched_ctrl.active_ubwp,
ubwpd,
UE->rnti,
UE,
pucch->resource_indicator,
pucch->csi_bits,
pucch->dai_c,
@@ -169,560 +159,22 @@ void nr_schedule_pucch(gNB_MAC_INST *nrmac,
}
}
//! Calculating number of bits set
uint8_t number_of_bits_set (uint8_t buf){
uint8_t nb_of_bits_set = 0;
uint8_t mask = 0xff;
uint8_t index = 0;
for (index=7; (buf & mask) && (index>=0) ; index--){
if (buf & (1<<index))
nb_of_bits_set++;
mask>>=1;
}
return nb_of_bits_set;
}
void compute_rsrp_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
uint8_t nb_resources,
nr_csi_report_t *csi_report) {
if (NR_CSI_ReportConfig__groupBasedBeamReporting_PR_disabled == csi_reportconfig->groupBasedBeamReporting.present) {
if (NULL != csi_reportconfig->groupBasedBeamReporting.choice.disabled->nrofReportedRS)
csi_report->CSI_report_bitlen.nb_ssbri_cri = *(csi_reportconfig->groupBasedBeamReporting.choice.disabled->nrofReportedRS)+1;
else
/*! From Spec 38.331
* nrofReportedRS
* The number (N) of measured RS resources to be reported per report setting in a non-group-based report. N <= N_max, where N_max is either 2 or 4 depending on UE
* capability. FFS: The signaling mechanism for the gNB to select a subset of N beams for the UE to measure and report.
* When the field is absent the UE applies the value 1
*/
csi_report->CSI_report_bitlen.nb_ssbri_cri= 1;
} else
csi_report->CSI_report_bitlen.nb_ssbri_cri= 2;
if (nb_resources) {
csi_report->CSI_report_bitlen.cri_ssbri_bitlen =ceil(log2 (nb_resources));
csi_report->CSI_report_bitlen.rsrp_bitlen = 7; //From spec 38.212 Table 6.3.1.1.2-6: CRI, SSBRI, and RSRP
csi_report->CSI_report_bitlen.diff_rsrp_bitlen =4; //From spec 38.212 Table 6.3.1.1.2-6: CRI, SSBRI, and RSRP
} else {
csi_report->CSI_report_bitlen.cri_ssbri_bitlen =0;
csi_report->CSI_report_bitlen.rsrp_bitlen = 0;
csi_report->CSI_report_bitlen.diff_rsrp_bitlen =0;
}
}
uint8_t compute_ri_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
nr_csi_report_t *csi_report){
struct NR_CodebookConfig *codebookConfig = csi_reportconfig->codebookConfig;
uint8_t nb_allowed_ri, ri_bitlen;
uint8_t ri_restriction = 0;
if (codebookConfig == NULL) {
csi_report->csi_meas_bitlen.ri_bitlen=0;
return ri_restriction;
}
// codebook type1 single panel
if (NR_CodebookConfig__codebookType__type1__subType_PR_typeI_SinglePanel==codebookConfig->codebookType.choice.type1->subType.present){
struct NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel *type1single = codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel;
if (type1single->nrOfAntennaPorts.present == NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts_PR_two){
ri_restriction = csi_reportconfig->codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel->typeI_SinglePanel_ri_Restriction.buf[0];
nb_allowed_ri = number_of_bits_set(ri_restriction);
ri_bitlen = ceil(log2(nb_allowed_ri));
ri_bitlen = ri_bitlen<1?ri_bitlen:1; //from the spec 38.212 and table 6.3.1.1.2-3: RI, LI, CQI, and CRI of codebookType=typeI-SinglePanel
csi_report->csi_meas_bitlen.ri_bitlen=ri_bitlen;
}
if (type1single->nrOfAntennaPorts.present == NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts_PR_moreThanTwo){
if (type1single->nrOfAntennaPorts.choice.moreThanTwo->n1_n2.present ==
NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_two_one_TypeI_SinglePanel_Restriction) {
// 4 ports
ri_restriction = csi_reportconfig->codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel->typeI_SinglePanel_ri_Restriction.buf[0];
nb_allowed_ri = number_of_bits_set(ri_restriction);
ri_bitlen = ceil(log2(nb_allowed_ri));
ri_bitlen = ri_bitlen<2?ri_bitlen:2; //from the spec 38.212 and table 6.3.1.1.2-3: RI, LI, CQI, and CRI of codebookType=typeI-SinglePanel
csi_report->csi_meas_bitlen.ri_bitlen=ri_bitlen;
}
else {
// more than 4 ports
ri_restriction = csi_reportconfig->codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel->typeI_SinglePanel_ri_Restriction.buf[0];
nb_allowed_ri = number_of_bits_set(ri_restriction);
ri_bitlen = ceil(log2(nb_allowed_ri));
csi_report->csi_meas_bitlen.ri_bitlen=ri_bitlen;
}
}
return ri_restriction;
}
else
AssertFatal(1==0,"Other configurations not yet implemented\n");
return -1;
}
void compute_li_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
uint8_t ri_restriction,
nr_csi_report_t *csi_report){
struct NR_CodebookConfig *codebookConfig = csi_reportconfig->codebookConfig;
for(int i=0; i<8; i++) {
if (codebookConfig == NULL || ((ri_restriction>>i)&0x01) == 0)
csi_report->csi_meas_bitlen.li_bitlen[i]=0;
else {
// codebook type1 single panel
if (NR_CodebookConfig__codebookType__type1__subType_PR_typeI_SinglePanel==codebookConfig->codebookType.choice.type1->subType.present)
csi_report->csi_meas_bitlen.li_bitlen[i]=ceil(log2(i+1))<2?ceil(log2(i+1)):2;
else
AssertFatal(1==0,"Other configurations not yet implemented\n");
}
}
}
void get_n1n2_o1o2_singlepanel(int *n1, int *n2, int *o1, int *o2,
struct NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo *morethantwo) {
// Table 5.2.2.2.1-2 in 38.214 for supported configurations
switch(morethantwo->n1_n2.present){
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_two_one_TypeI_SinglePanel_Restriction):
*n1 = 2;
*n2 = 1;
*o1 = 4;
*o2 = 1;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_two_two_TypeI_SinglePanel_Restriction):
*n1 = 2;
*n2 = 2;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_four_one_TypeI_SinglePanel_Restriction):
*n1 = 4;
*n2 = 1;
*o1 = 4;
*o2 = 1;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_three_two_TypeI_SinglePanel_Restriction):
*n1 = 3;
*n2 = 2;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_six_one_TypeI_SinglePanel_Restriction):
*n1 = 6;
*n2 = 1;
*o1 = 4;
*o2 = 1;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_four_two_TypeI_SinglePanel_Restriction):
*n1 = 4;
*n2 = 2;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_eight_one_TypeI_SinglePanel_Restriction):
*n1 = 8;
*n2 = 1;
*o1 = 4;
*o2 = 1;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_four_three_TypeI_SinglePanel_Restriction):
*n1 = 4;
*n2 = 3;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_six_two_TypeI_SinglePanel_Restriction):
*n1 = 4;
*n2 = 2;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_twelve_one_TypeI_SinglePanel_Restriction):
*n1 = 12;
*n2 = 1;
*o1 = 4;
*o2 = 1;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_four_four_TypeI_SinglePanel_Restriction):
*n1 = 4;
*n2 = 4;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_eight_two_TypeI_SinglePanel_Restriction):
*n1 = 8;
*n2 = 2;
*o1 = 4;
*o2 = 4;
break;
case (NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_sixteen_one_TypeI_SinglePanel_Restriction):
*n1 = 16;
*n2 = 1;
*o1 = 4;
*o2 = 1;
break;
default:
AssertFatal(1==0,"Not supported configuration for n1_n2 in codebook configuration");
}
}
void get_x1x2_bitlen_singlepanel(int n1, int n2, int o1, int o2,
int *x1, int *x2, int rank, int codebook_mode) {
// Table 6.3.1.1.2-1 in 38.212
switch(rank){
case 1:
if(n2>1) {
if (codebook_mode == 1) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 2;
}
else {
*x1 = ceil(log2(n1*o1/2)) + ceil(log2(n2*o2/2));
*x2 = 4;
}
}
else{
if (codebook_mode == 1) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 2;
}
else {
*x1 = ceil(log2(n1*o1/2));
*x2 = 4;
}
}
break;
case 2:
if(n1*n2 == 2) {
if (codebook_mode == 1) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 1;
}
else {
*x1 = ceil(log2(n1*o1/2));
*x2 = 3;
}
*x1 += 1;
}
else {
if(n2>1) {
if (codebook_mode == 1) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 3;
}
else {
*x1 = ceil(log2(n1*o1/2)) + ceil(log2(n2*o2/2));
*x2 = 3;
}
}
else{
if (codebook_mode == 1) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 1;
}
else {
*x1 = ceil(log2(n1*o1/2));
*x2 = 3;
}
}
*x1 += 2;
}
break;
case 3:
case 4:
if(n1*n2 == 2) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 1;
}
else {
if(n1*n2 >= 8) {
*x1 = ceil(log2(n1*o1/2)) + ceil(log2(n2*o2)) + 2;
*x2 = 1;
}
else {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2)) + 2;
*x2 = 1;
}
}
break;
case 5:
case 6:
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 1;
break;
case 7:
case 8:
if(n1 == 4 && n2 == 1) {
*x1 = ceil(log2(n1*o1/2)) + ceil(log2(n2*o2));
*x2 = 1;
}
else {
if(n1 > 2 && n2 == 2) {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2/2));
*x2 = 1;
}
else {
*x1 = ceil(log2(n1*o1)) + ceil(log2(n2*o2));
*x2 = 1;
}
}
break;
default:
AssertFatal(1==0,"Invalid rank in x1 x2 bit length computation\n");
}
}
void compute_pmi_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
uint8_t ri_restriction,
nr_csi_report_t *csi_report){
struct NR_CodebookConfig *codebookConfig = csi_reportconfig->codebookConfig;
for(int i=0; i<8; i++) {
csi_report->csi_meas_bitlen.pmi_x1_bitlen[i]=0;
csi_report->csi_meas_bitlen.pmi_x2_bitlen[i]=0;
if (codebookConfig == NULL || ((ri_restriction>>i)&0x01) == 0)
return;
else {
if(codebookConfig->codebookType.present == NR_CodebookConfig__codebookType_PR_type1) {
if(codebookConfig->codebookType.choice.type1->subType.present == NR_CodebookConfig__codebookType__type1__subType_PR_typeI_SinglePanel) {
if(codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel->nrOfAntennaPorts.present ==
NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts_PR_two) {
csi_report->N1 = 1;
csi_report->N2 = 1;
if (i==0)
csi_report->csi_meas_bitlen.pmi_x2_bitlen[i]=2;
if (i==1)
csi_report->csi_meas_bitlen.pmi_x2_bitlen[i]=1;
}
else { // more than two
int n1,n2,o1,o2,x1,x2;
get_n1n2_o1o2_singlepanel(&n1,&n2,&o1,&o2,codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel->nrOfAntennaPorts.choice.moreThanTwo);
get_x1x2_bitlen_singlepanel(n1,n2,o1,o2,&x1,&x2,i+1,codebookConfig->codebookType.choice.type1->codebookMode);
csi_report->N1 = n1;
csi_report->N2 = n2;
csi_report->codebook_mode = codebookConfig->codebookType.choice.type1->codebookMode;
csi_report->csi_meas_bitlen.pmi_x1_bitlen[i]=x1;
csi_report->csi_meas_bitlen.pmi_x2_bitlen[i]=x2;
}
}
else
AssertFatal(1==0,"Type1 Multi-panel Codebook Config not yet implemented\n");
}
else
AssertFatal(1==0,"Type2 Codebook Config not yet implemented\n");
}
}
}
void compute_cqi_bitlen(struct NR_CSI_ReportConfig *csi_reportconfig,
uint8_t ri_restriction,
nr_csi_report_t *csi_report){
struct NR_CodebookConfig *codebookConfig = csi_reportconfig->codebookConfig;
struct NR_CSI_ReportConfig__reportFreqConfiguration *freq_config = csi_reportconfig->reportFreqConfiguration;
if (*freq_config->cqi_FormatIndicator == NR_CSI_ReportConfig__reportFreqConfiguration__cqi_FormatIndicator_widebandCQI) {
for(int i=0; i<8; i++) {
if ((ri_restriction>>i)&0x01) {
csi_report->csi_meas_bitlen.cqi_bitlen[i] = 4;
if(codebookConfig != NULL) {
if (NR_CodebookConfig__codebookType__type1__subType_PR_typeI_SinglePanel == codebookConfig->codebookType.choice.type1->subType.present){
struct NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel *type1single = codebookConfig->codebookType.choice.type1->subType.choice.typeI_SinglePanel;
if (type1single->nrOfAntennaPorts.present == NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts_PR_moreThanTwo) {
if (type1single->nrOfAntennaPorts.choice.moreThanTwo->n1_n2.present >
NR_CodebookConfig__codebookType__type1__subType__typeI_SinglePanel__nrOfAntennaPorts__moreThanTwo__n1_n2_PR_two_one_TypeI_SinglePanel_Restriction) {
// more than 4 antenna ports
if (i > 4)
csi_report->csi_meas_bitlen.cqi_bitlen[i] += 4; // CQI for second TB
}
}
}
}
}
else
csi_report->csi_meas_bitlen.cqi_bitlen[i] = 0;
}
}
else
AssertFatal(1==0,"Sub-band CQI reporting not yet supported");
}
//!TODO : same function can be written to handle csi_resources
void compute_csi_bitlen(NR_CSI_MeasConfig_t *csi_MeasConfig, NR_UE_info_t *UE){
uint8_t csi_report_id = 0;
uint8_t nb_resources = 0;
NR_CSI_ReportConfig__reportQuantity_PR reportQuantity_type;
NR_CSI_ResourceConfigId_t csi_ResourceConfigId;
struct NR_CSI_ResourceConfig *csi_resourceconfig;
// for each CSI measurement report configuration (list of CSI-ReportConfig)
LOG_D(NR_MAC,"Searching %d csi_reports\n",csi_MeasConfig->csi_ReportConfigToAddModList->list.count);
for (csi_report_id=0; csi_report_id < csi_MeasConfig->csi_ReportConfigToAddModList->list.count; csi_report_id++){
struct NR_CSI_ReportConfig *csi_reportconfig = csi_MeasConfig->csi_ReportConfigToAddModList->list.array[csi_report_id];
// MAC structure for CSI measurement reports (per UE and per report)
nr_csi_report_t *csi_report = &UE->csi_report_template[csi_report_id];
// csi-ResourceConfigId of a CSI-ResourceConfig included in the configuration
// (either CSI-RS or SSB)
csi_ResourceConfigId = csi_reportconfig->resourcesForChannelMeasurement;
// looking for CSI-ResourceConfig
int found_resource = 0;
int csi_resourceidx = 0;
while (found_resource == 0 && csi_resourceidx < csi_MeasConfig->csi_ResourceConfigToAddModList->list.count) {
csi_resourceconfig = csi_MeasConfig->csi_ResourceConfigToAddModList->list.array[csi_resourceidx];
if ( csi_resourceconfig->csi_ResourceConfigId == csi_ResourceConfigId)
found_resource = 1;
csi_resourceidx++;
}
AssertFatal(found_resource==1,"Not able to found any CSI-ResourceConfig with csi-ResourceConfigId %ld\n",
csi_ResourceConfigId);
long resourceType = csi_resourceconfig->resourceType;
reportQuantity_type = csi_reportconfig->reportQuantity.present;
csi_report->reportQuantity_type = reportQuantity_type;
// setting the CSI or SSB index list
if (NR_CSI_ReportConfig__reportQuantity_PR_ssb_Index_RSRP == csi_report->reportQuantity_type) {
for (int csi_idx = 0; csi_idx < csi_MeasConfig->csi_SSB_ResourceSetToAddModList->list.count; csi_idx++) {
if (csi_MeasConfig->csi_SSB_ResourceSetToAddModList->list.array[csi_idx]->csi_SSB_ResourceSetId ==
*(csi_resourceconfig->csi_RS_ResourceSetList.choice.nzp_CSI_RS_SSB->csi_SSB_ResourceSetList->list.array[0])){
//We can configure only one SSB resource set from spec 38.331 IE CSI-ResourceConfig
nb_resources= csi_MeasConfig->csi_SSB_ResourceSetToAddModList->list.array[csi_idx]->csi_SSB_ResourceList.list.count;
csi_report->SSB_Index_list = csi_MeasConfig->csi_SSB_ResourceSetToAddModList->list.array[csi_idx]->csi_SSB_ResourceList.list.array;
csi_report->CSI_Index_list = NULL;
break;
}
}
}
else {
if (resourceType == NR_CSI_ResourceConfig__resourceType_periodic) {
AssertFatal(csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList != NULL,
"Wrong settings! Report quantity requires CSI-RS but csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList is NULL\n");
for (int csi_idx = 0; csi_idx < csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList->list.count; csi_idx++) {
if (csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList->list.array[csi_idx]->nzp_CSI_ResourceSetId ==
*(csi_resourceconfig->csi_RS_ResourceSetList.choice.nzp_CSI_RS_SSB->nzp_CSI_RS_ResourceSetList->list.array[0])) {
//For periodic and semi-persistent CSI Resource Settings, the number of CSI-RS Resource Sets configured is limited to S=1 for spec 38.212
nb_resources = csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList->list.array[csi_idx]->nzp_CSI_RS_Resources.list.count;
csi_report->CSI_Index_list = csi_MeasConfig->nzp_CSI_RS_ResourceSetToAddModList->list.array[csi_idx]->nzp_CSI_RS_Resources.list.array;
csi_report->SSB_Index_list = NULL;
break;
}
}
}
else AssertFatal(1==0,"Only periodic resource configuration currently supported\n");
}
LOG_D(NR_MAC,"nb_resources %d\n",nb_resources);
// computation of bit length depending on the report type
switch(reportQuantity_type){
case (NR_CSI_ReportConfig__reportQuantity_PR_ssb_Index_RSRP):
compute_rsrp_bitlen(csi_reportconfig, nb_resources, csi_report);
break;
case (NR_CSI_ReportConfig__reportQuantity_PR_cri_RSRP):
compute_rsrp_bitlen(csi_reportconfig, nb_resources, csi_report);
break;
case (NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_CQI):
csi_report->csi_meas_bitlen.cri_bitlen=ceil(log2(nb_resources));
csi_report->csi_meas_bitlen.ri_restriction = compute_ri_bitlen(csi_reportconfig, csi_report);
compute_cqi_bitlen(csi_reportconfig, csi_report->csi_meas_bitlen.ri_restriction, csi_report);
break;
case (NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_PMI_CQI):
csi_report->csi_meas_bitlen.cri_bitlen=ceil(log2(nb_resources));
csi_report->csi_meas_bitlen.ri_restriction = compute_ri_bitlen(csi_reportconfig, csi_report);
compute_cqi_bitlen(csi_reportconfig, csi_report->csi_meas_bitlen.ri_restriction, csi_report);
compute_pmi_bitlen(csi_reportconfig, csi_report->csi_meas_bitlen.ri_restriction, csi_report);
break;
case (NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_LI_PMI_CQI):
csi_report->csi_meas_bitlen.cri_bitlen=ceil(log2(nb_resources));
csi_report->csi_meas_bitlen.ri_restriction = compute_ri_bitlen(csi_reportconfig, csi_report);
compute_li_bitlen(csi_reportconfig, csi_report->csi_meas_bitlen.ri_restriction, csi_report);
compute_cqi_bitlen(csi_reportconfig, csi_report->csi_meas_bitlen.ri_restriction, csi_report);
compute_pmi_bitlen(csi_reportconfig, csi_report->csi_meas_bitlen.ri_restriction, csi_report);
break;
default:
AssertFatal(1==0,"Not yet supported CSI report quantity type");
}
}
}
uint16_t nr_get_csi_bitlen(NR_UE_info_t *UE,
uint8_t csi_report_id) {
uint16_t csi_bitlen = 0;
uint16_t max_bitlen = 0;
L1_RSRP_bitlen_t * CSI_report_bitlen = NULL;
CSI_Meas_bitlen_t * csi_meas_bitlen = NULL;
if (NR_CSI_ReportConfig__reportQuantity_PR_ssb_Index_RSRP==UE->csi_report_template[csi_report_id].reportQuantity_type||
NR_CSI_ReportConfig__reportQuantity_PR_cri_RSRP==UE->csi_report_template[csi_report_id].reportQuantity_type){
CSI_report_bitlen = &(UE->csi_report_template[csi_report_id].CSI_report_bitlen); //This might need to be moodif for Aperiodic CSI-RS measurements
csi_bitlen+= ((CSI_report_bitlen->cri_ssbri_bitlen * CSI_report_bitlen->nb_ssbri_cri) +
CSI_report_bitlen->rsrp_bitlen +(CSI_report_bitlen->diff_rsrp_bitlen *
(CSI_report_bitlen->nb_ssbri_cri -1 )));
} else{
csi_meas_bitlen = &(UE->csi_report_template[csi_report_id].csi_meas_bitlen); //This might need to be moodif for Aperiodic CSI-RS measurements
uint16_t temp_bitlen;
for (int i=0; i<8; i++) {
temp_bitlen = (csi_meas_bitlen->cri_bitlen+
csi_meas_bitlen->ri_bitlen+
csi_meas_bitlen->li_bitlen[i]+
csi_meas_bitlen->cqi_bitlen[i]+
csi_meas_bitlen->pmi_x1_bitlen[i]+
csi_meas_bitlen->pmi_x2_bitlen[i]);
if(temp_bitlen>max_bitlen)
max_bitlen = temp_bitlen;
}
csi_bitlen += max_bitlen;
}
return csi_bitlen;
}
void nr_csi_meas_reporting(int Mod_idP,
frame_t frame,
sub_frame_t slot) {
NR_ServingCellConfigCommon_t *scc = RC.nrmac[Mod_idP]->common_channels->ServingCellConfigCommon;
const int n_slots_frame = nr_slots_per_frame[*scc->ssbSubcarrierSpacing];
UE_iterator(RC.nrmac[Mod_idP]->UE_info.list, UE ) {
const NR_CellGroupConfig_t *CellGroup = UE->CellGroup;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_UL_BWP_t *ul_bwp = &UE->current_UL_BWP;
const int n_slots_frame = nr_slots_per_frame[ul_bwp->scs];
if ((sched_ctrl->rrc_processing_timer > 0) || (sched_ctrl->ul_failure==1 && get_softmodem_params()->phy_test==0)) {
continue;
}
if (!CellGroup || !CellGroup->spCellConfig || !CellGroup->spCellConfig->spCellConfigDedicated ||
!CellGroup->spCellConfig->spCellConfigDedicated->csi_MeasConfig) continue;
const NR_CSI_MeasConfig_t *csi_measconfig = CellGroup->spCellConfig->spCellConfigDedicated->csi_MeasConfig->choice.setup;
const NR_CSI_MeasConfig_t *csi_measconfig = ul_bwp->csi_MeasConfig;
if (!csi_measconfig) continue;
AssertFatal(csi_measconfig->csi_ReportConfigToAddModList->list.count > 0,
"NO CSI report configuration available");
NR_PUCCH_Config_t *pucch_Config = NULL;
if (sched_ctrl->active_ubwp) {
pucch_Config = sched_ctrl->active_ubwp->bwp_Dedicated->pucch_Config->choice.setup;
} else if (CellGroup &&
CellGroup->spCellConfig &&
CellGroup->spCellConfig->spCellConfigDedicated &&
CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig &&
CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP &&
CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP->pucch_Config->choice.setup) {
pucch_Config = CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP->pucch_Config->choice.setup;
}
NR_PUCCH_Config_t *pucch_Config = ul_bwp->pucch_Config;
for (int csi_report_id = 0; csi_report_id < csi_measconfig->csi_ReportConfigToAddModList->list.count; csi_report_id++){
NR_CSI_ReportConfig_t *csirep = csi_measconfig->csi_ReportConfigToAddModList->list.array[csi_report_id];
@@ -760,14 +212,9 @@ void nr_csi_meas_reporting(int Mod_idP,
curr_pucch->frame = frame;
curr_pucch->ul_slot = sched_slot;
curr_pucch->resource_indicator = res_index;
curr_pucch->csi_bits += nr_get_csi_bitlen(UE,csi_report_id);
curr_pucch->csi_bits += nr_get_csi_bitlen(UE->csi_report_template, csi_report_id);
const NR_SIB1_t *sib1 = RC.nrmac[Mod_idP]->common_channels[0].sib1 ? RC.nrmac[Mod_idP]->common_channels[0].sib1->message.choice.c1->choice.systemInformationBlockType1 : NULL;
NR_BWP_t *genericParameters = get_ul_bwp_genericParameters(sched_ctrl->active_ubwp,
scc,
sib1);
int bwp_start = NRRIV2PRBOFFSET(genericParameters->locationAndBandwidth,MAX_BWP_SIZE);
int bwp_start = ul_bwp->BWPStart;
// going through the list of PUCCH resources to find the one indexed by resource_id
uint16_t *vrb_map_UL = &RC.nrmac[Mod_idP]->common_channels[0].vrb_map_UL[sched_slot * MAX_BWP_SIZE];
@@ -824,7 +271,6 @@ static void handle_dl_harq(NR_UE_info_t * UE,
add_tail_nr_list(&UE->UE_sched_ctrl.available_dl_harq, harq_pid);
harq->round = 0;
harq->ndi ^= 1;
} else if (harq->round >= harq_round_max - 1) {
abort_nr_dl_harq(UE, harq_pid);
LOG_D(NR_MAC, "retransmission error for UE %04x (total %"PRIu64")\n", UE->rnti, UE->mac_stats.dl.errors);
@@ -836,13 +282,13 @@ static void handle_dl_harq(NR_UE_info_t * UE,
}
int checkTargetSSBInFirst64TCIStates_pdschConfig(int ssb_index_t, NR_UE_info_t * UE) {
NR_CellGroupConfig_t *CellGroup = UE->CellGroup;
int nb_tci_states = CellGroup->spCellConfig->spCellConfigDedicated->initialDownlinkBWP->pdsch_Config->choice.setup->tci_StatesToAddModList->list.count;
NR_TCI_State_t *tci =NULL;
int i;
for(i=0; i<nb_tci_states && i<64; i++) {
tci = (NR_TCI_State_t *)CellGroup->spCellConfig->spCellConfigDedicated->initialDownlinkBWP->pdsch_Config->choice.setup->tci_StatesToAddModList->list.array[i];
const NR_PDSCH_Config_t *pdsch_Config = UE->current_DL_BWP.pdsch_Config;
int nb_tci_states = pdsch_Config ? pdsch_Config->tci_StatesToAddModList->list.count : 0;
NR_TCI_State_t *tci =NULL;
for(int i=0; i<nb_tci_states && i<64; i++) {
tci = (NR_TCI_State_t *)pdsch_Config->tci_StatesToAddModList->list.array[i];
if(tci != NULL) {
if(tci->qcl_Type1.referenceSignal.present == NR_QCL_Info__referenceSignal_PR_ssb) {
@@ -862,18 +308,17 @@ int checkTargetSSBInFirst64TCIStates_pdschConfig(int ssb_index_t, NR_UE_info_t *
}
int checkTargetSSBInTCIStates_pdcchConfig(int ssb_index_t, NR_UE_info_t *UE) {
NR_CellGroupConfig_t *CellGroup = UE->CellGroup ;
int nb_tci_states = CellGroup->spCellConfig->spCellConfigDedicated->initialDownlinkBWP->pdsch_Config->choice.setup->tci_StatesToAddModList->list.count;
NR_TCI_State_t *tci =NULL;
NR_TCI_StateId_t *tci_id = NULL;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_ControlResourceSet_t *coreset = sched_ctrl->coreset;
int i;
int flag = 0;
int tci_stateID = -1;
for(i=0; i<nb_tci_states && i<128; i++) {
tci = (NR_TCI_State_t *)CellGroup->spCellConfig->spCellConfigDedicated->initialDownlinkBWP->pdsch_Config->choice.setup->tci_StatesToAddModList->list.array[i];
const NR_PDSCH_Config_t *pdsch_Config = UE->current_DL_BWP.pdsch_Config;
int nb_tci_states = pdsch_Config ? pdsch_Config->tci_StatesToAddModList->list.count : 0;
for(int i=0; i<nb_tci_states && i<128; i++) {
tci = (NR_TCI_State_t *)pdsch_Config->tci_StatesToAddModList->list.array[i];
if(tci != NULL && tci->qcl_Type1.referenceSignal.present == NR_QCL_Info__referenceSignal_PR_ssb) {
if(tci->qcl_Type1.referenceSignal.choice.ssb == ssb_index_t) {
@@ -929,21 +374,12 @@ void tci_handling(NR_UE_info_t *UE, frame_t frame, slot_t slot) {
uint8_t target_ssb_beam_index = curr_ssb_beam_index;
uint8_t is_triggering_ssb_beam_switch =0;
uint8_t ssb_idx = 0;
int pdsch_bwp_id =0;
int pdsch_bwp_id = 0;
int ssb_index[MAX_NUM_SSB] = {0};
int ssb_rsrp[MAX_NUM_SSB] = {0};
uint8_t idx = 0;
NR_UE_DL_BWP_t *dl_bwp = &UE->current_DL_BWP;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
const int bwp_id = sched_ctrl->active_bwp ? sched_ctrl->active_bwp->bwp_Id : 0;
NR_CellGroupConfig_t *CellGroup = UE->CellGroup;
//bwp indicator
int n_dl_bwp=0;
if (CellGroup->spCellConfig &&
CellGroup->spCellConfig->spCellConfigDedicated &&
CellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList)
n_dl_bwp = CellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList->list.count;
uint8_t nr_ssbri_cri = 0;
uint8_t nb_of_csi_ssb_report = UE->csi_report_template[cqi_idx].nb_of_csi_ssb_report;
@@ -951,6 +387,9 @@ void tci_handling(NR_UE_info_t *UE, frame_t frame, slot_t slot) {
uint8_t diff_rsrp_idx = 0;
uint8_t i, j;
//bwp indicator
int n_dl_bwp = dl_bwp->n_dl_bwp;
const int bwp_id = dl_bwp->bwp_id;
if (n_dl_bwp < 4)
pdsch_bwp_id = bwp_id;
else
@@ -1177,7 +616,6 @@ void evaluate_rsrp_report(NR_UE_info_t *UE,
stats->num_rsrp_meas++;
}
void evaluate_cri_report(uint8_t *payload,
uint8_t cri_bitlen,
int cumul_bits,
@@ -1213,9 +651,11 @@ void evaluate_cqi_report(uint8_t *payload,
nr_csi_report_t *csi_report,
int cumul_bits,
uint8_t ri,
NR_UE_sched_ctrl_t *sched_ctrl,
NR_UE_info_t *UE,
long *cqi_Table){
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
//TODO sub-band CQI report not yet implemented
int cqi_bitlen = csi_report->csi_meas_bitlen.cqi_bitlen[ri];
@@ -1238,7 +678,7 @@ void evaluate_cqi_report(uint8_t *payload,
// TODO for wideband case and multiple TB
const int cqi_idx = sched_ctrl->CSI_report.cri_ri_li_pmi_cqi_report.wb_cqi_1tb;
const int mcs_table = sched_ctrl->pdsch_semi_static.mcsTableIdx;
const int mcs_table = UE->current_DL_BWP.mcsTableIdx;
const int cqi_table = sched_ctrl->CSI_report.cri_ri_li_pmi_cqi_report.cqi_table;
sched_ctrl->dl_max_mcs = get_mcs_from_cqi(mcs_table, cqi_table, cqi_idx);
}
@@ -1313,11 +753,12 @@ void extract_pucch_csi_report(NR_CSI_MeasConfig_t *csi_MeasConfig,
NR_ServingCellConfigCommon_t *scc)
{
/** From Table 6.3.1.1.2-3: RI, LI, CQI, and CRI of codebookType=typeI-SinglePanel */
const int n_slots_frame = nr_slots_per_frame[*scc->ssbSubcarrierSpacing];
uint8_t *payload = uci_pdu->csi_part1.csi_part1_payload;
uint16_t bitlen = uci_pdu->csi_part1.csi_part1_bit_len;
NR_CSI_ReportConfig__reportQuantity_PR reportQuantity_type = NR_CSI_ReportConfig__reportQuantity_PR_NOTHING;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_UL_BWP_t *ul_bwp = &UE->current_UL_BWP;
const int n_slots_frame = nr_slots_per_frame[ul_bwp->scs];
int cumul_bits = 0;
int r_index = -1;
for (int csi_report_id = 0; csi_report_id < csi_MeasConfig->csi_ReportConfigToAddModList->list.count; csi_report_id++ ) {
@@ -1352,7 +793,7 @@ void extract_pucch_csi_report(NR_CSI_MeasConfig_t *csi_MeasConfig,
cumul_bits += ri_bitlen;
if (r_index != -1)
skip_zero_padding(&cumul_bits,csi_report,r_index,bitlen);
evaluate_cqi_report(payload,csi_report,cumul_bits,r_index,sched_ctrl,csirep->cqi_Table);
evaluate_cqi_report(payload,csi_report,cumul_bits,r_index,UE,csirep->cqi_Table);
break;
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_PMI_CQI:
cri_bitlen = csi_report->csi_meas_bitlen.cri_bitlen;
@@ -1368,7 +809,7 @@ void extract_pucch_csi_report(NR_CSI_MeasConfig_t *csi_MeasConfig,
pmi_bitlen = evaluate_pmi_report(payload,csi_report,cumul_bits,r_index,sched_ctrl);
sched_ctrl->CSI_report.cri_ri_li_pmi_cqi_report.csi_report_id = csi_report_id;
cumul_bits += pmi_bitlen;
evaluate_cqi_report(payload,csi_report,cumul_bits,r_index,sched_ctrl,csirep->cqi_Table);
evaluate_cqi_report(payload,csi_report,cumul_bits,r_index,UE,csirep->cqi_Table);
break;
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_LI_PMI_CQI:
cri_bitlen = csi_report->csi_meas_bitlen.cri_bitlen;
@@ -1386,7 +827,7 @@ void extract_pucch_csi_report(NR_CSI_MeasConfig_t *csi_MeasConfig,
pmi_bitlen = evaluate_pmi_report(payload,csi_report,cumul_bits,r_index,sched_ctrl);
sched_ctrl->CSI_report.cri_ri_li_pmi_cqi_report.csi_report_id = csi_report_id;
cumul_bits += pmi_bitlen;
evaluate_cqi_report(payload,csi_report,cumul_bits,r_index,sched_ctrl,csirep->cqi_Table);
evaluate_cqi_report(payload,csi_report,cumul_bits,r_index,UE,csirep->cqi_Table);
break;
default:
AssertFatal(1==0, "Invalid or not supported CSI measurement report\n");
@@ -1456,7 +897,7 @@ void handle_nr_uci_pucch_0_1(module_id_t mod_id,
for (int harq_bit = 0; harq_bit < uci_01->harq->num_harq; harq_bit++) {
const uint8_t harq_value = uci_01->harq->harq_list[harq_bit].harq_value;
const uint8_t harq_confidence = uci_01->harq->harq_confidence_level;
NR_UE_harq_t *harq = find_harq(frame, slot, UE, RC.nrmac[mod_id]->harq_round_max);
NR_UE_harq_t *harq = find_harq(frame, slot, UE, RC.nrmac[mod_id]->dl_bler.harq_round_max);
if (!harq) {
LOG_E(NR_MAC, "Oh no! Could not find a harq in %s!\n", __FUNCTION__);
break;
@@ -1465,7 +906,7 @@ void handle_nr_uci_pucch_0_1(module_id_t mod_id,
const int8_t pid = sched_ctrl->feedback_dl_harq.head;
remove_front_nr_list(&sched_ctrl->feedback_dl_harq);
LOG_D(NR_MAC,"%4d.%2d bit %d pid %d ack/nack %d\n",frame, slot, harq_bit,pid,harq_value);
handle_dl_harq(UE, pid, harq_value == 0 && harq_confidence == 0, RC.nrmac[mod_id]->harq_round_max);
handle_dl_harq(UE, pid, harq_value == 0 && harq_confidence == 0, RC.nrmac[mod_id]->dl_bler.harq_round_max);
if (harq_confidence == 1) UE->mac_stats.pucch0_DTX++;
}
}
@@ -1496,15 +937,10 @@ void handle_nr_uci_pucch_2_3_4(module_id_t mod_id,
LOG_E(NR_MAC, "%s(): unknown RNTI %04x in PUCCH UCI\n", __func__, uci_234->rnti);
return;
}
AssertFatal(UE->CellGroup,"Cellgroup is null for UE %04x\n", uci_234->rnti);
AssertFatal(UE->CellGroup->spCellConfig,
"Cellgroup->spCellConfig is null for UE %04x\n", uci_234->rnti);
AssertFatal(UE->CellGroup->spCellConfig->spCellConfigDedicated,
"Cellgroup->spCellConfig->spCellConfigDedicated is null for UE %04x\n", uci_234->rnti);
if ( UE->CellGroup->spCellConfig->spCellConfigDedicated->csi_MeasConfig==NULL)
return;
NR_CSI_MeasConfig_t *csi_MeasConfig = UE->CellGroup->spCellConfig->spCellConfigDedicated->csi_MeasConfig->choice.setup;
NR_CSI_MeasConfig_t *csi_MeasConfig = UE->current_UL_BWP.csi_MeasConfig;
if (csi_MeasConfig==NULL)
return;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
// tpc (power control)
@@ -1518,13 +954,13 @@ void handle_nr_uci_pucch_2_3_4(module_id_t mod_id,
// iterate over received harq bits
for (int harq_bit = 0; harq_bit < uci_234->harq.harq_bit_len; harq_bit++) {
const int acknack = ((uci_234->harq.harq_payload[harq_bit >> 3]) >> harq_bit) & 0x01;
NR_UE_harq_t *harq = find_harq(frame, slot, UE, RC.nrmac[mod_id]->harq_round_max);
NR_UE_harq_t *harq = find_harq(frame, slot, UE, RC.nrmac[mod_id]->dl_bler.harq_round_max);
if (!harq)
break;
DevAssert(harq->is_waiting);
const int8_t pid = sched_ctrl->feedback_dl_harq.head;
remove_front_nr_list(&sched_ctrl->feedback_dl_harq);
handle_dl_harq(UE, pid, uci_234->harq.harq_crc != 1 && acknack, RC.nrmac[mod_id]->harq_round_max);
handle_dl_harq(UE, pid, uci_234->harq.harq_crc != 1 && acknack, RC.nrmac[mod_id]->dl_bler.harq_round_max);
}
}
if ((uci_234->pduBitmap >> 2) & 0x01) {
@@ -1593,7 +1029,6 @@ bool test_acknack_vrb_occupation(NR_UE_sched_ctrl_t *sched_ctrl,
return true;
}
// this function returns an index to NR_sched_pucch structure
// currently this structure contains PUCCH0 at index 0 and PUCCH2 at index 1
// if the function returns -1 it was not possible to schedule acknack
@@ -1607,7 +1042,8 @@ int nr_acknack_scheduling(int mod_id,
const int CC_id = 0;
const int minfbtime = RC.nrmac[mod_id]->minRXTXTIMEpdsch;
const NR_ServingCellConfigCommon_t *scc = RC.nrmac[mod_id]->common_channels[CC_id].ServingCellConfigCommon;
const int n_slots_frame = nr_slots_per_frame[*scc->ssbSubcarrierSpacing];
const NR_UE_UL_BWP_t *ul_bwp = &UE->current_UL_BWP;
const int n_slots_frame = nr_slots_per_frame[ul_bwp->scs];
const NR_TDD_UL_DL_Pattern_t *tdd = scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL;
AssertFatal(tdd || RC.nrmac[mod_id]->common_channels[CC_id].frame_type == FDD, "Dynamic TDD not handled yet\n");
const int nr_slots_period = tdd ? n_slots_frame / get_nb_periods_per_frame(tdd->dl_UL_TransmissionPeriodicity) : n_slots_frame;
@@ -1622,23 +1058,10 @@ int nr_acknack_scheduling(int mod_id,
* later)
* * each UE has dedicated PUCCH Format 0 resources, and we use index 0! */
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_CellGroupConfig_t *cg = UE->CellGroup;
NR_PUCCH_Config_t *pucch_Config = ul_bwp->pucch_Config;
NR_PUCCH_Config_t *pucch_Config = NULL;
if (sched_ctrl->active_ubwp) {
pucch_Config = sched_ctrl->active_ubwp->bwp_Dedicated->pucch_Config->choice.setup;
} else if (cg &&
cg->spCellConfig &&
cg->spCellConfig->spCellConfigDedicated &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP) {
pucch_Config = cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP->pucch_Config->choice.setup;
}
NR_BWP_t *genericParameters = sched_ctrl->active_ubwp ?
&sched_ctrl->active_ubwp->bwp_Common->genericParameters:
&scc->uplinkConfigCommon->initialUplinkBWP->genericParameters;
int bwp_start = NRRIV2PRBOFFSET(genericParameters->locationAndBandwidth,MAX_BWP_SIZE);
int bwp_size = NRRIV2BW(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
int bwp_start = ul_bwp->BWPStart;
int bwp_size = ul_bwp->BWPSize;
NR_sched_pucch_t *pucch = &sched_ctrl->sched_pucch[0];
LOG_D(NR_MAC, "In %s: %4d.%2d Trying to allocate pucch, current DAI %d\n", __FUNCTION__, frame, slot, pucch->dai_c);
@@ -1662,7 +1085,7 @@ int nr_acknack_scheduling(int mod_id,
&& csi_pucch->csi_bits > 0
&& csi_pucch->frame == f
&& csi_pucch->ul_slot == s))
nr_fill_nfapi_pucch(RC.nrmac[mod_id], frame, slot, pucch, UE);
nr_fill_nfapi_pucch(RC.nrmac[mod_id], frame, slot, pucch, UE);
memset(pucch, 0, sizeof(*pucch));
pucch->frame = s == n_slots_frame - 1 ? (f + 1) % 1024 : f;
@@ -1693,22 +1116,13 @@ int nr_acknack_scheduling(int mod_id,
LOG_D(NR_MAC, "In %s: pucch_acknak 1. DL %4d.%2d, UL_ACK %4d.%2d, DAI_C %d\n", __FUNCTION__, frame, slot, pucch->frame, pucch->ul_slot, pucch->dai_c);
// this is hardcoded for now as ue specific only if we are not on the initialBWP (to be fixed to allow ue_Specific also on initialBWP
NR_BWP_UplinkDedicated_t *ubwpd=NULL;
nr_dci_format_t dci_format = NR_DL_DCI_FORMAT_1_0;
if(is_common == 0)
dci_format = UE->current_DL_BWP.dci_format;
if (cg &&
cg->spCellConfig &&
cg->spCellConfig->spCellConfigDedicated &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP)
ubwpd = cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP;
NR_SearchSpace__searchSpaceType_PR ss_type = (is_common==0 && (sched_ctrl->active_bwp || ubwpd)) ? NR_SearchSpace__searchSpaceType_PR_ue_Specific: NR_SearchSpace__searchSpaceType_PR_common;
uint8_t pdsch_to_harq_feedback[8];
const int bwp_id = sched_ctrl->active_bwp ? sched_ctrl->active_bwp->bwp_Id : 0;
int max_fb_time = 0;
get_pdsch_to_harq_feedback(UE, bwp_id, ss_type, &max_fb_time, pdsch_to_harq_feedback);
get_pdsch_to_harq_feedback(pucch_Config, dci_format, &max_fb_time, pdsch_to_harq_feedback);
LOG_D(NR_MAC, "In %s: 1b. DL %4d.%2d, UL_ACK %4d.%2d, DAI_C %d\n", __FUNCTION__, frame,slot,pucch->frame,pucch->ul_slot,pucch->dai_c);
/* there is a HARQ. Check whether we can use it for this ACKNACK */
@@ -1729,13 +1143,12 @@ int nr_acknack_scheduling(int mod_id,
// we cannot reach this timing anymore, allocate and try again
const int f = pucch->frame;
const int s = pucch->ul_slot;
const int n_slots_frame = nr_slots_per_frame[*scc->ssbSubcarrierSpacing];
LOG_D(NR_MAC, "In %s: %4d.%2d DAI > 0, cannot reach timing for pucch in %4d.%2d, advancing slot by 1 and trying again\n", __FUNCTION__, frame, slot, f, s);
if (!(csi_pucch &&
csi_pucch->csi_bits > 0 &&
csi_pucch->frame == f &&
csi_pucch->ul_slot == s))
nr_fill_nfapi_pucch(RC.nrmac[mod_id], frame, slot, pucch, UE);
nr_fill_nfapi_pucch(RC.nrmac[mod_id], frame, slot, pucch, UE);
memset(pucch, 0, sizeof(*pucch));
pucch->frame = s == n_slots_frame - 1 ? (f + 1) % 1024 : f;
if(((s + 1)%nr_slots_period) == 0)
@@ -1834,10 +1247,10 @@ int nr_acknack_scheduling(int mod_id,
csi_pucch->ul_slot == pucch->ul_slot) {
// skip the CSI PUCCH if it is present and if in the next frame/slot
// and if we don't multiplex
// FIXME currently we support at most 11 bits in pucch2 so skip also in that case
/* FIXME currently we support at most 11 bits in pucch2 so skip also in that case.
We need to set the limit to 10 because SR scheduling has been moved afterwards */
if(!csi_pucch->simultaneous_harqcsi
|| ((csi_pucch->csi_bits + csi_pucch->dai_c) >= 11)) {
|| ((csi_pucch->csi_bits + csi_pucch->dai_c) >= 10)) {
LOG_D(NR_MAC,"Cannot multiplex csi_pucch %d +csi_pucch->dai_c %d for %d.%d\n",csi_pucch->csi_bits,csi_pucch->dai_c,csi_pucch->frame,csi_pucch->ul_slot);
nr_fill_nfapi_pucch(RC.nrmac[mod_id], frame, slot, csi_pucch, UE);
memset(csi_pucch, 0, sizeof(*csi_pucch));
@@ -1857,9 +1270,7 @@ int nr_acknack_scheduling(int mod_id,
else {
csi_pucch->timing_indicator = ind_found;
csi_pucch->dai_c++;
// keep updating format 2 indicator
pucch->timing_indicator = ind_found; // index in the list of timing indicators
pucch->dai_c++;
memset(pucch,0,sizeof(*pucch));
LOG_D(NR_MAC,"multiplexing csi_pucch %d +csi_pucch->dai_c %d for %d.%d\n",csi_pucch->csi_bits,csi_pucch->dai_c,csi_pucch->frame,csi_pucch->ul_slot);
return 1;
@@ -1892,30 +1303,20 @@ void nr_sr_reporting(gNB_MAC_INST *nrmac, frame_t SFN, sub_frame_t slot)
{
if (!is_xlsch_in_slot(nrmac->ulsch_slot_bitmap[slot / 64], slot))
return;
NR_ServingCellConfigCommon_t *scc = nrmac->common_channels->ServingCellConfigCommon;
const int n_slots_frame = nr_slots_per_frame[*scc->ssbSubcarrierSpacing];
UE_iterator(nrmac->UE_info.list, UE) {
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_UL_BWP_t *ul_bwp = &UE->current_UL_BWP;
const int n_slots_frame = nr_slots_per_frame[ul_bwp->scs];
if (sched_ctrl->ul_failure==1 || sched_ctrl->rrc_processing_timer>0) continue;
NR_PUCCH_Config_t *pucch_Config = NULL;
if (sched_ctrl->active_ubwp) {
pucch_Config = sched_ctrl->active_ubwp->bwp_Dedicated->pucch_Config->choice.setup;
} else if (UE->CellGroup &&
UE->CellGroup->spCellConfig &&
UE->CellGroup->spCellConfig->spCellConfigDedicated &&
UE->CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig &&
UE->CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP &&
UE->CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP->pucch_Config->choice.setup) {
pucch_Config = UE->CellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP->pucch_Config->choice.setup;
}
else continue;
if (!pucch_Config->schedulingRequestResourceToAddModList)
continue;
NR_PUCCH_Config_t *pucch_Config = ul_bwp->pucch_Config;
if (!pucch_Config || !pucch_Config->schedulingRequestResourceToAddModList)
continue;
AssertFatal(pucch_Config->schedulingRequestResourceToAddModList->list.count>0,"NO SR configuration available");
for (int SR_resource_id =0; SR_resource_id < pucch_Config->schedulingRequestResourceToAddModList->list.count;SR_resource_id++) {
for (int SR_resource_id = 0; SR_resource_id < pucch_Config->schedulingRequestResourceToAddModList->list.count;SR_resource_id++) {
NR_SchedulingRequestResourceConfig_t *SchedulingRequestResourceConfig = pucch_Config->schedulingRequestResourceToAddModList->list.array[SR_resource_id];
int SR_period; int SR_offset;
+126 -226
View File
@@ -36,19 +36,9 @@
#include <openair2/UTIL/OPT/opt.h>
#include "LAYER2/NR_MAC_COMMON/nr_mac_extern.h"
extern void process_CellGroup(NR_CellGroupConfig_t *CellGroup, NR_UE_sched_ctrl_t *sched_ctrl);
//#define SRS_IND_DEBUG
int get_dci_format(NR_UE_sched_ctrl_t *sched_ctrl) {
int dci_format = sched_ctrl->search_space && sched_ctrl->search_space->searchSpaceType &&
sched_ctrl->search_space->searchSpaceType->present == NR_SearchSpace__searchSpaceType_PR_ue_Specific ?
NR_UL_DCI_FORMAT_0_1 : NR_UL_DCI_FORMAT_0_0;
return(dci_format);
}
const int get_ul_tda(const gNB_MAC_INST *nrmac, const NR_ServingCellConfigCommon_t *scc, int slot) {
/* there is a mixed slot only when in TDD */
@@ -336,38 +326,41 @@ int nr_process_mac_pdu( instance_t module_idP,
case UL_SCH_LCID_DTCH ... (UL_SCH_LCID_DTCH + 28):
// check if LCID is valid at current time.
if (!get_mac_len(pduP, pdu_len, &mac_len, &mac_subheader_len))
return 0;
if (!get_mac_len(pduP, pdu_len, &mac_len, &mac_subheader_len)) {
return 0;
}
LOG_D(NR_MAC, "[UE %04x] %d.%d : ULSCH -> UL-%s %d (gNB %ld, %d bytes)\n",
UE->rnti,
frameP,
slot,
rx_lcid<4?"DCCH":"DTCH",
rx_lcid,
module_idP,
mac_len);
UE->mac_stats.ul.lc_bytes[rx_lcid] += mac_len;
LOG_D(NR_MAC, "[UE %04x] %d.%d : ULSCH -> UL-%s %d (gNB %ld, %d bytes)\n",
UE->rnti,
frameP,
slot,
rx_lcid<4?"DCCH":"DTCH",
rx_lcid,
module_idP,
mac_len);
UE->mac_stats.ul.lc_bytes[rx_lcid] += mac_len;
mac_rlc_data_ind(module_idP,
UE->rnti,
module_idP,
frameP,
ENB_FLAG_YES,
MBMS_FLAG_NO,
rx_lcid,
(char *)(pduP + mac_subheader_len),
mac_len,
1,
NULL);
mac_rlc_data_ind(module_idP,
UE->rnti,
module_idP,
frameP,
ENB_FLAG_YES,
MBMS_FLAG_NO,
rx_lcid,
(char *)(pduP + mac_subheader_len),
mac_len,
1,
NULL);
/* Updated estimated buffer when receiving data */
if (sched_ctrl->estimated_ul_buffer >= mac_len)
sched_ctrl->estimated_ul_buffer -= mac_len;
else
sched_ctrl->estimated_ul_buffer = 0;
break;
/* Updated estimated buffer when receiving data */
if (sched_ctrl->estimated_ul_buffer >= mac_len) {
sched_ctrl->estimated_ul_buffer -= mac_len;
} else {
sched_ctrl->estimated_ul_buffer = 0;
}
break;
default:
LOG_E(NR_MAC, "Received unknown MAC header (LCID = 0x%02x)\n", rx_lcid);
@@ -402,7 +395,7 @@ int nr_process_mac_pdu( instance_t module_idP,
return 0;
}
void abort_nr_ul_harq( NR_UE_info_t* UE, int8_t harq_pid)
void abort_nr_ul_harq(NR_UE_info_t *UE, int8_t harq_pid)
{
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_ul_harq_t *harq = &sched_ctrl->ul_harq_processes[harq_pid];
@@ -452,7 +445,7 @@ void handle_nr_ul_harq(const int CC_idP,
remove_front_nr_list(&sched_ctrl->feedback_ul_harq);
sched_ctrl->ul_harq_processes[harq_pid].is_waiting = false;
if(sched_ctrl->ul_harq_processes[harq_pid].round >= RC.nrmac[mod_id]->harq_round_max - 1) {
if(sched_ctrl->ul_harq_processes[harq_pid].round >= RC.nrmac[mod_id]->ul_bler.harq_round_max - 1) {
abort_nr_ul_harq(UE, harq_pid);
} else {
sched_ctrl->ul_harq_processes[harq_pid].round++;
@@ -473,7 +466,7 @@ void handle_nr_ul_harq(const int CC_idP,
harq_pid,
crc_pdu->rnti);
add_tail_nr_list(&sched_ctrl->available_ul_harq, harq_pid);
} else if (harq->round >= RC.nrmac[mod_id]->harq_round_max - 1) {
} else if (harq->round >= RC.nrmac[mod_id]->ul_bler.harq_round_max - 1) {
abort_nr_ul_harq(UE, harq_pid);
LOG_D(NR_MAC,
"RNTI %04x: Ulharq id %d crc failed in all rounds\n",
@@ -546,7 +539,6 @@ void nr_rx_sdu(const module_id_t gnb_mod_idP,
else{
LOG_D(NR_MAC,"[UE %04x] Detected DTX : increasing UE TX power\n",UE->rnti);
UE_scheduling_control->tpc0 = 1;
}
#if defined(ENABLE_MAC_PAYLOAD_DEBUG)
@@ -749,14 +741,13 @@ void nr_rx_sdu(const module_id_t gnb_mod_idP,
return;
}
if (ra->msg3_round >= MAX_HARQ_ROUNDS - 1) {
LOG_D(NR_MAC, "Random Access %i failed at state %i (Reached msg3 max harq rounds)\n", i, ra->state);
if (ra->msg3_round >= gNB_mac->ul_bler.harq_round_max - 1) {
LOG_W(NR_MAC, "Random Access %i failed at state %i (Reached msg3 max harq rounds)\n", i, ra->state);
nr_mac_remove_ra_rnti(gnb_mod_idP, ra->rnti);
nr_clear_ra_proc(gnb_mod_idP, CC_idP, frameP, ra);
return;
}
LOG_D(NR_MAC, "Random Access %i Msg3 CRC did not pass)\n", i);
ra->msg3_round++;
@@ -815,23 +806,14 @@ void handle_nr_srs_measurements(const module_id_t module_id,
}
}
long get_K2(NR_ServingCellConfigCommon_t *scc,
NR_ServingCellConfigCommonSIB_t *scc_sib1,
NR_BWP_Uplink_t *ubwp,
long get_K2(NR_PUSCH_TimeDomainResourceAllocationList_t *tdaList,
int time_domain_assignment,
int mu) {
NR_PUSCH_TimeDomainResourceAllocation_t *tda_list = NULL;
if(ubwp) {
tda_list = ubwp->bwp_Common->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList->list.array[time_domain_assignment];
} else if(scc) {
tda_list = scc->uplinkConfigCommon->initialUplinkBWP->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList->list.array[time_domain_assignment];
} else if(scc_sib1) {
tda_list = scc_sib1->uplinkConfigCommon->initialUplinkBWP.pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList->list.array[time_domain_assignment];
}
NR_PUSCH_TimeDomainResourceAllocation_t *tda = tdaList->list.array[time_domain_assignment];
if (tda_list->k2)
return *tda_list->k2;
if (tda->k2)
return *tda->k2;
else if (mu < 2)
return 1;
else if (mu == 2)
@@ -846,10 +828,8 @@ static bool nr_UE_is_to_be_scheduled(const NR_ServingCellConfigCommon_t *scc,
const int n = nr_slots_per_frame[*scc->ssbSubcarrierSpacing];
const int now = frame * n + slot;
const NR_UE_sched_ctrl_t *sched_ctrl =&UE->UE_sched_ctrl;
const NR_TDD_UL_DL_Pattern_t *tdd =
scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL;
int num_slots_per_period;
@@ -895,40 +875,22 @@ static bool allocate_ul_retransmission(gNB_MAC_INST *nrmac,
const int CC_id = 0;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_sched_pusch_t *retInfo = &sched_ctrl->ul_harq_processes[harq_pid].sched_pusch;
NR_CellGroupConfig_t *cg = UE->CellGroup;
NR_BWP_UplinkDedicated_t *ubwpd = cg && cg->spCellConfig && cg->spCellConfig->spCellConfigDedicated &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig ?
cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP : NULL;
NR_BWP_t *genericParameters = get_ul_bwp_genericParameters(sched_ctrl->active_ubwp,
(NR_ServingCellConfigCommon_t *)scc,
sib1);
int rbStart = 0; // wrt BWP start
const uint16_t bwpSize = NRRIV2BW(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
const uint16_t bwpSize = UE->current_UL_BWP.BWPSize;
const uint8_t nrOfLayers = 1;
const uint8_t num_dmrs_cdm_grps_no_data = (sched_ctrl->active_bwp || ubwpd) ? 1 : 2;
LOG_D(NR_MAC,"retInfo->time_domain_allocation = %d, tda = %d\n", retInfo->time_domain_allocation, tda);
LOG_D(NR_MAC,"num_dmrs_cdm_grps_no_data %d, tbs %d\n",num_dmrs_cdm_grps_no_data, retInfo->tb_size);
LOG_D(NR_MAC,"tbs %d\n",retInfo->tb_size);
if (tda == retInfo->time_domain_allocation) {
/* check whether we need to switch the TDA allocation since tha last
* (re-)transmission */
NR_pusch_semi_static_t *ps = &sched_ctrl->pusch_semi_static;
int dci_format = get_dci_format(sched_ctrl);
if (ps->time_domain_allocation != tda
|| ps->dci_format != dci_format
|| ps->nrOfLayers != nrOfLayers
|| ps->num_dmrs_cdm_grps_no_data != num_dmrs_cdm_grps_no_data) {
nr_set_pusch_semi_static(sib1,
|| ps->nrOfLayers != nrOfLayers) {
nr_set_pusch_semi_static(&UE->current_UL_BWP,
scc,
sched_ctrl->active_ubwp,
ubwpd,
dci_format,
tda,
num_dmrs_cdm_grps_no_data,
nrOfLayers,
ps);
}
@@ -944,14 +906,9 @@ static bool allocate_ul_retransmission(gNB_MAC_INST *nrmac,
LOG_D(NR_MAC, "%s(): retransmission keeping TDA %d and TBS %d\n", __func__, tda, retInfo->tb_size);
} else {
NR_pusch_semi_static_t temp_ps;
int dci_format = get_dci_format(sched_ctrl);
nr_set_pusch_semi_static(sib1,
nr_set_pusch_semi_static(&UE->current_UL_BWP,
scc,
sched_ctrl->active_ubwp,
ubwpd,
dci_format,
tda,
num_dmrs_cdm_grps_no_data,
nrOfLayers,
&temp_ps);
/* the retransmission will use a different time domain allocation, check
@@ -1046,13 +1003,13 @@ static bool allocate_ul_retransmission(gNB_MAC_INST *nrmac,
return true;
}
void update_ul_ue_R_Qm(NR_sched_pusch_t *sched_pusch, const NR_pusch_semi_static_t *ps)
{
const int mcs = sched_pusch->mcs;
sched_pusch->R = nr_get_code_rate_ul(mcs, ps->mcs_table);
sched_pusch->Qm = nr_get_Qm_ul(mcs, ps->mcs_table);
void update_ul_ue_R_Qm(NR_sched_pusch_t *sched_pusch, const NR_PUSCH_Config_t *pusch_Config, const int mcs_table) {
if (ps->pusch_Config && ps->pusch_Config->tp_pi2BPSK && ((ps->mcs_table == 3 && mcs < 2) || (ps->mcs_table == 4 && mcs < 6))) {
const int mcs = sched_pusch->mcs;
sched_pusch->R = nr_get_code_rate_ul(mcs, mcs_table);
sched_pusch->Qm = nr_get_Qm_ul(mcs, mcs_table);
if (pusch_Config && pusch_Config->tp_pi2BPSK && ((mcs_table == 3 && mcs < 2) || (mcs_table == 4 && mcs < 6))) {
sched_pusch->R >>= 1;
sched_pusch->Qm <<= 1;
}
@@ -1071,7 +1028,7 @@ static int comparator(const void *p, const void *q) {
void pf_ul(module_id_t module_id,
frame_t frame,
sub_frame_t slot,
NR_UE_info_t *UE_list[],
NR_UE_info_t *UE_list[],
int max_num_ue,
int n_rb_sched,
uint16_t *rballoc_mask) {
@@ -1095,18 +1052,11 @@ void pf_ul(module_id_t module_id,
LOG_D(NR_MAC,"pf_ul: preparing UL scheduling for UE %04x\n",UE->rnti);
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_BWP_t *genericParameters = get_ul_bwp_genericParameters(sched_ctrl->active_ubwp,
scc,
sib1);
NR_UE_UL_BWP_t *current_BWP = &UE->current_UL_BWP;
int rbStart = 0; // wrt BWP start
NR_CellGroupConfig_t *cg = UE->CellGroup;
NR_BWP_UplinkDedicated_t *ubwpd = cg && cg->spCellConfig && cg->spCellConfig->spCellConfigDedicated &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig ?
cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP : NULL;
const uint16_t bwpSize = NRRIV2BW(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
const uint16_t bwpSize = current_BWP->BWPSize;
NR_sched_pusch_t *sched_pusch = &sched_ctrl->sched_pusch;
NR_pusch_semi_static_t *ps = &sched_ctrl->pusch_semi_static;
const NR_mac_dir_stats_t *stats = &UE->mac_stats.ul;
@@ -1132,10 +1082,11 @@ void pf_ul(module_id_t module_id,
/* reduce max_num_ue once we are sure UE can be allocated, i.e., has CCE */
remainUEs--;
// we have filled all with mandatory retransmissions
// no need to schedule new transmissions
if (remainUEs == 0)
// we have filled all with mandatory retransmissions
// no need to schedule new transmissions
return;
return;
continue;
}
const int B = max(0, sched_ctrl->estimated_ul_buffer - sched_ctrl->sched_ul_bytes);
@@ -1143,12 +1094,16 @@ void pf_ul(module_id_t module_id,
const bool do_sched = nr_UE_is_to_be_scheduled(scc, 0, UE, sched_pusch->frame, sched_pusch->slot, nrmac->ulsch_max_frame_inactivity);
LOG_D(NR_MAC,"pf_ul: do_sched UE %04x => %s\n",UE->rnti,do_sched ? "yes" : "no");
if ((B == 0 && !do_sched) || (sched_ctrl->rrc_processing_timer > 0))
if ((B == 0 && !do_sched) || (sched_ctrl->rrc_processing_timer > 0)) {
continue;
}
const NR_bler_options_t *bo = &nrmac->ul_bler;
const int max_mcs = bo->max_mcs; /* no per-user maximum MCS yet */
sched_pusch->mcs = get_mcs_from_bler(bo, stats, &UE->UE_sched_ctrl.ul_bler_stats, max_mcs, frame);
if (bo->harq_round_max == 1)
sched_pusch->mcs = max_mcs;
else
sched_pusch->mcs = get_mcs_from_bler(bo, stats, &UE->UE_sched_ctrl.ul_bler_stats, max_mcs, frame);
/* Schedule UE on SR or UL inactivity and no data (otherwise, will be scheduled
* based on data to transmit) */
@@ -1158,12 +1113,12 @@ void pf_ul(module_id_t module_id,
const uint32_t Y = get_Y(sched_ctrl->search_space, slot, UE->rnti);
uint8_t nr_of_candidates;
for (int i=0; i<5; i++) {
// for now taking the lowest value among the available aggregation levels
find_aggregation_candidates(&sched_ctrl->aggregation_level,
&nr_of_candidates,
sched_ctrl->search_space,
1<<i);
if(nr_of_candidates>0) break;
// for now taking the lowest value among the available aggregation levels
find_aggregation_candidates(&sched_ctrl->aggregation_level,
&nr_of_candidates,
sched_ctrl->search_space,
1<<i);
if(nr_of_candidates>0) break;
}
int CCEIndex = find_pdcch_candidate(RC.nrmac[module_id],
CC_id,
@@ -1172,38 +1127,31 @@ void pf_ul(module_id_t module_id,
&sched_ctrl->sched_pdcch,
sched_ctrl->coreset,
Y);
if (CCEIndex<0) {
LOG_D(NR_MAC, "%4d.%2d no free CCE for UL DCI UE %04x (BSR 0)\n", frame, slot, UE->rnti);
continue;
LOG_D(NR_MAC, "%4d.%2d no free CCE for UL DCI UE %04x (BSR 0)\n", frame, slot, UE->rnti);
continue;
}
/* reduce max_num_ue once we are sure UE can be allocated, i.e., has CCE */
remainUEs--;
// we have filled all with mandatory retransmissions
// no need to schedule new transmissions
if (remainUEs == 0)
// we have filled all with mandatory retransmissions
// no need to schedule new transmissions
return;
return;
/* Save PUSCH field */
/* we want to avoid a lengthy deduction of DMRS and other parameters in
* every TTI if we can save it, so check whether dci_format, TDA, or
* every TTI if we can save it, so check whether TDA, or
* num_dmrs_cdm_grps_no_data has changed and only then recompute */
const uint8_t nrOfLayers = 1;
const uint8_t num_dmrs_cdm_grps_no_data = (sched_ctrl->active_ubwp || ubwpd) ? 1 : 2;
int dci_format = get_dci_format(sched_ctrl);
const int tda = get_ul_tda(nrmac, scc, sched_pusch->slot);
if (ps->time_domain_allocation != tda
|| ps->dci_format != dci_format
|| ps->nrOfLayers != nrOfLayers
|| ps->num_dmrs_cdm_grps_no_data != num_dmrs_cdm_grps_no_data) {
nr_set_pusch_semi_static(sib1,
|| ps->nrOfLayers != nrOfLayers) {
nr_set_pusch_semi_static(current_BWP,
scc,
sched_ctrl->active_ubwp,
ubwpd,
dci_format,
tda,
num_dmrs_cdm_grps_no_data,
nrOfLayers,
ps);
}
@@ -1228,7 +1176,7 @@ void pf_ul(module_id_t module_id,
NR_sched_pusch_t *sched_pusch = &sched_ctrl->sched_pusch;
sched_pusch->mcs = min(nrmac->min_grant_mcs, sched_pusch->mcs);
update_ul_ue_R_Qm(sched_pusch, ps);
update_ul_ue_R_Qm(sched_pusch, current_BWP->pusch_Config, current_BWP->mcs_table);
sched_pusch->rbStart = rbStart;
sched_pusch->rbSize = min_rb;
sched_pusch->tb_size = nr_compute_tbs(sched_pusch->Qm,
@@ -1251,7 +1199,7 @@ void pf_ul(module_id_t module_id,
/* Create UE_sched for UEs eligibale for new data transmission*/
/* Calculate coefficient*/
const uint32_t tbs = ul_pf_tbs[ps->mcs_table][sched_pusch->mcs];
const uint32_t tbs = ul_pf_tbs[current_BWP->mcs_table][sched_pusch->mcs];
float coeff_ue = (float) tbs / UE->ul_thr_ue;
LOG_D(NR_MAC,"rnti %04x b %d, ul_thr_ue %f, tbs %d, coeff_ue %f\n",
UE->rnti, b, UE->ul_thr_ue, tbs, coeff_ue);
@@ -1278,7 +1226,7 @@ void pf_ul(module_id_t module_id,
sched_ctrl->search_space,
1<<i);
if(nr_of_candidates>0)
break;
break;
}
int CCEIndex = find_pdcch_candidate(RC.nrmac[module_id],
CC_id,
@@ -1294,44 +1242,29 @@ void pf_ul(module_id_t module_id,
}
else LOG_D(NR_MAC, "%4d.%2d free CCE for UL DCI UE %04x\n",frame,slot, iterator->UE->rnti);
NR_CellGroupConfig_t *cg = iterator->UE->CellGroup;
NR_BWP_UplinkDedicated_t *ubwpd = cg && cg->spCellConfig && cg->spCellConfig->spCellConfigDedicated
&& cg->spCellConfig->spCellConfigDedicated->uplinkConfig ?
cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP : NULL;
NR_UE_UL_BWP_t *current_BWP = &iterator->UE->current_UL_BWP;
NR_BWP_t *genericParameters = get_ul_bwp_genericParameters(sched_ctrl->active_ubwp,
scc,
sib1);
int rbStart = sched_ctrl->active_ubwp ? NRRIV2PRBOFFSET(genericParameters->locationAndBandwidth, MAX_BWP_SIZE) : 0;
const uint16_t bwpSize = NRRIV2BW(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
const uint16_t bwpSize = current_BWP->BWPSize;
NR_sched_pusch_t *sched_pusch = &sched_ctrl->sched_pusch;
NR_pusch_semi_static_t *ps = &sched_ctrl->pusch_semi_static;
/* Save PUSCH field */
/* we want to avoid a lengthy deduction of DMRS and other parameters in
* every TTI if we can save it, so check whether dci_format, TDA, or
* every TTI if we can save it, so check whether TDA, or
* num_dmrs_cdm_grps_no_data has changed and only then recompute */
const uint8_t nrOfLayers = 1;
const uint8_t num_dmrs_cdm_grps_no_data = (sched_ctrl->active_ubwp || ubwpd) ? 1 : 2;
int dci_format = get_dci_format(sched_ctrl);
const int tda = get_ul_tda(nrmac, scc, sched_pusch->slot);
if (ps->time_domain_allocation != tda
|| ps->dci_format != dci_format
|| ps->nrOfLayers != nrOfLayers
|| ps->num_dmrs_cdm_grps_no_data != num_dmrs_cdm_grps_no_data) {
nr_set_pusch_semi_static(sib1,
|| ps->nrOfLayers != nrOfLayers) {
nr_set_pusch_semi_static(current_BWP,
scc,
sched_ctrl->active_ubwp,
ubwpd,
dci_format,
tda,
num_dmrs_cdm_grps_no_data,
nrOfLayers,
ps);
}
update_ul_ue_R_Qm(sched_pusch, ps);
update_ul_ue_R_Qm(sched_pusch, current_BWP->pusch_Config, current_BWP->mcs_table);
int rbStart = 0;
const uint16_t slbitmap = SL_to_bitmap(ps->startSymbolIndex, ps->nrOfSymbols);
while (rbStart < bwpSize && (rballoc_mask[rbStart] & slbitmap) != slbitmap)
rbStart++;
@@ -1379,8 +1312,8 @@ void pf_ul(module_id_t module_id,
n_rb_sched -= sched_pusch->rbSize;
for (int rb = 0; rb < sched_ctrl->sched_pusch.rbSize; rb++)
rballoc_mask[rb + sched_ctrl->sched_pusch.rbStart] ^= slbitmap;
/* reduce max_num_ue once we are sure UE can be allocated, i.e., has CCE */
remainUEs--;
iterator++;
@@ -1397,11 +1330,8 @@ bool nr_fr1_ulsch_preprocessor(module_id_t module_id, frame_t frame, sub_frame_t
AssertFatal(scc!=NULL || scc_sib1!=NULL,"We need one serving cell config common\n");
const int mu = scc ? scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.subcarrierSpacing :
scc_sib1->uplinkConfigCommon->initialUplinkBWP.genericParameters.subcarrierSpacing;
// no UEs
if (nr_mac->UE_info.list[0] == NULL)
// no UEs
return false;
const int CC_id = 0;
@@ -1411,14 +1341,16 @@ bool nr_fr1_ulsch_preprocessor(module_id_t module_id, frame_t frame, sub_frame_t
* TDAs yet). If the TDA is negative, it means that there is no UL slot to
* schedule now (slot + k2 is not UL slot) */
NR_UE_sched_ctrl_t *sched_ctrl = &nr_mac->UE_info.list[0]->UE_sched_ctrl;
NR_UE_UL_BWP_t *current_BWP = &nr_mac->UE_info.list[0]->current_UL_BWP;
int mu = current_BWP->scs;
const int temp_tda = get_ul_tda(nr_mac, scc, slot);
int K2 = get_K2(scc, scc_sib1, sched_ctrl->active_ubwp, temp_tda, mu);
int K2 = get_K2(current_BWP->tdaList, temp_tda, mu);
const int sched_frame = (frame + (slot + K2 >= nr_slots_per_frame[mu])) & 1023;
const int sched_slot = (slot + K2) % nr_slots_per_frame[mu];
const int tda = get_ul_tda(nr_mac, scc, sched_slot);
if (tda < 0)
return false;
DevAssert(K2 == get_K2(scc, scc_sib1, sched_ctrl->active_ubwp, tda, mu));
DevAssert(K2 == get_K2(current_BWP->tdaList, tda, mu));
if (!is_xlsch_in_slot(nr_mac->ulsch_slot_bitmap[sched_slot / 64], sched_slot))
return false;
@@ -1432,7 +1364,7 @@ bool nr_fr1_ulsch_preprocessor(module_id_t module_id, frame_t frame, sub_frame_t
is_xlsch_in_slot(nr_mac->ulsch_slot_bitmap[sched_slot / 64], sched_slot);
// FIXME: Avoid mixed slots for initialUplinkBWP
if (sched_ctrl->active_ubwp==NULL && is_mixed_slot)
if (current_BWP->bwp_id==0 && is_mixed_slot)
return false;
// Avoid slots with the SRS
@@ -1447,9 +1379,9 @@ bool nr_fr1_ulsch_preprocessor(module_id_t module_id, frame_t frame, sub_frame_t
sched_ctrl->sched_pusch.frame = sched_frame;
UE_iterator(nr_mac->UE_info.list, UE2) {
NR_UE_sched_ctrl_t *sched_ctrl = &UE2->UE_sched_ctrl;
AssertFatal(K2 == get_K2(scc,scc_sib1,sched_ctrl->active_ubwp, tda, mu),
AssertFatal(K2 == get_K2(current_BWP->tdaList, tda, mu),
"Different K2, %d(UE%d) != %ld(UE%04x)\n",
K2, 0, get_K2(scc,scc_sib1,sched_ctrl->active_ubwp, tda, mu), UE2->rnti);
K2, 0, get_K2(current_BWP->tdaList, tda, mu), UE2->rnti);
sched_ctrl->sched_pusch.slot = sched_slot;
sched_ctrl->sched_pusch.frame = sched_frame;
}
@@ -1460,24 +1392,10 @@ bool nr_fr1_ulsch_preprocessor(module_id_t module_id, frame_t frame, sub_frame_t
uint16_t *vrb_map_UL =
&RC.nrmac[module_id]->common_channels[CC_id].vrb_map_UL[sched_slot * MAX_BWP_SIZE];
NR_BWP_t *genericParameters = get_ul_bwp_genericParameters(sched_ctrl->active_ubwp,
scc,
sib1);
const uint16_t bwpSize = current_BWP->BWPSize;
const uint16_t bwpStart = current_BWP->BWPStart;
const uint16_t bwpSize = NRRIV2BW(genericParameters->locationAndBandwidth,MAX_BWP_SIZE);
const uint16_t bwpStart = NRRIV2PRBOFFSET(genericParameters->locationAndBandwidth,MAX_BWP_SIZE);
NR_PUSCH_TimeDomainResourceAllocationList_t *tdaList = NULL;
if (sched_ctrl->active_ubwp) {
tdaList = sched_ctrl->active_ubwp->bwp_Common->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList;
} else if (scc) {
tdaList = scc->uplinkConfigCommon->initialUplinkBWP->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList;
} else {
NR_SIB1_t *sib1 = RC.nrmac[module_id]->common_channels[0].sib1->message.choice.c1->choice.systemInformationBlockType1;
tdaList = sib1->servingCellConfigCommon->uplinkConfigCommon->initialUplinkBWP.pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList;
}
const int startSymbolAndLength = tdaList->list.array[tda]->startSymbolAndLength;
const int startSymbolAndLength = current_BWP->tdaList->list.array[tda]->startSymbolAndLength;
int startSymbolIndex, nrOfSymbols;
SLIV2SL(startSymbolAndLength, &startSymbolIndex, &nrOfSymbols);
const uint16_t symb = SL_to_bitmap(startSymbolIndex, nrOfSymbols);
@@ -1577,10 +1495,7 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot)
if (sched_ctrl->ul_failure == 1 && get_softmodem_params()->phy_test==0) continue;
NR_CellGroupConfig_t *cg = UE->CellGroup;
NR_BWP_UplinkDedicated_t *ubwpd = cg && cg->spCellConfig && cg->spCellConfig->spCellConfigDedicated &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig ?
cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP : NULL;
NR_UE_UL_BWP_t *current_BWP = &UE->current_UL_BWP;
UE->mac_stats.ul.current_bytes = 0;
@@ -1626,7 +1541,7 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot)
NR_pusch_semi_static_t *ps = &sched_ctrl->pusch_semi_static;
/* Statistics */
AssertFatal(cur_harq->round < 8, "Indexing ulsch_rounds[%d] is out of bounds\n", cur_harq->round);
AssertFatal(cur_harq->round < nr_mac->ul_bler.harq_round_max, "Indexing ulsch_rounds[%d] is out of bounds\n", cur_harq->round);
UE->mac_stats.ul.rounds[cur_harq->round]++;
if (cur_harq->round == 0) {
UE->mac_stats.ulsch_total_bytes_scheduled += sched_pusch->tb_size;
@@ -1672,7 +1587,7 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot)
sched_pusch->tb_size,
harq_id,
cur_harq->round,
nr_rv_round_map[cur_harq->round],
nr_rv_round_map[cur_harq->round%4],
cur_harq->ndi,
sched_ctrl->estimated_ul_buffer,
sched_ctrl->sched_ul_bytes,
@@ -1706,23 +1621,20 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot)
pusch_pdu->handle = 0; //not yet used
/* FAPI: BWP */
NR_BWP_t *genericParameters = get_ul_bwp_genericParameters(sched_ctrl->active_ubwp,
scc,
sib1);
pusch_pdu->bwp_size = NRRIV2BW(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
pusch_pdu->bwp_start = NRRIV2PRBOFFSET(genericParameters->locationAndBandwidth, MAX_BWP_SIZE);
pusch_pdu->subcarrier_spacing = genericParameters->subcarrierSpacing;
pusch_pdu->bwp_size = current_BWP->BWPSize;
pusch_pdu->bwp_start = current_BWP->BWPStart;
pusch_pdu->subcarrier_spacing = current_BWP->scs;
pusch_pdu->cyclic_prefix = 0;
/* FAPI: PUSCH information always included */
pusch_pdu->target_code_rate = sched_pusch->R;
pusch_pdu->qam_mod_order = sched_pusch->Qm;
pusch_pdu->mcs_index = sched_pusch->mcs;
pusch_pdu->mcs_table = ps->mcs_table;
pusch_pdu->transform_precoding = ps->transform_precoding;
if (ps->pusch_Config && ps->pusch_Config->dataScramblingIdentityPUSCH)
pusch_pdu->data_scrambling_id = *ps->pusch_Config->dataScramblingIdentityPUSCH;
pusch_pdu->mcs_table = current_BWP->mcs_table;
pusch_pdu->transform_precoding = current_BWP->transform_precoding;
if (current_BWP->pusch_Config && current_BWP->pusch_Config->dataScramblingIdentityPUSCH)
pusch_pdu->data_scrambling_id = *current_BWP->pusch_Config->dataScramblingIdentityPUSCH;
else
pusch_pdu->data_scrambling_id = *scc->physCellId;
pusch_pdu->nrOfLayers = ps->nrOfLayers;
@@ -1758,7 +1670,7 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot)
pusch_pdu->rb_start = sched_pusch->rbStart;
pusch_pdu->rb_size = sched_pusch->rbSize;
pusch_pdu->vrb_to_prb_mapping = 0;
if (ps->pusch_Config==NULL || ps->pusch_Config->frequencyHopping==NULL)
if (current_BWP->pusch_Config==NULL || current_BWP->pusch_Config->frequencyHopping==NULL)
pusch_pdu->frequency_hopping = 0;
else
pusch_pdu->frequency_hopping = 1;
@@ -1768,8 +1680,8 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot)
pusch_pdu->nr_of_symbols = ps->nrOfSymbols;
/* PUSCH PDU */
AssertFatal(cur_harq->round < 4, "Indexing nr_rv_round_map[%d] is out of bounds\n", cur_harq->round);
pusch_pdu->pusch_data.rv_index = nr_rv_round_map[cur_harq->round];
AssertFatal(cur_harq->round < nr_mac->ul_bler.harq_round_max, "Indexing nr_rv_round_map[%d] is out of bounds\n", cur_harq->round%4);
pusch_pdu->pusch_data.rv_index = nr_rv_round_map[cur_harq->round%4];
pusch_pdu->pusch_data.harq_process_id = harq_id;
pusch_pdu->pusch_data.new_data_indicator = cur_harq->ndi;
pusch_pdu->pusch_data.tb_size = sched_pusch->tb_size;
@@ -1792,7 +1704,7 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot)
else
AssertFatal(1==0,"SequenceGroupHopping or sequenceHopping are NOT Supported\n");
LOG_D(NR_MAC,"TRANSFORM PRECODING IS ENABLED. CDM groups: %d, U: %d MCS table: %d\n", pusch_pdu->num_dmrs_cdm_grps_no_data, pusch_pdu->dfts_ofdm.low_papr_group_number, ps->mcs_table);
LOG_D(NR_MAC,"TRANSFORM PRECODING IS ENABLED. CDM groups: %d, U: %d MCS table: %d\n", pusch_pdu->num_dmrs_cdm_grps_no_data, pusch_pdu->dfts_ofdm.low_papr_group_number, current_BWP->mcs_table);
}
/*-----------------------------------------------------------------------------*/
@@ -1816,9 +1728,8 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot)
/* look up the PDCCH PDU for this BWP and CORESET. If it does not exist,
* create it */
const int bwp_id = sched_ctrl->active_bwp ? sched_ctrl->active_bwp->bwp_Id : 0;
NR_SearchSpace_t *ss = (sched_ctrl->active_bwp || ubwpd) ? sched_ctrl->search_space: RC.nrmac[module_id]->sched_ctrlCommon->search_space;
NR_ControlResourceSet_t *coreset = (sched_ctrl->active_bwp || ubwpd) ? sched_ctrl->coreset: RC.nrmac[module_id]->sched_ctrlCommon->coreset;
NR_SearchSpace_t *ss = sched_ctrl->search_space;
NR_ControlResourceSet_t *coreset = sched_ctrl->coreset;
const int coresetid = coreset->controlResourceSetId;
nfapi_nr_dl_tti_pdcch_pdu_rel15_t *pdcch_pdu = pdcch_pdu_coreset[coresetid];
if (!pdcch_pdu) {
@@ -1828,7 +1739,7 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot)
ul_dci_request_pdu->PDUSize = (uint8_t)(2+sizeof(nfapi_nr_dl_tti_pdcch_pdu));
pdcch_pdu = &ul_dci_request_pdu->pdcch_pdu.pdcch_pdu_rel15;
ul_dci_req->numPdus += 1;
nr_configure_pdcch(pdcch_pdu, coreset, genericParameters, &sched_ctrl->sched_pdcch);
nr_configure_pdcch(pdcch_pdu, coreset, false, &sched_ctrl->sched_pdcch);
pdcch_pdu_coreset[coresetid] = pdcch_pdu;
}
@@ -1853,35 +1764,24 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot)
dci_pdu_rel15_t uldci_payload;
memset(&uldci_payload, 0, sizeof(uldci_payload));
int n_ubwp=1;
if (cg &&
cg->spCellConfig &&
cg->spCellConfig->spCellConfigDedicated &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig &&
cg->spCellConfig->spCellConfigDedicated->uplinkConfig->uplinkBWP_ToAddModList) {
n_ubwp = cg->spCellConfig->spCellConfigDedicated->uplinkConfig->uplinkBWP_ToAddModList->list.count;
}
config_uldci(sib1,
sched_ctrl->active_ubwp,
ubwpd,
scc,
pusch_pdu,
&uldci_payload,
ps->dci_format,
ps->time_domain_allocation,
UE->UE_sched_ctrl.tpc0,
n_ubwp,
bwp_id);
current_BWP);
fill_dci_pdu_rel15(scc,
cg,
&UE->current_DL_BWP,
dci_pdu,
&uldci_payload,
ps->dci_format,
current_BWP->dci_format,
rnti_types[0],
pusch_pdu->bwp_size,
bwp_id,
coresetid,
current_BWP->bwp_id,
coreset,
nr_mac->cset0_bwp_size);
memset(sched_pusch, 0, sizeof(*sched_pusch));
+31 -61
View File
@@ -38,8 +38,6 @@ void set_cset_offset(uint16_t);
void mac_top_init_gNB(void);
void process_CellGroup(NR_CellGroupConfig_t *CellGroup, NR_UE_sched_ctrl_t *sched_ctrl);
void config_common(int Mod_idP,
int pdsch_AntennaPorts,
int pusch_AntennaPorts,
@@ -93,7 +91,7 @@ uint32_t schedule_control_sib1(module_id_t module_id,
int nrOfSymbols,
uint16_t dlDmrsSymbPos,
uint8_t candidate_idx,
int num_total_bytes);
uint16_t num_total_bytes);
/* \brief default FR1 DL preprocessor init routine, returns preprocessor to call */
nr_pp_impl_dl nr_init_fr1_dlsch_preprocessor(module_id_t module_id, int CC_id);
@@ -132,7 +130,6 @@ int nr_allocate_CCEs(int module_idP, int CC_idP, frame_t frameP, sub_frame_t slo
void nr_get_Msg3alloc(module_id_t module_id,
int CC_id,
NR_ServingCellConfigCommon_t *scc,
NR_BWP_Uplink_t *ubwp,
sub_frame_t current_subframe,
frame_t current_frame,
NR_RA_t *ra,
@@ -190,18 +187,14 @@ void handle_nr_uci_pucch_2_3_4(module_id_t mod_id,
void config_uldci(const NR_SIB1_t *sib1,
const NR_BWP_Uplink_t *ubwp,
const NR_BWP_UplinkDedicated_t *ubwpd,
const NR_ServingCellConfigCommon_t *scc,
const nfapi_nr_pusch_pdu_t *pusch_pdu,
dci_pdu_rel15_t *dci_pdu_rel15,
int dci_format,
int time_domain_assignment,
uint8_t tpc,
int n_ubwp,
int bwp_id);
NR_UE_UL_BWP_t *ul_bwp);
void nr_schedule_pucch(gNB_MAC_INST* nrmac,
void nr_schedule_pucch(gNB_MAC_INST *nrmac,
frame_t frameP,
sub_frame_t slotP);
@@ -216,16 +209,15 @@ void nr_csi_meas_reporting(int Mod_idP,
frame_t frameP,
sub_frame_t slotP);
int nr_acknack_scheduling( int Mod_idP,
NR_UE_info_t * UE,
frame_t frameP,
sub_frame_t slotP,
int r_pucch,
int do_common);
int nr_acknack_scheduling(int Mod_idP,
NR_UE_info_t *UE,
frame_t frameP,
sub_frame_t slotP,
int r_pucch,
int do_common);
void get_pdsch_to_harq_feedback(NR_UE_info_t *,
int bwp_id,
NR_SearchSpace__searchSpaceType_PR ss_type,
void get_pdsch_to_harq_feedback(NR_PUCCH_Config_t *pucch_Config,
nr_dci_format_t dci_format,
int *max_fb_time,
uint8_t *pdsch_to_harq_feedback);
@@ -249,17 +241,12 @@ int nr_is_dci_opportunity(nfapi_nr_search_space_t search_space,
*/
int nr_get_pucch_resource(NR_ControlResourceSet_t *coreset,
NR_BWP_Uplink_t *bwp,
NR_BWP_UplinkDedicated_t *bwpd,
NR_PUCCH_Config_t *pucch_Config,
int CCEIndex);
void nr_configure_pucch(const NR_SIB1_t *sib1,
nfapi_nr_pucch_pdu_t* pucch_pdu,
void nr_configure_pucch(nfapi_nr_pucch_pdu_t* pucch_pdu,
NR_ServingCellConfigCommon_t *scc,
NR_CellGroupConfig_t *CellGroup,
NR_BWP_Uplink_t *bwp,
NR_BWP_UplinkDedicated_t *bwpd,
uint16_t rnti,
NR_UE_info_t* UE,
uint8_t pucch_resource,
uint16_t O_csi,
uint16_t O_ack,
@@ -272,7 +259,7 @@ void find_search_space(int ss_type,
void nr_configure_pdcch(nfapi_nr_dl_tti_pdcch_pdu_rel15_t *pdcch_pdu,
NR_ControlResourceSet_t *coreset,
NR_BWP_t *bwp,
bool is_sib1,
NR_sched_pdcch_t *pdcch);
NR_sched_pdcch_t set_pdcch_structure(gNB_MAC_INST *gNB_mac,
@@ -298,19 +285,21 @@ void fill_pdcch_vrb_map(gNB_MAC_INST *mac,
void fill_dci_pdu_rel15(const NR_ServingCellConfigCommon_t *scc,
const NR_CellGroupConfig_t *CellGroup,
const NR_UE_DL_BWP_t *dl_bwp,
nfapi_nr_dl_dci_pdu_t *pdcch_dci_pdu,
dci_pdu_rel15_t *dci_pdu_rel15,
int dci_formats,
int rnti_types,
int N_RB,
int bwp_id,
NR_ControlResourceSetId_t coreset_id,
NR_ControlResourceSet_t *coreset,
uint16_t cset0_bwp_size);
void prepare_dci(const NR_CellGroupConfig_t *CellGroup,
const NR_UE_DL_BWP_t *dl_bwp,
const NR_ControlResourceSet_t *coreset,
dci_pdu_rel15_t *dci_pdu_rel15,
nr_dci_format_t format,
int bwp_id);
nr_dci_format_t format);
void set_r_pucch_parms(int rsetindex,
int r_pucch,
@@ -320,18 +309,6 @@ void set_r_pucch_parms(int rsetindex,
int *nr_of_symbols,
int *start_symbol_index);
NR_BWP_t *get_dl_bwp_genericParameters(NR_BWP_Downlink_t *active_bwp,
NR_ServingCellConfigCommon_t *ServingCellConfigCommon,
const NR_SIB1_t *sib1);
NR_BWP_t *get_ul_bwp_genericParameters(NR_BWP_Uplink_t *active_ubwp,
NR_ServingCellConfigCommon_t *ServingCellConfigCommon,
const NR_SIB1_t *sib1);
NR_PDSCH_TimeDomainResourceAllocationList_t *get_pdsch_TimeDomainAllocationList(const NR_BWP_Downlink_t *active_bwp,
const NR_ServingCellConfigCommon_t *ServingCellConfigCommon,
const NR_SIB1_t *sib1);
/* find coreset within the search space */
NR_ControlResourceSet_t *get_coreset(gNB_MAC_INST *nrmac,
NR_ServingCellConfigCommon_t *scc,
@@ -340,34 +317,24 @@ NR_ControlResourceSet_t *get_coreset(gNB_MAC_INST *nrmac,
NR_SearchSpace__searchSpaceType_PR ss_type);
/* find a search space within a BWP */
NR_SearchSpace_t *get_searchspace(const NR_SIB1_t *sib1,
NR_ServingCellConfigCommon_t *scc,
NR_SearchSpace_t *get_searchspace(NR_ServingCellConfigCommon_t *scc,
NR_BWP_DownlinkDedicated_t *bwp_Dedicated,
NR_SearchSpace__searchSpaceType_PR target_ss);
long get_K2(NR_ServingCellConfigCommon_t *scc,
NR_ServingCellConfigCommonSIB_t *scc_sib1,
NR_BWP_Uplink_t *ubwp,
long get_K2(NR_PUSCH_TimeDomainResourceAllocationList_t *tdaList,
int time_domain_assignment,
int mu);
void nr_set_pdsch_semi_static(const NR_SIB1_t *sib1,
void nr_set_pdsch_semi_static(const NR_UE_DL_BWP_t *dl_bwp,
const NR_ServingCellConfigCommon_t *scc,
const NR_CellGroupConfig_t *secondaryCellGroup,
const NR_BWP_Downlink_t *bwp,
const NR_BWP_DownlinkDedicated_t *bwpd0,
int tda,
uint8_t layers,
NR_UE_sched_ctrl_t *sched_ctrl,
NR_pdsch_semi_static_t *ps);
void nr_set_pusch_semi_static(const NR_SIB1_t *sib1,
void nr_set_pusch_semi_static(const NR_UE_UL_BWP_t *ul_bwp,
const NR_ServingCellConfigCommon_t *scc,
const NR_BWP_Uplink_t *ubwp,
const NR_BWP_UplinkDedicated_t *ubwpd,
long dci_format,
int tda,
uint8_t num_dmrs_cdm_grps_no_data,
uint8_t nrOfLayers,
NR_pusch_semi_static_t *ps);
@@ -402,7 +369,13 @@ NR_UE_info_t * find_nr_UE(NR_UEs_t* UEs, rnti_t rntiP);
int find_nr_RA_id(module_id_t mod_idP, int CC_idP, rnti_t rntiP);
NR_UE_info_t*add_new_nr_ue(gNB_MAC_INST *nr_mac, rnti_t rntiP, NR_CellGroupConfig_t *CellGroup);
void configure_UE_BWP(gNB_MAC_INST *nr_mac,
NR_ServingCellConfigCommon_t *scc,
NR_UE_sched_ctrl_t *sched_ctrl,
NR_RA_t *ra,
NR_UE_info_t *UE);
NR_UE_info_t* add_new_nr_ue(gNB_MAC_INST *nr_mac, rnti_t rntiP, NR_CellGroupConfig_t *CellGroup);
void mac_remove_nr_ue(gNB_MAC_INST *nr_mac, rnti_t rnti);
@@ -410,8 +383,6 @@ void nr_mac_remove_ra_rnti(module_id_t mod_id, rnti_t rnti);
int nr_get_default_pucch_res(int pucch_ResourceCommon);
void compute_csi_bitlen(NR_CSI_MeasConfig_t *csi_MeasConfig, NR_UE_info_t *UE);
int get_dlscs(nfapi_nr_config_request_t *cfg);
int get_ulscs(nfapi_nr_config_request_t *cfg);
@@ -501,7 +472,6 @@ uint8_t get_mcs_from_cqi(int mcs_table, int cqi_table, int cqi_idx);
uint8_t set_dl_nrOfLayers(NR_UE_sched_ctrl_t *sched_ctrl);
int get_dci_format(NR_UE_sched_ctrl_t *sched_ctrl);
const int get_dl_tda(const gNB_MAC_INST *nrmac, const NR_ServingCellConfigCommon_t *scc, int slot);
const int get_ul_tda(const gNB_MAC_INST *nrmac, const NR_ServingCellConfigCommon_t *scc, int slot);
+25 -17
View File
@@ -105,17 +105,21 @@ size_t dump_mac_stats(gNB_MAC_INST *gNB, char *output, size_t strlen, bool reset
end - output,
"UE %04x: CQI %d, RI %d, PMI (%d,%d)\n",
UE->rnti,
UE->UE_sched_ctrl.CSI_report.cri_ri_li_pmi_cqi_report.wb_cqi_1tb,
UE->UE_sched_ctrl.CSI_report.cri_ri_li_pmi_cqi_report.ri+1,
UE->UE_sched_ctrl.CSI_report.cri_ri_li_pmi_cqi_report.pmi_x1,
UE->UE_sched_ctrl.CSI_report.cri_ri_li_pmi_cqi_report.pmi_x2);
sched_ctrl->CSI_report.cri_ri_li_pmi_cqi_report.wb_cqi_1tb,
sched_ctrl->CSI_report.cri_ri_li_pmi_cqi_report.ri+1,
sched_ctrl->CSI_report.cri_ri_li_pmi_cqi_report.pmi_x1,
sched_ctrl->CSI_report.cri_ri_li_pmi_cqi_report.pmi_x2);
output += snprintf(output,
end - output,
"UE %04x: dlsch_rounds %"PRIu64"/%"PRIu64"/%"PRIu64"/%"PRIu64", dlsch_errors %"PRIu64", pucch0_DTX %d, BLER %.5f MCS %d\n",
UE->rnti,
stats->dl.rounds[0], stats->dl.rounds[1],
stats->dl.rounds[2], stats->dl.rounds[3],
"UE %04x: dlsch_rounds ", UE->rnti);
output += snprintf(output, end - output, "%"PRIu64, stats->dl.rounds[0]);
for (int i = 1; i < gNB->dl_bler.harq_round_max; i++)
output += snprintf(output, end - output, "/%"PRIu64, stats->dl.rounds[i]);
output += snprintf(output,
end - output,
", dlsch_errors %"PRIu64", pucch0_DTX %d, BLER %.5f MCS %d\n",
stats->dl.errors,
stats->pucch0_DTX,
sched_ctrl->dl_bler_stats.bler,
@@ -127,23 +131,27 @@ size_t dump_mac_stats(gNB_MAC_INST *gNB, char *output, size_t strlen, bool reset
output += snprintf(output,
end - output,
"UE %04x: dlsch_total_bytes %"PRIu64"\n",
UE->rnti,
stats->dl.total_bytes);
UE->rnti, stats->dl.total_bytes);
output += snprintf(output,
end - output,
"UE %04x: ulsch_rounds %"PRIu64"/%"PRIu64"/%"PRIu64"/%"PRIu64", ulsch_DTX %d, ulsch_errors %"PRIu64", BLER %.5f MCS %d\n",
UE->rnti,
stats->ul.rounds[0], stats->ul.rounds[1],
stats->ul.rounds[2], stats->ul.rounds[3],
"UE %04x: ulsch_rounds ", UE->rnti);
output += snprintf(output, end - output, "%"PRIu64, stats->ul.rounds[0]);
for (int i = 1; i < gNB->ul_bler.harq_round_max; i++)
output += snprintf(output, end - output, "/%"PRIu64, stats->ul.rounds[i]);
output += snprintf(output,
end - output,
", ulsch_DTX %d, ulsch_errors %"PRIu64", BLER %.5f MCS %d\n",
stats->ulsch_DTX,
stats->ul.errors,
sched_ctrl->ul_bler_stats.bler,
sched_ctrl->ul_bler_stats.mcs);
output += snprintf(output,
end - output,
"UE %04x: ulsch_total_bytes_scheduled %"PRIu64", ulsch_total_bytes_received %"PRIu64"\n",
UE->rnti,
stats->ulsch_total_bytes_scheduled, stats->ul.total_bytes);
"UE %04x: ulsch_total_bytes_scheduled %"PRIu64", ulsch_total_bytes_received %"PRIu64"\n",
UE->rnti,
stats->ulsch_total_bytes_scheduled, stats->ul.total_bytes);
for (int lc_id = 0; lc_id < 63; lc_id++) {
if (stats->dl.lc_bytes[lc_id] > 0)
output += snprintf(output,

Some files were not shown because too many files have changed in this diff Show More