Merge remote-tracking branch 'origin/develop' into ul-phr

This commit is contained in:
francescomani
2022-08-03 14:57:54 +02:00
116 changed files with 3079 additions and 1824 deletions
+1 -1
View File
@@ -66,7 +66,7 @@ pipeline {
withCredentials([ withCredentials([
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.DH_Credentials}", usernameVariable: 'DH_Username', passwordVariable: 'DH_Password'] [$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" sh "docker login -u ${DH_Username} -p ${DH_Password} > /dev/null 2>&1"
listOfImages.eachWithIndex { item, iindex -> listOfImages.eachWithIndex { item, iindex ->
sh "docker image tag ${item}:develop ${DH_Account}/${item}:develop" 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 // Name of the phone resource
def ciSmartPhoneResource = params.smartphonesResource def ciSmartPhoneResource = params.smartphonesResource
// Name of the phone resource
def ciEpcResource = params.epcResource
// Global Parameters. Normally they should be populated when the master job // Global Parameters. Normally they should be populated when the master job
// triggers the slave job with parameters // triggers the slave job with parameters
def eNB_Repository def eNB_Repository
@@ -51,7 +54,7 @@ pipeline {
options { options {
disableConcurrentBuilds() disableConcurrentBuilds()
ansiColor('xterm') ansiColor('xterm')
lock (ciSmartPhoneResource) lock(extra: [[resource: ciEpcResource]], resource: ciSmartPhoneResource)
} }
stages { stages {
stage ("Verify Parameters") { 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') { stage('Log Collection') {
parallel { parallel {
stage('Log Collection (eNB - Build)') { stage('Log Collection (eNB - Build)') {
@@ -242,7 +315,7 @@ pipeline {
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.eNB_Credentials}", usernameVariable: 'eNB_Username', passwordVariable: 'eNB_Password'] [$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.eNB_Credentials}", usernameVariable: 'eNB_Username', passwordVariable: 'eNB_Password']
]) { ]) {
echo '\u2705 \u001B[32mLog Collection (eNB - Run)\u001B[0m' 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' 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" 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"
}
}
}
}
} }
} }
} }
+8 -5
View File
@@ -20,6 +20,9 @@
* contact@openairinterface.org * contact@openairinterface.org
*/ */
// necessary for reading JSON
import groovy.json.JsonSlurper
// Template Jenkins Declarative Pipeline script to run Test w/ RF HW // 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 // Location of the python executor node shall be in the same subnet as the others servers
@@ -38,11 +41,11 @@ pipeline {
stage ("Launcher") { stage ("Launcher") {
steps { steps {
script { script {
//retrieve MR that are opened nd with tag NSA // 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 ' 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 MR:\n${MR_LIST}" echo "List of selected MRs: ${MR_LIST.trim()}"
def MR_ARRAY = MR_LIST.split('\n') def MR_ARRAY = new JsonSlurper().parseText(MR_LIST.trim())
//for every selected MR, retrieve the branch name and the latest commit // for every selected MR, retrieve the branch name and the latest commit
for (MR in MR_ARRAY) { 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=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() SRC_BRANCH=SRC_BRANCH.trim()
+2 -2
View File
@@ -50,7 +50,7 @@ amarisoft_ue_1:
WakeupScript : none WakeupScript : none
DetachScript : none DetachScript : none
#end #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 Config : /root/NV17-12-21/ue/config/oaicicd-ue-Ping-SATest.cfg
Duration : 60 Duration : 60
Ping : /tmp/test_ue1.log Ping : /tmp/test_ue1.log
@@ -71,7 +71,7 @@ amarisoft_ue_2:
WakeupScript : none WakeupScript : none
DetachScript : none DetachScript : none
#end #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 Config : /root/NV17-12-21/ue/config/xxxxxxx.cfg #to be updated for an other scenario
Duration : 60 Duration : 60
Ping : Ping :
+119
View File
@@ -74,6 +74,7 @@ class Containerize():
self.eNB2SourceCodePath = '' self.eNB2SourceCodePath = ''
self.forcedWorkspaceCleanup = False self.forcedWorkspaceCleanup = False
self.imageKind = '' self.imageKind = ''
self.proxyCommit = None
self.eNB_instance = 0 self.eNB_instance = 0
self.eNB_serverId = ['', '', ''] self.eNB_serverId = ['', '', '']
self.yamlPath = ['', '', ''] self.yamlPath = ['', '', '']
@@ -421,6 +422,124 @@ class Containerize():
HTML.CreateHtmlTabFooter(False) HTML.CreateHtmlTabFooter(False)
sys.exit(1) 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): def Copy_Image_to_Test_Server(self, HTML):
imageTag = 'develop' imageTag = 'develop'
if (self.ranAllowMerge): if (self.ranAllowMerge):
+6 -1
View File
@@ -102,7 +102,7 @@ def AssignParams(params_dict):
def GetParametersFromXML(action): 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') RAN.Build_eNB_args=test.findtext('Build_eNB_args')
CONTAINERS.imageKind=test.findtext('kind') CONTAINERS.imageKind=test.findtext('kind')
forced_workspace_cleanup = test.findtext('forced_workspace_cleanup') forced_workspace_cleanup = test.findtext('forced_workspace_cleanup')
@@ -138,6 +138,9 @@ def GetParametersFromXML(action):
RAN.backgroundBuild=True RAN.backgroundBuild=True
else: else:
RAN.backgroundBuild=False RAN.backgroundBuild=False
proxy_commit = test.findtext('proxy_commit')
if proxy_commit is not None:
CONTAINERS.proxyCommit = proxy_commit
elif action == 'WaitEndBuild_eNB': elif action == 'WaitEndBuild_eNB':
RAN.Build_eNB_args=test.findtext('Build_eNB_args') 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) HTML=ldpc.Run_PhySim(HTML,CONST,id)
elif action == 'Build_Image': elif action == 'Build_Image':
CONTAINERS.BuildImage(HTML) CONTAINERS.BuildImage(HTML)
elif action == 'Build_Proxy':
CONTAINERS.BuildProxy(HTML)
elif action == 'Copy_Image_to_Test': elif action == 'Copy_Image_to_Test':
CONTAINERS.Copy_Image_to_Test_Server(HTML) CONTAINERS.Copy_Image_to_Test_Server(HTML)
elif action == 'Deploy_Object': elif action == 'Deploy_Object':
+1
View File
@@ -1,3 +1,4 @@
- Build_Proxy
- Build_PhySim - Build_PhySim
- Run_PhySim - Run_PhySim
- Build_eNB - 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. # wrong in the pthread library, or something subtly wrong in this CMakeLists.txt. Use Ubuntu 20.04 instead.
endif () 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") 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_timer_thread.c
${OPENAIR2_DIR}/LAYER2/nr_pdcp/nr_pdcp_security_nea2.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_nia2.c
${OPENAIR2_DIR}/LAYER2/nr_pdcp/nr_pdcp_integrity_nia1.c
${OPENAIR2_DIR}/LAYER2/nr_pdcp/asn1_utils.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 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 Skip build for shared libraries to reduce compilation time when building frequently for debugging purposes
--ninja --ninja
Tell cmake to use the Ninja build system. Without, will generate make files 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 --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 --ittiSIM
Makes the itti simulator Makes the itti simulator
-h | --help -h | --help
@@ -451,10 +455,16 @@ function main() {
CMAKE_CMD="$CMAKE_CMD -GNinja" CMAKE_CMD="$CMAKE_CMD -GNinja"
MAKE_CMD=ninja MAKE_CMD=ninja
shift;; shift;;
--sanitize)
CMAKE_CMD="$CMAKE_CMD -DSANITIZE_ADDRESS=True -DSANITIZE_UNDEFINED=True"
shift;;
--sanitize-address | -fsanitize=address) --sanitize-address | -fsanitize=address)
grep -sq "Ubuntu 18.04" /etc/os-release && echo_error "Bug in OS with this option, see CMakeLists.txt" 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" CMAKE_CMD="$CMAKE_CMD -DSANITIZE_ADDRESS=True"
shift;; shift;;
--sanitize-undefined | -fundefined=address)
CMAKE_CMD="$CMAKE_CMD -DSANITIZE_UNDEFINED=True"
shift;;
--ittiSIM) --ittiSIM)
ittiSIM=1 ittiSIM=1
CMAKE_CMD="$CMAKE_CMD -DITTI_SIM=True" 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 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 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 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*/ 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 trials; /*!< \brief number of start point - end point iterations */
int meas_flag; /*!< \brief 1: stop_meas not called (consecutive calls of start_meas) */ 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); ts->diff += (out-ts->in);
/// process duration is the difference between two clock points /// process duration is the difference between two clock points
ts->p_time = (out-ts->in); 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) if ((out-ts->in) > ts->max)
ts->max = out-ts->in; 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 - PTRS support
- Support for 1, 2 and 4 RX antennas - Support for 1, 2 and 4 RX antennas
- Support for up to 2 layers (currently limited to DMRS configuration type 2) - 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). * NR-PUSCH (including Segmentation, LDPC encoding, rate matching, scrambling, modulation, RB mapping, etc).
- PUSCH mapping type A and B - PUSCH mapping type A and B
- DMRS configuration type 1 and 2 - 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 * UCI processing
- ACK/NACK processing - ACK/NACK processing
- Triggering periodic SR - Triggering periodic SR
- CSI measurement reporting (SSB RSRP only) - CSI measurement reporting
* DLSH scheduler * DLSCH scheduler
- Configuration of fapi PDU according to DCI - Configuration of fapi PDU according to DCI
- HARQ procedures - HARQ procedures
* ULSCH scheduler * ULSCH scheduler
- Configuration of fapi PDU according to DCI - 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 * Scheduler procedures for SRS transmission
- Periodic SRS transmission - Periodic SRS transmission
* Bandwidth part (BWP) operation * Bandwidth part (BWP) operation
+9 -16
View File
@@ -71,10 +71,6 @@ reboot
# https://docs.docker.com/compose/install/ # 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 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 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 ## 2.2 OAI CN5G Setup
@@ -82,39 +78,36 @@ sudo service docker restart
```bash ```bash
# Git oai-cn5g-fed repository # Git oai-cn5g-fed repository
git clone https://gitlab.eurecom.fr/oai/cn5g/oai-cn5g-fed.git ~/oai-cn5g-fed 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-amf:develop
docker pull oaisoftwarealliance/oai-nrf:develop docker pull oaisoftwarealliance/oai-nrf:develop
docker pull oaisoftwarealliance/oai-smf:develop docker pull oaisoftwarealliance/oai-smf:develop
docker pull oaisoftwarealliance/oai-udr:develop docker pull oaisoftwarealliance/oai-udr:develop
docker pull oaisoftwarealliance/oai-udm:develop docker pull oaisoftwarealliance/oai-udm:develop
docker pull oaisoftwarealliance/oai-ausf: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-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-amf:develop oai-amf:develop
docker image tag oaisoftwarealliance/oai-nrf:develop oai-nrf: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-smf:develop oai-smf:develop
docker image tag oaisoftwarealliance/oai-udr:develop oai-udr: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-udm:develop oai-udm:develop
docker image tag oaisoftwarealliance/oai-ausf:develop oai-ausf: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-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 ## 2.3 OAI CN5G Configuration files
Download and copy the configuration files to ~/oai-cn5g-fed/docker-compose: Download and copy configuration files:
- [docker-compose-basic-nrf.yaml](tutorial_resources/docker-compose-basic-nrf.yaml) - Copy [docker-compose-basic-nrf.yaml](tutorial_resources/docker-compose-basic-nrf.yaml) to `~/oai-cn5g-fed/docker-compose`
- [oai_db.sql](tutorial_resources/oai_db.sql) - 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: Change permissions on oai_db.sql to prevent mysql permission denied error:
```bash ```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 ## 2.4 SIM Card
@@ -175,7 +168,7 @@ cd cmake_targets
```bash ```bash
cd ~/oai-cn5g-fed/docker-compose 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.2 Run OAI gNB
+9 -16
View File
@@ -72,10 +72,6 @@ reboot
# https://docs.docker.com/compose/install/ # 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 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 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 ## 2.2 OAI CN5G Setup
@@ -83,39 +79,36 @@ sudo service docker restart
```bash ```bash
# Git oai-cn5g-fed repository # Git oai-cn5g-fed repository
git clone https://gitlab.eurecom.fr/oai/cn5g/oai-cn5g-fed.git ~/oai-cn5g-fed 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-amf:develop
docker pull oaisoftwarealliance/oai-nrf:develop docker pull oaisoftwarealliance/oai-nrf:develop
docker pull oaisoftwarealliance/oai-smf:develop docker pull oaisoftwarealliance/oai-smf:develop
docker pull oaisoftwarealliance/oai-udr:develop docker pull oaisoftwarealliance/oai-udr:develop
docker pull oaisoftwarealliance/oai-udm:develop docker pull oaisoftwarealliance/oai-udm:develop
docker pull oaisoftwarealliance/oai-ausf: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-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-amf:develop oai-amf:develop
docker image tag oaisoftwarealliance/oai-nrf:develop oai-nrf: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-smf:develop oai-smf:develop
docker image tag oaisoftwarealliance/oai-udr:develop oai-udr: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-udm:develop oai-udm:develop
docker image tag oaisoftwarealliance/oai-ausf:develop oai-ausf: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-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 ## 2.3 OAI CN5G Configuration files
Download and copy the configuration files to ~/oai-cn5g-fed/docker-compose: Download and copy configuration files:
- [docker-compose-basic-nrf.yaml](tutorial_resources/docker-compose-basic-nrf.yaml) - Copy [docker-compose-basic-nrf.yaml](tutorial_resources/docker-compose-basic-nrf.yaml) to `~/oai-cn5g-fed/docker-compose`
- [oai_db.sql](tutorial_resources/oai_db.sql) - 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: Change permissions on oai_db.sql to prevent mysql permission denied error:
```bash ```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 ## 2.4 SIM Card
@@ -193,7 +186,7 @@ The following steps are recommended. Please change the network interface(s) as r
```bash ```bash
cd ~/oai-cn5g-fed/docker-compose 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.2 Run OAI gNB
@@ -4,8 +4,8 @@ services:
container_name: "mysql" container_name: "mysql"
image: mysql:5.7 image: mysql:5.7
volumes: volumes:
- ./oai_db.sql:/docker-entrypoint-initdb.d/oai_db.sql - ./database/oai_db.sql:/docker-entrypoint-initdb.d/oai_db.sql
- ./mysql-healthcheck2.sh:/tmp/mysql-healthcheck.sh - ./healthscripts/mysql-healthcheck2.sh:/tmp/mysql-healthcheck.sh
environment: environment:
- TZ=Europe/Paris - TZ=Europe/Paris
- MYSQL_DATABASE=oai_db - MYSQL_DATABASE=oai_db
@@ -21,35 +21,45 @@ services:
public_net: public_net:
ipv4_address: 192.168.70.131 ipv4_address: 192.168.70.131
oai-udr: oai-udr:
container_name: oai-udr container_name: "oai-udr"
image: oai-udr:develop image: oai-udr:develop
environment: environment:
- TZ=Europe/Paris - TZ=Europe/Paris
- INSTANCE=0 - INSTANCE=0
- PID_DIRECTORY=/var/run - PID_DIRECTORY=/var/run
- UDR_NAME=OAI_UDR
- UDR_INTERFACE_NAME_FOR_NUDR=eth0 - UDR_INTERFACE_NAME_FOR_NUDR=eth0
- UDR_INTERFACE_PORT_FOR_NUDR=80 - UDR_INTERFACE_PORT_FOR_NUDR=80
- UDR_INTERFACE_HTTP2_PORT_FOR_NUDR=8080 - UDR_INTERFACE_HTTP2_PORT_FOR_NUDR=8080
- USE_HTTP2=no
- UDR_API_VERSION=v1 - UDR_API_VERSION=v1
- MYSQL_IPV4_ADDRESS=192.168.70.131 - MYSQL_IPV4_ADDRESS=192.168.70.131
- MYSQL_USER=test - MYSQL_USER=test
- MYSQL_PASS=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 - MYSQL_DB=oai_db
- WAIT_MYSQL=120 - 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: depends_on:
- mysql - mysql
- oai-nrf
networks: networks:
public_net: public_net:
ipv4_address: 192.168.70.136 ipv4_address: 192.168.70.136
volumes: volumes:
- ./udr-healthcheck.sh:/openair-udr/bin/udr-healthcheck.sh - ./healthscripts/udr-healthcheck.sh:/openair-udr/bin/udr-healthcheck.sh
healthcheck: healthcheck:
test: /bin/bash -c "/openair-udr/bin/udr-healthcheck.sh" test: /bin/bash -c "/openair-udr/bin/udr-healthcheck.sh"
interval: 10s interval: 10s
timeout: 5s timeout: 5s
retries: 5 retries: 5
oai-udm: oai-udm:
container_name: oai-udm container_name: "oai-udm"
image: oai-udm:develop image: oai-udm:develop
environment: environment:
- TZ=Europe/Paris - TZ=Europe/Paris
@@ -58,26 +68,33 @@ services:
- UDM_NAME=OAI_UDM - UDM_NAME=OAI_UDM
- SBI_IF_NAME=eth0 - SBI_IF_NAME=eth0
- SBI_PORT=80 - SBI_PORT=80
- SBI_HTTP2_PORT=8080
- USE_HTTP2=no
- UDM_VERSION_NB=v1 - UDM_VERSION_NB=v1
- USE_FQDN_DNS=yes - USE_FQDN_DNS=yes
- UDR_IP_ADDRESS=192.168.70.136 - UDR_IP_ADDRESS=192.168.70.136
- UDR_PORT=80 - UDR_PORT=80
- UDR_VERSION_NB=v1 - UDR_VERSION_NB=v1
- UDR_FQDN=oai-udr - 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: depends_on:
- oai-udr - oai-udr
networks: networks:
public_net: public_net:
ipv4_address: 192.168.70.137 ipv4_address: 192.168.70.137
volumes: volumes:
- ./udm-healthcheck.sh:/openair-udm/bin/udm-healthcheck.sh - ./healthscripts/udm-healthcheck.sh:/openair-udm/bin/udm-healthcheck.sh
healthcheck: healthcheck:
test: /bin/bash -c "/openair-udm/bin/udm-healthcheck.sh" test: /bin/bash -c "/openair-udm/bin/udm-healthcheck.sh"
interval: 10s interval: 10s
timeout: 5s timeout: 5s
retries: 5 retries: 5
oai-ausf: oai-ausf:
container_name: oai-ausf container_name: "oai-ausf"
image: oai-ausf:develop image: oai-ausf:develop
environment: environment:
- TZ=Europe/Paris - TZ=Europe/Paris
@@ -86,18 +103,25 @@ services:
- AUSF_NAME=OAI_AUSF - AUSF_NAME=OAI_AUSF
- SBI_IF_NAME=eth0 - SBI_IF_NAME=eth0
- SBI_PORT=80 - SBI_PORT=80
- USE_HTTP2
- SBI_HTTP2_PORT
- USE_FQDN_DNS=yes - USE_FQDN_DNS=yes
- UDM_IP_ADDRESS=192.168.70.137 - UDM_IP_ADDRESS=192.168.70.137
- UDM_PORT=80 - UDM_PORT=80
- UDM_VERSION_NB=v1 - UDM_VERSION_NB=v1
- UDM_FQDN=oai-udm - 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: depends_on:
- oai-udm - oai-udm
networks: networks:
public_net: public_net:
ipv4_address: 192.168.70.138 ipv4_address: 192.168.70.138
volumes: volumes:
- ./ausf-healthcheck.sh:/openair-ausf/bin/ausf-healthcheck.sh - ./healthscripts/ausf-healthcheck.sh:/openair-ausf/bin/ausf-healthcheck.sh
healthcheck: healthcheck:
test: /bin/bash -c "/openair-ausf/bin/ausf-healthcheck.sh" test: /bin/bash -c "/openair-ausf/bin/ausf-healthcheck.sh"
interval: 10s interval: 10s
@@ -107,9 +131,10 @@ services:
container_name: "oai-nrf" container_name: "oai-nrf"
image: oai-nrf:develop image: oai-nrf:develop
environment: environment:
- TZ=Europe/Paris
- NRF_INTERFACE_NAME_FOR_SBI=eth0 - NRF_INTERFACE_NAME_FOR_SBI=eth0
- NRF_INTERFACE_PORT_FOR_SBI=80 - NRF_INTERFACE_PORT_FOR_SBI=80
- NRF_INTERFACE_HTTP2_PORT_FOR_SBI=9090 - NRF_INTERFACE_HTTP2_PORT_FOR_SBI=8080
- NRF_API_VERSION=v1 - NRF_API_VERSION=v1
- INSTANCE=0 - INSTANCE=0
- PID_DIRECTORY=/var/run - PID_DIRECTORY=/var/run
@@ -117,7 +142,7 @@ services:
public_net: public_net:
ipv4_address: 192.168.70.130 ipv4_address: 192.168.70.130
volumes: volumes:
- ./nrf-healthcheck.sh:/openair-nrf/bin/nrf-healthcheck.sh - ./healthscripts/nrf-healthcheck.sh:/openair-nrf/bin/nrf-healthcheck.sh
healthcheck: healthcheck:
test: /bin/bash -c "/openair-nrf/bin/nrf-healthcheck.sh" test: /bin/bash -c "/openair-nrf/bin/nrf-healthcheck.sh"
interval: 10s interval: 10s
@@ -146,9 +171,7 @@ services:
- PLMN_SUPPORT_MNC=99 - PLMN_SUPPORT_MNC=99
- PLMN_SUPPORT_TAC=0x0001 - PLMN_SUPPORT_TAC=0x0001
- SST_0=1 - SST_0=1
- SD_0=1 - SD_0=0x1
- SST_1=1
- SD_1=12
- AMF_INTERFACE_NAME_FOR_NGAP=eth0 - AMF_INTERFACE_NAME_FOR_NGAP=eth0
- AMF_INTERFACE_NAME_FOR_N11=eth0 - AMF_INTERFACE_NAME_FOR_N11=eth0
- SMF_INSTANCE_ID_0=1 - SMF_INSTANCE_ID_0=1
@@ -168,22 +191,30 @@ services:
- OPERATOR_KEY=1006020f0a478bf6b699f15c062e42b3 - OPERATOR_KEY=1006020f0a478bf6b699f15c062e42b3
- NRF_IPV4_ADDRESS=192.168.70.130 - NRF_IPV4_ADDRESS=192.168.70.130
- NRF_PORT=80 - NRF_PORT=80
- EXTERNAL_NRF=no
- NF_REGISTRATION=yes - NF_REGISTRATION=yes
- SMF_SELECTION=yes - SMF_SELECTION=yes
- USE_FQDN_DNS=yes - USE_FQDN_DNS=yes
- EXTERNAL_AUSF=yes - EXTERNAL_AUSF=yes
- EXTERNAL_UDM=no
- EXTERNAL_NSSF=no
- USE_HTTP2=no
- NRF_API_VERSION=v1 - NRF_API_VERSION=v1
- NRF_FQDN=oai-nrf - NRF_FQDN=oai-nrf
- AUSF_IPV4_ADDRESS=192.168.70.138 - AUSF_IPV4_ADDRESS=192.168.70.138
- AUSF_PORT=80 - AUSF_PORT=80
- AUSF_API_VERSION=v1 - AUSF_API_VERSION=v1
- AUSF_FQDN=oai-ausf - AUSF_FQDN=oai-ausf
- UDM_IPV4_ADDRESS=192.168.70.137
- UDM_PORT=80
- UDM_API_VERSION=v2
- UDM_FQDN=oai-udm
depends_on: depends_on:
- mysql - mysql
- oai-nrf - oai-nrf
- oai-ausf - oai-ausf
volumes: volumes:
- ./amf-healthcheck.sh:/openair-amf/bin/amf-healthcheck.sh - ./healthscripts/amf-healthcheck.sh:/openair-amf/bin/amf-healthcheck.sh
healthcheck: healthcheck:
test: /bin/bash -c "/openair-amf/bin/amf-healthcheck.sh" test: /bin/bash -c "/openair-amf/bin/amf-healthcheck.sh"
interval: 10s interval: 10s
@@ -212,26 +243,35 @@ services:
- AMF_FQDN=oai-amf - AMF_FQDN=oai-amf
- UDM_IPV4_ADDRESS=192.168.70.137 - UDM_IPV4_ADDRESS=192.168.70.137
- UDM_PORT=80 - UDM_PORT=80
- UDM_API_VERSION=v1 - UDM_API_VERSION=v2
- UDM_FQDN=oai-udm - UDM_FQDN=oai-udm
- UPF_IPV4_ADDRESS=192.168.70.134 - UPF_IPV4_ADDRESS=192.168.70.134
- UPF_FQDN_0=oai-spgwu - UPF_FQDN_0=oai-spgwu
- NRF_IPV4_ADDRESS=192.168.70.130 - NRF_IPV4_ADDRESS=192.168.70.130
- NRF_PORT=80 - NRF_PORT=80
- NRF_API_VERSION=v1 - 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 - NRF_FQDN=oai-nrf
- REGISTER_NRF=yes - REGISTER_NRF=yes
- DISCOVER_UPF=yes - DISCOVER_UPF=yes
- USE_FQDN_DNS=yes - USE_FQDN_DNS=yes
- DNN_RANGE1=12.1.1.2 - 12.1.1.128 - HTTP_VERSION=1 # Default: 1
- DNN_RANGE0=12.2.1.2 - 12.2.1.128 - UE_MTU=1500
- DNN_NI1=oai - 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: depends_on:
- oai-nrf - oai-nrf
- oai-amf - oai-amf
volumes: volumes:
- ./smf-healthcheck.sh:/openair-smf/bin/smf-healthcheck.sh - ./healthscripts/smf-healthcheck.sh:/openair-smf/bin/smf-healthcheck.sh
healthcheck: healthcheck:
test: /bin/bash -c "/openair-smf/bin/smf-healthcheck.sh" test: /bin/bash -c "/openair-smf/bin/smf-healthcheck.sh"
interval: 10s interval: 10s
@@ -258,17 +298,23 @@ services:
- MNC03=099 - MNC03=099
- TAC=1 - TAC=1
- GW_ID=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 - REALM=openairinterface.org
- ENABLE_5G_FEATURES=yes - ENABLE_5G_FEATURES=yes
- REGISTER_NRF=yes - REGISTER_NRF=yes
- USE_FQDN_NRF=no - USE_FQDN_NRF=yes
- UPF_FQDN_5G=oai-spgwu - UPF_FQDN_5G=oai-spgwu
- NRF_IPV4_ADDRESS=192.168.70.130 - NRF_IPV4_ADDRESS=192.168.70.130
- NRF_PORT=80 - NRF_PORT=80
- NRF_API_VERSION=v1 - NRF_API_VERSION=v1
- NRF_FQDN=oai-nrf - NRF_FQDN=oai-nrf
- NSSAI_SST_0=1 - NSSAI_SST_0=1
- NSSAI_SD_0=1 - NSSAI_SD_0=0x1
- DNN_0=oai - DNN_0=oai
depends_on: depends_on:
- oai-nrf - oai-nrf
@@ -280,7 +326,7 @@ services:
- ALL - ALL
privileged: true privileged: true
volumes: volumes:
- ./spgwu-healthcheck.sh:/openair-spgwu-tiny/bin/spgwu-healthcheck.sh - ./healthscripts/spgwu-healthcheck.sh:/openair-spgwu-tiny/bin/spgwu-healthcheck.sh
healthcheck: healthcheck:
test: /bin/bash -c "/openair-spgwu-tiny/bin/spgwu-healthcheck.sh" test: /bin/bash -c "/openair-spgwu-tiny/bin/spgwu-healthcheck.sh"
interval: 10s interval: 10s
@@ -290,12 +336,10 @@ services:
public_net: public_net:
ipv4_address: 192.168.70.134 ipv4_address: 192.168.70.134
oai-ext-dn: oai-ext-dn:
image: ubuntu:bionic image: trf-gen-cn5g:latest
privileged: true privileged: true
container_name: oai-ext-dn container_name: oai-ext-dn
entrypoint: /bin/bash -c \ 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" "ip route add 12.1.1.0/24 via 192.168.70.134 dev eth0; sleep infinity"
depends_on: depends_on:
- oai-spgwu - oai-spgwu
@@ -303,14 +347,14 @@ services:
public_net: public_net:
ipv4_address: 192.168.70.135 ipv4_address: 192.168.70.135
networks: networks:
# public_net:
# external:
# name: demo-oai-public-net
public_net: public_net:
external: driver: bridge
name: demo-oai-public-net name: demo-oai-public-net
# public_net: ipam:
# driver: bridge config:
# name: demo-oai-public-net - subnet: 192.168.70.128/26
# ipam: driver_opts:
# config: com.docker.network.bridge.name: "demo-oai"
# - 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 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 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 `3gppChargingCharacteristics` varchar(50) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8; ) 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\"}]}}');
-- -------------------------------------------------------- -- --------------------------------------------------------
-- --
-3
View File
@@ -59,9 +59,6 @@ extern void set_function_spec_param(RU_t *ru);
extern void reset_opp_meas(void); extern void reset_opp_meas(void);
extern void print_opp_meas(void); extern void print_opp_meas(void);
extern void init_fep_thread(PHY_VARS_gNB *);
void init_gNB_afterRU(void); void init_gNB_afterRU(void);
extern int stop_L1L2(module_id_t gnb_id); extern int stop_L1L2(module_id_t gnb_id);
@@ -20,6 +20,7 @@
#define FAPI_NR_RX_PDU_TYPE_DLSCH 0x03 #define FAPI_NR_RX_PDU_TYPE_DLSCH 0x03
#define FAPI_NR_DCI_IND 0x04 #define FAPI_NR_DCI_IND 0x04
#define FAPI_NR_RX_PDU_TYPE_RAR 0x05 #define FAPI_NR_RX_PDU_TYPE_RAR 0x05
#define FAPI_NR_CSIRS_IND 0x06
#define FAPI_NR_SIBS_MASK_SIB1 0x1 #define FAPI_NR_SIBS_MASK_SIB1 0x1
@@ -36,9 +36,6 @@
*/ */
typedef struct { typedef struct {
uint8_t uci_format; uint8_t uci_format;
uint8_t uci_channel; uint8_t uci_channel;
@@ -50,7 +47,14 @@ typedef struct {
uint32_t sr; uint32_t sr;
} fapi_nr_uci_pdu_rel15_t; } 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 { typedef struct {
/// frequency_domain_resource; /// frequency_domain_resource;
@@ -87,7 +91,7 @@ typedef struct {
// N_CCE is L, or number of CCEs for DCI // N_CCE is L, or number of CCEs for DCI
int N_CCE; int N_CCE;
uint8_t payloadSize; 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_pdu_rel15_t dci;
} fapi_nr_dci_indication_pdu_t; } fapi_nr_dci_indication_pdu_t;
@@ -130,6 +134,7 @@ typedef struct {
fapi_nr_pdsch_pdu_t pdsch_pdu; fapi_nr_pdsch_pdu_t pdsch_pdu;
fapi_nr_ssb_pdu_t ssb_pdu; fapi_nr_ssb_pdu_t ssb_pdu;
fapi_nr_sib_pdu_t sib_pdu; fapi_nr_sib_pdu_t sib_pdu;
fapi_nr_csirs_measurements_t csirs_measurements;
}; };
} fapi_nr_rx_indication_body_t; } 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 // 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; 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 // 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; } 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; llr_t *s1,*s2,*yp1,*yp2,*yp;
unsigned int i,j,iind;//,pi; unsigned int i,j,iind;//,pi;
unsigned char iteration_cnt=0; unsigned char iteration_cnt=0;
unsigned int crc,oldcrc,crc_len; unsigned int crc, crc_len;
uint8_t temp; uint8_t temp;
#if defined(__x86_64__) || defined(__i386__) #if defined(__x86_64__) || defined(__i386__)
__m128i *yp128; __m128i *yp128;
@@ -1233,8 +1233,8 @@ uint8_t phy_threegpplte_turbo_decoder8(int16_t *y,
} }
// check the CRC // 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) { switch (crc_type) {
case CRC24_A: case CRC24_A:
oldcrc&=0x00ffffff; oldcrc&=0x00ffffff;
+2 -2
View File
@@ -244,11 +244,11 @@ crc16 (unsigned char * inptr, int bitlen)
while (octetlen-- > 0) { while (octetlen-- > 0) {
crc = (crc << 8) ^ (crc16Table[(*inptr++) ^ (crc >> 24)] << 16); crc = (crc << 8) ^ (((uint32_t)crc16Table[(*inptr++) ^ (crc >> 24)]) << 16);
} }
if (resbit > 0) 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; 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) 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 // If no error pcRes should be 0
// Only use valid CNs // Only use valid CNs
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem))); if (Mrem)
pcResSum |= (pcRes&(0xFFFFFFFF>>(32-Mrem)));
// If PC failed we can stop here // If PC failed we can stop here
if (pcResSum > 0) if (pcResSum > 0)
+11 -11
View File
@@ -596,20 +596,20 @@ int phy_init_nr_gNB(PHY_VARS_gNB *gNB,
// CSI RS init // CSI RS init
// ceil((NB_RB*8(max allocation per RB)*2(QPSK))/32) // ceil((NB_RB*8(max allocation per RB)*2(QPSK))/32)
int csi_dmrs_init_length = ((fp->N_RB_DL<<4)>>5)+1; 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_info = (nr_csi_info_t *)malloc16_clear(sizeof(nr_csi_info_t));
gNB->nr_csi_rs_info->nr_gold_csi_rs = (uint32_t ***)malloc16(fp->slots_per_frame*sizeof(uint32_t **)); gNB->nr_csi_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"); 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++) { 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 *)); gNB->nr_csi_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); 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++) { 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)); gNB->nr_csi_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); 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; gNB->nr_csi_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); 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++) { 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)); gNB->nr_srs_info[id] = (nr_srs_info_t *)malloc16_clear(sizeof(nr_srs_info_t));
@@ -760,14 +760,14 @@ void phy_free_nr_gNB(PHY_VARS_gNB *gNB)
} }
free_and_zero(pusch_dmrs); 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 slot = 0; slot < fp->slots_per_frame; slot++) {
for (int symb = 0; symb < fp->symbols_per_slot; symb++) 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][symb]);
free_and_zero(nr_gold_csi_rs[slot]); free_and_zero(nr_gold_csi_rs[slot]);
} }
free_and_zero(nr_gold_csi_rs); 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 id = 0; id < NUMBER_OF_NR_SRS_MAX; id++) {
free_and_zero(gNB->nr_srs_info[id]); free_and_zero(gNB->nr_srs_info[id]);
+16 -56
View File
@@ -34,19 +34,6 @@
#include "PHY/NR_REFSIG/nr_refsig.h" #include "PHY/NR_REFSIG/nr_refsig.h"
#include "PHY/MODULATION/nr_modulation.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]; 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_CSI_RS **const csirs_vars = ue->csirs_vars;
NR_UE_SRS **const srs_vars = ue->srs_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); 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) // ceil((NB_RB*8(max allocation per RB)*2(QPSK))/32)
int csi_dmrs_init_length = ((fp->N_RB_DL<<4)>>5)+1; 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_info = (nr_csi_info_t *)malloc16_clear(sizeof(nr_csi_info_t));
ue->nr_csi_rs_info->nr_gold_csi_rs = (uint32_t ***)malloc16(fp->slots_per_frame*sizeof(uint32_t **)); ue->nr_csi_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"); 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++) { 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 *)); ue->nr_csi_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); 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++) { 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)); ue->nr_csi_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); 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_info->csi_rs_generated_signal = (int32_t **)malloc16(NR_MAX_NB_PORTS * sizeof(int32_t *) );
ue->nr_csi_rs_info->csi_rs_generated_signal = (int32_t **)malloc16(NR_MAX_NB_PORTS * sizeof(int32_t *) );
for (i=0; i<NR_MAX_NB_PORTS; i++) { 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_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_srs_info = (nr_srs_info_t *)malloc16_clear(sizeof(nr_srs_info_t)); ue->nr_srs_info = (nr_srs_info_t *)malloc16_clear(sizeof(nr_srs_info_t));
@@ -474,35 +448,21 @@ void term_nr_ue_signal(PHY_VARS_NR_UE *ue, int nb_connected_gNB)
for (int gNB_id = 0; gNB_id < ue->n_connected_gNB; 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++) { for (int th_id = 0; th_id < RX_NB_TH_MAX; th_id++) {
free_and_zero(ue->pdcch_vars[th_id][gNB_id]); free_and_zero(ue->pdcch_vars[th_id][gNB_id]);
} }
for (int i=0; i<NR_MAX_NB_PORTS; i++) { for (int i=0; i<NR_MAX_NB_PORTS; i++) {
free_and_zero(ue->nr_csi_rs_info->csi_rs_generated_signal[i]); free_and_zero(ue->nr_csi_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);
for (int slot=0; slot<fp->slots_per_frame; slot++) { for (int slot=0; slot<fp->slots_per_frame; slot++) {
for (int symb=0; symb<fp->symbols_per_slot; symb++) { 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_info->nr_gold_csi_rs);
free_and_zero(ue->nr_csi_rs_info->nr_gold_csi_rs); free_and_zero(ue->nr_csi_info);
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_srs_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) { uint32_t get_prb(int N_RB_DL,int odd_slot,int vrb,int Ngap) {
int offset; int offset;
int ret=-1;
switch (N_RB_DL) { 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) { switch (vrb) {
case 0: // even: 0->0, 1->2, odd: 0->3, 1->5 case 0: // even: 0->0, 1->2, odd: 0->3, 1->5
case 1: case 1:
return ((3*odd_slot) + 2*(vrb&3))%6; ret= ((3*odd_slot) + 2*(vrb&3))%6;
break; break;
case 2: // even: 2->3, 3->5, odd: 2->0, 3->2 case 2: // even: 2->3, 3->5, odd: 2->0, 3->2
case 3: case 3:
return ((3*odd_slot) + 2*(vrb&3) + 5)%6; ret= ((3*odd_slot) + 2*(vrb&3) + 5)%6;
break; break;
case 4: // even: 4->1, odd: 4->4 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 case 5: // even: 5->4, odd: 5->1
return ((3*odd_slot) + 4)%6; ret= ((3*odd_slot) + 4)%6;
break; break;
} }
break; break;
@@ -562,88 +565,90 @@ uint32_t get_prb(int N_RB_DL,int odd_slot,int vrb,int Ngap) {
case 15: case 15:
if (vrb<12) { 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 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 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) if (vrb==12)
return (3+(7*odd_slot)) % 14; ret= (3+(7*odd_slot)) % 14;
if (vrb==13) if (vrb==13)
return (10+(7*odd_slot)) % 14; ret= (10+(7*odd_slot)) % 14;
return 14; ret= 14;
break; break;
// Formula in TS 36.211, chap 6.2.3.2
// Fix me: returns a PRB number > 24 when vrb is 24
case 25: 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; break;
case 50: // P=3 case 50: // P=3
if (Ngap==0) { if (Ngap==0) {
// Nrow=12,Nnull=2,NVRBDL=46,Ngap1= 27 // Nrow=12,Nnull=2,NVRBDL=46,Ngap1= 27
if (vrb>=23) if (vrb>=23)
offset=4; offset=4;
else else
offset=0; offset=0;
if (vrb<44) { if (vrb<44) {
if ((vrb&3)>=2) if ((vrb&3)>=2)
return offset+((23*odd_slot) + 12*(vrb&3) + (vrb>>2) + 45)%46; ret= offset+((23*odd_slot) + 12*(vrb&3) + (vrb>>2) + 45)%46;
else else
return offset+((23*odd_slot) + 12*(vrb&3) + (vrb>>2))%46; ret= offset+((23*odd_slot) + 12*(vrb&3) + (vrb>>2))%46;
} }
if (vrb==44) // even: 44->11, odd: 45->34 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 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) 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) if (vrb==47)
return offset+46+((23*odd_slot) + 23+12) % 46; ret= offset+46+((23*odd_slot) + 23+12) % 46;
if (vrb==48) 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) if (vrb==49)
return offset+46+((23*odd_slot) + 23+12) % 46; ret= offset+46+((23*odd_slot) + 23+12) % 46;
} }
else { else {
// Nrow=6,Nnull=6,NVRBDL=18,Ngap1= 27 // Nrow=6,Nnull=6,NVRBDL=18,Ngap1= 27
if (vrb>=9) if (vrb>=9)
offset=18; offset=18;
else else
offset=0; offset=0;
if (vrb<12) { if (vrb<12) {
if ((vrb&3)>=2) if ((vrb&3)>=2)
return offset+((9*odd_slot) + 6*(vrb&3) + (vrb>>2) + 17)%18; ret= offset+((9*odd_slot) + 6*(vrb&3) + (vrb>>2) + 17)%18;
else else
return offset+((9*odd_slot) + 6*(vrb&3) + (vrb>>2))%18; ret= offset+((9*odd_slot) + 6*(vrb&3) + (vrb>>2))%18;
} }
else { 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; break;
case 75: case 75:
// Ngap1 = 32, NVRBRL=64, P=4, Nrow= 16, Nnull=0 // Ngap1 = 32, NVRBRL=64, P=4, Nrow= 16, Nnull=0
if (Ngap ==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 { } else {
// Ngap2 = 16, NVRBDL=32, Nrow=8, Nnull=0 // 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; break;
case 100: case 100:
// Ngap1 = 48, NVRBDL=96, Nrow=24, Nnull=0 // Ngap1 = 48, NVRBDL=96, Nrow=24, Nnull=0
if (Ngap ==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 { } else {
// Ngap2 = 16, NVRBDL=32, Nrow=8, Nnull=0 // 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; break;
default: default:
LOG_E(PHY,"Unknown N_RB_DL %d\n",N_RB_DL); 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); // printf("RIV %d (%d) : first_rb %d NBRB %d\n",RIV,localRIV2alloc_LUT25[RIV],RBstart,Lcrbs);
localRIV2alloc_LUT6[RIV] = alloc0; 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; distRIV2alloc_odd_LUT6[RIV] = allocdist0_0_odd;
RIV2nb_rb_LUT6[RIV] = Lcrbs; RIV2nb_rb_LUT6[RIV] = Lcrbs;
RIV2first_rb_LUT6[RIV] = RBstart; RIV2first_rb_LUT6[RIV] = RBstart;
@@ -693,15 +698,14 @@ void generate_RIV_tables(void)
nVRB = Lcrbs-1+RBstart; nVRB = Lcrbs-1+RBstart;
//printf("RBstart %d, len %d --> ",RBstart,Lcrbs); //printf("RBstart %d, len %d --> ",RBstart,Lcrbs);
alloc0 |= (1<<nVRB); alloc0 |= (1<<nVRB);
allocdist0_0_even |= (1<<get_prb(25,0,nVRB,0)); allocdist0_0_even |= 1U << get_prb(25, 0, nVRB, 0);
allocdist0_0_odd |= (1<<get_prb(25,1,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); //printf("alloc 0 %x, allocdist0_even %x, allocdist0_odd %x\n",alloc0,allocdist0_0_even,allocdist0_0_odd);
RIV=computeRIV(25,RBstart,Lcrbs); RIV=computeRIV(25,RBstart,Lcrbs);
if (RIV>RIV_max25) if (RIV>RIV_max25)
RIV_max25 = RIV;; RIV_max25 = RIV;
localRIV2alloc_LUT25[RIV] = alloc0; localRIV2alloc_LUT25[RIV] = alloc0;
distRIV2alloc_even_LUT25[RIV] = allocdist0_0_even; distRIV2alloc_even_LUT25[RIV] = allocdist0_0_even;
@@ -730,37 +734,37 @@ void generate_RIV_tables(void)
if (nVRB<32) if (nVRB<32)
alloc0 |= (1<<nVRB); alloc0 |= 1U << nVRB;
else else
alloc1 |= (1<<(nVRB-32)); alloc1 |= 1U << (nVRB - 32);
// Distributed Gap1, even slot // Distributed Gap1, even slot
nVRB_even_dist = get_prb(50,0,nVRB,0); nVRB_even_dist = get_prb(50,0,nVRB,0);
if (nVRB_even_dist<32) if (nVRB_even_dist<32)
allocdist0_0_even |= (1<<nVRB_even_dist); allocdist0_0_even |= 1U << nVRB_even_dist;
else else
allocdist1_0_even |= (1<<(nVRB_even_dist-32)); allocdist1_0_even |= 1U << (nVRB_even_dist - 32);
// Distributed Gap1, odd slot // Distributed Gap1, odd slot
nVRB_odd_dist = get_prb(50,1,nVRB,0); nVRB_odd_dist = get_prb(50,1,nVRB,0);
if (nVRB_odd_dist<32) if (nVRB_odd_dist<32)
allocdist0_0_odd |= (1<<nVRB_odd_dist); allocdist0_0_odd |= (1U <<nVRB_odd_dist);
else else
allocdist1_0_odd |= (1<<(nVRB_odd_dist-32)); allocdist1_0_odd |= (1U <<(nVRB_odd_dist-32));
// Distributed Gap2, even slot // Distributed Gap2, even slot
nVRB_even_dist = get_prb(50,0,nVRB,1); nVRB_even_dist = get_prb(50,0,nVRB,1);
if (nVRB_even_dist<32) if (nVRB_even_dist<32)
allocdist0_1_even |= (1<<nVRB_even_dist); allocdist0_1_even |= 1U << nVRB_even_dist;
else else
allocdist1_1_even |= (1<<(nVRB_even_dist-32)); allocdist1_1_even |= 1U << (nVRB_even_dist - 32);
// Distributed Gap2, odd slot // Distributed Gap2, odd slot
nVRB_odd_dist = get_prb(50,1,nVRB,1); nVRB_odd_dist = get_prb(50,1,nVRB,1);
if (nVRB_odd_dist<32) if (nVRB_odd_dist<32)
allocdist0_1_odd |= (1<<nVRB_odd_dist); allocdist0_1_odd |= 1U << nVRB_odd_dist;
else else
allocdist1_1_odd |= (1<<(nVRB_odd_dist-32)); allocdist1_1_odd |= 1U << (nVRB_odd_dist - 32);
RIV=computeRIV(50,RBstart,Lcrbs); RIV=computeRIV(50,RBstart,Lcrbs);
@@ -811,13 +815,13 @@ void generate_RIV_tables(void)
nVRB = Lcrbs-1+RBstart; nVRB = Lcrbs-1+RBstart;
if (nVRB<32) if (nVRB<32)
alloc0 |= (1<<nVRB); alloc0 |= 1U << nVRB;
else if (nVRB<64) else if (nVRB<64)
alloc1 |= (1<<(nVRB-32)); alloc1 |= 1U << (nVRB - 32);
else if (nVRB<96) else if (nVRB<96)
alloc2 |= (1<<(nVRB-64)); alloc2 |= 1U << (nVRB - 64);
else else
alloc3 |= (1<<(nVRB-96)); alloc3 |= 1U << (nVRB - 96);
// Distributed Gap1, even slot // Distributed Gap1, even slot
nVRB_even_dist = get_prb(100,0,nVRB,0); nVRB_even_dist = get_prb(100,0,nVRB,0);
@@ -825,15 +829,14 @@ void generate_RIV_tables(void)
// if ((RBstart==0) && (Lcrbs<=8)) // if ((RBstart==0) && (Lcrbs<=8))
// printf("nVRB %d => nVRB_even_dist %d\n",nVRB,nVRB_even_dist); // printf("nVRB %d => nVRB_even_dist %d\n",nVRB,nVRB_even_dist);
if (nVRB_even_dist<32) 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) 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) else if (nVRB_even_dist<96)
allocdist2_0_even |= (1<<(nVRB_even_dist-64)); allocdist2_0_even |= 1U << (nVRB_even_dist - 64);
else else
allocdist3_0_even |= (1<<(nVRB_even_dist-96)); allocdist3_0_even |= 1U << (nVRB_even_dist - 96);
/* if ((RBstart==0) && (Lcrbs<=8)) /* if ((RBstart==0) && (Lcrbs<=8))
printf("rballoc =>(%08x.%08x.%08x.%08x)\n", printf("rballoc =>(%08x.%08x.%08x.%08x)\n",
allocdist0_0_even, allocdist0_0_even,
@@ -845,38 +848,37 @@ void generate_RIV_tables(void)
// Distributed Gap1, odd slot // Distributed Gap1, odd slot
nVRB_odd_dist = get_prb(100,1,nVRB,0); nVRB_odd_dist = get_prb(100,1,nVRB,0);
if (nVRB_odd_dist<32) 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) 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) else if (nVRB_odd_dist<96)
allocdist2_0_odd |= (1<<(nVRB_odd_dist-64)); allocdist2_0_odd |= 1U << (nVRB_odd_dist - 64);
else else
allocdist3_0_odd |= (1<<(nVRB_odd_dist-96)); allocdist3_0_odd |= 1U << (nVRB_odd_dist - 96);
// Distributed Gap2, even slot // Distributed Gap2, even slot
nVRB_even_dist = get_prb(100,0,nVRB,1); nVRB_even_dist = get_prb(100,0,nVRB,1);
if (nVRB_even_dist<32) 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) 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) else if (nVRB_even_dist<96)
allocdist2_1_even |= (1<<(nVRB_even_dist-64)); allocdist2_1_even |= 1U << (nVRB_even_dist - 64);
else else
allocdist3_1_even |= (1<<(nVRB_even_dist-96)); allocdist3_1_even |= 1U << (nVRB_even_dist - 96);
// Distributed Gap2, odd slot // Distributed Gap2, odd slot
nVRB_odd_dist = get_prb(100,1,nVRB,1); nVRB_odd_dist = get_prb(100,1,nVRB,1);
if (nVRB_odd_dist<32) 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) 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) else if (nVRB_odd_dist<96)
allocdist2_1_odd |= (1<<(nVRB_odd_dist-64)); allocdist2_1_odd |= 1U << (nVRB_odd_dist - 64);
else else
allocdist3_1_odd |= (1<<(nVRB_odd_dist-96)); allocdist3_1_odd |= 1U << (nVRB_odd_dist - 96);
RIV=computeRIV(100,RBstart,Lcrbs); 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]; LTE_DL_eNB_HARQ_t *hadlsch=rdata->dlsch->harq_processes[harq_pid];
if ( rdata-> round == 0) { 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); memset(tmp,LTE_NULL, TURBO_SIMD_SOFTBITS);
start_meas(rdata->te_stats); start_meas(rdata->te_stats);
encoder(rdata->input, 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_ri[16];
extern uint16_t beta_ack[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) 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; uint8_t harq_pid=0;
@@ -974,28 +980,28 @@ int check_dci_format1_1a_coherency(DCI_format_t dci_format,
{ {
switch (N_RB_DL) { switch (N_RB_DL) {
case 6: case 6:
NPRB = RIV2nb_rb_LUT6[rballoc];//NPRB; NPRB = rbAllocCheck(rballoc, RIV2nb_rb_LUT6);
if(rah) if(rah)
RIV_max = RIV_max6; RIV_max = RIV_max6;
else else
RIV_max = 0x3F; RIV_max = 0x3F;
break; break;
case 25: case 25:
NPRB = RIV2nb_rb_LUT25[rballoc];//NPRB; NPRB = rbAllocCheck(rballoc,RIV2nb_rb_LUT25);
if(rah) if(rah)
RIV_max = RIV_max25; RIV_max = RIV_max25;
else else
RIV_max = 0x1FFF; RIV_max = 0x1FFF;
break; break;
case 50: case 50:
NPRB = RIV2nb_rb_LUT50[rballoc];//NPRB; NPRB = rbAllocCheck(rballoc,RIV2nb_rb_LUT50);
if(rah) if(rah)
RIV_max = RIV_max50; RIV_max = RIV_max50;
else else
RIV_max = 0x1FFFF; RIV_max = 0x1FFFF;
break; break;
case 100: case 100:
NPRB = RIV2nb_rb_LUT100[rballoc];//NPRB; NPRB = rbAllocCheck(rballoc,RIV2nb_rb_LUT100);
if(rah) if(rah)
RIV_max = RIV_max100; RIV_max = RIV_max100;
else else
@@ -1034,9 +1040,14 @@ int check_dci_format1_1a_coherency(DCI_format_t dci_format,
// this is an eNB issue // this is an eNB issue
// retransmisison but old and new TBS are different !!! // retransmisison but old and new TBS are different !!!
// work around, consider it as a new transmission // 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; pdlsch0_harq->round = 0;
//return(0); // ?? to cross check //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 */ @return Transport block size */
uint32_t get_TBS_UL(uint8_t mcs, uint16_t nb_rb); 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 /* \brief Return prb for a given vrb index
@param vrb_type VRB type (0=localized,1=distributed) @param vrb_type VRB type (0=localized,1=distributed)
@param rb_alloc_dci rballoc field from DCI @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 /// Redundancy-version of the current sub-frame
uint8_t rvidx; uint8_t rvidx;
/// Turbo-code outputs (36-212 V8.6 2009-03, p.12 /// 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) /// Sub-block interleaver outputs (36-212 V8.6 2009-03, p.16-17)
uint8_t w[MAX_NUM_ULSCH_SEGMENTS][3*6144]; uint8_t w[MAX_NUM_ULSCH_SEGMENTS][3*6144];
/// Number of code segments (for definition see 36-212 V8.6 2009-03, p.9) /// 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++) { for (r=0; r<MAX_NUM_ULSCH_SEGMENTS; r++) {
if (ulsch->harq_processes[i]->c[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]->c[r],((r==0)?8:0) + 3+768);
free16(ulsch->harq_processes[i]->d[r],0);
ulsch->harq_processes[i]->c[r] = NULL; 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 *new_ue_ulsch(unsigned char N_RB_UL, uint8_t abstraction_flag) {
LTE_UE_ULSCH_t *ulsch; LTE_UE_ULSCH_t *ulsch;
unsigned char exit_flag = 0,i,j,r; unsigned char exit_flag = 0;
unsigned char bw_scaling =1; unsigned char bw_scaling =1;
switch (N_RB_UL) { 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)); memset(ulsch,0,sizeof(LTE_UE_ULSCH_t));
ulsch->Mlimit = 4; 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)); 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]); // 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) { if (abstraction_flag==0) {
for (r=0; r<MAX_NUM_ULSCH_SEGMENTS; r++) { for (int 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 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], "");
if (ulsch->harq_processes[i]->c[r]) ulsch->harq_processes[i]->d[r] = malloc16_clear(96+3+(3*6144));
memset(ulsch->harq_processes[i]->c[r],0,((r==0)?8:0) + 3+768); AssertFatal(ulsch->harq_processes[i]->d[r], "");
else {
LOG_E(PHY,"Can't get c\n");
exit_flag=2;
}
} }
} }
@@ -148,15 +145,7 @@ LTE_UE_ULSCH_t *new_ue_ulsch(unsigned char N_RB_UL, uint8_t abstraction_flag) {
exit_flag=3; exit_flag=3;
} }
} }
if (!exit_flag)
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)
return(ulsch); 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 Qprime_ACK=0,Qprime_CQI=0,Qprime_RI=0,len_ACK=0,len_RI=0;
// uint32_t E; // uint32_t E;
uint8_t ack_parity; uint8_t ack_parity;
uint32_t i,q,j,iprime,j2; uint32_t q,j,iprime,j2;
uint16_t o_RCC; uint16_t o_RCC;
uint8_t o_flip[8]; uint8_t o_flip[8];
uint32_t wACK_idx; uint32_t wACK_idx;
@@ -327,6 +316,8 @@ uint32_t ulsch_encoding(uint8_t *a,
#endif #endif
// offset=0; // offset=0;
start_meas(te_stats); 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], encoder(ulsch->harq_processes[harq_pid]->c[r],
Kr>>3, Kr>>3,
&ulsch->harq_processes[harq_pid]->d[r][96], &ulsch->harq_processes[harq_pid]->d[r][96],
@@ -539,8 +530,6 @@ uint32_t ulsch_encoding(uint8_t *a,
ulsch->q); ulsch->q);
} }
i=0;
// Do RI coding // Do RI coding
if (ulsch->O_RI == 1) { if (ulsch->O_RI == 1) {
switch (Q_m) { switch (Q_m) {
@@ -691,7 +680,7 @@ uint32_t ulsch_encoding(uint8_t *a,
j=0; j=0;
for (i=0; i<Qprime_RI; i++) { for (int i=0; i<Qprime_RI; i++) {
r = Rmux_prime - 1 - (i>>2); r = Rmux_prime - 1 - (i>>2);
for (q=0; q<Q_m; q++) { 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++; while (y[Q_m*j] != LTE_NULL) j++;
for (q=0; q<Q_m; q++) { for (q=0; q<Q_m; q++) {
@@ -788,7 +777,7 @@ uint32_t ulsch_encoding(uint8_t *a,
j=0; j=0;
for (i=0; i<Qprime_ACK; i++) { for (int i=0; i<Qprime_ACK; i++) {
r = Rmux_prime - 1 - (i>>2); r = Rmux_prime - 1 - (i>>2);
for (q=0; q<Q_m; q++) { for (q=0; q<Q_m; q++) {
@@ -808,7 +797,7 @@ uint32_t ulsch_encoding(uint8_t *a,
switch (Q_m) { switch (Q_m) {
case 2: case 2:
for (i=0; i<Cmux; i++) for (int i=0; i<Cmux; i++)
for (r=0; r<Rmux_prime; r++) { for (r=0; r<Rmux_prime; r++) {
yptr=&y[((r*Cmux)+i)<<1]; yptr=&y[((r*Cmux)+i)<<1];
ulsch->h[j++] = *yptr++; ulsch->h[j++] = *yptr++;
@@ -818,7 +807,7 @@ uint32_t ulsch_encoding(uint8_t *a,
break; break;
case 4: case 4:
for (i=0; i<Cmux; i++) for (int i=0; i<Cmux; i++)
for (r=0; r<Rmux_prime; r++) { for (r=0; r<Rmux_prime; r++) {
yptr = &y[((r*Cmux)+i)<<2]; yptr = &y[((r*Cmux)+i)<<2];
ulsch->h[j++] = *yptr++; ulsch->h[j++] = *yptr++;
@@ -830,7 +819,7 @@ uint32_t ulsch_encoding(uint8_t *a,
break; break;
case 6: case 6:
for (i=0; i<Cmux; i++) for (int i=0; i<Cmux; i++)
for (r=0; r<Rmux_prime; r++) { for (r=0; r<Rmux_prime; r++) {
yptr = &y[((r*Cmux)+i)*6]; yptr = &y[((r*Cmux)+i)*6];
ulsch->h[j++] = *yptr++; ulsch->h[j++] = *yptr++;
+4 -3
View File
@@ -226,10 +226,11 @@ void nr_modulation(uint32_t *in,
i *= 24; i *= 24;
bit_cnt = i * 8; bit_cnt = i * 8;
while (bit_cnt < length) { while (bit_cnt < length) {
x = *((uint32_t*)(in_bytes+i)); uint32_t xx;
x1 = x&4095; memcpy(&xx, in_bytes+i, sizeof(xx));
x1 = xx & 4095;
out64[j++] = nr_64qam_mod_table[x1]; out64[j++] = nr_64qam_mod_table[x1];
x1 = (x>>12)&4095; x1 = (xx >> 12) & 4095;
out64[j++] = nr_64qam_mod_table[x1]; out64[j++] = nr_64qam_mod_table[x1];
i += 3; i += 3;
bit_cnt += 24; bit_cnt += 24;
@@ -162,7 +162,7 @@ void gNB_I0_measurements(PHY_VARS_gNB *gNB,int slot, int first_symb,int num_symb
measurements->n0_subband_power[aarx][rb]=0; 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; 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]++; nb_symb[rb]++;
for (int aarx=0; aarx<frame_parms->nb_antennas_rx; aarx++) { for (int aarx=0; aarx<frame_parms->nb_antennas_rx; aarx++) {
int offset = offset0 + (s*frame_parms->ofdm_symbol_size); int offset = offset0 + (s*frame_parms->ofdm_symbol_size);
@@ -1115,7 +1115,7 @@ int nr_srs_channel_estimation(const PHY_VARS_gNB *gNB,
const uint64_t subcarrier_offset = frame_parms->first_carrier_offset + srs_pdu->bwp_start*12; const uint64_t subcarrier_offset = frame_parms->first_carrier_offset + srs_pdu->bwp_start*12;
const uint8_t srs_symbols_per_rb = srs_pdu->comb_size == 0 ? 6 : 3; 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*srs_symbols_per_rb; const uint8_t n_noise_est = frame_parms->nb_antennas_rx * srs_symbols_per_rb;
uint8_t count_estimates = 0; uint8_t count_estimates = 0;
uint64_t sum_re = 0; uint64_t sum_re = 0;
uint64_t sum_re2 = 0; uint64_t sum_re2 = 0;
@@ -1138,9 +1138,9 @@ int nr_srs_channel_estimation(const PHY_VARS_gNB *gNB,
sum_im2 = sum_im2 + noise_imag[ant*nr_srs_info->sc_list_length+sc_idx]*noise_imag[ant*nr_srs_info->sc_list_length+sc_idx]; sum_im2 = sum_im2 + noise_imag[ant*nr_srs_info->sc_list_length+sc_idx]*noise_imag[ant*nr_srs_info->sc_list_length+sc_idx];
count_estimates++; count_estimates++;
if (count_estimates == n_noise_estimates) { if (count_estimates == n_noise_est) {
noise_power_per_rb[rb] = sum_re2/n_noise_estimates - (sum_re/n_noise_estimates)*(sum_re/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_estimates - (sum_im/n_noise_estimates)*(sum_im/n_noise_estimates); 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; snr_per_rb[rb] = dB_fixed((int32_t)((*signal_power<<factor_bits)/noise_power_per_rb[rb])) - factor_dB;
count_estimates = 0; count_estimates = 0;
sum_re = 0; sum_re = 0;
+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_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_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); 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, uint16_t N_n_scid,
uint8_t 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 #endif
+47 -37
View File
@@ -27,7 +27,7 @@
//#define NR_CSIRS_DEBUG //#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; uint32_t x1, x2;
uint8_t reset; uint8_t reset;
int csi_dmrs_init_length = ((fp->N_RB_DL<<4)>>5)+1; 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, int32_t **dataF,
int16_t amp, const int16_t amp,
nr_csi_rs_info_t *nr_csi_rs_info, nr_csi_info_t *nr_csi_info,
nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params, const nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params,
int slot){ 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 #ifdef NR_CSIRS_DEBUG
LOG_I(NR_PHY, "csi_params->subcarrier_spacing = %i\n", csi_params->subcarrier_spacing); 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); LOG_I(NR_PHY, "csi_params->power_control_offset_ss = %i\n", csi_params->power_control_offset_ss);
#endif #endif
int dataF_offset = slot*frame_parms.samples_per_slot_wCP; 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]; uint32_t **nr_gold_csi_rs = nr_csi_info->nr_gold_csi_rs[slot];
//*8(max allocation per RB)*2(QPSK)) //*8(max allocation per RB)*2(QPSK))
int csi_rs_length = frame_parms.N_RB_DL<<4; 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))); 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 b = csi_params->freq_domain;
uint16_t n, p, k, l, mprime, na, kpn; uint16_t n, p, k, l, mprime, na, kpn;
uint8_t size, ports, kprime, lprime, i, gs; 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; uint8_t fi = 0;
double rho, alpha; double rho, alpha;
uint32_t beta = amp; 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"); 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 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) { if (csi_params->scramb_id != nr_csi_info->csi_gold_init) {
nr_csi_rs_info->csi_gold_init = csi_params->scramb_id; nr_csi_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); nr_init_csi_rs(frame_parms, nr_csi_info->nr_gold_csi_rs, csi_params->scramb_id);
} }
switch (csi_params->row) { 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 // 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++) { 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 for (int s=0 ; s<gs; s++) { // loop over each CDM group size
p = s+j[ji]*gs; // port index p = s+j[ji]*gs; // port index
for (kp=0; kp<=kprime; kp++) { // loop over frequency resource elements within a group 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 // wf according to tables 7.4.5.3-2 to 7.4.5.3-5
if (kp == 0) if (kp == 0)
wf = 1; wf = 1;
@@ -620,17 +628,17 @@ void nr_generate_csi_rs(NR_DL_FRAME_PARMS frame_parms,
// ZP CSI RS // ZP CSI RS
if (csi_params->csi_type == 2) { 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)+(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)+1+(2*dataF_offset)] = 0;
} }
else { 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)+(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)+1+(2*dataF_offset)] = (beta*wt*wf*mod_csi[l][(mprime<<1) + 1]) >> 15;
} }
#ifdef NR_CSIRS_DEBUG #ifdef NR_CSIRS_DEBUG
printf("l,k (%d,%d) seq. index %d \t port %d \t (%d,%d)\n",l,k,mprime,p+3000, 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)+(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)+1+(2*dataF_offset)]);
#endif #endif
} }
} }
@@ -638,23 +646,25 @@ void nr_generate_csi_rs(NR_DL_FRAME_PARMS frame_parms,
} }
} }
} }
nr_csi_rs_info->N_cdm_groups = size; if (N_cdm_groups) *N_cdm_groups = size;
nr_csi_rs_info->CDM_group_size = gs; if (CDM_group_size) *CDM_group_size = gs;
nr_csi_rs_info->kprime = kprime; if (k_prime) *k_prime = kprime;
nr_csi_rs_info->lprime = lprime; if (l_prime) *l_prime = lprime;
nr_csi_rs_info->N_ports = ports; if (N_ports) *N_ports = ports;
memcpy(nr_csi_rs_info->j,j,16*sizeof(uint8_t)); if (j_cdm) memcpy(j_cdm,j,16*sizeof(uint8_t));
memcpy(nr_csi_rs_info->koverline,koverline,16*sizeof(uint8_t)); if (k_overline) memcpy(k_overline,koverline,16*sizeof(uint8_t));
memcpy(nr_csi_rs_info->loverline,loverline,16*sizeof(uint8_t)); if (l_overline) memcpy(l_overline,loverline,16*sizeof(uint8_t));
#ifdef NR_CSIRS_DEBUG #ifdef NR_CSIRS_DEBUG
LOG_I(NR_PHY, "nr_csi_rs_info->N_ports = %d\n", nr_csi_rs_info->N_ports); if (N_ports) LOG_I(NR_PHY, "nr_csi_info->N_ports = %d\n", *N_ports);
LOG_I(NR_PHY, "nr_csi_rs_info->N_cdm_groups = %d\n", nr_csi_rs_info->N_cdm_groups); if (N_cdm_groups) LOG_I(NR_PHY, "nr_csi_info->N_cdm_groups = %d\n", *N_cdm_groups);
LOG_I(NR_PHY, "nr_csi_rs_info->CDM_group_size = %d\n", nr_csi_rs_info->CDM_group_size); if (CDM_group_size) LOG_I(NR_PHY, "nr_csi_info->CDM_group_size = %d\n", *CDM_group_size);
LOG_I(NR_PHY, "nr_csi_rs_info->kprime = %d\n", nr_csi_rs_info->kprime); if (k_prime) LOG_I(NR_PHY, "nr_csi_info->kprime = %d\n", *k_prime);
LOG_I(NR_PHY, "nr_csi_rs_info->lprime = %d\n", nr_csi_rs_info->lprime); if (l_prime) LOG_I(NR_PHY, "nr_csi_info->lprime = %d\n", *l_prime);
for(int ji=0; ji<nr_csi_rs_info->N_cdm_groups; ji++) { if (N_cdm_groups) {
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]); 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 #endif
} }
+9 -9
View File
@@ -111,9 +111,10 @@ void nr_generate_dci(PHY_VARS_gNB *gNB,
// DMRS length is per OFDM symbol // DMRS length is per OFDM symbol
uint32_t dmrs_length = n_rb*6; //2(QPSK)*3(per RB)*6(REG per CCE) 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) 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", if (dci_pdu->RNTI != 0xFFFF)
rb_offset, n_rb,dmrs_length, encoded_length,pdcch_pdu_rel15->precoderGranularity,pdcch_pdu_rel15->CceRegMappingType, 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",
dci_pdu->ScramblingId,dci_pdu->ScramblingRNTI,dci_pdu->PayloadSizeBits); 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_length += rb_offset*6; // To accommodate more DMRS symbols in case of rb offset
/// DMRS QPSK modulation /// 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 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 #ifdef DEBUG_PDCCH_DMRS
if(dci_pdu->RNTI!=0xFFFF) { if(dci_pdu->RNTI!=0xFFFF) {
for (int i=0; i<dmrs_length>>1; i++) 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, 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] ); &gold_pdcch_dmrs[symb][i>>5],gold_pdcch_dmrs[symb][i>>5], mod_dmrs[symb][i<<1], mod_dmrs[symb][(i<<1)+1]);
} }
#endif #endif
} }
@@ -265,7 +266,6 @@ void nr_generate_dci_top(processingData_L1tx_t *msgTx,
int16_t amp, int16_t amp,
NR_DL_FRAME_PARMS *frame_parms) { NR_DL_FRAME_PARMS *frame_parms) {
for (int i=0; i<msgTx->num_ul_pdcch; i++) 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); 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++) 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); rel15->dlDmrsSymbPos);
n_ptrs = (rel15->rbSize + rel15->PTRSFreqDensity - 1)/rel15->PTRSFreqDensity; 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 /// CRC, coding, interleaving and rate matching
AssertFatal(harq->pdu!=NULL,"harq->pdu is null\n"); 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 */ /* calculate if current symbol is PTRS symbols */
ptrs_idx = 0; ptrs_idx = 0;
int16_t *mod_ptrs = NULL;
if(rel15->pduBitmap & 0x1) { if(rel15->pduBitmap & 0x1) {
ptrs_symbol = is_ptrs_symbol(l,dlPtrsSymPos); ptrs_symbol = is_ptrs_symbol(l,dlPtrsSymPos);
if(ptrs_symbol) { if(ptrs_symbol) {
/* PTRS QPSK Modulation for each OFDM symbol in a slot */ /* 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); 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); 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)); bzero(dlsch,sizeof(NR_gNB_DLSCH_t));
dlsch->Kmimo = Kmimo; dlsch->Kmimo = Kmimo;
dlsch->Mdlharq = Mdlharq; dlsch->Mdlharq = Mdlharq;
dlsch->Mlimit = 4;
dlsch->Nsoft = Nsoft; 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 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
+13 -5
View File
@@ -337,12 +337,20 @@ void init_prach_ru_list(RU_t *ru);
void free_nr_ru_prach_entry(RU_t *ru, int prach_id); void free_nr_ru_prach_entry(RU_t *ru, int prach_id);
uint8_t get_nr_prach_duration(uint8_t prach_format); 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, int32_t **dataF,
int16_t amp, const int16_t amp,
nr_csi_rs_info_t *nr_csi_rs_info, nr_csi_info_t *nr_csi_info,
nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params, const nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *csi_params,
int slot); 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); void free_nr_prach_entry(PHY_VARS_gNB *gNB, int prach_id);
+13 -5
View File
@@ -68,12 +68,20 @@ void nr_fill_ulsch(PHY_VARS_gNB *gNB,
ulsch->rnti = ulsch_pdu->rnti; ulsch->rnti = ulsch_pdu->rnti;
//ulsch->rnti_type; //ulsch->rnti_type;
ulsch->harq_mask |= 1<<harq_pid; ulsch->harq_mask |= 1<<harq_pid;
ulsch->harq_process_id[slot] = harq_pid;
ulsch->harq_processes[harq_pid]->frame=frame; NR_UL_gNB_HARQ_t *harq = ulsch->harq_processes[harq_pid];
ulsch->harq_processes[harq_pid]->slot=slot; harq->frame=frame;
ulsch->harq_processes[harq_pid]->handled= 0; harq->slot=slot;
ulsch->harq_processes[harq_pid]->status= NR_ACTIVE; 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)); 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); 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 = (NR_gNB_ULSCH_t *)malloc16_clear(sizeof(NR_gNB_ULSCH_t));
ulsch->max_ldpc_iterations = max_ldpc_iterations; ulsch->max_ldpc_iterations = max_ldpc_iterations;
ulsch->Mlimit = 4;
for (i=0; i<NR_MAX_ULSCH_HARQ_PROCESSES; i++) { 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->rnti_type = 0;
ulsch->cyclicShift = 0; ulsch->cyclicShift = 0;
ulsch->cooperation_flag = 0; ulsch->cooperation_flag = 0;
ulsch->Mlimit = 0;
ulsch->max_ldpc_iterations = 0; ulsch->max_ldpc_iterations = 0;
ulsch->last_iteration_cnt = 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++) { for (i=0; i<NR_MAX_ULSCH_HARQ_PROCESSES; i++) {
if (ulsch->harq_processes[i]){ if (ulsch->harq_processes[i]){
+2 -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].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].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].r >>= 31;
corr[aa][l].i >>= 31; corr[aa][l].i >>= 31;
} }
} }
LOG_D(PHY,"PUCCH IDFT[%d/%d] = (%ld,%ld)=>%f\n", LOG_D(PHY,"PUCCH IDFT[%d/%d] = (%ld,%ld)=>%f\n",
+678 -89
View File
@@ -33,16 +33,103 @@
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include "executables/nr-softmodem-common.h"
#include "nr_transport_proto_ue.h" #include "nr_transport_proto_ue.h"
#include "PHY/phy_extern_nr_ue.h" #include "PHY/phy_extern_nr_ue.h"
#include "common/utils/nr/nr_common.h" #include "common/utils/nr/nr_common.h"
#include "PHY/NR_TRANSPORT/nr_transport_proto.h" #include "PHY/NR_TRANSPORT/nr_transport_proto.h"
#include "PHY/NR_UE_ESTIMATION/filt16a_32.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_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; 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; return ret;
} }
int nr_get_csi_rs_signal(PHY_VARS_NR_UE *ue, int nr_get_csi_rs_signal(const PHY_VARS_NR_UE *ue,
UE_nr_rxtx_proc_t *proc, const UE_nr_rxtx_proc_t *proc,
fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu, const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu,
nr_csi_rs_info_t *nr_csi_rs_info, const nr_csi_info_t *nr_csi_info,
int32_t **csi_rs_received_signal) { 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; 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++) { 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++) { 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; continue;
} }
for (int cdm_id = 0; cdm_id < nr_csi_rs_info->N_cdm_groups; cdm_id++) { for (int cdm_id = 0; cdm_id < N_cdm_groups; cdm_id++) {
for (int s = 0; s < nr_csi_rs_info->CDM_group_size; s++) { for (int s = 0; s < CDM_group_size; s++) {
// loop over frequency resource elements within a group // 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 // loop over time resource elements within a group
for (int lp = 0; lp <= nr_csi_rs_info->lprime; lp++) { for (int lp = 0; lp <= l_prime; lp++) {
uint16_t symb = lp + nr_csi_rs_info->loverline[cdm_id]; uint16_t symb = lp + l_overline[cdm_id];
uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size; uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size;
int16_t *rx_signal = (int16_t*)&rxdataF[ant_rx][symbol_offset]; c16_t *rx_signal = (c16_t*)&rxdataF[ant_rx][symbol_offset];
int16_t *rx_csi_rs_signal = (int16_t*)&csi_rs_received_signal[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<<1] = rx_signal[k<<1]; rx_csi_rs_signal[k].r = rx_signal[k].r;
rx_csi_rs_signal[(k<<1)+1] = rx_signal[(k<<1)+1]; 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 #ifdef NR_CSIRS_DEBUG
int dataF_offset = proc->nr_slot_rx*ue->frame_parms.samples_per_slot_wCP; 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; uint16_t port_tx = s+j_cdm[cdm_id]*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]; 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", LOG_I(NR_PHY, "l,k (%2d,%4d) |\tport_tx %d (%4d,%4d)\tant_rx %d (%4d,%4d)\n",
symb, symb,
k, k,
port_tx+3000, port_tx+3000,
tx_csi_rs_signal[k<<1], tx_csi_rs_signal[k].r,
tx_csi_rs_signal[(k<<1)+1], tx_csi_rs_signal[k].i,
ant_rx, ant_rx,
rx_csi_rs_signal[k<<1], rx_csi_rs_signal[k].r,
rx_csi_rs_signal[(k<<1)+1]); rx_csi_rs_signal[k].i);
#endif #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; 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_x = 0;
uint64_t sum_x2 = 0; uint64_t sum_x2 = 0;
uint16_t size = 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); return sum_x2/size - (sum_x/size)*(sum_x/size);
} }
int nr_csi_rs_channel_estimation(PHY_VARS_NR_UE *ue, int nr_csi_rs_channel_estimation(const PHY_VARS_NR_UE *ue,
UE_nr_rxtx_proc_t *proc, const UE_nr_rxtx_proc_t *proc,
fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu, const fapi_nr_dl_config_csirs_pdu_rel15_t *csirs_config_pdu,
nr_csi_rs_info_t *nr_csi_rs_info, const nr_csi_info_t *nr_csi_info,
int32_t **csi_rs_generated_signal, const int32_t **csi_rs_generated_signal,
int32_t **csi_rs_received_signal, const int32_t csi_rs_received_signal[][ue->frame_parms.samples_per_slot_wCP],
int32_t ***csi_rs_estimated_channel_freq, 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) { uint32_t *noise_power) {
NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms; const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
int dataF_offset = proc->nr_slot_rx*ue->frame_parms.samples_per_slot_wCP; const int dataF_offset = proc->nr_slot_rx*ue->frame_parms.samples_per_slot_wCP;
*noise_power = 0; *noise_power = 0;
int maxh = 0;
int count = 0;
for (int ant_rx = 0; ant_rx < frame_parms->nb_antennas_rx; ant_rx++) { for (int ant_rx = 0; ant_rx < frame_parms->nb_antennas_rx; ant_rx++) {
/// LS channel estimation /// LS channel estimation
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(nr_csi_rs_info->csi_rs_ls_estimated_channel[ant_rx][port_tx], 0, frame_parms->ofdm_symbol_size*sizeof(int32_t)); 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++) { 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; continue;
} }
for (int cdm_id = 0; cdm_id < nr_csi_rs_info->N_cdm_groups; cdm_id++) { for (int cdm_id = 0; cdm_id < N_cdm_groups; cdm_id++) {
for (int s = 0; s < nr_csi_rs_info->CDM_group_size; s++) { 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 // 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 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 // loop over time resource elements within a group
for (int lp = 0; lp <= nr_csi_rs_info->lprime; lp++) { for (int lp = 0; lp <= l_prime; lp++) {
uint16_t symb = lp + nr_csi_rs_info->loverline[cdm_id]; uint16_t symb = lp + l_overline[cdm_id];
uint64_t symbol_offset = symb*frame_parms->ofdm_symbol_size; 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]; c16_t *tx_csi_rs_signal = (c16_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]; c16_t *rx_csi_rs_signal = (c16_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 *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_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<<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_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 // 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. // 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_channel16[kinit].r += 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].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++) { for(int k = 0; k<frame_parms->ofdm_symbol_size; k++) {
LOG_I(NR_PHY, "l,k (%2d,%4d) | ", symb, 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; 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]; c16_t *tx_csi_rs_signal = (c16_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]; c16_t *rx_csi_rs_signal = (c16_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 *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) | ", printf("port_tx %d --> ant_rx %d, tx (%4d,%4d), rx (%4d,%4d), ls (%4d,%4d) | ",
port_tx+3000, ant_rx, port_tx+3000, ant_rx,
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,
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,
csi_rs_ls_estimated_channel[k<<1], csi_rs_ls_estimated_channel[(k<<1)+1]); csi_rs_ls_estimated_channel16[k].r, csi_rs_ls_estimated_channel16[k].i);
} }
printf("\n"); printf("\n");
} }
@@ -250,7 +374,7 @@ int nr_csi_rs_channel_estimation(PHY_VARS_NR_UE *ue,
/// Channel interpolation /// 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)); 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; continue;
} }
count++;
uint16_t k = (frame_parms->first_carrier_offset + rb*NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size; 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++) { for(uint16_t port_tx = 0; port_tx<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_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]; 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 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) || } 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 (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 } 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 /// 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_real[frame_parms->nb_antennas_rx][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_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++) { 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)) { if (csirs_config_pdu->freq_density <= 1 && csirs_config_pdu->freq_density != (rb % 2)) {
continue; continue;
} }
uint16_t k = (frame_parms->first_carrier_offset + rb*NR_NB_SC_PER_RB) % frame_parms->ofdm_symbol_size; 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++) { for(uint16_t port_tx = 0; port_tx<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]; c16_t *csi_rs_ls_estimated_channel16 = (c16_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]; 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_channel[0]-csi_rs_estimated_channel16[0]); 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_channel[1]-csi_rs_estimated_channel16[1]); 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)); *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->first_carrier_offset)/NR_NB_SC_PER_RB :
(k + frame_parms->ofdm_symbol_size - 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); LOG_I(NR_PHY, "(k = %4d) |\t", 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++) {
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 *csi_rs_ls_estimated_channel16 = (c16_t*)&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]; 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) | ", printf("Channel port_tx %d --> ant_rx %d : ls (%4d,%4d), int (%4d,%4d), noise (%4d,%4d) | ",
port_tx+3000, ant_rx, port_tx+3000, ant_rx,
csi_rs_ls_estimated_channel[k<<1], csi_rs_ls_estimated_channel[(k<<1)+1], csi_rs_ls_estimated_channel16[k].r, csi_rs_ls_estimated_channel16[k].i,
csi_rs_estimated_channel16[k<<1], csi_rs_estimated_channel16[(k<<1)+1], 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_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]); 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 #ifdef NR_CSIRS_DEBUG
LOG_I(NR_PHY, "Noise power estimation based on CSI-RS: %i\n", *noise_power); 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; 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) { 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; 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; 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 #ifdef NR_CSIRS_DEBUG
LOG_I(NR_PHY, "csirs_config_pdu->subcarrier_spacing = %i\n", csirs_config_pdu->subcarrier_spacing); 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); LOG_I(NR_PHY, "csirs_config_pdu->power_control_offset_ss = %i\n", csirs_config_pdu->power_control_offset_ss);
#endif #endif
nr_generate_csi_rs(ue->frame_parms, const NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms;
ue->nr_csi_rs_info->csi_rs_generated_signal, 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, AMP,
ue->nr_csi_rs_info, ue->nr_csi_info,
(nfapi_nr_dl_tti_csi_rs_pdu_rel15_t *) csirs_config_pdu, (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, nr_get_csi_rs_signal(ue,
proc, proc,
csirs_config_pdu, csirs_config_pdu,
ue->nr_csi_rs_info, ue->nr_csi_info,
ue->nr_csi_rs_info->csi_rs_received_signal); 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, nr_csi_rs_channel_estimation(ue,
proc, proc,
csirs_config_pdu, csirs_config_pdu,
ue->nr_csi_rs_info, ue->nr_csi_info,
ue->nr_csi_rs_info->csi_rs_generated_signal, (const int32_t **) ue->nr_csi_info->csi_rs_generated_signal,
ue->nr_csi_rs_info->csi_rs_received_signal, csi_rs_received_signal,
ue->nr_csi_rs_info->csi_rs_estimated_channel_freq, N_cdm_groups,
ue->nr_csi_rs_info->noise_power); 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; 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->Mdlharq = Mdlharq;
dlsch->number_harq_processes_for_pdsch = Mdlharq; dlsch->number_harq_processes_for_pdsch = Mdlharq;
dlsch->Nsoft = Nsoft; dlsch->Nsoft = Nsoft;
dlsch->Mlimit = 4;
dlsch->max_ldpc_iterations = max_ldpc_iterations; dlsch->max_ldpc_iterations = max_ldpc_iterations;
for (int i=0; i<Mdlharq; i++) { 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", //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); // 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->status = SCH_IDLE;
harq_process->DLround = 0;
harq_process->ack = 1; 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", //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", //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); // 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; 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) { //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", // 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; nb_rb = harq_process->nb_rb;
harq_process->trials[harq_process->DLround]++;
A = harq_process->TBS; A = harq_process->TBS;
ret = dlsch->max_ldpc_iterations + 1; ret = dlsch->max_ldpc_iterations + 1;
dlsch->last_iteration_cnt = ret; dlsch->last_iteration_cnt = ret;
@@ -466,88 +466,87 @@ int nr_rx_pdsch(PHY_VARS_NR_UE *ue,
if (cpumeas(CPUMEAS_GETSTATE)) 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)); 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 */ /* 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) { if(dlsch0_harq->status == ACTIVE) {
startSymbIdx = dlsch0_harq->start_symbol; startSymbIdx = dlsch0_harq->start_symbol;
nbSymb = dlsch0_harq->nb_symbols; nbSymb = dlsch0_harq->nb_symbols;
pduBitmap = dlsch0_harq->pduBitmap; pduBitmap = dlsch0_harq->pduBitmap;
} }
if(dlsch1_harq) { if(dlsch1_harq) {
startSymbIdx = dlsch1_harq->start_symbol; startSymbIdx = dlsch1_harq->start_symbol;
nbSymb = dlsch1_harq->nb_symbols; nbSymb = dlsch1_harq->nb_symbols;
pduBitmap = dlsch1_harq->pduBitmap; pduBitmap = dlsch1_harq->pduBitmap;
} }
/* Check for PTRS bitmap and process it respectively */ /* Check for PTRS bitmap and process it respectively */
if((pduBitmap & 0x1) && (type == PDSCH)) { if((pduBitmap & 0x1) && (type == PDSCH)) {
nr_pdsch_ptrs_processing(ue, nr_pdsch_ptrs_processing(ue,
pdsch_vars, pdsch_vars,
frame_parms, frame_parms,
dlsch0_harq, dlsch0_harq,
dlsch1_harq, dlsch1_harq,
gNB_id, gNB_id,
nr_slot_rx, nr_slot_rx,
symbol, symbol,
(nb_rb_pdsch*12), (nb_rb_pdsch*12),
dlsch[0]->rnti,rx_type); dlsch[0]->rnti,rx_type);
pdsch_vars[gNB_id]->dl_valid_re[symbol-1] -= pdsch_vars[gNB_id]->ptrs_re_per_slot[0][symbol]; 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 */ /* at last symbol in a slot calculate LLR's for whole slot */
if(symbol == (startSymbIdx + nbSymb -1)) { if(symbol == (startSymbIdx + nbSymb -1)) {
for(uint8_t i =startSymbIdx; i < (startSymbIdx+nbSymb);i++) { for(uint8_t i =startSymbIdx; i < (startSymbIdx+nbSymb);i++) {
/* re evaluating the first symbol flag as LLR's are done in symbol loop */ /* re evaluating the first symbol flag as LLR's are done in symbol loop */
if(i == startSymbIdx && i < 3) { if(i == startSymbIdx && i < 3) {
first_symbol_flag =1; 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);
} }
else {
int dmrs_type = dlsch[0]->harq_processes[harq_pid]->dmrsConfigType; first_symbol_flag=0;
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, /* Calculate LLR's for each symbol */
dlsch[0]->harq_processes[harq_pid]->nb_symbols, nr_dlsch_llr(pdsch_vars, frame_parms,
nb_re_dmrs, rxdataF_comp_ptr, dl_ch_mag_ptr,
dmrs_len, dlsch0_harq, dlsch1_harq,
dlsch[0]->harq_processes[harq_pid]->Qm, rx_type, harq_pid,
dlsch[0]->harq_processes[harq_pid]->Nl); gNB_id, gNB_id_i,
nr_dlsch_layer_demapping(pdsch_vars[gNB_id]->llr, first_symbol_flag,
dlsch[0]->harq_processes[harq_pid]->Nl, i, nb_rb_pdsch,
dlsch[0]->harq_processes[harq_pid]->Qm, codeword_TB0, codeword_TB1,
dlsch[0]->harq_processes[harq_pid]->G, pdsch_vars[gNB_id]->dl_valid_re[i-1],
codeword_TB0, nr_slot_rx, beamforming_mode);
codeword_TB1,
pdsch_vars[gNB_id]->layer_llr);
} }
stop_meas(&ue->generic_stat_bis[proc->thread_id][slot]); int dmrs_type = dlsch[0]->harq_processes[harq_pid]->dmrsConfigType;
if (cpumeas(CPUMEAS_GETSTATE)) uint8_t nb_re_dmrs;
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)); 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 #ifdef DEBUG_PDSCH_RX
char filename[50]; char filename[50];
uint8_t aa = 0; 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_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 // initialize the pusch dmrs
for (int i=0; i<NR_NB_NSCID; i++) { 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, int32_t *after_mf_11,
unsigned short nb_rb); 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, void dlsch_channel_level_TM34_meas(int *ch00,
int *ch01, int *ch01,
int *ch10, int *ch10,
@@ -885,19 +881,15 @@ void nr_dlsch_detection_mrc(int **rxdataF_comp,
unsigned short nb_rb, unsigned short nb_rb,
int length); int length);
void det_HhH(int32_t *after_mf_00, void nr_conjch0_mult_ch1(int *ch0,
int32_t *after_mf_01, int *ch1,
int32_t *after_mf_10, int32_t *ch0conj_ch1,
int32_t *after_mf_11, unsigned short nb_rb,
int32_t *det_fin_128, unsigned char output_shift0);
unsigned short nb_rb);
void numer(int32_t *Hh_h_00_sq, void nr_a_sum_b(__m128i *input_x,
int32_t *Hh_h_01_sq, __m128i *input_y,
int32_t *Hh_h_10_sq, unsigned short nb_rb);
int32_t *Hh_h_11_sq,
int32_t *num_fin,
unsigned short nb_rb);
uint8_t rank_estimation_tm3_tm4(int *dl_ch_estimates_00, uint8_t rank_estimation_tm3_tm4(int *dl_ch_estimates_00,
int *dl_ch_estimates_01, int *dl_ch_estimates_01,
@@ -161,15 +161,13 @@ typedef struct {
//uint8_t num_cba_dci[10]; //uint8_t num_cba_dci[10];
/// allocated CBA RNTI /// allocated CBA RNTI
//uint16_t cba_rnti[4];//NUM_MAX_CBA_GROUP]; //uint16_t cba_rnti[4];//NUM_MAX_CBA_GROUP];
/// UL max-harq-retransmission
uint16_t Mlimit;
} NR_UE_ULSCH_t; } NR_UE_ULSCH_t;
typedef struct { typedef struct {
/// Indicator of first reception /// Indicator of first reception
uint8_t first_rx; uint8_t first_rx;
/// Last Ndi received for this process on DCI (used for C-RNTI only) /// Last Ndi received for this process on DCI (used for C-RNTI only)
uint8_t DCINdi; uint8_t Ndi;
/// DLSCH status flag indicating /// DLSCH status flag indicating
SCH_status_t status; SCH_status_t status;
/// Transport block size /// Transport block size
@@ -241,10 +239,6 @@ typedef struct {
vrb_t vrb_type; vrb_t vrb_type;
/// downlink power offset field /// downlink power offset field
uint8_t dl_power_off; 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 /// codeword this transport block is mapped to
uint8_t codeword; uint8_t codeword;
/// HARQ-ACKs /// HARQ-ACKs
@@ -312,8 +306,6 @@ typedef struct {
uint8_t max_ldpc_iterations; uint8_t max_ldpc_iterations;
/// number of iterations used in last turbo decoding /// number of iterations used in last turbo decoding
uint8_t last_iteration_cnt; uint8_t last_iteration_cnt;
/// Maximum number of HARQ rounds
uint8_t Mlimit;
} NR_UE_DLSCH_t; } NR_UE_DLSCH_t;
typedef enum {format0_0, 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)); memset(ulsch, 0, sizeof(*ulsch));
ulsch->number_harq_processes_for_pusch = NR_MAX_ULSCH_HARQ_PROCESSES; 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++) { for (int i = 0; i < number_of_harq_pids; i++) {
+2 -8
View File
@@ -188,8 +188,6 @@ typedef struct {
uint8_t codebook_index; uint8_t codebook_index;
/// Maximum number of HARQ processes /// Maximum number of HARQ processes
uint8_t Mdlharq; uint8_t Mdlharq;
/// Maximum number of HARQ rounds
uint8_t Mlimit;
/// MIMO transmission mode indicator for this sub-frame /// MIMO transmission mode indicator for this sub-frame
uint8_t Kmimo; uint8_t Kmimo;
/// Nsoft parameter related to UE Category /// Nsoft parameter related to UE Category
@@ -345,8 +343,6 @@ typedef struct {
typedef struct { typedef struct {
/// Pointers to 16 HARQ processes for the ULSCH /// Pointers to 16 HARQ processes for the ULSCH
NR_UL_gNB_HARQ_t *harq_processes[NR_MAX_ULSCH_HARQ_PROCESSES]; 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 /// HARQ process mask, indicates which processes are currently active
uint16_t harq_mask; uint16_t harq_mask;
/// ACK/NAK Bundling flag /// ACK/NAK Bundling flag
@@ -373,8 +369,6 @@ typedef struct {
uint8_t cyclicShift; uint8_t cyclicShift;
/// for cooperative communication /// for cooperative communication
uint8_t cooperation_flag; uint8_t cooperation_flag;
/// Maximum number of HARQ rounds
uint8_t Mlimit;
/// Maximum number of LDPC iterations /// Maximum number of LDPC iterations
uint8_t max_ldpc_iterations; uint8_t max_ldpc_iterations;
/// number of iterations used in last LDPC decoding /// number of iterations used in last LDPC decoding
@@ -765,8 +759,8 @@ typedef struct PHY_VARS_gNB_s {
/// SRS variables /// SRS variables
nr_srs_info_t *nr_srs_info[NUMBER_OF_NR_SRS_MAX]; nr_srs_info_t *nr_srs_info[NUMBER_OF_NR_SRS_MAX];
/// CSI-RS variables /// CSI variables
nr_csi_rs_info_t *nr_csi_rs_info; nr_csi_info_t *nr_csi_info;
uint8_t pbch_configured; uint8_t pbch_configured;
char gNB_generate_rar; char gNB_generate_rar;
+4 -4
View File
@@ -878,8 +878,8 @@ typedef struct {
/// SRS variables /// SRS variables
nr_srs_info_t *nr_srs_info; nr_srs_info_t *nr_srs_info;
/// CSI-RS variables /// CSI variables
nr_csi_rs_info_t *nr_csi_rs_info; nr_csi_info_t *nr_csi_info;
//#if defined(UPGRADE_RAT_NR) //#if defined(UPGRADE_RAT_NR)
#if 1 #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_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]; SLIST_HEAD(ral_thresholds_lte_poll_s, ral_threshold_phy_t) ral_thresholds_lte_polled[RAL_LINK_PARAM_LTE_MAX];
#endif #endif
int dl_errors;
int dl_stats[5]; int dl_stats[8];
void* scopeData; void* scopeData;
} PHY_VARS_NR_UE; } PHY_VARS_NR_UE;
+4 -13
View File
@@ -43,6 +43,7 @@
#define nr_slot_t lte_subframe_t #define nr_slot_t lte_subframe_t
#define MAX_NUM_SUBCARRIER_SPACING 5 #define MAX_NUM_SUBCARRIER_SPACING 5
#define NR_MAX_OFDM_SYMBOL_SIZE 4096
#define NR_NB_SC_PER_RB 12 #define NR_NB_SC_PER_RB 12
#define NR_NB_REG_PER_CCE 6 #define NR_NB_REG_PER_CCE 6
@@ -247,23 +248,13 @@ typedef struct {
} nr_srs_info_t; } nr_srs_info_t;
typedef struct { 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; uint16_t csi_gold_init;
uint32_t ***nr_gold_csi_rs; uint32_t ***nr_gold_csi_rs;
uint8_t csi_rs_generated_signal_bits; uint8_t csi_rs_generated_signal_bits;
int32_t **csi_rs_generated_signal; int32_t **csi_rs_generated_signal;
int32_t **csi_rs_received_signal; bool csi_im_meas_computed;
int32_t ***csi_rs_ls_estimated_channel; uint32_t interference_plus_noise_power;
int32_t ***csi_rs_estimated_channel_freq; } nr_csi_info_t;
uint32_t *noise_power;
} nr_csi_rs_info_t;
typedef struct NR_DL_FRAME_PARMS NR_DL_FRAME_PARMS; typedef struct NR_DL_FRAME_PARMS NR_DL_FRAME_PARMS;
+9 -5
View File
@@ -71,9 +71,9 @@
#include "common/utils/system.h" #include "common/utils/system.h"
#include <time.h> #include <time.h>
#include "openair1/SCHED/sched_common_extern.h"
extern int oai_exit; #include "targets/RT/USER/lte-softmodem.h"
#include "common/ran_context.h"
void feptx0(RU_t *ru, void feptx0(RU_t *ru,
int slot) 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; RU_proc_t *proc = &ru->proc;
if (proc->pthread_fep == 0)
return;
pthread_mutex_lock( &proc->mutex_fep ); pthread_mutex_lock( &proc->mutex_fep );
proc->instance_cnt_fep = 0; proc->instance_cnt_fep = 0;
pthread_cond_signal(&proc->cond_fep); 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; RU_proc_t *proc = &ru->proc;
if (proc->pthread_feptx == 0)
return;
pthread_mutex_lock( &proc->mutex_feptx ); pthread_mutex_lock( &proc->mutex_feptx );
proc->instance_cnt_feptx = 0; proc->instance_cnt_feptx = 0;
pthread_cond_signal(&proc->cond_feptx); pthread_cond_signal(&proc->cond_feptx);
+2
View File
@@ -29,4 +29,6 @@
extern int16_t hundred_times_delta_TF[100]; extern int16_t hundred_times_delta_TF[100];
extern uint16_t hundred_times_log10_NPRB[100]; extern uint16_t hundred_times_log10_NPRB[100];
void kill_fep_thread(RU_t *ru);
#endif /*__SCHED_EXTERN_H__ */ #endif /*__SCHED_EXTERN_H__ */
+5 -21
View File
@@ -172,7 +172,7 @@ void phy_procedures_gNB_TX(processingData_L1tx_t *msgTx,
if (csirs->active == 1) { if (csirs->active == 1) {
LOG_D(PHY, "CSI-RS generation started in frame %d.%d\n",frame,slot); 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; 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; csirs->active = 0;
} }
} }
@@ -242,13 +242,6 @@ void nr_postDecode(PHY_VARS_gNB *gNB, notifiedFIFO_elt_t *req) {
ulsch_harq->ulsch_pdu.rb_size, ulsch_harq->ulsch_pdu.rb_size,
ulsch_harq->TBS, ulsch_harq->TBS,
r); 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; ulsch_harq->handled = 1;
LOG_D(PHY, "ULSCH %d in error\n",rdata->ulsch_id); LOG_D(PHY, "ULSCH %d in error\n",rdata->ulsch_id);
@@ -413,17 +406,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 (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); 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) - 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); dB_fixed_x10(gNB->pusch_vars[ULSCH_id]->ulsch_noise_power_tot);
@@ -573,7 +557,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); 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++) { 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; 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);
} }
} }
} }
@@ -858,8 +842,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; 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_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][frame_parms->ofdm_symbol_size*N_symb_SRS]; int32_t srs_ls_estimated_channel[frame_parms->nb_antennas_rx][frame_parms->ofdm_symbol_size*N_symb_SRS];
int32_t srs_estimated_channel_freq[frame_parms->nb_antennas_rx][frame_parms->ofdm_symbol_size*N_symb_SRS]; int32_t srs_estimated_channel_freq[frame_parms->nb_antennas_rx][frame_parms->ofdm_symbol_size*N_symb_SRS] __attribute__ ((aligned(32)));
int32_t srs_estimated_channel_time[frame_parms->nb_antennas_rx][frame_parms->ofdm_symbol_size]; int32_t srs_estimated_channel_time[frame_parms->nb_antennas_rx][frame_parms->ofdm_symbol_size] __attribute__ ((aligned(32)));
int32_t srs_estimated_channel_time_shifted[frame_parms->nb_antennas_rx][frame_parms->ofdm_symbol_size]; int32_t srs_estimated_channel_time_shifted[frame_parms->nb_antennas_rx][frame_parms->ofdm_symbol_size];
uint32_t noise_power_per_rb[srs_pdu->bwp_size]; uint32_t noise_power_per_rb[srs_pdu->bwp_size];
int8_t snr_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, NR_UE_DLSCH_t *dlsch1,
uint16_t n_pdus, uint16_t n_pdus,
UE_nr_rxtx_proc_t *proc, UE_nr_rxtx_proc_t *proc,
void * typeSpecific); void *typeSpecific);
bool nr_ue_dlsch_procedures(PHY_VARS_NR_UE *ue, bool nr_ue_dlsch_procedures(PHY_VARS_NR_UE *ue,
UE_nr_rxtx_proc_t *proc, 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: case FAPI_NR_DL_CONFIG_TYPE_CSI_IM:
csiim_config_pdu = &dl_config->dl_config_list[i].csiim_config_pdu.csiim_config_rel15; 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)); 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; break;
case FAPI_NR_DL_CONFIG_TYPE_CSI_RS: case FAPI_NR_DL_CONFIG_TYPE_CSI_RS:
csirs_config_pdu = &dl_config->dl_config_list[i].csirs_config_pdu.csirs_config_rel15; 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->status = SCH_IDLE;
dl_harq->first_rx = 1; dl_harq->first_rx = 1;
dl_harq->DLround = 0; dl_harq->DLround = 0;
dl_harq->DCINdi = 1; dl_harq->Ndi = 1;
dl_harq->ack = DL_ACKNACK_NO_SET; 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_ || if (rnti_type == _SI_RNTI_ ||
rnti_type == _P_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; dl_harq->first_rx = 1;
} else { } else {
LOG_D(PHY,"receive harq process: %p harqPid=%d, rv=%d, ndi=%d, rntiType=%d new transmission= %s\n", 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); AssertFatal(rv<4 && rv>=0, "invalid redondancy version %d\n", rv);
if (dci_ndi!=dl_harq->Ndi) {
if (ndi!=dl_harq->DCINdi) {
if (dl_harq->ack == DL_NACK) if (dl_harq->ack == DL_NACK)
LOG_D(PHY,"New transmission on a harq pid (%d) never acknowledged\n", harq_pid); LOG_D(PHY,"New transmission on a harq pid (%d) never acknowledged\n", harq_pid);
else 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); 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->first_rx = true;
dl_harq->DLround = 0; dl_harq->DLround = 0;
} else { } 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->status = ACTIVE;
dl_harq->DCINdi = ndi; dl_harq->Ndi = dci_ndi;
//dl_harq->status = SCH_IDLE; //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 *dlsch0,
NR_UE_DLSCH_t *dlsch1, NR_UE_DLSCH_t *dlsch1,
uint16_t n_pdus, uint16_t n_pdus,
UE_nr_rxtx_proc_t *proc, UE_nr_rxtx_proc_t *proc,
void * typeSpecific){ void *typeSpecific){
NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms; 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.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]; rx_ind->rx_indication_body[n_pdus - 1].ssb_pdu.rsrp_dBm = ue->measurements.rsrp_dBm[gNB_id];
break; 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: default:
break; 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 half_frame_index = fp->half_frame_bit;
//uint8_t i_ssb = fp->ssb_index; //uint8_t i_ssb = fp->ssb_index;
uint8_t Lmax = fp->Lmax; uint8_t Lmax = fp->Lmax;
if ((config->ssb_table.ssb_period > 0) && !(frame % (1 << (config->ssb_table.ssb_period - 1)))) {
if (!(frame%(1<<(config->ssb_table.ssb_period-1)))){
if(Lmax <= 8) { 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)) 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)) { if ((frame_rx%64 == 0) && (nr_slot_rx==0)) {
LOG_I(NR_PHY,"============================================\n"); 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"); LOG_I(NR_PHY,"============================================\n");
} }
@@ -1692,6 +1705,19 @@ int phy_procedures_nrUE_RX(PHY_VARS_NR_UE *ue,
// do procedures for CSI-IM // do procedures for CSI-IM
if ((ue->csiim_vars[gNB_id]) && (ue->csiim_vars[gNB_id]->active == 1)) { 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); nr_ue_csi_im_procedures(ue, proc, gNB_id);
ue->csiim_vars[gNB_id]->active = 0; ue->csiim_vars[gNB_id]->active = 0;
} }
+10 -6
View File
@@ -512,12 +512,16 @@ int main(int argc, char **argv) {
int re; int re;
int s,Kr,Kr_bytes; int s,Kr,Kr_bytes;
LTE_DL_FRAME_PARMS *frame_parms; LTE_DL_FRAME_PARMS *frame_parms;
double s_re0[30720*2],s_im0[30720*2],r_re0[30720*2],r_im0[30720*2]; double *tmpTX[4], *tmpRX[4] ;
double s_re1[30720*2],s_im1[30720*2],r_re1[30720*2],r_im1[30720*2]; for (int i = 0; i < 4; i++) {
double *s_re[2]= {s_re0,s_re1}; tmpTX[i] = malloc(30720 * NB_ANTENNAS_TX * sizeof(*tmpTX));
double *s_im[2]= {s_im0,s_im1}; tmpRX[i] = malloc(30720 * NB_ANTENNAS_RX * sizeof(*tmpRX));
double *r_re[2]= {r_re0,r_re1}; }
double *r_im[2]= {r_im0,r_im1}; 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; uint8_t transmission_mode=1,n_tx_port=1,n_tx_phy=1,n_rx=2;
int eNB_id = 0; int eNB_id = 0;
unsigned char round; unsigned char round;
+7 -7
View File
@@ -358,7 +358,7 @@ int main(int argc, char **argv) {
unsigned short input_buffer_length; unsigned short input_buffer_length;
unsigned int ret; unsigned int ret;
unsigned int coded_bits_per_codeword,nsymb; 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; FILE *bler_fd=NULL;
char bler_fname[512]; char bler_fname[512];
FILE *time_meas_fd=NULL; FILE *time_meas_fd=NULL;
@@ -387,7 +387,6 @@ int main(int argc, char **argv) {
double cpu_freq_GHz; double cpu_freq_GHz;
int iter_trials; int iter_trials;
uint32_t UL_alloc_pdu; uint32_t UL_alloc_pdu;
int s,Kr,Kr_bytes;
int dump_perf=0; int dump_perf=0;
static int dump_table =0; static int dump_table =0;
double effective_rate=0.0; double effective_rate=0.0;
@@ -1233,20 +1232,21 @@ int main(int argc, char **argv) {
if (n_frames==1) { if (n_frames==1) {
printf("ULSCH errors found o_ACK[0]= %d\n",eNB->ulsch[0]->harq_processes[harq_pid]->o_ACK[0]); 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++) { for (s=0; s<eNB->ulsch[0]->harq_processes[harq_pid]->C; s++) {
if (s<eNB->ulsch[0]->harq_processes[harq_pid]->Cminus) 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 else
Kr = eNB->ulsch[0]->harq_processes[harq_pid]->Kplus; Kr_bytes = eNB->ulsch[0]->harq_processes[harq_pid]->Kplus;
Kr_bytes = Kr_bytes >> 3;
Kr_bytes = Kr>>3;
printf("Decoded_output (Segment %d):\n",s); printf("Decoded_output (Segment %d):\n",s);
for (i=0; i<Kr_bytes; i++) for (i=0; i<Kr_bytes; i++)
printf("%d : %x (%x)\n",i,eNB->ulsch[0]->harq_processes[harq_pid]->c[s][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]); 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); dump_ulsch(eNB,eNB->proc.frame_rx,subframe,0,round);
round=5; round=5;
+11 -11
View File
@@ -114,16 +114,16 @@ int main(int argc, char **argv)
//int run_initial_sync=0; //int run_initial_sync=0;
int loglvl = OAILOG_WARNING; int loglvl = OAILOG_WARNING;
uint8_t dlsch_threads = 0; uint8_t dlsch_threads = 0;
float target_error_rate = 0.01; float target_error_rate = 0.01;
uint64_t SSB_positions=0x01; uint64_t SSB_positions=0x01;
uint16_t nb_symb_sch = 12; uint16_t nb_symb_sch = 12;
uint16_t nb_rb = 50; uint16_t nb_rb = 50;
uint8_t Imcs = 9; uint8_t Imcs = 9;
uint8_t mcs_table = 0; uint8_t mcs_table = 0;
double DS_TDL = .03; double DS_TDL = .03;
cpuf = get_cpu_freq_GHz(); cpuf = get_cpu_freq_GHz();
char gNBthreads[128]="n"; char gNBthreads[128]="n";
int Tbslbrm = 950984; int Tbslbrm = 950984;
if (load_configmodule(argc, argv, CONFIG_ENABLECMDLINEONLY) == 0) { if (load_configmodule(argc, argv, CONFIG_ENABLECMDLINEONLY) == 0) {
exit_fun("[NR_DLSCHSIM] Error, configuration module init failed\n"); exit_fun("[NR_DLSCHSIM] Error, configuration module init failed\n");
@@ -299,7 +299,7 @@ int main(int argc, char **argv)
break; break;
case 'X': case 'X':
strncpy(gNBthreads, optarg, sizeof(gNBthreads)); strncpy(gNBthreads, optarg, sizeof(gNBthreads)-1);
gNBthreads[sizeof(gNBthreads)-1]=0; gNBthreads[sizeof(gNBthreads)-1]=0;
break; break;
+15 -5
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 //Fixme: Uniq dirty DU instance, by global var, datamodel need better management
instance_t DUuniqInstance=0; instance_t DUuniqInstance=0;
instance_t CUuniqInstance=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, teid_t newGtpuCreateTunnel(instance_t instance,
transport_layer_addr_t remoteAddr, int port, gtpCallback callBack) { rnti_t rnti,
return 0; 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) { int newGtpuDeleteAllTunnels(instance_t instance, rnti_t rnti) {
@@ -670,7 +678,7 @@ int main(int argc, char **argv)
break; break;
case 'X': case 'X':
strncpy(gNBthreads, optarg, sizeof(gNBthreads)); strncpy(gNBthreads, optarg, sizeof(gNBthreads)-1);
gNBthreads[sizeof(gNBthreads)-1]=0; gNBthreads[sizeof(gNBthreads)-1]=0;
break; break;
@@ -761,6 +769,8 @@ int main(int argc, char **argv)
gNB_RRC_INST rrc; gNB_RRC_INST rrc;
memset((void*)&rrc,0,sizeof(rrc)); memset((void*)&rrc,0,sizeof(rrc));
gNB_mac->dl_bler.harq_round_max = num_rounds;
/* /*
// read in SCGroupConfig // read in SCGroupConfig
AssertFatal(scg_fd != NULL,"no reconfig.raw file\n"); AssertFatal(scg_fd != NULL,"no reconfig.raw file\n");
@@ -1142,7 +1152,7 @@ int main(int argc, char **argv)
Sched_INFO.frame = frame; Sched_INFO.frame = frame;
Sched_INFO.slot = slot; Sched_INFO.slot = slot;
Sched_INFO.DL_req = &gNB_mac->DL_req[0]; 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.UL_dci_req = NULL;
Sched_INFO.TX_req = &gNB_mac->TX_req[0]; Sched_INFO.TX_req = &gNB_mac->TX_req[0];
pushNotifiedFIFO(gNB->L1_tx_free,msgL1Tx); 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, NR_UE_DLSCH_t *dlsch1,
uint16_t n_pdus, uint16_t n_pdus,
UE_nr_rxtx_proc_t *proc, 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 //Fixme: Uniq dirty DU instance, by global var, datamodel need better management
instance_t DUuniqInstance=0; instance_t DUuniqInstance=0;
instance_t CUuniqInstance=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, teid_t newGtpuCreateTunnel(instance_t instance,
transport_layer_addr_t remoteAddr, int port, gtpCallback callBack) { rnti_t rnti,
return 0; 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) { int newGtpuDeleteAllTunnels(instance_t instance, rnti_t rnti) {
+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 //Fixme: Uniq dirty DU instance, by global var, datamodel need better management
instance_t DUuniqInstance=0; instance_t DUuniqInstance=0;
instance_t CUuniqInstance=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, teid_t newGtpuCreateTunnel(instance_t instance,
transport_layer_addr_t remoteAddr, int port, gtpCallback callBack) { rnti_t rnti,
return 0; 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) { 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; int num_tunnels;
//teid_t upf_NGu_teid[NR_GTPV1U_MAX_BEARERS_PER_UE]; ///< Tunnel Endpoint Identifier //teid_t upf_NGu_teid[NR_GTPV1U_MAX_BEARERS_PER_UE]; ///< Tunnel Endpoint Identifier
teid_t outgoing_teid[NR_GTPV1U_MAX_BEARERS_PER_UE]; 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]; pdusessionid_t pdusession_id[NR_GTPV1U_MAX_BEARERS_PER_UE];
ebi_t incoming_rb_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]; //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); 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); memcpy(addr.buffer,&f1ap_ue_context_setup_req->drbs_to_be_setup[i].up_dl_tnl[0].tl_address, sz);
addr.length = sz*8; addr.length = sz*8;
f1ap_ue_context_setup_req->drbs_to_be_setup[i].up_ul_tnl[j].teid= f1ap_ue_context_setup_req->drbs_to_be_setup[i].up_ul_tnl[j].teid = newGtpuCreateTunnel(getCxt(CUtype, instance)->gtpInst,
newGtpuCreateTunnel(getCxt(CUtype, instance)->gtpInst, f1ap_ue_context_setup_req->rnti,
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, 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
0xFFFF, // We will set the right value from DU answer -1, // no qfi
addr, addr,
f1ap_ue_context_setup_req->drbs_to_be_setup[i].up_dl_tnl[0].port, f1ap_ue_context_setup_req->drbs_to_be_setup[i].up_dl_tnl[0].port,
cu_f1u_data_req); cu_f1u_data_req,
NULL);
/* 12.3.1 ULTunnels_ToBeSetup_Item */ /* 12.3.1 ULTunnels_ToBeSetup_Item */
asn1cSequenceAdd(drbs_toBeSetup_item->uLUPTNLInformation_ToBeSetup_List.list, asn1cSequenceAdd(drbs_toBeSetup_item->uLUPTNLInformation_ToBeSetup_List.list,
F1AP_ULUPTNLInformation_ToBeSetup_Item_t, uLUPTNLInformation_ToBeSetup_Item); 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); memcpy(addr.buffer,&f1ap_ue_context_modification_req->drbs_to_be_setup[i].up_dl_tnl[0].tl_address, sz);
addr.length = sz*8; addr.length = sz*8;
f1ap_ue_context_modification_req->drbs_to_be_setup[i].up_ul_tnl[j].teid= f1ap_ue_context_modification_req->drbs_to_be_setup[i].up_ul_tnl[j].teid = newGtpuCreateTunnel(getCxt(CUtype, instance)->gtpInst,
newGtpuCreateTunnel(getCxt(CUtype, instance)->gtpInst, f1ap_ue_context_modification_req->rnti,
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, 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
0xFFFF, // We will set the right value from DU answer -1, // no qfi
addr, addr,
f1ap_ue_context_modification_req->drbs_to_be_setup[i].up_dl_tnl[0].port, f1ap_ue_context_modification_req->drbs_to_be_setup[i].up_dl_tnl[0].port,
cu_f1u_data_req); cu_f1u_data_req,
NULL);
/* 12.3.1 ULTunnels_ToBeSetup_Item */ /* 12.3.1 ULTunnels_ToBeSetup_Item */
asn1cSequenceAdd(drbs_toBeSetupMod_item->uLUPTNLInformation_ToBeSetup_List.list, asn1cSequenceAdd(drbs_toBeSetupMod_item->uLUPTNLInformation_ToBeSetup_List.list,
F1AP_ULUPTNLInformation_ToBeSetup_Item_t, uLUPTNLInformation_ToBeSetup_Item); 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; 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)); 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; addr.length=sizeof(drb_p->up_ul_tnl[0].tl_address)*8;
drb_p->up_dl_tnl[0].teid=newGtpuCreateTunnel(INSTANCE_DEFAULT, drb_p->up_dl_tnl[0].teid = newGtpuCreateTunnel(INSTANCE_DEFAULT,
f1ap_ue_context_setup_req->rnti, f1ap_ue_context_setup_req->rnti,
drb_p->drb_id, drb_p->drb_id,
drb_p->drb_id, drb_p->drb_id,
drb_p->up_ul_tnl[0].teid, drb_p->up_ul_tnl[0].teid,
addr, -1, // no qfi
drb_p->up_ul_tnl[0].port, addr,
lteDURecvCb); drb_p->up_ul_tnl[0].port,
lteDURecvCb,
NULL);
drb_p->up_dl_tnl_length++; 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; 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)); 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; addr.length=sizeof(drb_p->up_ul_tnl[0].tl_address)*8;
drb_p->up_dl_tnl[0].teid=newGtpuCreateTunnel(INSTANCE_DEFAULT, drb_p->up_dl_tnl[0].teid = newGtpuCreateTunnel(INSTANCE_DEFAULT,
f1ap_ue_context_modification_req->rnti, f1ap_ue_context_modification_req->rnti,
drb_p->drb_id, drb_p->drb_id,
drb_p->drb_id, drb_p->drb_id,
drb_p->up_ul_tnl[0].teid, drb_p->up_ul_tnl[0].teid,
addr, -1, // no qfi
drb_p->up_ul_tnl[0].port, addr,
lteDURecvCb); drb_p->up_ul_tnl[0].port,
lteDURecvCb,
NULL);
drb_p->up_dl_tnl_length++; 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_UPPER "ul_bler_target_upper"
#define CONFIG_STRING_MACRLC_UL_BLER_TARGET_LOWER "ul_bler_target_lower" #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_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_PRB "min_grant_prb"
#define CONFIG_STRING_MACRLC_MIN_GRANT_MCS "min_grant_mcs" #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_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_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_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_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_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}, \ {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_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_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_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_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_CC_IDX 0
#define MACRLC_TRANSPORT_N_PREFERENCE_IDX 1 #define MACRLC_TRANSPORT_N_PREFERENCE_IDX 1
@@ -139,9 +141,46 @@
#define MACRLC_UL_BLER_TARGET_UPPER_IDX 26 #define MACRLC_UL_BLER_TARGET_UPPER_IDX 26
#define MACRLC_UL_BLER_TARGET_LOWER_IDX 27 #define MACRLC_UL_BLER_TARGET_LOWER_IDX 27
#define MACRLC_UL_MAX_MCS_IDX 28 #define MACRLC_UL_MAX_MCS_IDX 28
#define MACRLC_HARQ_ROUND_MAX_IDX 29 #define MACRLC_DL_HARQ_ROUND_MAX_IDX 29
#define MACRLC_MIN_GRANT_PRB_IDX 30 #define MACRLC_UL_HARQ_ROUND_MAX_IDX 30
#define MACRLC_MIN_GRANT_MCS_IDX 31 #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 #endif
+6 -1
View File
@@ -816,6 +816,10 @@ void RCconfig_nr_macrlc() {
} }
paramdef_t MacRLC_Params[] = MACRLCPARAMS_DESC; paramdef_t MacRLC_Params[] = MACRLCPARAMS_DESC;
paramlist_def_t MacRLC_ParamList = {CONFIG_STRING_MACRLC_LIST,NULL,0}; 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); config_getlist( &MacRLC_ParamList,MacRLC_Params,sizeof(MacRLC_Params)/sizeof(paramdef_t), NULL);
if ( MacRLC_ParamList.numelt > 0) { 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->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->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->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; 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->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->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); 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_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]->min_grant_mcs = *(MacRLC_ParamList.paramarray[j][MACRLC_MIN_GRANT_MCS_IDX].u8ptr);
RC.nrmac[j]->num_ulprbbl = num_prbbl; 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_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_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_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_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 #define GNB_GNB_ID_IDX 0
@@ -2366,22 +2366,6 @@ rrc_mac_remove_ue(module_id_t mod_idP,
return 0; 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 // 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) { 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 // Release RNTI of LTE PHY when RA does not succeed
UE_free_list_t *free_list = NULL; put_UE_in_freelist(enb_mod_idP, current_rnti, true);
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);
cancel_ra_proc(enb_mod_idP, CC_idP, frameP, current_rnti); cancel_ra_proc(enb_mod_idP, CC_idP, frameP, current_rnti);
nfapi_hi_dci0_request_t *hi_dci0_req = NULL; nfapi_hi_dci0_request_t *hi_dci0_req = NULL;
+1 -9
View File
@@ -1195,14 +1195,6 @@ typedef struct {
///remove RA flag ///remove RA flag
bool raFlag; bool raFlag;
} UE_free_ctrl_t; } 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 * describes contiguous RBs
@@ -1443,7 +1435,7 @@ typedef struct eNB_MAC_INST_s {
/// processing time of eNB PCH scheduler /// processing time of eNB PCH scheduler
time_stats_t schedule_pch; 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 /// for scheduling selection
SCHEDULER_MODES scheduler_mode; SCHEDULER_MODES scheduler_mode;
/// Default scheduler: Pre-processor implementation. Algorithms for UL/DL /// Default scheduler: Pre-processor implementation. Algorithms for UL/DL
+34
View File
@@ -39,6 +39,7 @@
#include <stdbool.h> #include <stdbool.h>
#include "NR_SubcarrierSpacing.h" #include "NR_SubcarrierSpacing.h"
#include "NR_CSI-ReportConfig.h"
#include "openair1/SCHED_NR_UE/harq_nr.h" #include "openair1/SCHED_NR_UE/harq_nr.h"
#define NR_SHORT_BSR_TABLE_SIZE 32 #define NR_SHORT_BSR_TABLE_SIZE 32
@@ -63,6 +64,7 @@
#define CCCH_PAYLOAD_SIZE_MAX 512 #define CCCH_PAYLOAD_SIZE_MAX 512
#define RAR_PAYLOAD_SIZE_MAX 128 #define RAR_PAYLOAD_SIZE_MAX 128
#define MAX_BWP_SIZE 275 #define MAX_BWP_SIZE 275
#define MAX_CSI_REPORTCONFIG 48
typedef enum frequency_range_e { typedef enum frequency_range_e {
FR1 = 0, FR1 = 0,
@@ -512,5 +514,37 @@ typedef struct Type0_PDCCH_CSS_config_s {
bool active; bool active;
} NR_Type0_PDCCH_CSS_config_t; } 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__ */ #endif /*__LAYER2_MAC_H__ */
@@ -4221,3 +4221,521 @@ bool set_ul_ptrs_values(NR_PTRS_UplinkConfig_t *ul_ptrs_config,
} }
return valid; 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;
}
+33 -1
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 compute_nr_root_seq(NR_RACH_ConfigCommon_t *rach_config,
uint8_t nb_preambles, uint8_t nb_preambles,
uint8_t unpaired, uint8_t unpaired,
frequency_range_t); frequency_range_t);
int ul_ant_bits(NR_DMRS_UplinkConfig_t *NR_DMRS_UplinkConfig,long transformPrecoder); int ul_ant_bits(NR_DMRS_UplinkConfig_t *NR_DMRS_UplinkConfig,long transformPrecoder);
@@ -234,4 +234,36 @@ void nr_mac_gNB_rrc_ul_failure_reset(const module_id_t Mod_instP,
const frame_t frameP, const frame_t frameP,
const sub_frame_t subframeP, const sub_frame_t subframeP,
const rnti_t rntiP); 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 #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; cfg->ssb_table.ssb_subcarrier_offset = mac->ssb_subcarrier_offset;
if (mac->frequency_range == FR1){ 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; cfg->ssb_table.ssb_mask_list[1].ssb_mask = 0;
} }
else{ 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; cfg->ssb_table.ssb_mask_list[1].ssb_mask = 0;
break; break;
case 2 : 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; cfg->ssb_table.ssb_mask_list[1].ssb_mask = 0;
break; break;
case 3 : case 3 :
+5
View File
@@ -399,6 +399,11 @@ typedef struct {
/// measured SSB RSRP in dBm /// measured SSB RSRP in dBm
short ssb_rsrp_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 /// Last NDI of UL HARQ processes
uint8_t UL_ndi[NR_MAX_HARQ_PROCESSES]; uint8_t UL_ndi[NR_MAX_HARQ_PROCESSES];
/// first ULTX of UL 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); 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); 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); 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_ResourceConfigId_t csi_ResourceConfigId,
NR_CSI_MeasConfig_t *csi_MeasConfig); 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, uint8_t nr_get_csi_payload(NR_UE_MAC_INST_t *mac,
PUCCH_sched_t *pucch, PUCCH_sched_t *pucch,
int csi_report_id, 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); 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_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); NR_PDSCH_TimeDomainResourceAllocationList_t *choose_dl_tda_list(NR_PDSCH_Config_t *pdsch_Config,NR_PDSCH_ConfigCommon_t *pdsch_ConfigCommon);
+147 -11
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) { void nr_ue_init_mac(module_id_t module_idP) {
int i; int i;
@@ -985,7 +992,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; 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. // Sanity check for pucch_resource_indicator value received to check for false DCI.
valid = 0; 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 &&
mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pucch_Config && mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pucch_Config &&
mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pucch_Config->choice.setup&& mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pucch_Config->choice.setup&&
@@ -1454,6 +1462,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, void set_harq_status(NR_UE_MAC_INST_t *mac,
uint8_t pucch_id, uint8_t pucch_id,
uint8_t harq_id, uint8_t harq_id,
@@ -1512,13 +1530,12 @@ void nr_ue_configure_pucch(NR_UE_MAC_INST_t *mac,
NR_BWP_UplinkCommon_t *initialUplinkBWP; NR_BWP_UplinkCommon_t *initialUplinkBWP;
if (mac->scc) initialUplinkBWP = mac->scc->uplinkConfigCommon->initialUplinkBWP; if (mac->scc) initialUplinkBWP = mac->scc->uplinkConfigCommon->initialUplinkBWP;
else initialUplinkBWP = &mac->scc_SIB->uplinkConfigCommon->initialUplinkBWP; else initialUplinkBWP = &mac->scc_SIB->uplinkConfigCommon->initialUplinkBWP;
NR_BWP_Uplink_t *ubwp = mac->ULbwp[bwp_id-1]; if (mac->cg && bwp_id > 1 && mac->ULbwp[bwp_id - 1] &&
if (mac->cg && ubwp &&
mac->cg->spCellConfig && mac->cg->spCellConfig &&
mac->cg->spCellConfig->spCellConfigDedicated && mac->cg->spCellConfig->spCellConfigDedicated &&
mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig && mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig &&
mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP) { mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP) {
scs = ubwp->bwp_Common->genericParameters.subcarrierSpacing; scs = mac->ULbwp[bwp_id - 1]->bwp_Common->genericParameters.subcarrierSpacing;
} }
else else
scs = initialUplinkBWP->genericParameters.subcarrierSpacing; scs = initialUplinkBWP->genericParameters.subcarrierSpacing;
@@ -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_BWP_Id_t bwp_id = mac->UL_BWP_Id;
NR_PUCCH_Config_t *pucch_Config = NULL; NR_PUCCH_Config_t *pucch_Config = NULL;
int scs; int scs;
NR_BWP_Uplink_t *ubwp = mac->ULbwp[bwp_id-1];
NR_BWP_UplinkCommon_t *initialUplinkBWP; NR_BWP_UplinkCommon_t *initialUplinkBWP;
if (mac->scc) initialUplinkBWP = mac->scc->uplinkConfigCommon->initialUplinkBWP; if (mac->scc) initialUplinkBWP = mac->scc->uplinkConfigCommon->initialUplinkBWP;
else initialUplinkBWP = &mac->scc_SIB->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 &&
mac->cg->spCellConfig->spCellConfigDedicated && mac->cg->spCellConfig->spCellConfigDedicated &&
mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig && mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig &&
mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP) { mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP) {
scs = ubwp->bwp_Common->genericParameters.subcarrierSpacing; scs = mac->ULbwp[bwp_id - 1]->bwp_Common->genericParameters.subcarrierSpacing;
} }
else else
scs = initialUplinkBWP->genericParameters.subcarrierSpacing; 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: case NR_CSI_ReportConfig__reportQuantity_PR_ssb_Index_RSRP:
n_csi_bits = get_ssb_rsrp_payload(mac,pucch,csi_reportconfig,csi_ResourceConfigId,csi_MeasConfig); n_csi_bits = get_ssb_rsrp_payload(mac,pucch,csi_reportconfig,csi_ResourceConfigId,csi_MeasConfig);
break; break;
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RSRP:
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_PMI_CQI: 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:
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_i1_CQI: 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_CQI:
case NR_CSI_ReportConfig__reportQuantity_PR_cri_RI_LI_PMI_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; break;
default: default:
AssertFatal(1==0,"Invalid CSI report quantity type %d\n",csi_reportconfig->reportQuantity.present); 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; 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 // returns index from RSRP
// according to Table 10.1.6.1-1 in 38.133 // 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_format,
uint8_t dci_size, uint8_t dci_size,
uint16_t rnti, uint16_t rnti,
@@ -3580,7 +3716,7 @@ void nr_ue_process_mac_pdu(nr_downlink_indication_t *dl_info,
#endif #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; break;
case DL_SCH_LCID_CON_RES_ID: 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; NR_BWP_Id_t ul_bwp_id = mac->UL_BWP_Id;
// Get K2 from RRC configuration // 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; NR_PUSCH_TimeDomainResourceAllocationList_t *pusch_TimeDomainAllocationList = NULL;
if (pusch_config && pusch_config->pusch_TimeDomainAllocationList) { if (pusch_config && pusch_config->pusch_TimeDomainAllocationList) {
pusch_TimeDomainAllocationList = pusch_config->pusch_TimeDomainAllocationList->choice.setup; 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&&
mac->ULbwp[ul_bwp_id-1]->bwp_Common->pusch_ConfigCommon&& mac->ULbwp[ul_bwp_id-1]->bwp_Common->pusch_ConfigCommon&&
mac->ULbwp[ul_bwp_id-1]->bwp_Common->pusch_ConfigCommon->choice.setup && 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 // 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 // based on the TDD pattern (slot configuration period) and number of UL+mixed
// slots in the period. TS 38.213 Sec 11.1 // 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->ULbwp[ul_bwp_id-1]->bwp_Common->genericParameters.subcarrierSpacing :
mac->scc_SIB->uplinkConfigCommon->initialUplinkBWP.genericParameters.subcarrierSpacing; mac->scc_SIB->uplinkConfigCommon->initialUplinkBWP.genericParameters.subcarrierSpacing;
const int n = nr_slots_per_frame[mu]; 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; 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 : mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pusch_Config->choice.setup :
(ubwpd? (ubwpd?
ubwpd->pusch_Config->choice.setup: 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) mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig->initialUplinkBWP)
ubwpd = 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"); AssertFatal(pusch_Config!=NULL,"pusch_Config shouldn't be null\n");
long transformPrecoder; long transformPrecoder;
@@ -581,7 +582,7 @@ int nr_config_pusch_pdu(NR_UE_MAC_INST_t *mac,
if (rar_grant) { if (rar_grant) {
// Note: for Msg3 or MsgA PUSCH transmission the N_PRB_oh is always set to 0 // 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; NR_BWP_UplinkDedicated_t *ibwp;
int scs,abwp_start,abwp_size,startSymbolAndLength,mappingtype; int scs,abwp_start,abwp_size,startSymbolAndLength,mappingtype;
NR_PUSCH_Config_t *pusch_Config=NULL; 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, mappingtype, add_pos, dmrslength,
pusch_config_pdu->start_symbol_index, pusch_config_pdu->start_symbol_index,
mac->scc ? mac->scc->dmrs_TypeA_Position : mac->mib->dmrs_TypeA_Position); 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 (ul_bwp_id > 0 &&
if (*dci_format != NR_UL_DCI_FORMAT_0_1) { mac->ULbwp[ul_bwp_id - 1] &&
pusch_config_pdu->num_dmrs_cdm_grps_no_data = 1; pusch_config_pdu->transform_precoding == NR_PUSCH_Config__transformPrecoder_disabled &&
} *dci_format != NR_UL_DCI_FORMAT_0_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)) { 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; 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; else N_PRB_oh = 0;
/* PTRS */ /* 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 &&
mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pusch_Config && mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pusch_Config &&
mac->ULbwp[ul_bwp_id-1]->bwp_Dedicated->pusch_Config->choice.setup && 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; 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); 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); 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 { else {
// this is for Msg2/Msg4 // this is for Msg2/Msg4
@@ -1564,15 +1571,14 @@ int nr_ue_pusch_scheduler(NR_UE_MAC_INST_t *mac,
int delta = 0; int delta = 0;
NR_BWP_Id_t ul_bwp_id = mac->UL_BWP_Id; 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 // Get the numerology to calculate the Tx frame and slot
int mu = ubwp ? int mu = ul_bwp_id > 0 && mac->ULbwp[ul_bwp_id-1] ?
ubwp->bwp_Common->genericParameters.subcarrierSpacing : mac->ULbwp[ul_bwp_id-1]->bwp_Common->genericParameters.subcarrierSpacing :
mac->scc_SIB->uplinkConfigCommon->initialUplinkBWP.genericParameters.subcarrierSpacing; mac->scc_SIB->uplinkConfigCommon->initialUplinkBWP.genericParameters.subcarrierSpacing;
NR_PUSCH_TimeDomainResourceAllocationList_t *pusch_TimeDomainAllocationList = ubwp ? NR_PUSCH_TimeDomainResourceAllocationList_t *pusch_TimeDomainAllocationList = ul_bwp_id > 0 && mac->ULbwp[ul_bwp_id-1] ?
ubwp->bwp_Common->pusch_ConfigCommon->choice.setup->pusch_TimeDomainAllocationList: 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; 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 // 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 // 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 // SSB Table Configuration
uint32_t absolute_diff = (*scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencySSB - scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencyPointA); uint32_t absolute_diff = (*scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencySSB - scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencyPointA);
const int scaling_5khz = scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencyPointA < 600000 ? 3 : 1; 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) if(frequency_range == FR2)
sco >>= 1; // this assumes 120kHz SCS for SSB and subCarrierSpacingCommon (only option supported by OAI for 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; 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; cfg->ssb_table.ssb_mask_list[1].ssb_mask.value = 0;
break; break;
case 2 : 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; cfg->ssb_table.ssb_mask_list[1].ssb_mask.value = 0;
break; break;
case 3 : case 3 :
@@ -1090,13 +1090,16 @@ void fill_msg3_pusch_pdu(nfapi_nr_pusch_pdu_t *pusch_pdu,
pusch_pdu->vrb_to_prb_mapping = 0; pusch_pdu->vrb_to_prb_mapping = 0;
pusch_pdu->frequency_hopping = fh; 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; pusch_pdu->uplink_frequency_shift_7p5khz = 0;
//Resource Allocation in time domain //Resource Allocation in time domain
pusch_pdu->start_symbol_index = start_symbol_index; pusch_pdu->start_symbol_index = start_symbol_index;
pusch_pdu->nr_of_symbols = nr_of_symbols; pusch_pdu->nr_of_symbols = nr_of_symbols;
//Optional Data only included if indicated in pduBitmap //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.harq_process_id = 0;
pusch_pdu->pusch_data.new_data_indicator = 1; pusch_pdu->pusch_data.new_data_indicator = 1;
pusch_pdu->pusch_data.num_cb = 0; pusch_pdu->pusch_data.num_cb = 0;
@@ -1807,7 +1810,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->qamModOrder[0] = 2;
pdsch_pdu_rel15->mcsIndex[0] = mcsIndex; pdsch_pdu_rel15->mcsIndex[0] = mcsIndex;
pdsch_pdu_rel15->mcsTable[0] = mcsTableIdx; 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->dataScramblingId = *scc->physCellId;
pdsch_pdu_rel15->nrOfLayers = 1; pdsch_pdu_rel15->nrOfLayers = 1;
pdsch_pdu_rel15->transmissionScheme = 0; pdsch_pdu_rel15->transmissionScheme = 0;
@@ -285,7 +285,7 @@ uint32_t schedule_control_sib1(module_id_t module_id,
int nrOfSymbols, int nrOfSymbols,
uint16_t dlDmrsSymbPos, uint16_t dlDmrsSymbPos,
uint8_t candidate_idx, uint8_t candidate_idx,
int num_total_bytes) { uint16_t num_total_bytes) {
gNB_MAC_INST *gNB_mac = RC.nrmac[module_id]; gNB_MAC_INST *gNB_mac = RC.nrmac[module_id];
NR_COMMON_channels_t *cc = &gNB_mac->common_channels[CC_id]; NR_COMMON_channels_t *cc = &gNB_mac->common_channels[CC_id];
@@ -437,7 +437,7 @@ void nr_fill_nfapi_dl_sib1_pdu(int Mod_idP,
pdsch_pdu_rel15->qamModOrder[0] = 2; pdsch_pdu_rel15->qamModOrder[0] = 2;
pdsch_pdu_rel15->mcsIndex[0] = gNB_mac->sched_ctrlCommon->sched_pdsch.mcs; pdsch_pdu_rel15->mcsIndex[0] = gNB_mac->sched_ctrlCommon->sched_pdsch.mcs;
pdsch_pdu_rel15->mcsTable[0] = 0; 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->dataScramblingId = *scc->physCellId;
pdsch_pdu_rel15->nrOfLayers = 1; pdsch_pdu_rel15->nrOfLayers = 1;
pdsch_pdu_rel15->transmissionScheme = 0; pdsch_pdu_rel15->transmissionScheme = 0;
@@ -571,7 +571,7 @@ void schedule_nr_sib1(module_id_t module_idP, frame_t frameP, sub_frame_t slotP)
// Get SIB1 // Get SIB1
uint8_t sib1_payload[NR_MAX_SIB_LENGTH/8]; 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_sdu_length = %i\n", sib1_sdu_length);
LOG_D(NR_MAC,"SIB1: \n"); LOG_D(NR_MAC,"SIB1: \n");
for (int k=0;k<sib1_sdu_length;k++) for (int k=0;k<sib1_sdu_length;k++)
@@ -599,7 +599,8 @@ void schedule_nr_sib1(module_id_t module_idP, frame_t frameP, sub_frame_t slotP)
startSymbolIndex, startSymbolIndex,
nrOfSymbols, nrOfSymbols,
dlDmrsSymbPos, 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; 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]++; int pdu_index = gNB_mac->pdu_index[0]++;
@@ -643,7 +643,10 @@ void pf_dl(module_id_t module_id,
const NR_bler_options_t *bo = &mac->dl_bler; const NR_bler_options_t *bo = &mac->dl_bler;
const int max_mcs_table = ps->mcsTableIdx == 1 ? 27 : 28; const int max_mcs_table = ps->mcsTableIdx == 1 ? 27 : 28;
const int max_mcs = min(sched_ctrl->dl_max_mcs, max_mcs_table); 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); UE->layers = set_dl_nrOfLayers(sched_ctrl);
const uint8_t Qm = nr_get_Qm_dl(sched_pdsch->mcs, ps->mcsTableIdx); 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 uint16_t R = nr_get_code_rate_dl(sched_pdsch->mcs, ps->mcsTableIdx);
@@ -927,8 +930,6 @@ void nr_schedule_ue_spec(module_id_t module_id,
if (!is_xlsch_in_slot(gNB_mac->dlsch_slot_bitmap[slot / 64], slot)) if (!is_xlsch_in_slot(gNB_mac->dlsch_slot_bitmap[slot / 64], slot))
return; return;
//if (slot==7 || slot == 17) return;
/* PREPROCESSOR */ /* PREPROCESSOR */
gNB_mac->pre_processor_dl(module_id, frame, slot); gNB_mac->pre_processor_dl(module_id, frame, slot);
const int CC_id = 0; const int CC_id = 0;
@@ -1017,7 +1018,7 @@ void nr_schedule_ue_spec(module_id_t module_id,
TBS, TBS,
current_harq_pid, current_harq_pid,
harq->round, harq->round,
nr_rv_round_map[harq->round], nr_rv_round_map[harq->round%4],
harq->ndi, harq->ndi,
pucch->timing_indicator, pucch->timing_indicator,
pucch->frame, pucch->frame,
@@ -1085,8 +1086,8 @@ void nr_schedule_ue_spec(module_id_t module_id,
pdsch_pdu->mcsIndex[0] = sched_pdsch->mcs; pdsch_pdu->mcsIndex[0] = sched_pdsch->mcs;
pdsch_pdu->mcsTable[0] = ps->mcsTableIdx; pdsch_pdu->mcsTable[0] = ps->mcsTableIdx;
AssertFatal(harq!=NULL,"harq is null\n"); AssertFatal(harq!=NULL,"harq is null\n");
AssertFatal(harq->round<4,"%d",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]; pdsch_pdu->rvIndex[0] = nr_rv_round_map[harq->round%4];
pdsch_pdu->TBSize[0] = TBS; pdsch_pdu->TBSize[0] = TBS;
pdsch_pdu->dataScramblingId = *scc->physCellId; pdsch_pdu->dataScramblingId = *scc->physCellId;
pdsch_pdu->nrOfLayers = nrOfLayers; pdsch_pdu->nrOfLayers = nrOfLayers;
@@ -1120,9 +1121,8 @@ void nr_schedule_ue_spec(module_id_t module_id,
csi_report->codebook_mode); csi_report->codebook_mode);
} }
// TBS_LBRM according to section 5.4.2.1 of 38.212 // 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 = cg && cg->spCellConfig && cg->spCellConfig->spCellConfigDedicated ? *cg->spCellConfig->spCellConfigDedicated->pdsch_ServingCellConfig->choice.setup->ext1->maxMIMO_Layers : 1;
AssertFatal (maxMIMO_Layers != NULL,"Option with max MIMO layers not configured is not supported\n"); int nl_tbslbrm = maxMIMO_Layers < 4 ? maxMIMO_Layers : 4;
int nl_tbslbrm = *maxMIMO_Layers < 4 ? *maxMIMO_Layers : 4;
// Maximum number of PRBs across all configured DL BWPs // Maximum number of PRBs across all configured DL BWPs
int bw_tbslbrm = get_bw_tbslbrm(genericParameters, cg); int bw_tbslbrm = get_bw_tbslbrm(genericParameters, cg);
pdsch_pdu->maintenance_parms_v3.tbSizeLbrmBytes = nr_compute_tbslbrm(ps->mcsTableIdx, pdsch_pdu->maintenance_parms_v3.tbSizeLbrmBytes = nr_compute_tbslbrm(ps->mcsTableIdx,
@@ -1319,7 +1319,7 @@ void nr_schedule_ue_spec(module_id_t module_id,
lcid < 4 ? "DCCH" : "DTCH", lcid < 4 ? "DCCH" : "DTCH",
lcid, lcid,
ndata, ndata,
bufEnd-buf-+sizeof(NR_MAC_SUBHEADER_LONG)); bufEnd-buf-sizeof(NR_MAC_SUBHEADER_LONG));
if (len == 0) if (len == 0)
break; break;
@@ -1350,6 +1350,8 @@ void nr_schedule_ue_spec(module_id_t module_id,
header->L = htons(bufEnd-buf); header->L = htons(bufEnd-buf);
dlsch_total_bytes += bufEnd-buf; dlsch_total_bytes += bufEnd-buf;
for (; ((intptr_t)buf) % 4; buf++)
*buf = lrand48() & 0xff;
for (; buf < bufEnd - 3; buf += 4) { for (; buf < bufEnd - 3; buf += 4) {
uint32_t *buf32 = (uint32_t *)buf; uint32_t *buf32 = (uint32_t *)buf;
*buf32 = lrand48(); *buf32 = lrand48();
@@ -1445,7 +1445,6 @@ void set_r_pucch_parms(int rsetindex,
*start_symbol_index = default_pucch_firstsymb[rsetindex]; *start_symbol_index = default_pucch_firstsymb[rsetindex];
} }
void prepare_dci(const NR_CellGroupConfig_t *CellGroup, void prepare_dci(const NR_CellGroupConfig_t *CellGroup,
dci_pdu_rel15_t *dci_pdu_rel15, dci_pdu_rel15_t *dci_pdu_rel15,
nr_dci_format_t format, nr_dci_format_t format,
@@ -2395,7 +2394,7 @@ NR_UE_info_t *add_new_nr_ue(gNB_MAC_INST *nr_mac, rnti_t rntiP, NR_CellGroupConf
CellGroup->spCellConfig->spCellConfigDedicated && CellGroup->spCellConfig->spCellConfigDedicated &&
CellGroup->spCellConfig->spCellConfigDedicated->csi_MeasConfig && CellGroup->spCellConfig->spCellConfigDedicated->csi_MeasConfig &&
CellGroup->spCellConfig->spCellConfigDedicated->csi_MeasConfig->choice.setup) { CellGroup->spCellConfig->spCellConfigDedicated->csi_MeasConfig->choice.setup) {
compute_csi_bitlen(CellGroup->spCellConfig->spCellConfigDedicated->csi_MeasConfig->choice.setup, UE); compute_csi_bitlen(CellGroup->spCellConfig->spCellConfigDedicated->csi_MeasConfig->choice.setup, UE->csi_report_template);
} }
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl; NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
@@ -2446,16 +2445,15 @@ NR_UE_info_t *add_new_nr_ue(gNB_MAC_INST *nr_mac, rnti_t rntiP, NR_CellGroupConf
sched_ctrl->next_dl_bwp_id = -1; sched_ctrl->next_dl_bwp_id = -1;
sched_ctrl->next_ul_bwp_id = -1; sched_ctrl->next_ul_bwp_id = -1;
const struct NR_UplinkConfig__uplinkBWP_ToAddModList *ubwpList = servingCellConfig ? servingCellConfig->uplinkConfig->uplinkBWP_ToAddModList : NULL; const struct NR_UplinkConfig__uplinkBWP_ToAddModList *ubwpList = servingCellConfig ? servingCellConfig->uplinkConfig->uplinkBWP_ToAddModList : NULL;
if (ubwpList) AssertFatal(ubwpList == NULL || ubwpList->list.count <= NR_MAX_NUM_BWP,
AssertFatal(ubwpList->list.count <= NR_MAX_NUM_BWP, "uplinkBWP_ToAddModList has %d BWP!\n",
"uplinkBWP_ToAddModList has %d BWP!\n", ubwpList->list.count);
ubwpList->list.count);
const int ul_bwp_id = servingCellConfig ? *servingCellConfig->uplinkConfig->firstActiveUplinkBWP_Id : 0; const int ul_bwp_id = servingCellConfig ? *servingCellConfig->uplinkConfig->firstActiveUplinkBWP_Id : 0;
sched_ctrl->active_ubwp = ubwpList && ul_bwp_id > 0 ? ubwpList->list.array[ul_bwp_id - 1] : NULL; sched_ctrl->active_ubwp = ubwpList && ul_bwp_id > 0 ? ubwpList->list.array[ul_bwp_id - 1] : NULL;
/* get Number of HARQ processes for this UE */ /* get Number of HARQ processes for this UE */
if (servingCellConfig) AssertFatal(servingCellConfig == NULL
AssertFatal(servingCellConfig->pdsch_ServingCellConfig->present == NR_SetupRelease_PDSCH_ServingCellConfig_PR_setup, || servingCellConfig->pdsch_ServingCellConfig->present == NR_SetupRelease_PDSCH_ServingCellConfig_PR_setup,
"no pdsch-ServingCellConfig found for UE %04x\n", "no pdsch-ServingCellConfig found for UE %04x\n",
UE->rnti); UE->rnti);
const NR_PDSCH_ServingCellConfig_t *pdsch = servingCellConfig ? servingCellConfig->pdsch_ServingCellConfig->choice.setup : NULL; const NR_PDSCH_ServingCellConfig_t *pdsch = servingCellConfig ? servingCellConfig->pdsch_ServingCellConfig->choice.setup : NULL;
@@ -2967,6 +2965,10 @@ void nr_mac_update_timers(module_id_t module_id,
LOG_I(NR_MAC, "(%d.%d) Switching to initialUplinkBWP\n", frame, slot); LOG_I(NR_MAC, "(%d.%d) Switching to initialUplinkBWP\n", frame, slot);
} }
UE->Msg3_dcch_dtch = false; UE->Msg3_dcch_dtch = false;
// Schedule BWP switching to the first active BWP (previous active BWP before RA with Msg3 carrying DCCH or DTCH message)
sched_ctrl->next_dl_bwp_id = current_bwp_id;
sched_ctrl->next_ul_bwp_id = current_ubwp_id;
} else if (spCellConfigDedicated && } else if (spCellConfigDedicated &&
spCellConfigDedicated->downlinkBWP_ToAddModList && spCellConfigDedicated->downlinkBWP_ToAddModList &&
spCellConfigDedicated->uplinkConfig && spCellConfigDedicated->uplinkConfig &&
@@ -2979,6 +2981,19 @@ void nr_mac_update_timers(module_id_t module_id,
if (*spCellConfigDedicated->uplinkConfig->firstActiveUplinkBWP_Id != current_ubwp_id) { if (*spCellConfigDedicated->uplinkConfig->firstActiveUplinkBWP_Id != current_ubwp_id) {
LOG_I(NR_MAC, "(%d.%d) Switching to UL-BWP %li\n", frame, slot, sched_ctrl->active_ubwp->bwp_Id); LOG_I(NR_MAC, "(%d.%d) Switching to UL-BWP %li\n", frame, slot, sched_ctrl->active_ubwp->bwp_Id);
} }
// Update next_dl_bwp_id to not trigger BWP switching, UE should be already on active_bwp
sched_ctrl->next_dl_bwp_id = sched_ctrl->active_bwp->bwp_Id;
// Update next_ul_bwp_id to not trigger BWP switching, UE should be already on active_ubwp
sched_ctrl->next_ul_bwp_id = sched_ctrl->active_ubwp->bwp_Id;
} else {
sched_ctrl->active_bwp = NULL;
sched_ctrl->active_ubwp = NULL;
// Update next_dl_bwp_id to not trigger BWP switching, UE should be already on Initial BWP
sched_ctrl->next_dl_bwp_id = 0;
// Update next_ul_bwp_id to not trigger BWP switching, UE should be already on Initial BWP
sched_ctrl->next_ul_bwp_id = 0;
} }
// Update coreset/searchspace // Update coreset/searchspace
@@ -3012,7 +3027,7 @@ void nr_mac_update_timers(module_id_t module_id,
cg->spCellConfig->spCellConfigDedicated && cg->spCellConfig->spCellConfigDedicated &&
cg->spCellConfig->spCellConfigDedicated->csi_MeasConfig && cg->spCellConfig->spCellConfigDedicated->csi_MeasConfig &&
cg->spCellConfig->spCellConfigDedicated->csi_MeasConfig->choice.setup) { cg->spCellConfig->spCellConfigDedicated->csi_MeasConfig->choice.setup) {
compute_csi_bitlen (cg->spCellConfig->spCellConfigDedicated->csi_MeasConfig->choice.setup, UE); compute_csi_bitlen (cg->spCellConfig->spCellConfigDedicated->csi_MeasConfig->choice.setup, UE->csi_report_template);
} }
NR_pdsch_semi_static_t *ps = &sched_ctrl->pdsch_semi_static; NR_pdsch_semi_static_t *ps = &sched_ctrl->pdsch_semi_static;
@@ -3072,14 +3087,27 @@ void schedule_nr_bwp_switch(module_id_t module_id,
UE_iterator(UE_info->list, UE) { UE_iterator(UE_info->list, UE) {
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl; NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
if (sched_ctrl->rrc_processing_timer == 0 && if (sched_ctrl->rrc_processing_timer == 0 && UE->Msg4_ACKed && sched_ctrl->next_dl_bwp_id >= 0) {
UE->Msg4_ACKed &&
((sched_ctrl->next_dl_bwp_id >= 0 && sched_ctrl->active_bwp && sched_ctrl->active_bwp->bwp_Id != sched_ctrl->next_dl_bwp_id) ||
(sched_ctrl->next_ul_bwp_id >= 0 && sched_ctrl->active_ubwp && sched_ctrl->active_ubwp->bwp_Id != sched_ctrl->next_ul_bwp_id))) {
LOG_W(NR_MAC,"%4d.%2d UE %04x Schedule BWP switch from dl_bwp_id %ld to %ld and from ul_bwp_id %ld to %ld\n", int schedule_bwp_switching = false;
frame, slot, UE->rnti, sched_ctrl->active_bwp->bwp_Id, sched_ctrl->next_dl_bwp_id, sched_ctrl->active_ubwp->bwp_Id, sched_ctrl->next_ul_bwp_id); if (sched_ctrl->active_bwp == NULL) {
nr_mac_rrc_bwp_switch_req(module_id, frame, slot, UE->rnti, sched_ctrl->next_dl_bwp_id, sched_ctrl->next_ul_bwp_id); // Switching from Initial BWP to Dedicated BWP
if (sched_ctrl->next_dl_bwp_id > 0 && sched_ctrl->next_ul_bwp_id > 0) {
schedule_bwp_switching = true;
LOG_W(NR_MAC,"%4d.%2d UE %04x Schedule BWP switch from Initial DL BWP to %ld and from Initial UL BWP to %ld\n",
frame, slot, UE->rnti, sched_ctrl->next_dl_bwp_id, sched_ctrl->next_ul_bwp_id);
}
} else if (sched_ctrl->active_bwp->bwp_Id != sched_ctrl->next_dl_bwp_id && sched_ctrl->active_ubwp->bwp_Id != sched_ctrl->next_ul_bwp_id) {
// Switching between Dedicated BWPs
schedule_bwp_switching = true;
LOG_W(NR_MAC,"%4d.%2d UE %04x Schedule BWP switch from dl_bwp_id %ld to %ld and from ul_bwp_id %ld to %ld\n",
frame, slot, UE->rnti, sched_ctrl->active_bwp->bwp_Id, sched_ctrl->next_dl_bwp_id, sched_ctrl->active_ubwp->bwp_Id, sched_ctrl->next_ul_bwp_id);
}
if (schedule_bwp_switching) {
AssertFatal(sched_ctrl->next_dl_bwp_id > 0 && sched_ctrl->next_ul_bwp_id > 0, "BWP switching from a Dedicated BWP to the Initial BWP not handled yet!");
nr_mac_rrc_bwp_switch_req(module_id, frame, slot, UE->rnti, sched_ctrl->next_dl_bwp_id, sched_ctrl->next_ul_bwp_id);
}
} }
} }
} }
+7 -536
View File
@@ -169,530 +169,6 @@ 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, void nr_csi_meas_reporting(int Mod_idP,
frame_t frame, frame_t frame,
sub_frame_t slot) { sub_frame_t slot) {
@@ -700,7 +176,6 @@ void nr_csi_meas_reporting(int Mod_idP,
NR_ServingCellConfigCommon_t *scc = RC.nrmac[Mod_idP]->common_channels->ServingCellConfigCommon; NR_ServingCellConfigCommon_t *scc = RC.nrmac[Mod_idP]->common_channels->ServingCellConfigCommon;
const int n_slots_frame = nr_slots_per_frame[*scc->ssbSubcarrierSpacing]; const int n_slots_frame = nr_slots_per_frame[*scc->ssbSubcarrierSpacing];
UE_iterator(RC.nrmac[Mod_idP]->UE_info.list, UE ) { UE_iterator(RC.nrmac[Mod_idP]->UE_info.list, UE ) {
const NR_CellGroupConfig_t *CellGroup = UE->CellGroup; const NR_CellGroupConfig_t *CellGroup = UE->CellGroup;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl; NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
@@ -760,7 +235,7 @@ void nr_csi_meas_reporting(int Mod_idP,
curr_pucch->frame = frame; curr_pucch->frame = frame;
curr_pucch->ul_slot = sched_slot; curr_pucch->ul_slot = sched_slot;
curr_pucch->resource_indicator = res_index; 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; 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, NR_BWP_t *genericParameters = get_ul_bwp_genericParameters(sched_ctrl->active_ubwp,
@@ -824,7 +299,6 @@ static void handle_dl_harq(NR_UE_info_t * UE,
add_tail_nr_list(&UE->UE_sched_ctrl.available_dl_harq, harq_pid); add_tail_nr_list(&UE->UE_sched_ctrl.available_dl_harq, harq_pid);
harq->round = 0; harq->round = 0;
harq->ndi ^= 1; harq->ndi ^= 1;
} else if (harq->round >= harq_round_max - 1) { } else if (harq->round >= harq_round_max - 1) {
abort_nr_dl_harq(UE, harq_pid); 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); LOG_D(NR_MAC, "retransmission error for UE %04x (total %"PRIu64")\n", UE->rnti, UE->mac_stats.dl.errors);
@@ -1177,7 +651,6 @@ void evaluate_rsrp_report(NR_UE_info_t *UE,
stats->num_rsrp_meas++; stats->num_rsrp_meas++;
} }
void evaluate_cri_report(uint8_t *payload, void evaluate_cri_report(uint8_t *payload,
uint8_t cri_bitlen, uint8_t cri_bitlen,
int cumul_bits, int cumul_bits,
@@ -1456,7 +929,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++) { 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_value = uci_01->harq->harq_list[harq_bit].harq_value;
const uint8_t harq_confidence = uci_01->harq->harq_confidence_level; 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) { if (!harq) {
LOG_E(NR_MAC, "Oh no! Could not find a harq in %s!\n", __FUNCTION__); LOG_E(NR_MAC, "Oh no! Could not find a harq in %s!\n", __FUNCTION__);
break; break;
@@ -1465,7 +938,7 @@ void handle_nr_uci_pucch_0_1(module_id_t mod_id,
const int8_t pid = sched_ctrl->feedback_dl_harq.head; const int8_t pid = sched_ctrl->feedback_dl_harq.head;
remove_front_nr_list(&sched_ctrl->feedback_dl_harq); 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); 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++; if (harq_confidence == 1) UE->mac_stats.pucch0_DTX++;
} }
} }
@@ -1518,13 +991,13 @@ void handle_nr_uci_pucch_2_3_4(module_id_t mod_id,
// iterate over received harq bits // iterate over received harq bits
for (int harq_bit = 0; harq_bit < uci_234->harq.harq_bit_len; harq_bit++) { 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; 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) if (!harq)
break; break;
DevAssert(harq->is_waiting); DevAssert(harq->is_waiting);
const int8_t pid = sched_ctrl->feedback_dl_harq.head; const int8_t pid = sched_ctrl->feedback_dl_harq.head;
remove_front_nr_list(&sched_ctrl->feedback_dl_harq); 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) { if ((uci_234->pduBitmap >> 2) & 0x01) {
@@ -1593,7 +1066,6 @@ bool test_acknack_vrb_occupation(NR_UE_sched_ctrl_t *sched_ctrl,
return true; return true;
} }
// this function returns an index to NR_sched_pucch structure // this function returns an index to NR_sched_pucch structure
// currently this structure contains PUCCH0 at index 0 and PUCCH2 at index 1 // 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 // if the function returns -1 it was not possible to schedule acknack
@@ -1662,7 +1134,7 @@ int nr_acknack_scheduling(int mod_id,
&& csi_pucch->csi_bits > 0 && csi_pucch->csi_bits > 0
&& csi_pucch->frame == f && csi_pucch->frame == f
&& csi_pucch->ul_slot == s)) && 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)); memset(pucch, 0, sizeof(*pucch));
pucch->frame = s == n_slots_frame - 1 ? (f + 1) % 1024 : f; pucch->frame = s == n_slots_frame - 1 ? (f + 1) % 1024 : f;
@@ -1735,7 +1207,7 @@ int nr_acknack_scheduling(int mod_id,
csi_pucch->csi_bits > 0 && csi_pucch->csi_bits > 0 &&
csi_pucch->frame == f && csi_pucch->frame == f &&
csi_pucch->ul_slot == s)) 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)); memset(pucch, 0, sizeof(*pucch));
pucch->frame = s == n_slots_frame - 1 ? (f + 1) % 1024 : f; pucch->frame = s == n_slots_frame - 1 ? (f + 1) % 1024 : f;
if(((s + 1)%nr_slots_period) == 0) if(((s + 1)%nr_slots_period) == 0)
@@ -1837,7 +1309,6 @@ int nr_acknack_scheduling(int mod_id,
// 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
if(!csi_pucch->simultaneous_harqcsi if(!csi_pucch->simultaneous_harqcsi
|| ((csi_pucch->csi_bits + csi_pucch->dai_c) >= 11)) { || ((csi_pucch->csi_bits + csi_pucch->dai_c) >= 11)) {
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); 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); nr_fill_nfapi_pucch(RC.nrmac[mod_id], frame, slot, csi_pucch, UE);
memset(csi_pucch, 0, sizeof(*csi_pucch)); memset(csi_pucch, 0, sizeof(*csi_pucch));
@@ -435,7 +435,7 @@ int nr_process_mac_pdu(instance_t module_idP,
return 0; 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_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_ul_harq_t *harq = &sched_ctrl->ul_harq_processes[harq_pid]; NR_UE_ul_harq_t *harq = &sched_ctrl->ul_harq_processes[harq_pid];
@@ -485,7 +485,7 @@ void handle_nr_ul_harq(const int CC_idP,
remove_front_nr_list(&sched_ctrl->feedback_ul_harq); remove_front_nr_list(&sched_ctrl->feedback_ul_harq);
sched_ctrl->ul_harq_processes[harq_pid].is_waiting = false; 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); abort_nr_ul_harq(UE, harq_pid);
} else { } else {
sched_ctrl->ul_harq_processes[harq_pid].round++; sched_ctrl->ul_harq_processes[harq_pid].round++;
@@ -506,7 +506,7 @@ void handle_nr_ul_harq(const int CC_idP,
harq_pid, harq_pid,
crc_pdu->rnti); crc_pdu->rnti);
add_tail_nr_list(&sched_ctrl->available_ul_harq, harq_pid); 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); abort_nr_ul_harq(UE, harq_pid);
LOG_D(NR_MAC, LOG_D(NR_MAC,
"RNTI %04x: Ulharq id %d crc failed in all rounds\n", "RNTI %04x: Ulharq id %d crc failed in all rounds\n",
@@ -579,7 +579,6 @@ void nr_rx_sdu(const module_id_t gnb_mod_idP,
else{ else{
LOG_D(NR_MAC,"[UE %04x] Detected DTX : increasing UE TX power\n",UE->rnti); LOG_D(NR_MAC,"[UE %04x] Detected DTX : increasing UE TX power\n",UE->rnti);
UE_scheduling_control->tpc0 = 1; UE_scheduling_control->tpc0 = 1;
} }
#if defined(ENABLE_MAC_PAYLOAD_DEBUG) #if defined(ENABLE_MAC_PAYLOAD_DEBUG)
@@ -782,14 +781,13 @@ void nr_rx_sdu(const module_id_t gnb_mod_idP,
return; return;
} }
if (ra->msg3_round >= MAX_HARQ_ROUNDS - 1) { if (ra->msg3_round >= gNB_mac->ul_bler.harq_round_max - 1) {
LOG_D(NR_MAC, "Random Access %i failed at state %i (Reached msg3 max harq rounds)\n", i, ra->state); 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_mac_remove_ra_rnti(gnb_mod_idP, ra->rnti);
nr_clear_ra_proc(gnb_mod_idP, CC_idP, frameP, ra); nr_clear_ra_proc(gnb_mod_idP, CC_idP, frameP, ra);
return; return;
} }
LOG_D(NR_MAC, "Random Access %i Msg3 CRC did not pass)\n", i); LOG_D(NR_MAC, "Random Access %i Msg3 CRC did not pass)\n", i);
ra->msg3_round++; ra->msg3_round++;
@@ -879,10 +877,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 n = nr_slots_per_frame[*scc->ssbSubcarrierSpacing];
const int now = frame * n + slot; const int now = frame * n + slot;
const NR_UE_sched_ctrl_t *sched_ctrl =&UE->UE_sched_ctrl; const NR_UE_sched_ctrl_t *sched_ctrl =&UE->UE_sched_ctrl;
const NR_TDD_UL_DL_Pattern_t *tdd = const NR_TDD_UL_DL_Pattern_t *tdd =
scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL; scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL;
int num_slots_per_period; int num_slots_per_period;
@@ -1148,7 +1144,7 @@ static int comparator(const void *p, const void *q) {
void pf_ul(module_id_t module_id, void pf_ul(module_id_t module_id,
frame_t frame, frame_t frame,
sub_frame_t slot, sub_frame_t slot,
NR_UE_info_t *UE_list[], NR_UE_info_t *UE_list[],
int max_num_ue, int max_num_ue,
int n_rb_sched, int n_rb_sched,
uint16_t *rballoc_mask) { uint16_t *rballoc_mask) {
@@ -1209,10 +1205,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 */ /* reduce max_num_ue once we are sure UE can be allocated, i.e., has CCE */
remainUEs--; remainUEs--;
// we have filled all with mandatory retransmissions
// no need to schedule new transmissions
if (remainUEs == 0) if (remainUEs == 0)
// we have filled all with mandatory retransmissions return;
// no need to schedule new transmissions
return;
continue; continue;
} }
const int B = max(0, sched_ctrl->estimated_ul_buffer - sched_ctrl->sched_ul_bytes); const int B = max(0, sched_ctrl->estimated_ul_buffer - sched_ctrl->sched_ul_bytes);
@@ -1220,12 +1217,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); 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"); 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; continue;
}
const NR_bler_options_t *bo = &nrmac->ul_bler; const NR_bler_options_t *bo = &nrmac->ul_bler;
const int max_mcs = bo->max_mcs; /* no per-user maximum MCS yet */ 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 /* Schedule UE on SR or UL inactivity and no data (otherwise, will be scheduled
* based on data to transmit) */ * based on data to transmit) */
@@ -1235,12 +1236,12 @@ void pf_ul(module_id_t module_id,
const uint32_t Y = get_Y(sched_ctrl->search_space, slot, UE->rnti); const uint32_t Y = get_Y(sched_ctrl->search_space, slot, UE->rnti);
uint8_t nr_of_candidates; uint8_t nr_of_candidates;
for (int i=0; i<5; i++) { for (int i=0; i<5; i++) {
// for now taking the lowest value among the available aggregation levels // for now taking the lowest value among the available aggregation levels
find_aggregation_candidates(&sched_ctrl->aggregation_level, find_aggregation_candidates(&sched_ctrl->aggregation_level,
&nr_of_candidates, &nr_of_candidates,
sched_ctrl->search_space, sched_ctrl->search_space,
1<<i); 1<<i);
if(nr_of_candidates>0) break; if(nr_of_candidates>0) break;
} }
int CCEIndex = find_pdcch_candidate(RC.nrmac[module_id], int CCEIndex = find_pdcch_candidate(RC.nrmac[module_id],
CC_id, CC_id,
@@ -1251,16 +1252,17 @@ void pf_ul(module_id_t module_id,
Y); Y);
if (CCEIndex<0) { if (CCEIndex<0) {
LOG_D(NR_MAC, "%4d.%2d no free CCE for UL DCI UE %04x (BSR 0)\n", frame, slot, UE->rnti); LOG_D(NR_MAC, "%4d.%2d no free CCE for UL DCI UE %04x (BSR 0)\n", frame, slot, UE->rnti);
continue; continue;
} }
/* reduce max_num_ue once we are sure UE can be allocated, i.e., has CCE */ /* reduce max_num_ue once we are sure UE can be allocated, i.e., has CCE */
remainUEs--; remainUEs--;
// we have filled all with mandatory retransmissions
// no need to schedule new transmissions
if (remainUEs == 0) if (remainUEs == 0)
// we have filled all with mandatory retransmissions return;
// no need to schedule new transmissions
return;
/* Save PUSCH field */ /* Save PUSCH field */
/* we want to avoid a lengthy deduction of DMRS and other parameters in /* we want to avoid a lengthy deduction of DMRS and other parameters in
@@ -1355,7 +1357,7 @@ void pf_ul(module_id_t module_id,
sched_ctrl->search_space, sched_ctrl->search_space,
1<<i); 1<<i);
if(nr_of_candidates>0) if(nr_of_candidates>0)
break; break;
} }
int CCEIndex = find_pdcch_candidate(RC.nrmac[module_id], int CCEIndex = find_pdcch_candidate(RC.nrmac[module_id],
CC_id, CC_id,
@@ -1464,8 +1466,8 @@ void pf_ul(module_id_t module_id,
n_rb_sched -= sched_pusch->rbSize; n_rb_sched -= sched_pusch->rbSize;
for (int rb = 0; rb < sched_ctrl->sched_pusch.rbSize; rb++) for (int rb = 0; rb < sched_ctrl->sched_pusch.rbSize; rb++)
rballoc_mask[rb + sched_ctrl->sched_pusch.rbStart] ^= slbitmap; 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 */ /* reduce max_num_ue once we are sure UE can be allocated, i.e., has CCE */
remainUEs--; remainUEs--;
iterator++; iterator++;
@@ -1485,8 +1487,8 @@ bool nr_fr1_ulsch_preprocessor(module_id_t module_id, frame_t frame, sub_frame_t
const int mu = scc ? scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.subcarrierSpacing : const int mu = scc ? scc->uplinkConfigCommon->initialUplinkBWP->genericParameters.subcarrierSpacing :
scc_sib1->uplinkConfigCommon->initialUplinkBWP.genericParameters.subcarrierSpacing; scc_sib1->uplinkConfigCommon->initialUplinkBWP.genericParameters.subcarrierSpacing;
// no UEs
if (nr_mac->UE_info.list[0] == NULL) if (nr_mac->UE_info.list[0] == NULL)
// no UEs
return false; return false;
const int CC_id = 0; const int CC_id = 0;
@@ -1533,8 +1535,7 @@ bool nr_fr1_ulsch_preprocessor(module_id_t module_id, frame_t frame, sub_frame_t
UE_iterator(nr_mac->UE_info.list, UE2) { UE_iterator(nr_mac->UE_info.list, UE2) {
NR_UE_sched_ctrl_t *sched_ctrl = &UE2->UE_sched_ctrl; 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(scc,scc_sib1,sched_ctrl->active_ubwp, tda, mu),
"Different K2, %d(UE%d) != %ld(UE%04x)\n", "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(scc,scc_sib1,sched_ctrl->active_ubwp, tda, mu), UE2->rnti);
sched_ctrl->sched_pusch.slot = sched_slot; sched_ctrl->sched_pusch.slot = sched_slot;
sched_ctrl->sched_pusch.frame = sched_frame; sched_ctrl->sched_pusch.frame = sched_frame;
} }
@@ -1711,7 +1712,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; NR_pusch_semi_static_t *ps = &sched_ctrl->pusch_semi_static;
/* Statistics */ /* 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]++; UE->mac_stats.ul.rounds[cur_harq->round]++;
if (cur_harq->round == 0) { if (cur_harq->round == 0) {
UE->mac_stats.ulsch_total_bytes_scheduled += sched_pusch->tb_size; UE->mac_stats.ulsch_total_bytes_scheduled += sched_pusch->tb_size;
@@ -1757,7 +1758,7 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, sub_frame_t slot)
sched_pusch->tb_size, sched_pusch->tb_size,
harq_id, harq_id,
cur_harq->round, cur_harq->round,
nr_rv_round_map[cur_harq->round], nr_rv_round_map[cur_harq->round%4],
cur_harq->ndi, cur_harq->ndi,
sched_ctrl->estimated_ul_buffer, sched_ctrl->estimated_ul_buffer,
sched_ctrl->sched_ul_bytes, sched_ctrl->sched_ul_bytes,
@@ -1853,8 +1854,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->nr_of_symbols = ps->nrOfSymbols;
/* PUSCH PDU */ /* PUSCH PDU */
AssertFatal(cur_harq->round < 4, "Indexing nr_rv_round_map[%d] is out of bounds\n", 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]; 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.harq_process_id = harq_id;
pusch_pdu->pusch_data.new_data_indicator = cur_harq->ndi; pusch_pdu->pusch_data.new_data_indicator = cur_harq->ndi;
pusch_pdu->pusch_data.tb_size = sched_pusch->tb_size; pusch_pdu->pusch_data.tb_size = sched_pusch->tb_size;
+8 -10
View File
@@ -93,7 +93,7 @@ uint32_t schedule_control_sib1(module_id_t module_id,
int nrOfSymbols, int nrOfSymbols,
uint16_t dlDmrsSymbPos, uint16_t dlDmrsSymbPos,
uint8_t candidate_idx, uint8_t candidate_idx,
int num_total_bytes); uint16_t num_total_bytes);
/* \brief default FR1 DL preprocessor init routine, returns preprocessor to call */ /* \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); nr_pp_impl_dl nr_init_fr1_dlsch_preprocessor(module_id_t module_id, int CC_id);
@@ -201,7 +201,7 @@ void config_uldci(const NR_SIB1_t *sib1,
int n_ubwp, int n_ubwp,
int bwp_id); int bwp_id);
void nr_schedule_pucch(gNB_MAC_INST* nrmac, void nr_schedule_pucch(gNB_MAC_INST *nrmac,
frame_t frameP, frame_t frameP,
sub_frame_t slotP); sub_frame_t slotP);
@@ -216,12 +216,12 @@ void nr_csi_meas_reporting(int Mod_idP,
frame_t frameP, frame_t frameP,
sub_frame_t slotP); sub_frame_t slotP);
int nr_acknack_scheduling( int Mod_idP, int nr_acknack_scheduling(int Mod_idP,
NR_UE_info_t * UE, NR_UE_info_t *UE,
frame_t frameP, frame_t frameP,
sub_frame_t slotP, sub_frame_t slotP,
int r_pucch, int r_pucch,
int do_common); int do_common);
void get_pdsch_to_harq_feedback(NR_UE_info_t *, void get_pdsch_to_harq_feedback(NR_UE_info_t *,
int bwp_id, int bwp_id,
@@ -410,8 +410,6 @@ void nr_mac_remove_ra_rnti(module_id_t mod_id, rnti_t rnti);
int nr_get_default_pucch_res(int pucch_ResourceCommon); 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_dlscs(nfapi_nr_config_request_t *cfg);
int get_ulscs(nfapi_nr_config_request_t *cfg); int get_ulscs(nfapi_nr_config_request_t *cfg);
+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, end - output,
"UE %04x: CQI %d, RI %d, PMI (%d,%d)\n", "UE %04x: CQI %d, RI %d, PMI (%d,%d)\n",
UE->rnti, UE->rnti,
UE->UE_sched_ctrl.CSI_report.cri_ri_li_pmi_cqi_report.wb_cqi_1tb, 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, 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, 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.pmi_x2);
output += snprintf(output, output += snprintf(output,
end - output, end - output,
"UE %04x: dlsch_rounds %"PRIu64"/%"PRIu64"/%"PRIu64"/%"PRIu64", dlsch_errors %"PRIu64", pucch0_DTX %d, BLER %.5f MCS %d\n", "UE %04x: dlsch_rounds ", UE->rnti);
UE->rnti, output += snprintf(output, end - output, "%"PRIu64, stats->dl.rounds[0]);
stats->dl.rounds[0], stats->dl.rounds[1], for (int i = 1; i < gNB->dl_bler.harq_round_max; i++)
stats->dl.rounds[2], stats->dl.rounds[3], 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->dl.errors,
stats->pucch0_DTX, stats->pucch0_DTX,
sched_ctrl->dl_bler_stats.bler, 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, output += snprintf(output,
end - output, end - output,
"UE %04x: dlsch_total_bytes %"PRIu64"\n", "UE %04x: dlsch_total_bytes %"PRIu64"\n",
UE->rnti, UE->rnti, stats->dl.total_bytes);
stats->dl.total_bytes);
output += snprintf(output, output += snprintf(output,
end - output, end - output,
"UE %04x: ulsch_rounds %"PRIu64"/%"PRIu64"/%"PRIu64"/%"PRIu64", ulsch_DTX %d, ulsch_errors %"PRIu64", BLER %.5f MCS %d\n", "UE %04x: ulsch_rounds ", UE->rnti);
UE->rnti, output += snprintf(output, end - output, "%"PRIu64, stats->ul.rounds[0]);
stats->ul.rounds[0], stats->ul.rounds[1], for (int i = 1; i < gNB->ul_bler.harq_round_max; i++)
stats->ul.rounds[2], stats->ul.rounds[3], 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->ulsch_DTX,
stats->ul.errors, stats->ul.errors,
sched_ctrl->ul_bler_stats.bler, sched_ctrl->ul_bler_stats.bler,
sched_ctrl->ul_bler_stats.mcs); sched_ctrl->ul_bler_stats.mcs);
output += snprintf(output, output += snprintf(output,
end - output, end - output,
"UE %04x: ulsch_total_bytes_scheduled %"PRIu64", ulsch_total_bytes_received %"PRIu64"\n", "UE %04x: ulsch_total_bytes_scheduled %"PRIu64", ulsch_total_bytes_received %"PRIu64"\n",
UE->rnti, UE->rnti,
stats->ulsch_total_bytes_scheduled, stats->ul.total_bytes); stats->ulsch_total_bytes_scheduled, stats->ul.total_bytes);
for (int lc_id = 0; lc_id < 63; lc_id++) { for (int lc_id = 0; lc_id < 63; lc_id++) {
if (stats->dl.lc_bytes[lc_id] > 0) if (stats->dl.lc_bytes[lc_id] > 0)
output += snprintf(output, output += snprintf(output,
+1 -35
View File
@@ -75,7 +75,6 @@
#define MAX_NUM_BWP 5 #define MAX_NUM_BWP 5
#define MAX_NUM_CORESET 12 #define MAX_NUM_CORESET 12
#define MAX_NUM_CCE 90 #define MAX_NUM_CCE 90
#define MAX_HARQ_ROUNDS 4
/*!\brief Maximum number of random access process */ /*!\brief Maximum number of random access process */
#define NR_NB_RA_PROC_MAX 4 #define NR_NB_RA_PROC_MAX 4
#define MAX_NUM_OF_SSB 64 #define MAX_NUM_OF_SSB 64
@@ -510,38 +509,6 @@ struct CSI_Report {
#define MAX_SR_BITLEN 8 #define MAX_SR_BITLEN 8
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;
/*! As per the spec 38.212 and table: 6.3.1.1.2-12 in a single UCI sequence we can have multiple CSI_report /*! As per the spec 38.212 and table: 6.3.1.1.2-12 in a single UCI sequence we can have multiple CSI_report
the number of CSI_report will depend on number of CSI resource sets that are configured in CSI-ResourceConfig RRC IE the number of CSI_report will depend on number of CSI resource sets that are configured in CSI-ResourceConfig RRC IE
From spec 38.331 from the IE CSI-ResourceConfig for SSB RSRP reporting we can configure only one resource set From spec 38.331 from the IE CSI-ResourceConfig for SSB RSRP reporting we can configure only one resource set
@@ -701,10 +668,10 @@ typedef struct NR_bler_options {
double upper; double upper;
double lower; double lower;
uint8_t max_mcs; uint8_t max_mcs;
uint8_t harq_round_max;
} NR_bler_options_t; } NR_bler_options_t;
/*! \brief UE list used by gNB to order UEs/CC for scheduling*/ /*! \brief UE list used by gNB to order UEs/CC for scheduling*/
#define MAX_CSI_REPORTCONFIG 48
typedef struct { typedef struct {
rnti_t rnti; rnti_t rnti;
/// scheduling control info /// scheduling control info
@@ -855,7 +822,6 @@ typedef struct gNB_MAC_INST_s {
bool first_MIB; bool first_MIB;
NR_bler_options_t dl_bler; NR_bler_options_t dl_bler;
NR_bler_options_t ul_bler; NR_bler_options_t ul_bler;
uint8_t harq_round_max;
uint8_t min_grant_prb; uint8_t min_grant_prb;
uint8_t min_grant_mcs; uint8_t min_grant_mcs;
} gNB_MAC_INST; } gNB_MAC_INST;
+13 -7
View File
@@ -27,6 +27,7 @@
#include "nr_pdcp_security_nea2.h" #include "nr_pdcp_security_nea2.h"
#include "nr_pdcp_integrity_nia2.h" #include "nr_pdcp_integrity_nia2.h"
#include "nr_pdcp_integrity_nia1.h"
#include "nr_pdcp_sdu.h" #include "nr_pdcp_sdu.h"
#include "LOG/log.h" #include "LOG/log.h"
@@ -240,16 +241,21 @@ static void nr_pdcp_entity_set_security(nr_pdcp_entity_t *entity,
} }
if (integrity_algorithm != 0 && integrity_algorithm != -1) { if (integrity_algorithm != 0 && integrity_algorithm != -1) {
if (integrity_algorithm != 2) {
LOG_E(PDCP, "FATAL: only nia2 supported for the moment\n");
exit(1);
}
entity->has_integrity = 1; entity->has_integrity = 1;
if (entity->free_integrity != NULL) if (entity->free_integrity != NULL)
entity->free_integrity(entity->integrity_context); entity->free_integrity(entity->integrity_context);
entity->integrity_context = nr_pdcp_integrity_nia2_init(entity->integrity_key); if (integrity_algorithm == 2) {
entity->integrity = nr_pdcp_integrity_nia2_integrity; entity->integrity_context = nr_pdcp_integrity_nia2_init(entity->integrity_key);
entity->free_integrity = nr_pdcp_integrity_nia2_free_integrity; entity->integrity = nr_pdcp_integrity_nia2_integrity;
entity->free_integrity = nr_pdcp_integrity_nia2_free_integrity;
} else if (integrity_algorithm == 1) {
entity->integrity_context = nr_pdcp_integrity_nia1_init(entity->integrity_key);
entity->integrity = nr_pdcp_integrity_nia1_integrity;
entity->free_integrity = nr_pdcp_integrity_nia1_free_integrity;
} else {
LOG_E(PDCP, "FATAL: only nia1 and nia2 supported for the moment\n");
exit(1);
}
} }
if (ciphering_algorithm == 0) { if (ciphering_algorithm == 0) {
@@ -0,0 +1,66 @@
/*
* 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
*/
#include "nr_pdcp_integrity_nia1.h"
#include <stdlib.h>
#include <string.h>
#include <stdint.h>
#include <openssl/cmac.h>
#include "UTIL/OSA/osa_defs.h"
int stream_compute_integrity_eia1(stream_cipher_t *stream_cipher, uint8_t out[4]);
void *nr_pdcp_integrity_nia1_init(unsigned char *integrity_key)
{
stream_cipher_t *ret;
ret = calloc(1, sizeof(*ret)); if (ret == NULL) abort();
ret->key = malloc(16); if (ret->key == NULL) abort();
memcpy(ret->key, integrity_key, 16);
ret->key_length = 16; /* unused */
return ret;
}
void nr_pdcp_integrity_nia1_integrity(void *integrity_context,
unsigned char *out,
unsigned char *buffer, int length,
int bearer, int count, int direction)
{
stream_cipher_t *ctx = integrity_context;
ctx->message = buffer;
ctx->count = count;
ctx->bearer = bearer-1;
ctx->direction = direction;
ctx->blength = length * 8;
stream_compute_integrity_eia1(ctx, out);
}
void nr_pdcp_integrity_nia1_free_integrity(void *integrity_context)
{
stream_cipher_t *ctx = integrity_context;
free(ctx->key);
free(ctx);
}
@@ -0,0 +1,34 @@
/*
* 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
*/
#ifndef _NR_PDCP_INTEGRITY_NIA1_H_
#define _NR_PDCP_INTEGRITY_NIA1_H_
void *nr_pdcp_integrity_nia1_init(unsigned char *integrity_key);
void nr_pdcp_integrity_nia1_integrity(void *integrity_context,
unsigned char *out,
unsigned char *buffer, int length,
int bearer, int count, int direction);
void nr_pdcp_integrity_nia1_free_integrity(void *integrity_context);
#endif /* _NR_PDCP_INTEGRITY_NIA1_H_ */
+11 -1
View File
@@ -1103,6 +1103,10 @@ int8_t handle_dlsch(nr_downlink_indication_t *dl_info, NR_UL_TIME_ALIGNMENT_t *u
return 0; return 0;
} }
int8_t handle_csirs_measurements(module_id_t module_id, frame_t frame, int slot, fapi_nr_csirs_measurements_t *csirs_measurements) {
return nr_ue_process_csirs_measurements(module_id, frame, slot, csirs_measurements);
}
void update_harq_status(module_id_t module_id, uint8_t harq_pid, uint8_t ack_nack) { void update_harq_status(module_id_t module_id, uint8_t harq_pid, uint8_t ack_nack) {
NR_UE_MAC_INST_t *mac = get_mac_inst(module_id); NR_UE_MAC_INST_t *mac = get_mac_inst(module_id);
@@ -1228,7 +1232,7 @@ int nr_ue_dl_indication(nr_downlink_indication_t *dl_info, NR_UL_TIME_ALIGNMENT_
(dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.ssb_length, (dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.ssb_length,
(dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.ssb_start_subcarrier, (dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.ssb_start_subcarrier,
(dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.cell_id)) << FAPI_NR_RX_PDU_TYPE_SSB; (dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.cell_id)) << FAPI_NR_RX_PDU_TYPE_SSB;
free((dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.pdu); free((dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.pdu);
break; break;
case FAPI_NR_RX_PDU_TYPE_SIB: case FAPI_NR_RX_PDU_TYPE_SIB:
ret_mask |= (handle_bcch_dlsch(dl_info->module_id, ret_mask |= (handle_bcch_dlsch(dl_info->module_id,
@@ -1243,6 +1247,12 @@ int nr_ue_dl_indication(nr_downlink_indication_t *dl_info, NR_UL_TIME_ALIGNMENT_
case FAPI_NR_RX_PDU_TYPE_RAR: case FAPI_NR_RX_PDU_TYPE_RAR:
ret_mask |= (handle_dlsch(dl_info, ul_time_alignment, i)) << FAPI_NR_RX_PDU_TYPE_RAR; ret_mask |= (handle_dlsch(dl_info, ul_time_alignment, i)) << FAPI_NR_RX_PDU_TYPE_RAR;
break; break;
case FAPI_NR_CSIRS_IND:
ret_mask |= (handle_csirs_measurements(dl_info->module_id,
dl_info->frame,
dl_info->slot,
&(dl_info->rx_ind->rx_indication_body+i)->csirs_measurements)) << FAPI_NR_CSIRS_IND;
break;
default: default:
break; break;
} }
+33 -91
View File
@@ -976,28 +976,24 @@ rrc_eNB_free_UE(
put_UE_in_freelist(enb_mod_idP, rnti, 1); put_UE_in_freelist(enb_mod_idP, rnti, 1);
} }
void remove_UE_from_freelist(module_id_t mod_id, rnti_t rnti) {
eNB_MAC_INST *eNB_MAC = RC.mac[mod_id];
pthread_mutex_lock(&lock_ue_freelist);
UE_free_list_t *free_list = &eNB_MAC->UE_free_list;
free_list->UE_free_ctrl[free_list->head_freelist].rnti = 0;
free_list->head_freelist = (free_list->head_freelist + 1) % (NUMBER_OF_UE_MAX+1);
free_list->num_UEs--;
pthread_mutex_unlock(&lock_ue_freelist);
}
void put_UE_in_freelist(module_id_t mod_id, rnti_t rnti, bool removeFlag) { void put_UE_in_freelist(module_id_t mod_id, rnti_t rnti, bool removeFlag) {
UE_free_list_t *free_list = NULL;
eNB_MAC_INST *eNB_MAC = RC.mac[mod_id]; eNB_MAC_INST *eNB_MAC = RC.mac[mod_id];
pthread_mutex_lock(&lock_ue_freelist); pthread_mutex_lock(&lock_ue_freelist);
free_list = &eNB_MAC->UE_free_list; LOG_I(PHY,"add ue %d in fre list, context flag: %d\n", rnti, removeFlag);
free_list->UE_free_ctrl[free_list->tail_freelist].rnti = rnti; int i;
free_list->UE_free_ctrl[free_list->tail_freelist].removeContextFlg = removeFlag; for (i=0; i < sizeofArray(eNB_MAC->UE_free_ctrl); i++)
free_list->UE_free_ctrl[free_list->tail_freelist].raFlag = 0; if (eNB_MAC->UE_free_ctrl[i].rnti == 0)
free_list->num_UEs++; break;
if (i==sizeofArray(eNB_MAC->UE_free_ctrl)) {
LOG_E(PHY,"List of UE to free is full\n");
pthread_mutex_unlock(&lock_ue_freelist);
return;
}
eNB_MAC->UE_free_ctrl[i].rnti = rnti;
eNB_MAC->UE_free_ctrl[i].removeContextFlg = removeFlag;
eNB_MAC->UE_free_ctrl[i].raFlag = 0;
eNB_MAC->UE_release_req.ue_release_request_body.ue_release_request_TLVs_list[eNB_MAC->UE_release_req.ue_release_request_body.number_of_TLVs].rnti = rnti; eNB_MAC->UE_release_req.ue_release_request_body.ue_release_request_TLVs_list[eNB_MAC->UE_release_req.ue_release_request_body.number_of_TLVs].rnti = rnti;
eNB_MAC->UE_release_req.ue_release_request_body.number_of_TLVs++; eNB_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); pthread_mutex_unlock(&lock_ue_freelist);
} }
@@ -1007,104 +1003,47 @@ extern void clean_eNb_ulsch(LTE_eNB_ULSCH_t *ulsch);
extern void clean_eNb_dlsch(LTE_eNB_DLSCH_t *dlsch); extern void clean_eNb_dlsch(LTE_eNB_DLSCH_t *dlsch);
void release_UE_in_freeList(module_id_t mod_id) { void release_UE_in_freeList(module_id_t mod_id) {
int i, j, CC_id, pdu_number;
protocol_ctxt_t ctxt;
nfapi_ul_config_request_body_t *ul_req_tmp = NULL;
PHY_VARS_eNB *eNB_PHY = NULL; PHY_VARS_eNB *eNB_PHY = NULL;
struct rrc_eNB_ue_context_s *ue_context_pP = NULL;
eNB_MAC_INST *eNB_MAC = RC.mac[mod_id]; eNB_MAC_INST *eNB_MAC = RC.mac[mod_id];
bool remove_UEContext;
rnti_t rnti;
int head, tail, ue_num;
pthread_mutex_lock(&lock_ue_freelist); pthread_mutex_lock(&lock_ue_freelist);
head = eNB_MAC->UE_free_list.head_freelist;
tail = eNB_MAC->UE_free_list.tail_freelist;
if(head == tail) { for(int ue_num = 0; ue_num < sizeofArray(eNB_MAC->UE_free_ctrl) ; ue_num++) {
pthread_mutex_unlock(&lock_ue_freelist); rnti_t rnti = eNB_MAC->UE_free_ctrl[ue_num].rnti;
return;
}
if(tail < head) {
tail = head + eNB_MAC->UE_free_list.num_UEs;
}
pthread_mutex_unlock(&lock_ue_freelist);
for(ue_num = head; ue_num < tail; ue_num++) {
ue_num = ue_num % (NUMBER_OF_UE_MAX+1);
rnti = eNB_MAC->UE_free_list.UE_free_ctrl[ue_num].rnti;
if(rnti != 0) { if(rnti != 0) {
remove_UEContext = eNB_MAC->UE_free_list.UE_free_ctrl[ue_num].removeContextFlg; protocol_ctxt_t ctxt;
PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt, mod_id, ENB_FLAG_YES, rnti, 0, 0,mod_id); PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt, mod_id, ENB_FLAG_YES, rnti, 0, 0,mod_id);
for (CC_id = 0; CC_id < MAX_NUM_CCs; CC_id++) { for (int CC_id = 0; CC_id < MAX_NUM_CCs; CC_id++) {
eNB_PHY = RC.eNB[mod_id][CC_id]; eNB_PHY = RC.eNB[mod_id][CC_id];
int id; int id;
// clean ULSCH entries for rnti // clean ULSCH entries for rnti
id = find_ulsch(rnti,eNB_PHY,eNB_MAC->UE_free_list.UE_free_ctrl[ue_num].raFlag ? SEARCH_EXIST_RA : SEARCH_EXIST); id = find_ulsch(rnti,eNB_PHY,eNB_MAC->UE_free_ctrl[ue_num].raFlag ? SEARCH_EXIST_RA : SEARCH_EXIST);
if (id>=0) clean_eNb_ulsch(eNB_PHY->ulsch[id]); if (id>=0) clean_eNb_ulsch(eNB_PHY->ulsch[id]);
// clean DLSCH entries for rnti // clean DLSCH entries for rnti
id = find_dlsch(rnti,eNB_PHY,eNB_MAC->UE_free_list.UE_free_ctrl[ue_num].raFlag ? SEARCH_EXIST_RA : SEARCH_EXIST); id = find_dlsch(rnti,eNB_PHY,eNB_MAC->UE_free_ctrl[ue_num].raFlag ? SEARCH_EXIST_RA : SEARCH_EXIST);
if (id>=0) clean_eNb_dlsch(eNB_PHY->dlsch[id][0]); if (id>=0) clean_eNb_dlsch(eNB_PHY->dlsch[id][0]);
// clean UCI entries for rnti // clean UCI entries for rnti
for (i=0; i<NUMBER_OF_UCI_MAX; i++) { for (int i=0; i<NUMBER_OF_UCI_MAX; i++) {
if(eNB_PHY->uci_vars[i].rnti == rnti) { if(eNB_PHY->uci_vars[i].rnti == rnti) {
LOG_I(MAC, "clean eNb uci_vars[%d] UE %x \n",i, rnti); LOG_I(MAC, "clean eNb uci_vars[%d] UE %x \n",i, rnti);
memset(&eNB_PHY->uci_vars[i],0,sizeof(LTE_eNB_UCI)); memset(&eNB_PHY->uci_vars[i],0,sizeof(LTE_eNB_UCI));
} }
} }
/*
for (i=0; i<MAX_MOBILES_PER_ENB; i++) {
ulsch = eNB_PHY->ulsch[i];
if((ulsch != NULL) && (ulsch->rnti == rnti)) {
void clean_eNb_ulsch(LTE_eNB_ULSCH_t *ulsch);
LOG_I(RRC, "clean_eNb_ulsch ulsch[%d] UE %x\n", i, rnti);
clean_eNb_ulsch(ulsch);
}
dlsch = eNB_PHY->dlsch[i][0];
if((dlsch != NULL) && (dlsch->rnti == rnti)) {
void clean_eNb_dlsch(LTE_eNB_DLSCH_t *dlsch);
LOG_I(RRC, "clean_eNb_dlsch dlsch[%d] UE %x \n", i, rnti);
clean_eNb_dlsch(dlsch);
}
}
ulsch = eNB_PHY->ulsch[i];
if((ulsch != NULL) && (ulsch->rnti == rnti)) {
void clean_eNb_ulsch(LTE_eNB_ULSCH_t *ulsch);
LOG_I(RRC, "clean_eNb_ulsch ulsch[%d] UE %x\n", i, rnti);
clean_eNb_ulsch(ulsch);
}
for (i=0; i<NUMBER_OF_UCI_MAX; i++) {
if(eNB_PHY->uci_vars[i].rnti == rnti) {
LOG_I(MAC, "clean eNb uci_vars[%d] UE %x \n",i, rnti);
memset(&eNB_PHY->uci_vars[i],0,sizeof(LTE_eNB_UCI));
}
}
*/
if (flexran_agent_get_rrc_xface(mod_id)) { if (flexran_agent_get_rrc_xface(mod_id)) {
flexran_agent_get_rrc_xface(mod_id)->flexran_agent_notify_ue_state_change( flexran_agent_get_rrc_xface(mod_id)->flexran_agent_notify_ue_state_change( mod_id, rnti, PROTOCOL__FLEX_UE_STATE_CHANGE_TYPE__FLUESC_DEACTIVATED);
mod_id, rnti, PROTOCOL__FLEX_UE_STATE_CHANGE_TYPE__FLUESC_DEACTIVATED);
} }
for(j = 0; j < 10; j++) { for(int j = 0; j < 10; j++) {
ul_req_tmp = &eNB_MAC->UL_req_tmp[CC_id][j].ul_config_request_body; nfapi_ul_config_request_body_t *ul_req_tmp = &eNB_MAC->UL_req_tmp[CC_id][j].ul_config_request_body;
if(ul_req_tmp) { if(ul_req_tmp) {
pdu_number = ul_req_tmp->number_of_pdus; int pdu_number = ul_req_tmp->number_of_pdus;
for(int pdu_index = pdu_number-1; pdu_index >= 0; pdu_index--) { for(int pdu_index = pdu_number-1; pdu_index >= 0; pdu_index--) {
if((ul_req_tmp->ul_config_pdu_list[pdu_index].ulsch_pdu.ulsch_pdu_rel8.rnti == rnti) || if((ul_req_tmp->ul_config_pdu_list[pdu_index].ulsch_pdu.ulsch_pdu_rel8.rnti == rnti) ||
@@ -1126,7 +1065,8 @@ void release_UE_in_freeList(module_id_t mod_id) {
} }
if (!NODE_IS_CU(RC.rrc[mod_id]->node_type)) { if (!NODE_IS_CU(RC.rrc[mod_id]->node_type)) {
rrc_mac_remove_ue(mod_id,rnti); if (!eNB_MAC->UE_free_ctrl[ue_num].raFlag)
rrc_mac_remove_ue(mod_id,rnti);
rrc_rlc_remove_ue(&ctxt); rrc_rlc_remove_ue(&ctxt);
pdcp_remove_UE(&ctxt); pdcp_remove_UE(&ctxt);
} else { } else {
@@ -1139,19 +1079,20 @@ void release_UE_in_freeList(module_id_t mod_id) {
itti_send_msg_to_task(TASK_CU_F1, mod_id, m); itti_send_msg_to_task(TASK_CU_F1, mod_id, m);
} }
if(remove_UEContext) { if(eNB_MAC->UE_free_ctrl[ue_num].removeContextFlg) {
ue_context_pP = rrc_eNB_get_ue_context(RC.rrc[mod_id],rnti); struct rrc_eNB_ue_context_s *ue_context_pP = rrc_eNB_get_ue_context(RC.rrc[mod_id],rnti);
if(ue_context_pP) { if(ue_context_pP) {
LOG_I(PHY, "remove RNTI %04x\n", rnti);
rrc_eNB_remove_ue_context(&ctxt,RC.rrc[mod_id], rrc_eNB_remove_ue_context(&ctxt,RC.rrc[mod_id],
(struct rrc_eNB_ue_context_s *) ue_context_pP); (struct rrc_eNB_ue_context_s *) ue_context_pP);
} }
} }
LOG_I(RRC, "[release_UE_in_freeList] remove UE %x from freeList\n", rnti); LOG_I(RRC, "[release_UE_in_freeList] remove UE %x from freeList ra context: %d\n", rnti, eNB_MAC->UE_free_ctrl[ue_num].raFlag);
remove_UE_from_freelist(mod_id, rnti); eNB_MAC->UE_free_ctrl[ue_num].rnti = 0;
} }
} }
pthread_mutex_unlock(&lock_ue_freelist);
} }
int rrc_eNB_previous_SRB2(rrc_eNB_ue_context_t *ue_context_pP) { int rrc_eNB_previous_SRB2(rrc_eNB_ue_context_t *ue_context_pP) {
@@ -7246,6 +7187,7 @@ rrc_eNB_decode_ccch(
LOG_I(RRC," S-TMSI exists, ue_context_p %p, old rnti %x => %x\n",ue_context_p,ue_context_p->ue_context.rnti,ctxt_pP->rnti); LOG_I(RRC," S-TMSI exists, ue_context_p %p, old rnti %x => %x\n",ue_context_p,ue_context_p->ue_context.rnti,ctxt_pP->rnti);
if (!NODE_IS_CU(RC.rrc[ctxt_pP->module_id]->node_type)) { if (!NODE_IS_CU(RC.rrc[ctxt_pP->module_id]->node_type)) {
LOG_I(PHY, "remove RNTI %04x\n", ue_context_p->ue_context.rnti);
rrc_mac_remove_ue(ctxt_pP->module_id, ue_context_p->ue_context.rnti); rrc_mac_remove_ue(ctxt_pP->module_id, ue_context_p->ue_context.rnti);
} else { } else {
MessageDef *m = itti_alloc_new_message(TASK_RRC_ENB, 0, F1AP_UE_CONTEXT_RELEASE_CMD); MessageDef *m = itti_alloc_new_message(TASK_RRC_ENB, 0, F1AP_UE_CONTEXT_RELEASE_CMD);

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