Commit 92e6b5e5 authored by Robert Schmidt's avatar Robert Schmidt

Merge branch 'integration_2022_wk46' into 'develop'

integration_2022_wk46

See merge request oai/openairinterface5g!1822

!1782 NR UE improve RA procedures (pt.1)
!1801 fix in NR PUCCH scheduler when the list is larger than a frame
!1802 workaround issue of N310 with UHD >= 4.2.0 when changing the BW
!1804 Fix for NR MSG4 scheduler
!1805 Pucch2 hotfix
!1808 fix NFAPI_MAX_NUM_UL_PDU according to SCF specifications
!1810 F1 fixes for interoperability with Accelleran CU
!1786 removing PRB at DC to avoid wrong noise level computation for PUSCH
!1813 Fix broken multiple DRBs
!1816 NR ULSCH/DLSCH scheduler fixes
!1660 Add SA test with COTS UE and F1 split
!1795 feat(ci): transition the Slack notification from old pipeline to container-based pipeline
parents 0cacf29d 3da7dafd
...@@ -2021,7 +2021,6 @@ set (MAC_NR_SRC_UE ...@@ -2021,7 +2021,6 @@ set (MAC_NR_SRC_UE
${NR_UE_MAC_DIR}/nr_ue_procedures.c ${NR_UE_MAC_DIR}/nr_ue_procedures.c
${NR_UE_MAC_DIR}/nr_ue_scheduler.c ${NR_UE_MAC_DIR}/nr_ue_scheduler.c
${NR_UE_MAC_DIR}/nr_ue_dci_configuration.c ${NR_UE_MAC_DIR}/nr_ue_dci_configuration.c
${NR_UE_MAC_DIR}/nr_l1_helpers.c
${NR_UE_MAC_DIR}/nr_ra_procedures.c ${NR_UE_MAC_DIR}/nr_ra_procedures.c
) )
......
...@@ -449,6 +449,10 @@ pipeline { ...@@ -449,6 +449,10 @@ pipeline {
def message = "OAI " + JOB_NAME + " build (" + BUILD_ID + "): passed (" + BUILD_URL + ")" def message = "OAI " + JOB_NAME + " build (" + BUILD_ID + "): passed (" + BUILD_URL + ")"
if ("MERGE".equals(env.gitlabActionType)) { if ("MERGE".equals(env.gitlabActionType)) {
addGitLabMRComment comment: message addGitLabMRComment comment: message
def message2 = message + " -- MergeRequest #" + env.gitlabMergeRequestIid + " (" + env.gitlabMergeRequestTitle + ")"
sendSocialMediaMessage('ci-enb', 'good', message2)
} else {
sendSocialMediaMessage('ci-enb', 'good', message)
} }
echo "Pipeline is SUCCESSFUL" echo "Pipeline is SUCCESSFUL"
} }
...@@ -458,6 +462,10 @@ pipeline { ...@@ -458,6 +462,10 @@ pipeline {
def message = "OAI " + JOB_NAME + " build (" + BUILD_ID + "): failed (" + BUILD_URL + ")" def message = "OAI " + JOB_NAME + " build (" + BUILD_ID + "): failed (" + BUILD_URL + ")"
if ("MERGE".equals(env.gitlabActionType)) { if ("MERGE".equals(env.gitlabActionType)) {
addGitLabMRComment comment: message addGitLabMRComment comment: message
def message2 = message + " -- MergeRequest #" + env.gitlabMergeRequestIid + " (" + env.gitlabMergeRequestTitle + ")"
sendSocialMediaMessage('ci-enb', 'danger', message2)
} else {
sendSocialMediaMessage('ci-enb', 'danger', message)
} }
echo "Pipeline FAILED" echo "Pipeline FAILED"
} }
...@@ -541,3 +549,9 @@ def finalizeSlaveJob(jobName) { ...@@ -541,3 +549,9 @@ def finalizeSlaveJob(jobName) {
} }
} }
} }
// Abstraction function to send social media messages:
// like on Slack or Mattermost
def sendSocialMediaMessage(pipeChannel, pipeColor, pipeMessage) {
slackSend channel: pipeChannel, color: pipeColor, message: pipeMessage
}
...@@ -20,16 +20,6 @@ ...@@ -20,16 +20,6 @@
* contact@openairinterface.org * contact@openairinterface.org
*/ */
// Abstraction function to send social media messages:
// like on Slack or Mattermost
def sendSocialMediaMessage(pipeChannel, pipeColor, pipeMessage) {
if (params.pipelineUsesSlack != null) {
if (params.pipelineUsesSlack) {
slackSend channel: pipeChannel, color: pipeColor, message: pipeMessage
}
}
}
// Location of the executor node // Location of the executor node
def nodeExecutor = params.nodeExecutor def nodeExecutor = params.nodeExecutor
...@@ -389,10 +379,6 @@ OAI CI Team''', ...@@ -389,10 +379,6 @@ OAI CI Team''',
if ("MERGE".equals(env.gitlabActionType)) { if ("MERGE".equals(env.gitlabActionType)) {
echo "This is a MERGE event" echo "This is a MERGE event"
addGitLabMRComment comment: message addGitLabMRComment comment: message
def message2 = "OAI " + JOB_NAME + " build (" + BUILD_ID + "): passed (" + BUILD_URL + ") -- MergeRequest #" + env.gitlabMergeRequestIid + " (" + env.gitlabMergeRequestTitle + ")"
sendSocialMediaMessage('ci-enb', 'good', message2)
} else {
sendSocialMediaMessage('ci-enb', 'good', message)
} }
} }
} }
...@@ -402,10 +388,6 @@ OAI CI Team''', ...@@ -402,10 +388,6 @@ OAI CI Team''',
if ("MERGE".equals(env.gitlabActionType)) { if ("MERGE".equals(env.gitlabActionType)) {
echo "This is a MERGE event" echo "This is a MERGE event"
addGitLabMRComment comment: message addGitLabMRComment comment: message
def message2 = "OAI " + JOB_NAME + " build (" + BUILD_ID + "): failed (" + BUILD_URL + ") -- MergeRequest #" + env.gitlabMergeRequestIid + " (" + env.gitlabMergeRequestTitle + ")"
sendSocialMediaMessage('ci-enb', 'danger', message2)
} else {
sendSocialMediaMessage('ci-enb', 'danger', message)
} }
} }
} }
......
...@@ -65,13 +65,20 @@ pipeline { ...@@ -65,13 +65,20 @@ pipeline {
WEEK_REF = WEEK_REF.trim() WEEK_REF = WEEK_REF.trim()
WEEK_TAG = sh returnStdout: true, script: 'python3 ./ci-scripts/provideUniqueImageTag.py --start_tag ' + WEEK_REF WEEK_TAG = sh returnStdout: true, script: 'python3 ./ci-scripts/provideUniqueImageTag.py --start_tag ' + WEEK_REF
WEEK_TAG = WEEK_TAG.trim() WEEK_TAG = WEEK_TAG.trim()
if ((params.forceTag != null) && (params.tagToUse != null)) {
if (params.forceTag) {
WEEK_TAG = params.tagToUse
echo "Forced Tag is ${WEEK_TAG}"
}
}
WEEK_SHA = sh returnStdout: true, script: 'git log -n1 --pretty=format:"%h" origin/develop | cut -c 1-8' WEEK_SHA = sh returnStdout: true, script: 'git log -n1 --pretty=format:"%h" origin/develop | cut -c 1-8'
WEEK_SHA = WEEK_SHA.trim() WEEK_SHA = WEEK_SHA.trim()
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", "proxy"] def listOfImages = ["oai-enb", "oai-gnb", "oai-lte-ue", "oai-nr-ue"]
// Logging in on both registries
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"
sh "docker login -u oaicicd -p oaicicd porcepix.sboai.cs.eurecom.fr > /dev/null 2>&1" sh "docker login -u oaicicd -p oaicicd porcepix.sboai.cs.eurecom.fr > /dev/null 2>&1"
listOfImages.eachWithIndex { item, iindex -> listOfImages.eachWithIndex { item, iindex ->
...@@ -82,6 +89,13 @@ pipeline { ...@@ -82,6 +89,13 @@ pipeline {
sh "docker push --quiet ${DH_Account}/${item}:develop" sh "docker push --quiet ${DH_Account}/${item}:develop"
sh "docker rmi ${DH_Account}/${item}:${WEEK_TAG} ${DH_Account}/${item}:develop porcepix.sboai.cs.eurecom.fr/${item}:develop-${WEEK_SHA}" sh "docker rmi ${DH_Account}/${item}:${WEEK_TAG} ${DH_Account}/${item}:develop porcepix.sboai.cs.eurecom.fr/${item}:develop-${WEEK_SHA}"
} }
// Proxy is not following the same pattern.
sh "docker image tag proxy:develop ${DH_Account}/proxy:develop"
sh "docker image tag proxy:develop ${DH_Account}/proxy:${WEEK_TAG}"
sh "docker push --quiet ${DH_Account}/proxy:develop"
sh "docker push --quiet ${DH_Account}/proxy:${WEEK_TAG}"
sh "docker rmi ${DH_Account}/proxy:develop ${DH_Account}/proxy:${WEEK_TAG}"
// Logging out on both registries
sh "docker logout porcepix.sboai.cs.eurecom.fr > /dev/null 2>&1" sh "docker logout porcepix.sboai.cs.eurecom.fr > /dev/null 2>&1"
sh "docker logout > /dev/null 2>&1" sh "docker logout > /dev/null 2>&1"
} }
......
...@@ -773,22 +773,19 @@ class Containerize(): ...@@ -773,22 +773,19 @@ class Containerize():
mySSH.command(f'sed -i -e "s#image: {image}:latest#image: {imageToUse}#" ci-docker-compose.yml', '\$', 2) mySSH.command(f'sed -i -e "s#image: {image}:latest#image: {imageToUse}#" ci-docker-compose.yml', '\$', 2)
localMmeIpAddr = EPC.MmeIPAddress localMmeIpAddr = EPC.MmeIPAddress
mySSH.command('sed -i -e "s/CI_MME_IP_ADDR/' + localMmeIpAddr + '/" ci-docker-compose.yml', '\$', 2) mySSH.command('sed -i -e "s/CI_MME_IP_ADDR/' + localMmeIpAddr + '/" ci-docker-compose.yml', '\$', 2)
# if self.flexranCtrlDeployed:
# mySSH.command('sed -i -e "s/FLEXRAN_ENABLED:.*/FLEXRAN_ENABLED: \'yes\'/" ci-docker-compose.yml', '\$', 2)
# mySSH.command('sed -i -e "s/CI_FLEXRAN_CTL_IP_ADDR/' + self.flexranCtrlIpAddress + '/" ci-docker-compose.yml', '\$', 2)
# else:
# mySSH.command('sed -i -e "s/FLEXRAN_ENABLED:.*$/FLEXRAN_ENABLED: \'no\'/" ci-docker-compose.yml', '\$', 2)
# mySSH.command('sed -i -e "s/CI_FLEXRAN_CTL_IP_ADDR/127.0.0.1/" ci-docker-compose.yml', '\$', 2)
# Currently support only one # Currently support only one
mySSH.command('echo ' + lPassWord + ' | sudo -S b2xx_fx3_utils --reset-device', '\$', 15) mySSH.command('echo ' + lPassWord + ' | sudo -S b2xx_fx3_utils --reset-device', '\$', 15)
mySSH.command('docker-compose --file ci-docker-compose.yml config --services | sed -e "s@^@service=@" 2>&1', '\$', 10) svcName = self.services[self.eNB_instance]
result = re.search('service=(?P<svc_name>[a-zA-Z0-9\_]+)', mySSH.getBefore()) if svcName == '':
if result is not None: logging.warning('no service name given: starting all services in ci-docker-compose.yml!')
svcName = result.group('svc_name')
mySSH.command('docker-compose --file ci-docker-compose.yml up -d ' + svcName, '\$', 15) mySSH.command(f'docker-compose --file ci-docker-compose.yml up -d -- {svcName}', '\$', 30)
# Checking Status # Checking Status
mySSH.command('docker-compose --file ci-docker-compose.yml config', '\$', 5) grep = ''
if svcName != '': grep = f' | grep -A3 {svcName}'
mySSH.command(f'docker-compose --file ci-docker-compose.yml config {grep}', '\$', 5)
result = re.search('container_name: (?P<container_name>[a-zA-Z0-9\-\_]+)', mySSH.getBefore()) result = re.search('container_name: (?P<container_name>[a-zA-Z0-9\-\_]+)', mySSH.getBefore())
unhealthyNb = 0 unhealthyNb = 0
healthyNb = 0 healthyNb = 0
...@@ -848,8 +845,8 @@ class Containerize(): ...@@ -848,8 +845,8 @@ class Containerize():
else: else:
# containers are unhealthy, so we won't start. However, logs are stored at the end # containers are unhealthy, so we won't start. However, logs are stored at the end
# in UndeployObject so we here store the logs of the unhealthy container to report it # in UndeployObject so we here store the logs of the unhealthy container to report it
logfilename = f'{lSourcePath}/cmake_targets/{self.eNB_logFile[self.eNB_instance]}' logfilename = f'{lSourcePath}/cmake_targets/log/{self.eNB_logFile[self.eNB_instance]}'
mySSH.command('docker logs {containerName} > {logfilename}', '\$', 30) mySSH.command(f'docker logs {containerName} > {logfilename}', '\$', 30)
mySSH.copyin(lIpAddr, lUserName, lPassWord, logfilename, '.') mySSH.copyin(lIpAddr, lUserName, lPassWord, logfilename, '.')
mySSH.close() mySSH.close()
...@@ -896,58 +893,67 @@ class Containerize(): ...@@ -896,58 +893,67 @@ class Containerize():
mySSH = SSH.SSHConnection() mySSH = SSH.SSHConnection()
mySSH.open(lIpAddr, lUserName, lPassWord) mySSH.open(lIpAddr, lUserName, lPassWord)
mySSH.command('cd ' + lSourcePath + '/' + self.yamlPath[self.eNB_instance], '\$', 5) mySSH.command('cd ' + lSourcePath + '/' + self.yamlPath[self.eNB_instance], '\$', 5)
# Currently support only one
mySSH.command('docker-compose --file ci-docker-compose.yml config', '\$', 5) svcName = self.services[self.eNB_instance]
containerName = '' forceDown = False
containerToKill = False if svcName != '':
result = re.search('container_name: (?P<container_name>[a-zA-Z0-9\-\_]+)', mySSH.getBefore()) logging.warning(f'service name given, but will stop all services in ci-docker-compose.yml!')
if self.eNB_logFile[self.eNB_instance] == '': svcName = ''
self.eNB_logFile[self.eNB_instance] = 'enb_' + HTML.testCase_id + '.log'
if result is not None: mySSH.command(f'docker-compose -f ci-docker-compose.yml config --services', '\$', 5)
containerName = result.group('container_name') # first line has command, last line has next command prompt
containerToKill = True allServices = mySSH.getBefore().split('\r\n')[1:-1]
if containerToKill: services = []
mySSH.command('docker inspect ' + containerName, '\$', 30) for s in allServices:
result = re.search('Error: No such object: ' + containerName, mySSH.getBefore()) mySSH.command(f'docker-compose -f ci-docker-compose.yml ps --all -- {s}', '\$', 5, silent=False)
if result is not None: running = mySSH.getBefore().split('\r\n')[3:-1]
containerToKill = False #logging.debug(f'running services: {running}')
if containerToKill: if len(running) > 0: # something is running for that service
mySSH.command('docker kill --signal INT ' + containerName, '\$', 30) services.append(s)
time.sleep(5) logging.info(f'stopping services {services}')
mySSH.command('docker kill --signal KILL ' + containerName, '\$', 30)
time.sleep(5) mySSH.command(f'docker-compose -f ci-docker-compose.yml stop', '\$', 30)
mySSH.command('docker logs ' + containerName + ' > ' + lSourcePath + '/cmake_targets/' + self.eNB_logFile[self.eNB_instance], '\$', 30) time.sleep(5) # give some time to running containers to stop
mySSH.command('docker rm -f ' + containerName, '\$', 30) for svcName in services:
# Forcing the down now to remove the networks and any artifacts # head -n -1 suppresses the final "X exited with status code Y"
mySSH.command('docker-compose --file ci-docker-compose.yml down', '\$', 5) filename = f'{svcName}-{HTML.testCase_id}.log'
#mySSH.command(f'docker-compose -f ci-docker-compose.yml logs --no-log-prefix -- {svcName} | head -n -1 &> {lSourcePath}/cmake_targets/log/{filename}', '\$', 30)
mySSH.command(f'docker-compose -f ci-docker-compose.yml logs --no-log-prefix -- {svcName} &> {lSourcePath}/cmake_targets/log/{filename}', '\$', 30)
mySSH.command('docker-compose -f ci-docker-compose.yml down', '\$', 5)
# Cleaning any created tmp volume # Cleaning any created tmp volume
mySSH.command('docker volume prune --force || true', '\$', 20) mySSH.command('docker volume prune --force', '\$', 20)
mySSH.close() mySSH.close()
# Analyzing log file! # Analyzing log file!
if containerToKill: files = ','.join([f'{s}-{HTML.testCase_id}' for s in services])
copyin_res = mySSH.copyin(lIpAddr, lUserName, lPassWord, lSourcePath + '/cmake_targets/' + self.eNB_logFile[self.eNB_instance], '.') if len(services) > 1:
else: files = '{' + files + '}'
copyin_res = 0 copyin_res = 0
nodeB_prefix = 'e' if len(services) > 0:
if (copyin_res == -1): copyin_res = mySSH.copyin(lIpAddr, lUserName, lPassWord, f'{lSourcePath}/cmake_targets/log/{files}.log', '.')
HTML.htmleNBFailureMsg='Could not copy ' + nodeB_prefix + 'NB logfile to analyze it!' if copyin_res == -1:
HTML.htmleNBFailureMsg='Could not copy logfile to analyze it!'
HTML.CreateHtmlTestRow('N/A', 'KO', CONST.ENB_PROCESS_NOLOGFILE_TO_ANALYZE) HTML.CreateHtmlTestRow('N/A', 'KO', CONST.ENB_PROCESS_NOLOGFILE_TO_ANALYZE)
self.exitStatus = 1
else: else:
if containerToKill: for svcName in services:
logging.debug('\u001B[1m Analyzing ' + nodeB_prefix + 'NB logfile \u001B[0m ' + self.eNB_logFile[self.eNB_instance]) filename = f'{svcName}-{HTML.testCase_id}.log'
logStatus = RAN.AnalyzeLogFile_eNB(self.eNB_logFile[self.eNB_instance], HTML, self.ran_checkers) logging.debug(f'\u001B[1m Analyzing logfile {filename}\u001B[0m')
else: logStatus = RAN.AnalyzeLogFile_eNB(filename, HTML, self.ran_checkers)
logStatus = 0 if (logStatus < 0):
if (logStatus < 0): HTML.CreateHtmlTestRow(RAN.runtime_stats, 'KO', logStatus)
HTML.CreateHtmlTestRow(RAN.runtime_stats, 'KO', logStatus) self.exitStatus = 1
else: else:
HTML.CreateHtmlTestRow(RAN.runtime_stats, 'OK', CONST.ALL_PROCESSES_OK) HTML.CreateHtmlTestRow(RAN.runtime_stats, 'OK', CONST.ALL_PROCESSES_OK)
# all the xNB run logs shall be on the server 0 for logCollecting # all the xNB run logs shall be on the server 0 for logCollecting
if containerToKill and self.eNB_serverId[self.eNB_instance] != '0': if self.eNB_serverId[self.eNB_instance] != '0':
mySSH.copyout(self.eNBIPAddress, self.eNBUserName, self.eNBPassword, './' + self.eNB_logFile[self.eNB_instance], self.eNBSourceCodePath + '/cmake_targets/') mySSH.copyout(self.eNBIPAddress, self.eNBUserName, self.eNBPassword, f'./{files}.log', f'{self.eNBSourceCodePath}/cmake_targets/')
logging.info('\u001B[1m Undeploying OAI Object Pass\u001B[0m') if self.exitStatus == 0:
logging.info('\u001B[1m Undeploying OAI Object Pass\u001B[0m')
else:
logging.error('\u001B[1m Undeploying OAI Object Failed\u001B[0m')
def DeployGenObject(self, HTML, RAN, UE): def DeployGenObject(self, HTML, RAN, UE):
self.exitStatus = 0 self.exitStatus = 0
......
...@@ -19,6 +19,7 @@ gNBs = ...@@ -19,6 +19,7 @@ gNBs =
nr_cellid = 12345678L; nr_cellid = 12345678L;
force_256qam_off = 1;
tr_s_preference = "f1"; tr_s_preference = "f1";
......
...@@ -22,6 +22,7 @@ gNBs = ...@@ -22,6 +22,7 @@ gNBs =
////////// Physical parameters: ////////// Physical parameters:
min_rxtxtime = 6; min_rxtxtime = 6;
force_256qam_off = 1;
pdcch_ConfigSIB1 = ( pdcch_ConfigSIB1 = (
{ {
...@@ -57,7 +58,7 @@ gNBs = ...@@ -57,7 +58,7 @@ gNBs =
# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120 # 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
initialDLBWPsubcarrierSpacing = 1; initialDLBWPsubcarrierSpacing = 1;
#pdcch-ConfigCommon #pdcch-ConfigCommon
initialDLBWPcontrolResourceSetZero = 11; initialDLBWPcontrolResourceSetZero = 12;
initialDLBWPsearchSpaceZero = 0; initialDLBWPsearchSpaceZero = 0;
#uplinkConfigCommon #uplinkConfigCommon
...@@ -181,7 +182,8 @@ MACRLCs = ( ...@@ -181,7 +182,8 @@ MACRLCs = (
local_n_portd = 2152; local_n_portd = 2152;
remote_n_portc = 501; remote_n_portc = 501;
remote_n_portd = 2152; remote_n_portd = 2152;
pusch_TargetSNRx10 = 200;
pucch_TargetSNRx10 = 200;
} }
); );
......
...@@ -17,9 +17,8 @@ gNBs = ...@@ -17,9 +17,8 @@ gNBs =
////////// Physical parameters: ////////// Physical parameters:
min_rxtxtime = 2; do_CSIRS = 0;
do_CSIRS = 1; do_SRS = 0;
do_SRS = 1;
pdcch_ConfigSIB1 = ( pdcch_ConfigSIB1 = (
{ {
...@@ -36,21 +35,21 @@ gNBs = ...@@ -36,21 +35,21 @@ gNBs =
# downlinkConfigCommon # downlinkConfigCommon
#frequencyInfoDL #frequencyInfoDL
# this is 3600 MHz + 43 PRBs@30kHz SCS (same as initial BWP) # this is 3300.30 MHz + (19 PRBs + 10 SCs)@30kHz SCS (GSCN: 7715)
absoluteFrequencySSB = 641280; absoluteFrequencySSB = 620736;
dl_frequencyBand = 78; dl_frequencyBand = 78;
# this is 3600 MHz # this is 3300.30 MHz
dl_absoluteFrequencyPointA = 640008; dl_absoluteFrequencyPointA = 620020;
#scs-SpecificCarrierList #scs-SpecificCarrierList
dl_offstToCarrier = 0; dl_offstToCarrier = 0;
# subcarrierSpacing # subcarrierSpacing
# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120 # 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
dl_subcarrierSpacing = 1; dl_subcarrierSpacing = 1;
dl_carrierBandwidth = 106; dl_carrierBandwidth = 51;
#initialDownlinkBWP #initialDownlinkBWP
#genericParameters #genericParameters
# this is RBstart=27,L=48 (275*(L-1))+RBstart # this is RBstart=27,L=48 (275*(L-1))+RBstart
initialDLBWPlocationAndBandwidth = 28875; # 6366 12925 12956 28875 12952 initialDLBWPlocationAndBandwidth = 13750;
# subcarrierSpacing # subcarrierSpacing
# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120 # 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
initialDLBWPsubcarrierSpacing = 1; initialDLBWPsubcarrierSpacing = 1;
...@@ -66,11 +65,11 @@ gNBs = ...@@ -66,11 +65,11 @@ gNBs =
# subcarrierSpacing # subcarrierSpacing
# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120 # 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
ul_subcarrierSpacing = 1; ul_subcarrierSpacing = 1;
ul_carrierBandwidth = 106; ul_carrierBandwidth = 51;
pMax = 20; pMax = 20;
#initialUplinkBWP #initialUplinkBWP
#genericParameters #genericParameters
initialULBWPlocationAndBandwidth = 28875; initialULBWPlocationAndBandwidth = 13750;
# subcarrierSpacing # subcarrierSpacing
# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120 # 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
initialULBWPsubcarrierSpacing = 1; initialULBWPsubcarrierSpacing = 1;
...@@ -156,65 +155,6 @@ gNBs = ...@@ -156,65 +155,6 @@ gNBs =
); );
# Dedicated Serving Cell Configuration
servingCellConfigDedicated = ({
# BWP-Downlink
# BWP 1 Configuration
dl_bwp-Id_1 = 1;
dl_bwp1_locationAndBandwidth = 28875; // RBstart=0, L=106 (40 MHz BW)
# subcarrierSpacing
# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
dl_bwp1_subcarrierSpacing = 1;
# BWP 2 Configuration
dl_bwp-Id_2 = 2;
dl_bwp2_locationAndBandwidth = 13750; // RBstart=0, L=51 (20 MHz BW)
# subcarrierSpacing
# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
dl_bwp2_subcarrierSpacing = 1;
# BWP 3 Configuration
dl_bwp-Id_3 = 3;
dl_bwp3_locationAndBandwidth = 6325; // RBstart=0, L=24 (10 MHz BW)
# subcarrierSpacing
# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
dl_bwp3_subcarrierSpacing = 1;
firstActiveDownlinkBWP-Id = 1; #BWP-Id
defaultDownlinkBWP-Id = 1; #BWP-Id
# bwp-InactivityTimer ENUMERATED {ms2, ms3, ms4, ms5, ms6, ms8, ms10, ms20, ms30,
# ms40,ms50, ms60, ms80,ms100, ms200,ms300, ms500,
# ms750, ms1280, ms1920, ms2560, spare10, spare9, spare8,
# spare7, spare6, spare5, spare4, spare3, spare2, spare1 }
# UplinkConfig
# BWP-Uplink
# BWP 1 Configuration
ul_bwp-Id_1 = 1;
ul_bwp1_locationAndBandwidth = 28875; // RBstart=0, L=106 (40 MHz BW)
# subcarrierSpacing
# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
ul_bwp1_subcarrierSpacing = 1;
# BWP 2 Configuration
ul_bwp-Id_2 = 2;
ul_bwp2_locationAndBandwidth = 13750; // RBstart=0, L=51 (20 MHz BW)
# subcarrierSpacing
# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
ul_bwp2_subcarrierSpacing = 1;
# BWP 3 Configuration
ul_bwp-Id_3 = 3;
ul_bwp3_locationAndBandwidth = 6325; // RBstart=0, L=24 (10 MHz BW)
# subcarrierSpacing
# 0=kHz15, 1=kHz30, 2=kHz60, 3=kHz120
ul_bwp3_subcarrierSpacing = 1;
firstActiveUplinkBWP-Id = 1; #BWP-Id
}
);
# ------- SCTP definitions # ------- SCTP definitions
SCTP : SCTP :
{ {
...@@ -252,6 +192,7 @@ MACRLCs = ( ...@@ -252,6 +192,7 @@ MACRLCs = (
tr_n_preference = "local_RRC"; tr_n_preference = "local_RRC";
pusch_TargetSNRx10 = 200; pusch_TargetSNRx10 = 200;
pucch_TargetSNRx10 = 200; pucch_TargetSNRx10 = 200;
ul_prbblack_SNR_threshold = 10;
ulsch_max_frame_inactivity = 0; ulsch_max_frame_inactivity = 0;
} }
); );
...@@ -271,8 +212,8 @@ RUs = ( ...@@ -271,8 +212,8 @@ RUs = (
local_rf = "yes" local_rf = "yes"
nb_tx = 1 nb_tx = 1
nb_rx = 1 nb_rx = 1
att_tx = 10; att_tx = 14;
att_rx = 10; att_rx = 14;
bands = [78]; bands = [78];
max_pdschReferenceSignalPower = -27; max_pdschReferenceSignalPower = -27;
max_rxgain = 114; max_rxgain = 114;
......
...@@ -423,6 +423,9 @@ def GetParametersFromXML(action): ...@@ -423,6 +423,9 @@ def GetParametersFromXML(action):
string_field=test.findtext('u_retx_th') string_field=test.findtext('u_retx_th')
if (string_field is not None): if (string_field is not None):
CONTAINERS.ran_checkers['u_retx_th'] = [float(x) for x in string_field.split(',')] CONTAINERS.ran_checkers['u_retx_th'] = [float(x) for x in string_field.split(',')]
string_field = test.findtext('services')
if string_field is not None:
CONTAINERS.services[CONTAINERS.eNB_instance] = string_field
elif action == 'DeployGenObject' or action == 'UndeployGenObject' or action == 'StatsFromGenObject': elif action == 'DeployGenObject' or action == 'UndeployGenObject' or action == 'StatsFromGenObject':
string_field=test.findtext('yaml_path') string_field=test.findtext('yaml_path')
...@@ -986,6 +989,9 @@ elif re.match('^TesteNB$', mode, re.IGNORECASE) or re.match('^TestUE$', mode, re ...@@ -986,6 +989,9 @@ elif re.match('^TesteNB$', mode, re.IGNORECASE) or re.match('^TestUE$', mode, re
RAN.prematureExit = True RAN.prematureExit = True
elif action == 'Undeploy_Object': elif action == 'Undeploy_Object':
CONTAINERS.UndeployObject(HTML, RAN) CONTAINERS.UndeployObject(HTML, RAN)
if CONTAINERS.exitStatus == 1:
CiTestObj.AutoTerminateeNB(HTML,RAN,EPC,CONTAINERS)
RAN.prematureExit = True
elif action == 'Cppcheck_Analysis': elif action == 'Cppcheck_Analysis':
SCA.CppCheckAnalysis(HTML) SCA.CppCheckAnalysis(HTML)
elif action == 'LicenceAndFormattingCheck': elif action == 'LicenceAndFormattingCheck':
......
...@@ -748,7 +748,7 @@ class RANManagement(): ...@@ -748,7 +748,7 @@ class RANManagement():
mySSH.command('echo ' + self.eNBPassword + ' | sudo -S mv /tmp/enb_*.pcap .','\$',20) mySSH.command('echo ' + self.eNBPassword + ' | sudo -S mv /tmp/enb_*.pcap .','\$',20)
mySSH.command('echo ' + self.eNBPassword + ' | sudo -S mv /tmp/gnb_*.pcap .','\$',20) mySSH.command('echo ' + self.eNBPassword + ' | sudo -S mv /tmp/gnb_*.pcap .','\$',20)
mySSH.command('echo ' + self.eNBPassword + ' | sudo -S rm -f enb.log.zip', '\$', 5) mySSH.command('echo ' + self.eNBPassword + ' | sudo -S rm -f enb.log.zip', '\$', 5)
mySSH.command('echo ' + self.eNBPassword + ' | sudo -S zip enb.log.zip enb*.log enb_*record.raw enb_*.pcap gnb_*.pcap enb_*txt physim_*.log *stats.log *monitor.pickle *monitor*.png ping*.log* iperf*.log log/*/*.log log/*/*.pcap', '\$', 60) mySSH.command('echo ' + self.eNBPassword + ' | sudo -S zip enb.log.zip *.log enb_*record.raw enb_*.pcap gnb_*.pcap enb_*txt physim_*.log *stats.log *monitor.pickle *monitor*.png ping*.log* iperf*.log log/*/*.log log/*/*.pcap', '\$', 60)
result = re.search('core.\d+', mySSH.getBefore()) result = re.search('core.\d+', mySSH.getBefore())
if result is not None: if result is not None:
mySSH.command('echo ' + self.eNBPassword + ' | sudo -S zip enb.log.zip core* ran_build/build/{lte,nr}-softmodem', '\$', 60) # add core and executable to zip mySSH.command('echo ' + self.eNBPassword + ' | sudo -S zip enb.log.zip core* ran_build/build/{lte,nr}-softmodem', '\$', 60) # add core and executable to zip
...@@ -771,13 +771,13 @@ class RANManagement(): ...@@ -771,13 +771,13 @@ class RANManagement():
#case where numerator > denumerator with denum ==0 is disregarded, cannot hapen in principle, will lead to 0% #case where numerator > denumerator with denum ==0 is disregarded, cannot hapen in principle, will lead to 0%
perc[i] = 0 if (retx_data[i] == 0) else 100 * retx_data[i + 1] / retx_data[i] perc[i] = 0 if (retx_data[i] == 0) else 100 * retx_data[i + 1] / retx_data[i]
#treating % > 100 , % > requirement #treating % > 100 , % > requirement
stats[i] = perc[i] < 100 and perc[i] <= checkers[i] stats[i] = perc[i] <= 100 and perc[i] <= checkers[i]
return stats return stats
def AnalyzeLogFile_eNB(self, eNBlogFile, HTML, checkers={}): def AnalyzeLogFile_eNB(self, eNBlogFile, HTML, checkers={}):
if (not os.path.isfile('./' + eNBlogFile)): if (not os.path.isfile(eNBlogFile)):
return -1 return -1
enb_log_file = open('./' + eNBlogFile, 'r') enb_log_file = open(eNBlogFile, 'r')
exitSignalReceived = False exitSignalReceived = False
foundAssertion = False foundAssertion = False
msgAssertion = '' msgAssertion = ''
...@@ -1048,10 +1048,7 @@ class RANManagement(): ...@@ -1048,10 +1048,7 @@ class RANManagement():
gnb_markers[k].append(line_cnt) gnb_markers[k].append(line_cnt)
# check whether e/gNB log finishes with "Bye." message # check whether e/gNB log finishes with "Bye." message
# Note that it is "=" not "|=" so not only is the regex showedByeMsg |= re.search(r'^Bye.\n', str(line), re.MULTILINE) is not None
# asking for EOF (\Z) but we also only retain the last
# line's result
showedByeMsg = re.search(r'^Bye.\n\Z', str(line), re.MULTILINE) is not None
enb_log_file.close() enb_log_file.close()
......
...@@ -22,7 +22,7 @@ ...@@ -22,7 +22,7 @@
--> -->
<testCaseList> <testCaseList>
<htmlTabRef>TEST-SA-FR1-B200</htmlTabRef> <htmlTabRef>TEST-SA-FR1-B200</htmlTabRef>
<htmlTabName>SA SanityCheck with QUECTEL</htmlTabName> <htmlTabName>40 MHz TDD SA</htmlTabName>
<htmlTabIcon>tasks</htmlTabIcon> <htmlTabIcon>tasks</htmlTabIcon>
<repeatCount>1</repeatCount> <repeatCount>1</repeatCount>
<TestCaseRequestedList> <TestCaseRequestedList>
...@@ -34,13 +34,13 @@ ...@@ -34,13 +34,13 @@
000001 000001
050000 050000
050001 050001
070001
070000
010002 010002
000001 000001
030201 030201
</TestCaseRequestedList> </TestCaseRequestedList>
<!-- <!--
070001
070000
070002 070002
050002 050002
050003 050003
...@@ -126,8 +126,8 @@ ...@@ -126,8 +126,8 @@
<testCase id="070000"> <testCase id="070000">
<class>Iperf</class> <class>Iperf</class>
<desc>iperf (DL/125Mbps/UDP)(60 sec)(single-ue profile)</desc> <desc>iperf (DL/30Mbps/UDP)(30 sec)(single-ue profile)</desc>
<iperf_args>-u -b 125M -t 60 -i 1 -fm</iperf_args> <iperf_args>-u -b 30M -t 30 -i 1 -fm -l1400</iperf_args>
<direction>DL</direction> <direction>DL</direction>
<id>idefix</id> <id>idefix</id>
<iperf_packetloss_threshold>25</iperf_packetloss_threshold> <iperf_packetloss_threshold>25</iperf_packetloss_threshold>
...@@ -137,8 +137,8 @@ ...@@ -137,8 +137,8 @@
<testCase id="070001"> <testCase id="070001">
<class>Iperf</class> <class>Iperf</class>
<desc>iperf (UL/8Mbps/UDP)(60 sec)(single-ue profile)</desc> <desc>iperf (UL/8Mbps/UDP)(30 sec)(single-ue profile)</desc>
<iperf_args>-u -b 8M -t 60 -i 1 -fm</iperf_args> <iperf_args>-u -b 8M -t 30 -i 1 -fm -l1400</iperf_args>
<direction>UL</direction> <direction>UL</direction>
<id>idefix</id> <id>idefix</id>
<iperf_packetloss_threshold>1</iperf_packetloss_threshold> <iperf_packetloss_threshold>1</iperf_packetloss_threshold>
......
...@@ -22,12 +22,11 @@ ...@@ -22,12 +22,11 @@
--> -->
<testCaseList> <testCaseList>
<htmlTabRef>TEST-SA-FR1-B200-terminate</htmlTabRef> <htmlTabRef>TEST-SA-FR1-B200-terminate</htmlTabRef>
<htmlTabName>SA tear-down in case of problem</htmlTabName> <htmlTabName>Tear-down</htmlTabName>
<htmlTabIcon>tasks</htmlTabIcon> <htmlTabIcon>tasks</htmlTabIcon>
<repeatCount>1</repeatCount> <repeatCount>1</repeatCount>
<TestCaseRequestedList> <TestCaseRequestedList>
030201 030201
222222
</TestCaseRequestedList> </TestCaseRequestedList>
<TestCaseExclusionList></TestCaseExclusionList> <TestCaseExclusionList></TestCaseExclusionList>
...@@ -35,15 +34,8 @@ ...@@ -35,15 +34,8 @@
<class>Undeploy_Object</class> <class>Undeploy_Object</class>
<desc>Undeploy gNB</desc> <desc>Undeploy gNB</desc>
<yaml_path>ci-scripts/yaml_files/sa_b200_gnb</yaml_path> <yaml_path>ci-scripts/yaml_files/sa_b200_gnb</yaml_path>
<eNB_instance>1</eNB_instance> <eNB_instance>0</eNB_instance>
<eNB_serverId>1</eNB_serverId> <eNB_serverId>0</eNB_serverId>
<image_tag>sa-test</image_tag>
</testCase>
<testCase id="222222">
<class>Clean_Test_Server_Images</class>
<desc>Clean Test Images on Test Server</desc>
<test_svr_id>0</test_svr_id>
</testCase> </testCase>
</testCaseList> </testCaseList>
<!--
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>TEST-SA-FR1-F1-B200</htmlTabRef>
<htmlTabName>40 MHz TDD F1 SA</htmlTabName>
<htmlTabIcon>tasks</htmlTabIcon>
<repeatCount>1</repeatCount>
<TestCaseRequestedList>
110002
130101
130102
100001
110000
100001
150000
150001
110002
100001
130201
</TestCaseRequestedList>
<!--
070001
070000
070002
050002
050003
-->
<TestCaseExclusionList></TestCaseExclusionList>
<testCase id="110000">
<class>Initialize_UE</class>
<desc>Initialize Quectel</desc>
<id>idefix</id>
</testCase>
<testCase id="110002">
<class>Terminate_UE</class>
<desc>Terminate Quectel</desc>
<id>idefix</id>
</testCase>
<testCase id="130101">
<class>Deploy_Object</class>
<desc>Deploy gNB-CU in a container</desc>
<yaml_path>ci-scripts/yaml_files/sa_f1_b200_gnb</yaml_path>
<eNB_instance>0</eNB_instance>
<eNB_serverId>0</eNB_serverId>
<services>gnb_cu</services>
</testCase>
<testCase id="130102">
<class>Deploy_Object</class>
<desc>Deploy gNB-DU (TDD/Band78/40MHz/B200) in a container</desc>
<yaml_path>ci-scripts/yaml_files/sa_f1_b200_gnb</yaml_path>
<eNB_instance>0</eNB_instance>
<eNB_serverId>0</eNB_serverId>
<services>gnb_du_tdd</services>
</testCase>
<testCase id="100001">
<class>IdleSleep</class>
<desc>Sleep</desc>
<idle_sleep_time_in_sec>5</idle_sleep_time_in_sec>
</testCase>
<testCase id="100002">
<class>IdleSleep</class>
<desc>Sleep</desc>
<idle_sleep_time_in_sec>20</idle_sleep_time_in_sec>
</testCase>
<testCase id="150000">
<class>Ping</class>
<desc>Ping: 20pings in 20sec</desc>
<id>idefix</id>
<ping_args>-c 20</ping_args>
<ping_packetloss_threshold>1</ping_packetloss_threshold>
<ping_rttavg_threshold>25</ping_rttavg_threshold>
</testCase>
<testCase id="150001">
<class>Ping</class>
<desc>Ping: 100pings in 20sec</desc>
<id>idefix</id>
<ping_args>-c 100 -i 0.2</ping_args>
<ping_packetloss_threshold>1</ping_packetloss_threshold>
<ping_rttavg_threshold>110</ping_rttavg_threshold>
</testCase>
<testCase id="150002">
<class>Ping</class>
<desc>Ping: 20pings in 20sec</desc>
<id>idefix</id>
<ping_args>-c 20</ping_args>
<ping_packetloss_threshold>1</ping_packetloss_threshold>
<ping_rttavg_threshold>110</ping_rttavg_threshold>
</testCase>
<testCase id="150003">
<class>Ping</class>
<desc>Ping: 100pings in 20sec</desc>
<id>idefix</id>
<ping_args>-c 100 -i 0.2</ping_args>
<ping_packetloss_threshold>1</ping_packetloss_threshold>
<ping_rttavg_threshold>110</ping_rttavg_threshold>
</testCase>
<testCase id="170000">
<class>Iperf</class>
<desc>iperf (DL/125Mbps/UDP)(60 sec)(single-ue profile)</desc>
<iperf_args>-u -b 125M -t 60 -i 1 -fm</iperf_args>
<direction>DL</direction>
<id>idefix</id>
<iperf_packetloss_threshold>25</iperf_packetloss_threshold>
<iperf_bitrate_threshold>80</iperf_bitrate_threshold>
<iperf_profile>single-ue</iperf_profile>
</testCase>
<testCase id="170001">
<class>Iperf</class>
<desc>iperf (UL/8Mbps/UDP)(60 sec)(single-ue profile)</desc>
<iperf_args>-u -b 8M -t 60 -i 1 -fm</iperf_args>
<direction>UL</direction>
<id>idefix</id>
<iperf_packetloss_threshold>1</iperf_packetloss_threshold>
<iperf_bitrate_threshold>95</iperf_bitrate_threshold>
<iperf_profile>single-ue</iperf_profile>
</testCase>
<testCase id="170002">
<class>Iperf</class>
<desc>iperf (BIDIR TCP)(10 sec)(single-ue profile)</desc>
<iperf_args>-t 10 --bidir</iperf_args>
<direction>BIDIR</direction>
<id>idefix</id>
<iperf_profile>single-ue</iperf_profile>
</testCase>
<testCase id="130201">
<class>Undeploy_Object</class>
<desc>Undeploy CU-DU</desc>
<yaml_path>ci-scripts/yaml_files/sa_f1_b200_gnb</yaml_path>
<eNB_instance>0</eNB_instance>
<eNB_serverId>0</eNB_serverId>
<d_retx_th>1,100,100,100</d_retx_th>
<u_retx_th>1,100,100,100</u_retx_th>
</testCase>
</testCaseList>
<!--
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>TEST-SA-FR1-F1-B200-terminate</htmlTabRef>
<htmlTabName>Tear-down</htmlTabName>
<htmlTabIcon>tasks</htmlTabIcon>
<repeatCount>1</repeatCount>
<TestCaseRequestedList>
230201
222222
</TestCaseRequestedList>
<TestCaseExclusionList></TestCaseExclusionList>
<testCase id="230201">
<class>Undeploy_Object</class>
<desc>Undeploy CU-DU</desc>
<yaml_path>ci-scripts/yaml_files/sa_f1_b200_gnb</yaml_path>
<eNB_instance>0</eNB_instance>
<eNB_serverId>0</eNB_serverId>
</testCase>
<testCase id="222222">
<class>Clean_Test_Server_Images</class>
<desc>Clean Test Images on Test Server</desc>
<test_svr_id>0</test_svr_id>
</testCase>
</testCaseList>
...@@ -270,7 +270,7 @@ services: ...@@ -270,7 +270,7 @@ services:
container_name: rfsim5g-oai-du container_name: rfsim5g-oai-du
environment: environment:
RFSIMULATOR: server RFSIMULATOR: server
USE_SA_TDD_CU: 'yes' USE_SA_TDD_DU: 'yes'
GNB_NAME: du-rfsim GNB_NAME: du-rfsim
TAC: 1 TAC: 1
MCC: '208' MCC: '208'
......
...@@ -20,7 +20,7 @@ services: ...@@ -20,7 +20,7 @@ services:
GNB_NGA_IP_ADDRESS: 192.168.68.194 GNB_NGA_IP_ADDRESS: 192.168.68.194
GNB_NGU_IF_NAME: eth0 GNB_NGU_IF_NAME: eth0
GNB_NGU_IP_ADDRESS: 192.168.68.194 GNB_NGU_IP_ADDRESS: 192.168.68.194
USE_ADDITIONAL_OPTIONS: --sa -E -q --RUs.[0].sdr_addrs serial=30C51D4 --continuous-tx --log_config.global_log_options level,nocolor,time,line_num,function USE_ADDITIONAL_OPTIONS: --sa --RUs.[0].sdr_addrs serial=30C51D4 --continuous-tx --log_config.global_log_options level,nocolor,time,line_num,function
volumes: volumes:
- /dev:/dev - /dev:/dev
networks: networks:
......
version: '3.8'
services:
gnb_cu:
image: oai-gnb:latest
privileged: true
container_name: sa-cu-gnb
environment:
USE_SA_CU: 'yes'
USE_B2XX: 'yes'
GNB_NAME: gNB-CU-in-docker
MCC: '222'
MNC: '01'
MNC_LENGTH: 2
TAC: 1
NSSAI_SST: 1
NSSAI_SD0: 1
NSSAI_SD1: 2
AMF_IP_ADDRESS: 172.21.16.136
GNB_NGA_IF_NAME: eth0
GNB_NGA_IP_ADDRESS: 192.168.68.194
GNB_NGU_IF_NAME: eth0
GNB_NGU_IP_ADDRESS: 192.168.68.194
F1_IF_NAME: eth0
F1_CU_IP_ADDRESS: 192.168.68.194
F1_DU_IP_ADDRESS: 192.168.68.195
F1_CU_D_PORT: 2153
F1_DU_D_PORT: 2153
USE_ADDITIONAL_OPTIONS: --sa --log_config.global_log_options level,nocolor,time,line_num,function
volumes:
- /dev:/dev
networks:
public_net:
ipv4_address: 192.168.68.194
#entrypoint: /bin/bash -c "sleep infinity"
healthcheck:
# pgrep does NOT work
test: /bin/bash -c "ps aux | grep -v grep | grep -c softmodem"
interval: 10s
timeout: 5s
retries: 5
gnb_du_tdd:
image: oai-gnb:latest
privileged: true
container_name: sa-du-b200-gnb
environment:
USE_SA_TDD_DU: 'yes'
USE_B2XX: 'yes'
GNB_NAME: gNB-DU-in-docker
MCC: '222'
MNC: '01'
MNC_LENGTH: 2
TAC: 1
NSSAI_SST: 1
NSSAI_SD0: 1
NSSAI_SD1: 2
AMF_IP_ADDRESS: 172.21.16.136
GNB_NGA_IF_NAME: eth0
GNB_NGA_IP_ADDRESS: 192.168.68.194
GNB_NGU_IF_NAME: eth0
GNB_NGU_IP_ADDRESS: 192.168.68.194
F1_IF_NAME: eth0
F1_CU_IP_ADDRESS: 192.168.68.194
F1_DU_IP_ADDRESS: 192.168.68.195
F1_CU_D_PORT: 2153
F1_DU_D_PORT: 2153
USE_ADDITIONAL_OPTIONS: --sa --RUs.[0].sdr_addrs serial=30C51D4 --continuous-tx -E --log_config.global_log_options level,nocolor,time,line_num,function --gNBs.[0].min_rxtxtime 2 --gNBs.[0].do_CSIRS 1 --gNBs.[0].do_SRS 1 --RUs.[0].att_rx 14 --RUs.[0].att_tx 14
volumes:
- /dev:/dev
networks:
public_net:
ipv4_address: 192.168.68.195
#entrypoint: /bin/bash -c "sleep infinity"
healthcheck:
# pgrep does NOT work
test: /bin/bash -c "ps aux | grep -v grep | grep -c softmodem"
interval: 10s
timeout: 5s
retries: 5
networks:
public_net:
name: sa-b200-gnb-net
ipam:
config:
- subnet: 192.168.68.192/26
driver_opts:
com.docker.network.bridge.name: "sa-gnb-net"
...@@ -60,7 +60,7 @@ def main(): ...@@ -60,7 +60,7 @@ def main():
"rcc.band40.tm1.25PRB": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}', "rcc.band40.tm1.25PRB": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}',
"gnb.band78.tm1.fr1.106PRB.usrpb210.conf": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}', "gnb.band78.tm1.fr1.106PRB.usrpb210.conf": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}',
"gnb.band78.sa.fr1.106PRB.usrpn310.conf": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}', "gnb.band78.sa.fr1.106PRB.usrpn310.conf": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}',
"gnb.sa.band78.fr1.106PRB.usrpb210.conf": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}', "gnb.sa.band78.fr1.51PRB.usrpb210.conf": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}',
"gnb.sa.band66.fr1.106PRB.usrpn300.conf": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}', "gnb.sa.band66.fr1.106PRB.usrpn300.conf": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}',
"gNB_SA_CU.conf": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}', "gNB_SA_CU.conf": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}',
"gNB_SA_DU.conf": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}', "gNB_SA_DU.conf": f'{data[0]["paths"]["dest_dir"]}/{outputfilename}',
......
...@@ -13,7 +13,7 @@ if [[ -v USE_SA_TDD_MONO ]]; then cp $PREFIX/etc/gnb.sa.tdd.conf $PREFIX/etc/gnb ...@@ -13,7 +13,7 @@ if [[ -v USE_SA_TDD_MONO ]]; then cp $PREFIX/etc/gnb.sa.tdd.conf $PREFIX/etc/gnb
if [[ -v USE_SA_TDD_MONO_B2XX ]]; then cp $PREFIX/etc/gnb.sa.tdd.b2xx.conf $PREFIX/etc/gnb.conf; fi if [[ -v USE_SA_TDD_MONO_B2XX ]]; then cp $PREFIX/etc/gnb.sa.tdd.b2xx.conf $PREFIX/etc/gnb.conf; fi
if [[ -v USE_SA_FDD_MONO ]]; then cp $PREFIX/etc/gnb.sa.fdd.conf $PREFIX/etc/gnb.conf; fi if [[ -v USE_SA_FDD_MONO ]]; then cp $PREFIX/etc/gnb.sa.fdd.conf $PREFIX/etc/gnb.conf; fi
if [[ -v USE_SA_CU ]]; then cp $PREFIX/etc/gnb.sa.cu.conf $PREFIX/etc/gnb.conf; fi if [[ -v USE_SA_CU ]]; then cp $PREFIX/etc/gnb.sa.cu.conf $PREFIX/etc/gnb.conf; fi
if [[ -v USE_SA_TDD_CU ]]; then cp $PREFIX/etc/gnb.sa.du.tdd.conf $PREFIX/etc/gnb.conf; fi if [[ -v USE_SA_TDD_DU ]]; then cp $PREFIX/etc/gnb.sa.du.tdd.conf $PREFIX/etc/gnb.conf; fi
if [[ -v USE_SA_NFAPI_VNF ]]; then cp $PREFIX/etc/gnb.sa.nfapi.vnf.conf $PREFIX/etc/gnb.conf; fi if [[ -v USE_SA_NFAPI_VNF ]]; then cp $PREFIX/etc/gnb.sa.nfapi.vnf.conf $PREFIX/etc/gnb.conf; fi
# Sometimes, the templates are not enough. We mount a conf file on $PREFIX/etc. It can be a template itself. # Sometimes, the templates are not enough. We mount a conf file on $PREFIX/etc. It can be a template itself.
if [[ -v USE_VOLUMED_CONF ]]; then cp $PREFIX/etc/mounted.conf $PREFIX/etc/gnb.conf; fi if [[ -v USE_VOLUMED_CONF ]]; then cp $PREFIX/etc/mounted.conf $PREFIX/etc/gnb.conf; fi
......
...@@ -109,7 +109,7 @@ ...@@ -109,7 +109,7 @@
- key: parallel_config - key: parallel_config
env: "@THREAD_PARALLEL_CONFIG@" env: "@THREAD_PARALLEL_CONFIG@"
- filePrefix: gnb.sa.band78.fr1.106PRB.usrpb210.conf - filePrefix: gnb.sa.band78.fr1.51PRB.usrpb210.conf
outputfilename: "gnb.sa.tdd.b2xx.conf" outputfilename: "gnb.sa.tdd.b2xx.conf"
config: config:
- key: gNB_ID - key: gNB_ID
......
...@@ -162,10 +162,8 @@ void init_nr_ue_vars(PHY_VARS_NR_UE *ue, ...@@ -162,10 +162,8 @@ void init_nr_ue_vars(PHY_VARS_NR_UE *ue,
ue->dci_thres = 0; ue->dci_thres = 0;
// Setting UE mode to NOT_SYNCHED by default // Setting UE mode to NOT_SYNCHED by default
for (gNB_id = 0; gNB_id < nb_connected_gNB; gNB_id++){ for (gNB_id = 0; gNB_id < nb_connected_gNB; gNB_id++)
ue->UE_mode[gNB_id] = NOT_SYNCHED; ue->UE_mode[gNB_id] = NOT_SYNCHED;
ue->prach_resources[gNB_id] = (NR_PRACH_RESOURCES_t *)malloc16_clear(sizeof(NR_PRACH_RESOURCES_t));
}
// initialize all signal buffers // initialize all signal buffers
init_nr_ue_signal(ue, nb_connected_gNB); init_nr_ue_signal(ue, nb_connected_gNB);
...@@ -268,7 +266,7 @@ static void process_queued_nr_nfapi_msgs(NR_UE_MAC_INST_t *mac, int sfn_slot) ...@@ -268,7 +266,7 @@ static void process_queued_nr_nfapi_msgs(NR_UE_MAC_INST_t *mac, int sfn_slot)
} }
free_and_zero(rach_ind->pdu_list); free_and_zero(rach_ind->pdu_list);
free_and_zero(rach_ind); free_and_zero(rach_ind);
nr_Msg1_transmitted(0, 0, NFAPI_SFNSLOT2SFN(sfn_slot), 0); nr_Msg1_transmitted(0);
} }
if (dl_tti_request) if (dl_tti_request)
{ {
...@@ -300,7 +298,7 @@ static void process_queued_nr_nfapi_msgs(NR_UE_MAC_INST_t *mac, int sfn_slot) ...@@ -300,7 +298,7 @@ static void process_queued_nr_nfapi_msgs(NR_UE_MAC_INST_t *mac, int sfn_slot)
} }
} }
static void check_nr_prach(NR_UE_MAC_INST_t *mac, nr_uplink_indication_t *ul_info, NR_PRACH_RESOURCES_t *prach_resources) static void check_nr_prach(NR_UE_MAC_INST_t *mac, nr_uplink_indication_t *ul_info)
{ {
fapi_nr_ul_config_request_t *ul_config = get_ul_config_request(mac, ul_info->slot_tx); fapi_nr_ul_config_request_t *ul_config = get_ul_config_request(mac, ul_info->slot_tx);
if (!ul_config) if (!ul_config)
...@@ -313,8 +311,7 @@ static void check_nr_prach(NR_UE_MAC_INST_t *mac, nr_uplink_indication_t *ul_inf ...@@ -313,8 +311,7 @@ static void check_nr_prach(NR_UE_MAC_INST_t *mac, nr_uplink_indication_t *ul_inf
AssertFatal(ul_config->number_pdus < sizeof(ul_config->ul_config_list) / sizeof(ul_config->ul_config_list[0]), AssertFatal(ul_config->number_pdus < sizeof(ul_config->ul_config_list) / sizeof(ul_config->ul_config_list[0]),
"Number of PDUS in ul_config = %d > ul_config_list num elements", ul_config->number_pdus); "Number of PDUS in ul_config = %d > ul_config_list num elements", ul_config->number_pdus);
fapi_nr_ul_config_prach_pdu *prach_pdu = &ul_config->ul_config_list[ul_config->number_pdus].prach_config_pdu; fapi_nr_ul_config_prach_pdu *prach_pdu = &ul_config->ul_config_list[ul_config->number_pdus].prach_config_pdu;
uint8_t nr_prach = nr_ue_get_rach(prach_resources, uint8_t nr_prach = nr_ue_get_rach(prach_pdu,
prach_pdu,
ul_info->module_id, ul_info->module_id,
ul_info->cc_id, ul_info->cc_id,
ul_info->frame_tx, ul_info->frame_tx,
...@@ -349,8 +346,6 @@ static void *NRUE_phy_stub_standalone_pnf_task(void *arg) ...@@ -349,8 +346,6 @@ static void *NRUE_phy_stub_standalone_pnf_task(void *arg)
reset_queue(&nr_ul_dci_req_queue); reset_queue(&nr_ul_dci_req_queue);
reset_queue(&nr_ul_tti_req_queue); reset_queue(&nr_ul_tti_req_queue);
NR_PRACH_RESOURCES_t prach_resources;
memset(&prach_resources, 0, sizeof(prach_resources));
NR_UL_TIME_ALIGNMENT_t ul_time_alignment; NR_UL_TIME_ALIGNMENT_t ul_time_alignment;
memset(&ul_time_alignment, 0, sizeof(ul_time_alignment)); memset(&ul_time_alignment, 0, sizeof(ul_time_alignment));
int last_sfn_slot = -1; int last_sfn_slot = -1;
...@@ -462,7 +457,7 @@ static void *NRUE_phy_stub_standalone_pnf_task(void *arg) ...@@ -462,7 +457,7 @@ static void *NRUE_phy_stub_standalone_pnf_task(void *arg)
nr_ue_scheduler(NULL, &ul_info); nr_ue_scheduler(NULL, &ul_info);
nr_ue_prach_scheduler(mod_id, ul_info.frame_tx, ul_info.slot_tx); nr_ue_prach_scheduler(mod_id, ul_info.frame_tx, ul_info.slot_tx);
nr_ue_pucch_scheduler(mod_id, ul_info.frame_tx, ul_info.slot_tx, NULL); nr_ue_pucch_scheduler(mod_id, ul_info.frame_tx, ul_info.slot_tx, NULL);
check_nr_prach(mac, &ul_info, &prach_resources); check_nr_prach(mac, &ul_info);
} }
if (!IS_SOFTMODEM_NOS1 && get_softmodem_params()->sa) { if (!IS_SOFTMODEM_NOS1 && get_softmodem_params()->sa) {
NR_UE_MAC_INST_t *mac = get_mac_inst(0); NR_UE_MAC_INST_t *mac = get_mac_inst(0);
......
...@@ -24,7 +24,7 @@ ...@@ -24,7 +24,7 @@
#include "PHY/impl_defs_nr.h" #include "PHY/impl_defs_nr.h"
#define NFAPI_UE_MAX_NUM_CB 8 #define NFAPI_UE_MAX_NUM_CB 8
#define NFAPI_MAX_NUM_UL_PDU 8 #define NFAPI_MAX_NUM_UL_PDU 255
/* /*
typedef unsigned int uint32_t; typedef unsigned int uint32_t;
...@@ -191,7 +191,10 @@ typedef struct { ...@@ -191,7 +191,10 @@ typedef struct {
uint16_t freq_msg1; uint16_t freq_msg1;
// When multiple SSBs per RO is configured, this indicates which one is selected in this RO -> this is used to properly compute the PRACH preamble // When multiple SSBs per RO is configured, this indicates which one is selected in this RO -> this is used to properly compute the PRACH preamble
uint8_t ssb_nb_in_ro; uint8_t ssb_nb_in_ro;
// nfapi_nr_ul_beamforming_t beamforming; /// Preamble index for PRACH (0-63)
uint8_t ra_PreambleIndex;
/// PRACH TX power (TODO possibly modify to uint)
int16_t prach_tx_power;
} fapi_nr_ul_config_prach_pdu; } fapi_nr_ul_config_prach_pdu;
typedef struct { typedef struct {
......
...@@ -19,7 +19,7 @@ ...@@ -19,7 +19,7 @@
#define NFAPI_NR_MAX_NB_SEARCH_SPACES 40 #define NFAPI_NR_MAX_NB_SEARCH_SPACES 40
#define NFAPI_MAX_NUM_UL_UE_PER_GROUP 6 #define NFAPI_MAX_NUM_UL_UE_PER_GROUP 6
#define NFAPI_MAX_NUM_UL_PDU 8 #define NFAPI_MAX_NUM_UL_PDU 255
#define NFAPI_MAX_NUM_UCI_INDICATION 8 #define NFAPI_MAX_NUM_UCI_INDICATION 8
#define NFAPI_MAX_NUM_GROUPS 8 #define NFAPI_MAX_NUM_GROUPS 8
#define NFAPI_MAX_NUM_CB 8 #define NFAPI_MAX_NUM_CB 8
......
...@@ -35,6 +35,8 @@ ...@@ -35,6 +35,8 @@
#include "PHY/phy_extern.h" #include "PHY/phy_extern.h"
#include "nr_ul_estimation.h" #include "nr_ul_estimation.h"
#define I0_SKIP_DC 1
extern openair0_config_t openair0_cfg[MAX_CARDS]; extern openair0_config_t openair0_cfg[MAX_CARDS];
int nr_est_timing_advance_pusch(PHY_VARS_gNB* gNB, int UE_id) int nr_est_timing_advance_pusch(PHY_VARS_gNB* gNB, int UE_id)
...@@ -155,43 +157,43 @@ void gNB_I0_measurements(PHY_VARS_gNB *gNB,int slot, int first_symb,int num_symb ...@@ -155,43 +157,43 @@ void gNB_I0_measurements(PHY_VARS_gNB *gNB,int slot, int first_symb,int num_symb
memset(measurements->n0_subband_power, 0, sizeof(measurements->n0_subband_power)); memset(measurements->n0_subband_power, 0, sizeof(measurements->n0_subband_power));
for (int s=first_symb;s<(first_symb+num_symb);s++) { for (int s=first_symb;s<(first_symb+num_symb);s++) {
int offset0 = ((slot&3)*frame_parms->symbols_per_slot + s) * frame_parms->ofdm_symbol_size;
for (rb=0; rb<frame_parms->N_RB_UL; rb++) { for (rb=0; rb<frame_parms->N_RB_UL; rb++) {
if (s==first_symb /*&& ((gNB->rb_mask_ul[s][rb>>5]&(1<<(rb&31))) == 0)*/) { if ((gNB->rb_mask_ul[s][rb >> 5] & (1U << (rb & 31))) == 0 && // check that rb was not used in this subframe
nb_symb[rb]=0; !(I0_SKIP_DC && rb == frame_parms->N_RB_UL>>1)) { // skip middle PRB because of artificial noise possibly created by FFT
for (int aarx=0; aarx<frame_parms->nb_antennas_rx;aarx++) int offset = offset0 + (frame_parms->first_carrier_offset + (rb*12))%frame_parms->ofdm_symbol_size;
measurements->n0_subband_power[aarx][rb]=0; nb_symb[rb]++;
}
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] & (1U << (rb & 31))) == 0) { // check that rb was not used in this subframe
nb_symb[rb]++;
for (int aarx=0; aarx<frame_parms->nb_antennas_rx; aarx++) { for (int aarx=0; aarx<frame_parms->nb_antennas_rx; aarx++) {
int offset = offset0 + (s*frame_parms->ofdm_symbol_size); int32_t *ul_ch = &common_vars->rxdataF[aarx][offset];
int32_t *ul_ch = &common_vars->rxdataF[aarx][offset]; int32_t signal_energy;
int len = 12;
if (((frame_parms->N_RB_UL&1) == 1) && if (((frame_parms->N_RB_UL&1) == 1) &&
(rb==(frame_parms->N_RB_UL>>1))) { (rb==(frame_parms->N_RB_UL>>1))) {
len=6; signal_energy = signal_energy_nodc(ul_ch, 6);
ul_ch = &common_vars->rxdataF[aarx][offset0];
signal_energy += signal_energy_nodc(ul_ch, 6);
} else {
signal_energy = signal_energy_nodc(ul_ch, 12);
} }
AssertFatal(ul_ch, "RX signal buffer (freq) problem\n"); measurements->n0_subband_power[aarx][rb] += signal_energy;
measurements->n0_subband_power[aarx][rb] += signal_energy_nodc(ul_ch,len); LOG_D(PHY,"slot %d symbol %d RB %d aarx %d n0_subband_power %d\n", slot, s, rb, aarx, signal_energy);
} //antenna } //antenna
} }
} //rb } //rb
} // symb } // symb
int nb_rb=0; int nb_rb=0;
int32_t n0_subband_tot=0; int32_t n0_subband_tot=0;
int32_t n0_subband_tot_perPRB=0; int32_t n0_subband_tot_perANT[frame_parms->nb_antennas_rx];
int32_t n0_subband_tot_perANT[1+frame_parms->nb_antennas_rx];
memset(n0_subband_tot_perANT, 0, sizeof(n0_subband_tot_perANT));
for (int rb = 0 ; rb<frame_parms->N_RB_UL;rb++) { for (int rb = 0 ; rb<frame_parms->N_RB_UL;rb++) {
n0_subband_tot_perPRB=0; int32_t n0_subband_tot_perPRB=0;
if (nb_symb[rb] > 0) { if (nb_symb[rb] > 0) {
for (int aarx=0;aarx<frame_parms->nb_antennas_rx;aarx++) { for (int aarx=0;aarx<frame_parms->nb_antennas_rx;aarx++) {
measurements->n0_subband_power[aarx][rb]/=nb_symb[rb]; measurements->n0_subband_power[aarx][rb]/=nb_symb[rb];
measurements->n0_subband_power_dB[aarx][rb] = dB_fixed(measurements->n0_subband_power[aarx][rb]); measurements->n0_subband_power_dB[aarx][rb] = dB_fixed(measurements->n0_subband_power[aarx][rb]);
n0_subband_tot_perPRB+=measurements->n0_subband_power[aarx][rb]; n0_subband_tot_perPRB+=measurements->n0_subband_power[aarx][rb];
if (rb==0) n0_subband_tot_perANT[aarx]=measurements->n0_subband_power[aarx][rb]; n0_subband_tot_perANT[aarx]+=measurements->n0_subband_power[aarx][rb];
else n0_subband_tot_perANT[aarx]+=measurements->n0_subband_power[aarx][rb];
} }
n0_subband_tot_perPRB/=frame_parms->nb_antennas_rx; n0_subband_tot_perPRB/=frame_parms->nb_antennas_rx;
measurements->n0_subband_power_tot_dB[rb] = dB_fixed(n0_subband_tot_perPRB); measurements->n0_subband_power_tot_dB[rb] = dB_fixed(n0_subband_tot_perPRB);
......
...@@ -413,14 +413,13 @@ void rx_nr_prach_ru(RU_t *ru, ...@@ -413,14 +413,13 @@ void rx_nr_prach_ru(RU_t *ru,
} }
void rx_nr_prach(PHY_VARS_gNB *gNB, void rx_nr_prach(PHY_VARS_gNB *gNB,
nfapi_nr_prach_pdu_t *prach_pdu, nfapi_nr_prach_pdu_t *prach_pdu,
int prachOccasion, int prachOccasion,
int frame, int frame,
int subframe, int slot,
uint16_t *max_preamble, uint16_t *max_preamble,
uint16_t *max_preamble_energy, uint16_t *max_preamble_energy,
uint16_t *max_preamble_delay uint16_t *max_preamble_delay)
)
{ {
AssertFatal(gNB!=NULL,"Can only be called from gNB\n"); AssertFatal(gNB!=NULL,"Can only be called from gNB\n");
...@@ -481,7 +480,7 @@ void rx_nr_prach(PHY_VARS_gNB *gNB, ...@@ -481,7 +480,7 @@ void rx_nr_prach(PHY_VARS_gNB *gNB,
prach_ifft = gNB->prach_vars.prach_ifft; prach_ifft = gNB->prach_vars.prach_ifft;
prachF = gNB->prach_vars.prachF; prachF = gNB->prach_vars.prachF;
if (LOG_DEBUGFLAG(PRACH)){ if (LOG_DEBUGFLAG(PRACH)){
if ((frame&1023) < 20) LOG_D(PHY,"PRACH (gNB) : running rx_prach for subframe %d, msg1_frequencystart %d, rootSequenceIndex %d\n", subframe,msg1_frequencystart,rootSequenceIndex); if ((frame&1023) < 20) LOG_D(PHY,"PRACH (gNB) : running rx_prach for slot %d, msg1_frequencystart %d, rootSequenceIndex %d\n", slot, msg1_frequencystart, rootSequenceIndex);
} }
start_meas(&gNB->rx_prach); start_meas(&gNB->rx_prach);
...@@ -506,7 +505,7 @@ void rx_nr_prach(PHY_VARS_gNB *gNB, ...@@ -506,7 +505,7 @@ void rx_nr_prach(PHY_VARS_gNB *gNB,
if (LOG_DEBUGFLAG(PRACH)){ if (LOG_DEBUGFLAG(PRACH)){
int en = dB_fixed(signal_energy((int32_t*)&rxsigF[0][0],(N_ZC==839) ? 840: 140)); int en = dB_fixed(signal_energy((int32_t*)&rxsigF[0][0],(N_ZC==839) ? 840: 140));
if (en>60) LOG_D(PHY,"frame %d, subframe %d : Trying preamble %d \n",frame,subframe,preamble_index); if (en>60) LOG_D(PHY,"frame %d, slot %d : Trying preamble %d \n",frame,slot,preamble_index);
} }
if (restricted_set == 0) { if (restricted_set == 0) {
// This is the relative offset in the root sequence table (5.7.2-4 from 36.211) for the given preamble index // This is the relative offset in the root sequence table (5.7.2-4 from 36.211) for the given preamble index
...@@ -585,8 +584,8 @@ void rx_nr_prach(PHY_VARS_gNB *gNB, ...@@ -585,8 +584,8 @@ void rx_nr_prach(PHY_VARS_gNB *gNB,
// Compute DFT of RX signal (conjugate input, results in conjugate output) for each new rootSequenceIndex // Compute DFT of RX signal (conjugate input, results in conjugate output) for each new rootSequenceIndex
if (LOG_DEBUGFLAG(PRACH)) { if (LOG_DEBUGFLAG(PRACH)) {
int en = dB_fixed(signal_energy((int32_t*)&rxsigF[0][0],840)); int en = dB_fixed(signal_energy((int32_t*)&rxsigF[0][0],840));
if (en>60) LOG_I(PHY,"frame %d, subframe %d : preamble index %d, NCS %d, N_ZC/NCS %d: offset %d, preamble shift %d , en %d)\n", if (en>60) LOG_D(PHY,"frame %d, slot %d : preamble index %d, NCS %d, N_ZC/NCS %d: offset %d, preamble shift %d , en %d)\n",
frame,subframe,preamble_index,NCS,N_ZC/NCS,preamble_offset,preamble_shift,en); frame,slot,preamble_index,NCS,N_ZC/NCS,preamble_offset,preamble_shift,en);
} }
LOG_D(PHY,"PRACH RX preamble_index %d, preamble_offset %d\n",preamble_index,preamble_offset); LOG_D(PHY,"PRACH RX preamble_index %d, preamble_offset %d\n",preamble_index,preamble_offset);
...@@ -605,8 +604,8 @@ void rx_nr_prach(PHY_VARS_gNB *gNB, ...@@ -605,8 +604,8 @@ void rx_nr_prach(PHY_VARS_gNB *gNB,
memset(prachF, 0, sizeof(int16_t)*2*1024 ); memset(prachF, 0, sizeof(int16_t)*2*1024 );
if (LOG_DUMPFLAG(PRACH)) { if (LOG_DUMPFLAG(PRACH)) {
LOG_M("prach_rxF0.m","prach_rxF0",rxsigF[0],N_ZC,1,1); LOG_M("prach_rxF0.m","prach_rxF0",rxsigF[0],N_ZC,1,1);
LOG_M("prach_rxF1.m","prach_rxF1",rxsigF[1],6144,1,1); LOG_M("prach_rxF1.m","prach_rxF1",rxsigF[1],6144,1,1);
} }
for (aa=0;aa<nb_rx; aa++) { for (aa=0;aa<nb_rx; aa++) {
...@@ -659,10 +658,10 @@ void rx_nr_prach(PHY_VARS_gNB *gNB, ...@@ -659,10 +658,10 @@ void rx_nr_prach(PHY_VARS_gNB *gNB,
lev = (int32_t)prach_ifft[(preamble_shift2+i)]; lev = (int32_t)prach_ifft[(preamble_shift2+i)];
levdB = dB_fixed_times10(lev); levdB = dB_fixed_times10(lev);
if (levdB>*max_preamble_energy) { if (levdB>*max_preamble_energy) {
LOG_D(PHY,"preamble_index %d, delay %d en %d dB > %d dB\n",preamble_index,i,levdB,*max_preamble_energy); LOG_D(PHY,"preamble_index %d, delay %d en %d dB > %d dB\n",preamble_index,i,levdB,*max_preamble_energy);
*max_preamble_energy = levdB; *max_preamble_energy = levdB;
*max_preamble_delay = i; // Note: This has to be normalized to the 30.72 Ms/s sampling rate *max_preamble_delay = i; // Note: This has to be normalized to the 30.72 Ms/s sampling rate
*max_preamble = preamble_index; *max_preamble = preamble_index;
} }
} }
}// preamble_index }// preamble_index
......
...@@ -1515,31 +1515,50 @@ void nr_decode_pucch2(PHY_VARS_gNB *gNB, ...@@ -1515,31 +1515,50 @@ void nr_decode_pucch2(PHY_VARS_gNB *gNB,
#endif #endif
prod_re[aa] = simde_mm256_hadds_epi16(prod_re[aa],prod_re[aa]);// 0+1 prod_re[aa] = simde_mm256_hadds_epi16(prod_re[aa],prod_re[aa]);// 0+1
#ifdef DEBUG_NR_PUCCH_RX
printf("0.prod_re[%d] => (%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d)\n",aa,
((int16_t*)&prod_re[aa])[0],((int16_t*)&prod_re[aa])[1],((int16_t*)&prod_re[aa])[2],((int16_t*)&prod_re[aa])[3],
((int16_t*)&prod_re[aa])[4],((int16_t*)&prod_re[aa])[5],((int16_t*)&prod_re[aa])[6],((int16_t*)&prod_re[aa])[7],
((int16_t*)&prod_re[aa])[8],((int16_t*)&prod_re[aa])[9],((int16_t*)&prod_re[aa])[10],((int16_t*)&prod_re[aa])[11],
((int16_t*)&prod_re[aa])[12],((int16_t*)&prod_re[aa])[13],((int16_t*)&prod_re[aa])[14],((int16_t*)&prod_re[aa])[15]);
#endif
prod_im[aa] = simde_mm256_hadds_epi16(prod_im[aa],prod_im[aa]); prod_im[aa] = simde_mm256_hadds_epi16(prod_im[aa],prod_im[aa]);
prod_re[aa] = simde_mm256_hadds_epi16(prod_re[aa],prod_re[aa]);// 0+1+2+3 prod_re[aa] = simde_mm256_hadds_epi16(prod_re[aa],prod_re[aa]);// 0+1+2+3
#ifdef DEBUG_NR_PUCCH_RX
printf("1.prod_re[%d] => (%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d)\n",aa,
((int16_t*)&prod_re[aa])[0],((int16_t*)&prod_re[aa])[1],((int16_t*)&prod_re[aa])[2],((int16_t*)&prod_re[aa])[3],
((int16_t*)&prod_re[aa])[4],((int16_t*)&prod_re[aa])[5],((int16_t*)&prod_re[aa])[6],((int16_t*)&prod_re[aa])[7],
((int16_t*)&prod_re[aa])[8],((int16_t*)&prod_re[aa])[9],((int16_t*)&prod_re[aa])[10],((int16_t*)&prod_re[aa])[11],
((int16_t*)&prod_re[aa])[12],((int16_t*)&prod_re[aa])[13],((int16_t*)&prod_re[aa])[14],((int16_t*)&prod_re[aa])[15]);
#endif
prod_im[aa] = simde_mm256_hadds_epi16(prod_im[aa],prod_im[aa]); prod_im[aa] = simde_mm256_hadds_epi16(prod_im[aa],prod_im[aa]);
prod_re[aa] = simde_mm256_hadds_epi16(prod_re[aa],prod_re[aa]);// 0+1+2+3+4+5+6+7 prod_re[aa] = simde_mm256_hadds_epi16(prod_re[aa],prod_re[aa]);// 0+1+2+3+4+5+6+7
prod_im[aa] = simde_mm256_hadds_epi16(prod_im[aa],prod_im[aa]); #ifdef DEBUG_NR_PUCCH_RX
prod_re[aa] = simde_mm256_hadds_epi16(prod_re[aa],prod_re[aa]);// 0+1+2+3+4+5+6+7+8+9+10+11+12+13+14+15 printf("2.prod_re[%d] => (%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d)\n",aa,
((int16_t*)&prod_re[aa])[0],((int16_t*)&prod_re[aa])[1],((int16_t*)&prod_re[aa])[2],((int16_t*)&prod_re[aa])[3],
((int16_t*)&prod_re[aa])[4],((int16_t*)&prod_re[aa])[5],((int16_t*)&prod_re[aa])[6],((int16_t*)&prod_re[aa])[7],
((int16_t*)&prod_re[aa])[8],((int16_t*)&prod_re[aa])[9],((int16_t*)&prod_re[aa])[10],((int16_t*)&prod_re[aa])[11],
((int16_t*)&prod_re[aa])[12],((int16_t*)&prod_re[aa])[13],((int16_t*)&prod_re[aa])[14],((int16_t*)&prod_re[aa])[15]);
#endif
prod_im[aa] = simde_mm256_hadds_epi16(prod_im[aa],prod_im[aa]); prod_im[aa] = simde_mm256_hadds_epi16(prod_im[aa],prod_im[aa]);
} }
int64_t corr_re=0,corr_im=0; int64_t corr_re=0,corr_im=0;
for (int aa=0;aa<Prx;aa++) { for (int aa=0;aa<Prx;aa++) {
corr_re = ( corr32_re[symb][group][aa]+((int16_t*)(&prod_re[aa]))[0]+((int16_t*)(&prod_re[aa]))[8]);
corr_im = ( corr32_im[symb][group][aa]+((int16_t*)(&prod_im[aa]))[0]+((int16_t*)(&prod_im[aa]))[8]);
#ifdef DEBUG_NR_PUCCH_RX #ifdef DEBUG_NR_PUCCH_RX
printf("pucch2 cw %d group %d aa %d: (%d,%d)+(%d,%d) = (%d,%d)\n",cw,group,aa, printf("pucch2 cw %d group %d aa %d: (%d,%d)+(%d,%d) = (%d,%d)\n",cw,group,aa,
corr32_re[symb][group][aa],corr32_im[symb][group][aa], corr32_re[symb][group][aa],corr32_im[symb][group][aa],
((int16_t*)(&prod_re[aa]))[0], ((int16_t*)(&prod_re[aa]))[0]+((int16_t*)(&prod_re[aa]))[8],
((int16_t*)(&prod_im[aa]))[0], ((int16_t*)(&prod_im[aa]))[0]+((int16_t*)(&prod_im[aa]))[8],
corr32_re[symb][group][aa]+((int16_t*)(&prod_re[aa]))[0], corr_re,corr_im
corr32_im[symb][group][aa]+((int16_t*)(&prod_im[aa]))[0]); );
#endif #endif
corr_re = ( corr32_re[symb][group][aa]+((int16_t*)(&prod_re[aa]))[0]);
corr_im = ( corr32_im[symb][group][aa]+((int16_t*)(&prod_im[aa]))[0]);
corr_tmp += corr_re*corr_re + corr_im*corr_im; corr_tmp += corr_re*corr_re + corr_im*corr_im;
} // aa loop } // aa loop
}// group loop }// group loop
...@@ -1547,11 +1566,14 @@ void nr_decode_pucch2(PHY_VARS_gNB *gNB, ...@@ -1547,11 +1566,14 @@ void nr_decode_pucch2(PHY_VARS_gNB *gNB,
if (corr_tmp > corr) { if (corr_tmp > corr) {
corr = corr_tmp; corr = corr_tmp;
cw_ML=cw; cw_ML=cw;
#ifdef DEBUG_NR_PUCCH_RX
printf("slot %d PUCCH2 cw_ML %d, corr %llu\n",slot,cw_ML,corr);
#endif
} }
} // cw loop } // cw loop
corr_dB = dB_fixed64((uint64_t)corr); corr_dB = dB_fixed64((uint64_t)corr);
#ifdef DEBUG_NR_PUCCH_RX #ifdef DEBUG_NR_PUCCH_RX
LOG_I(PHY,"slot %d PUCCH2 cw_ML %d, metric %d dB\n",slot,cw_ML,corr_dB); printf("slot %d PUCCH2 cw_ML %d, metric %d \n",slot,cw_ML,corr_dB);
#endif #endif
decodedPayload[0]=(uint64_t)cw_ML; decodedPayload[0]=(uint64_t)cw_ML;
} }
......
...@@ -110,8 +110,6 @@ void nr_adjust_synch_ue(NR_DL_FRAME_PARMS *frame_parms, ...@@ -110,8 +110,6 @@ void nr_adjust_synch_ue(NR_DL_FRAME_PARMS *frame_parms,
//mac_resynch(); //mac_resynch();
//dl_phy_sync_success(ue->Mod_id,frame,0,1);//ue->common_vars.eNb_id); //dl_phy_sync_success(ue->Mod_id,frame,0,1);//ue->common_vars.eNb_id);
ue->UE_mode[0] = PRACH; ue->UE_mode[0] = PRACH;
ue->prach_resources[gNB_id]->sync_frame = frame;
ue->prach_resources[gNB_id]->init_msg1 = 0;
} else { } else {
ue->UE_mode[0] = PUSCH; ue->UE_mode[0] = PUSCH;
} }
......
...@@ -123,8 +123,6 @@ void phy_adjust_gain_nr(PHY_VARS_NR_UE *ue, ...@@ -123,8 +123,6 @@ void phy_adjust_gain_nr(PHY_VARS_NR_UE *ue,
uint32_t rx_power_fil_dB, uint32_t rx_power_fil_dB,
uint8_t gNB_id); uint8_t gNB_id);
int16_t get_nr_PL(uint8_t Mod_id, uint8_t CC_id, uint8_t gNB_index);
void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue, void nr_pdsch_ptrs_processing(PHY_VARS_NR_UE *ue,
NR_UE_PDSCH **pdsch_vars, NR_UE_PDSCH **pdsch_vars,
NR_DL_FRAME_PARMS *frame_parms, NR_DL_FRAME_PARMS *frame_parms,
......
...@@ -46,42 +46,6 @@ ...@@ -46,42 +46,6 @@
//#define DEBUG_MEAS_UE //#define DEBUG_MEAS_UE
//#define DEBUG_RANK_EST //#define DEBUG_RANK_EST
// Returns the pathloss in dB for the active UL BWP on the selected carrier based on the DL RS associated with the PRACH transmission
// computation according to clause 7.4 (Physical random access channel) of 3GPP TS 38.213 version 16.3.0 Release 16
// Assumptions:
// - PRACH transmission from a UE is not in response to a detection of a PDCCH order by the UE
// Measurement units:
// - referenceSignalPower: dBm/RE (average EPRE of the resources elements that carry secondary synchronization signals in dBm)
int16_t get_nr_PL(uint8_t Mod_id, uint8_t CC_id, uint8_t gNB_index){
PHY_VARS_NR_UE *ue = PHY_vars_UE_g[Mod_id][CC_id];
int16_t pathloss;
if (get_softmodem_params()->do_ra){
long referenceSignalPower = ue->nrUE_config.ssb_config.ss_pbch_power;
pathloss = (int16_t)(referenceSignalPower - ue->measurements.rsrp_dBm[gNB_index]);
LOG_D(MAC, "In %s: pathloss %d dB, UE RX total gain %d dB, referenceSignalPower %ld dBm/RE (%f mW), RSRP %d dBm (%f mW)\n",
__FUNCTION__,
pathloss,
ue->rx_total_gain_dB,
referenceSignalPower,
pow(10, referenceSignalPower/10),
ue->measurements.rsrp_dBm[gNB_index],
pow(10, ue->measurements.rsrp_dBm[gNB_index]/10));
} else {
pathloss = ((int16_t)(((10*ue->rx_total_gain_dB) - dB_fixed_times10(ue->measurements.rsrp[gNB_index]))/10));
}
return pathloss;
}
uint32_t get_nr_rx_total_gain_dB (module_id_t Mod_id,uint8_t CC_id) uint32_t get_nr_rx_total_gain_dB (module_id_t Mod_id,uint8_t CC_id)
{ {
......
...@@ -61,7 +61,6 @@ int32_t generate_nr_prach(PHY_VARS_NR_UE *ue, uint8_t gNB_id, int frame, uint8_t ...@@ -61,7 +61,6 @@ int32_t generate_nr_prach(PHY_VARS_NR_UE *ue, uint8_t gNB_id, int frame, uint8_t
NR_DL_FRAME_PARMS *fp=&ue->frame_parms; NR_DL_FRAME_PARMS *fp=&ue->frame_parms;
fapi_nr_config_request_t *nrUE_config = &ue->nrUE_config; fapi_nr_config_request_t *nrUE_config = &ue->nrUE_config;
NR_PRACH_RESOURCES_t *prach_resources = ue->prach_resources[gNB_id];
fapi_nr_ul_config_prach_pdu *prach_pdu = &ue->prach_vars[gNB_id]->prach_pdu; fapi_nr_ul_config_prach_pdu *prach_pdu = &ue->prach_vars[gNB_id]->prach_pdu;
uint8_t Mod_id, fd_occasion, preamble_index, restricted_set, not_found; uint8_t Mod_id, fd_occasion, preamble_index, restricted_set, not_found;
...@@ -73,7 +72,6 @@ int32_t generate_nr_prach(PHY_VARS_NR_UE *ue, uint8_t gNB_id, int frame, uint8_t ...@@ -73,7 +72,6 @@ int32_t generate_nr_prach(PHY_VARS_NR_UE *ue, uint8_t gNB_id, int frame, uint8_t
int16_t Ncp = 0, amp, *prach, *prach2, *prachF, *Xu; int16_t Ncp = 0, amp, *prach, *prach2, *prachF, *Xu;
int32_t Xu_re, Xu_im; int32_t Xu_re, Xu_im;
int prach_start, prach_sequence_length, i, prach_len, dftlen, mu, kbar, K, n_ra_prb, k, prachStartSymbol, sample_offset_slot; int prach_start, prach_sequence_length, i, prach_len, dftlen, mu, kbar, K, n_ra_prb, k, prachStartSymbol, sample_offset_slot;
//int restricted_Type;
fd_occasion = 0; fd_occasion = 0;
prach_len = 0; prach_len = 0;
...@@ -91,12 +89,13 @@ int32_t generate_nr_prach(PHY_VARS_NR_UE *ue, uint8_t gNB_id, int frame, uint8_t ...@@ -91,12 +89,13 @@ int32_t generate_nr_prach(PHY_VARS_NR_UE *ue, uint8_t gNB_id, int frame, uint8_t
n_ra_prb = nrUE_config->prach_config.num_prach_fd_occasions_list[fd_occasion].k1,//prach_pdu->freq_msg1; n_ra_prb = nrUE_config->prach_config.num_prach_fd_occasions_list[fd_occasion].k1,//prach_pdu->freq_msg1;
NCS = prach_pdu->num_cs; NCS = prach_pdu->num_cs;
prach_fmt_id = prach_pdu->prach_format; prach_fmt_id = prach_pdu->prach_format;
preamble_index = prach_resources->ra_PreambleIndex; preamble_index = prach_pdu->ra_PreambleIndex;
kbar = 1; kbar = 1;
K = 24; K = 24;
k = 12*n_ra_prb - 6*fp->N_RB_UL; k = 12*n_ra_prb - 6*fp->N_RB_UL;
prachStartSymbol = prach_pdu->prach_start_symbol; prachStartSymbol = prach_pdu->prach_start_symbol;
//restricted_Type = 0;
LOG_D(PHY,"Generate NR PRACH %d.%d\n", frame, slot);
compute_nr_prach_seq(nrUE_config->prach_config.prach_sequence_length, compute_nr_prach_seq(nrUE_config->prach_config.prach_sequence_length,
nrUE_config->prach_config.num_prach_fd_occasions_list[fd_occasion].num_root_sequences, nrUE_config->prach_config.num_prach_fd_occasions_list[fd_occasion].num_root_sequences,
......
...@@ -647,9 +647,9 @@ typedef struct { ...@@ -647,9 +647,9 @@ typedef struct {
//! estimated avg noise power (dB) //! estimated avg noise power (dB)
unsigned int n0_power_tot_dB; unsigned int n0_power_tot_dB;
//! estimated avg noise power per RB per RX ant (lin) //! estimated avg noise power per RB per RX ant (lin)
unsigned int n0_subband_power[MAX_NUM_RU_PER_gNB][275]; unsigned int n0_subband_power[NB_ANTENNAS_RX][275];
//! estimated avg noise power per RB per RX ant (dB) //! estimated avg noise power per RB per RX ant (dB)
unsigned int n0_subband_power_dB[MAX_NUM_RU_PER_gNB][275]; unsigned int n0_subband_power_dB[NB_ANTENNAS_RX][275];
//! estimated avg subband noise power (dB) //! estimated avg subband noise power (dB)
unsigned int n0_subband_power_avg_dB; unsigned int n0_subband_power_avg_dB;
//! estimated avg subband noise power per antenna (dB) //! estimated avg subband noise power per antenna (dB)
......
...@@ -590,11 +590,9 @@ typedef struct { ...@@ -590,11 +590,9 @@ typedef struct {
// when off, defaults to frequency domain interpolation // when off, defaults to frequency domain interpolation
int chest_freq; int chest_freq;
int chest_time; int chest_time;
int generate_ul_signal[NUMBER_OF_CONNECTED_gNB_MAX];
UE_NR_SCAN_INFO_t scan_info[NB_BANDS_MAX]; UE_NR_SCAN_INFO_t scan_info[NB_BANDS_MAX];
NR_PRACH_RESOURCES_t *prach_resources[NUMBER_OF_CONNECTED_gNB_MAX];
/// \brief ?. /// \brief ?.
/// - first index: gNB [0..NUMBER_OF_CONNECTED_gNB_MAX[ (hard coded) /// - first index: gNB [0..NUMBER_OF_CONNECTED_gNB_MAX[ (hard coded)
uint32_t total_TBS[NUMBER_OF_CONNECTED_gNB_MAX]; uint32_t total_TBS[NUMBER_OF_CONNECTED_gNB_MAX];
......
...@@ -93,7 +93,6 @@ ...@@ -93,7 +93,6 @@
#define NR_MAX_NB_HARQ_PROCESSES 16 #define NR_MAX_NB_HARQ_PROCESSES 16
#define NR_MAX_PDSCH_TBS 3824 #define NR_MAX_PDSCH_TBS 3824
#define NR_MAX_SIB_LENGTH 2976 // 3GPP TS 38.331 section 5.2.1 - The physical layer imposes a limit to the maximum size a SIB can take. The maximum SIB1 or SI message size is 2976 bits.
#define MAX_NUM_NR_DLSCH_SEGMENTS_PER_LAYER 36 #define MAX_NUM_NR_DLSCH_SEGMENTS_PER_LAYER 36
...@@ -203,39 +202,6 @@ typedef struct NR_BWP_PARMS { ...@@ -203,39 +202,6 @@ typedef struct NR_BWP_PARMS {
nr_prg_parms_t prg_parms; nr_prg_parms_t prg_parms;
} NR_BWP_PARMS; } NR_BWP_PARMS;
typedef struct {
/// PRACH format retrieved from prach_ConfigIndex
uint16_t prach_format;
/// Preamble index for PRACH (0-63)
uint8_t ra_PreambleIndex;
/// Preamble Tx Counter
uint8_t RA_PREAMBLE_TRANSMISSION_COUNTER;
/// Preamble Power Ramping Counter
uint8_t RA_PREAMBLE_POWER_RAMPING_COUNTER;
/// 2-step RA power offset
int POWER_OFFSET_2STEP_RA;
/// Target received power at gNB. Baseline is range -202..-60 dBm. Depends on delta preamble, power ramping counter and step.
int ra_PREAMBLE_RECEIVED_TARGET_POWER;
/// PRACH index for TDD (0 ... 6) depending on TDD configuration and prachConfigIndex
uint8_t ra_TDD_map_index;
/// RA Preamble Power Ramping Step in dB
uint32_t RA_PREAMBLE_POWER_RAMPING_STEP;
///
uint8_t RA_PREAMBLE_BACKOFF;
///
uint8_t RA_SCALING_FACTOR_BI;
/// Indicating whether it is 2-step or 4-step RA
nr_ra_type_e RA_TYPE;
/// UE configured maximum output power
int RA_PCMAX;
/// Corresponding RA-RNTI for UL-grant
uint16_t ra_RNTI;
/// Frame of last completed synch
uint16_t sync_frame;
/// Flag to indicate that prach is ready to start: it is enabled with an initial delay after the sync
uint8_t init_msg1;
} NR_PRACH_RESOURCES_t;
typedef struct { typedef struct {
uint8_t k_0_p[MAX_NUM_NR_SRS_AP][MAX_NUM_NR_SRS_SYMBOLS]; uint8_t k_0_p[MAX_NUM_NR_SRS_AP][MAX_NUM_NR_SRS_SYMBOLS];
uint8_t srs_generated_signal_bits; uint8_t srs_generated_signal_bits;
......
...@@ -121,30 +121,12 @@ void L1_nr_prach_procedures(PHY_VARS_gNB *gNB,int frame,int slot) { ...@@ -121,30 +121,12 @@ void L1_nr_prach_procedures(PHY_VARS_gNB *gNB,int frame,int slot) {
ru=gNB->RU_list[0]; ru=gNB->RU_list[0];
int prach_id=find_nr_prach(gNB,frame,slot,SEARCH_EXIST); int prach_id=find_nr_prach(gNB,frame,slot,SEARCH_EXIST);
if (prach_id>=0) { if (prach_id>=0) {
nfapi_nr_prach_pdu_t *prach_pdu = &gNB->prach_vars.list[prach_id].pdu; nfapi_nr_prach_pdu_t *prach_pdu = &gNB->prach_vars.list[prach_id].pdu;
uint8_t prachStartSymbol; uint8_t prachStartSymbol;
uint8_t N_dur = get_nr_prach_duration(prach_pdu->prach_format); uint8_t N_dur = get_nr_prach_duration(prach_pdu->prach_format);
/*
uint16_t format,RA_sfn_index;
uint8_t start_symbol,N_t_slot,N_dur,N_RA_slot,config_period;
get_nr_prach_info_from_index(gNB->gNB_config.prach_config.prach_ConfigurationIndex.value,
frame,slot,
gNB->gNB_config.carrier_config.dl_frequency.value,
gNB->frame_parms.numerology_index,
gNB->frame_parms.frame_type,
&format,
&start_symbol,
&N_t_slot,
&N_dur,
&RA_sfn_index,
&N_RA_slot,
&config_period);
*/
for(int prach_oc = 0; prach_oc < prach_pdu->num_prach_ocas; prach_oc++) { for(int prach_oc = 0; prach_oc < prach_pdu->num_prach_ocas; prach_oc++) {
for (ru_aa=0,aa=0;ru_aa<ru->nb_rx;ru_aa++,aa++) { for (ru_aa=0,aa=0;ru_aa<ru->nb_rx;ru_aa++,aa++) {
gNB->prach_vars.rxsigF[aa] = ru->prach_rxsigF[prach_oc][ru_aa]; gNB->prach_vars.rxsigF[aa] = ru->prach_rxsigF[prach_oc][ru_aa];
...@@ -152,7 +134,7 @@ void L1_nr_prach_procedures(PHY_VARS_gNB *gNB,int frame,int slot) { ...@@ -152,7 +134,7 @@ void L1_nr_prach_procedures(PHY_VARS_gNB *gNB,int frame,int slot) {
prachStartSymbol = prach_pdu->prach_start_symbol+prach_oc*N_dur; prachStartSymbol = prach_pdu->prach_start_symbol+prach_oc*N_dur;
//comment FK: the standard 38.211 section 5.3.2 has one extra term +14*N_RA_slot. This is because there prachStartSymbol is given wrt to start of the 15kHz slot or 60kHz slot. Here we work slot based, so this function is anyway only called in slots where there is PRACH. Its up to the MAC to schedule another PRACH PDU in the case there are there N_RA_slot \in {0,1}. //comment FK: the standard 38.211 section 5.3.2 has one extra term +14*N_RA_slot. This is because there prachStartSymbol is given wrt to start of the 15kHz slot or 60kHz slot. Here we work slot based, so this function is anyway only called in slots where there is PRACH. Its up to the MAC to schedule another PRACH PDU in the case there are there N_RA_slot \in {0,1}.
rx_nr_prach(gNB, rx_nr_prach(gNB,
prach_pdu, prach_pdu,
prach_oc, prach_oc,
...@@ -160,8 +142,8 @@ void L1_nr_prach_procedures(PHY_VARS_gNB *gNB,int frame,int slot) { ...@@ -160,8 +142,8 @@ void L1_nr_prach_procedures(PHY_VARS_gNB *gNB,int frame,int slot) {
slot, slot,
&max_preamble[0], &max_preamble[0],
&max_preamble_energy[0], &max_preamble_energy[0],
&max_preamble_delay[0] &max_preamble_delay[0]);
);
free_nr_prach_entry(gNB,prach_id); free_nr_prach_entry(gNB,prach_id);
LOG_D(PHY,"[RAPROC] Frame %d, slot %d, occasion %d (prachStartSymbol %d) : Most likely preamble %d, energy %d.%d dB delay %d (prach_energy counter %d)\n", LOG_D(PHY,"[RAPROC] Frame %d, slot %d, occasion %d (prachStartSymbol %d) : Most likely preamble %d, energy %d.%d dB delay %d (prach_energy counter %d)\n",
frame,slot,prach_oc,prachStartSymbol, frame,slot,prach_oc,prachStartSymbol,
......
...@@ -696,8 +696,9 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) { ...@@ -696,8 +696,9 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) {
else num_symb=NR_NUMBER_OF_SYMBOLS_PER_SLOT; else num_symb=NR_NUMBER_OF_SYMBOLS_PER_SLOT;
gNB_I0_measurements(gNB,slot_rx,first_symb,num_symb); gNB_I0_measurements(gNB,slot_rx,first_symb,num_symb);
const int soffset = (slot_rx&3) * gNB->frame_parms.symbols_per_slot * gNB->frame_parms.ofdm_symbol_size;
int offset = 10*gNB->frame_parms.ofdm_symbol_size + gNB->frame_parms.first_carrier_offset; int offset = 10*gNB->frame_parms.ofdm_symbol_size + gNB->frame_parms.first_carrier_offset;
int power_rxF = signal_energy_nodc(&gNB->common_vars.rxdataF[0][offset+(47*12)],12*18); int power_rxF = signal_energy_nodc(&gNB->common_vars.rxdataF[0][soffset+offset+(47*12)],12*18);
LOG_D(PHY,"frame %d, slot %d: UL signal energy %d\n",frame_rx,slot_rx,power_rxF); LOG_D(PHY,"frame %d, slot %d: UL signal energy %d\n",frame_rx,slot_rx,power_rxF);
start_meas(&gNB->phy_proc_rx); start_meas(&gNB->phy_proc_rx);
...@@ -726,7 +727,7 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) { ...@@ -726,7 +727,7 @@ int phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) {
nfapi_nr_uci_pucch_pdu_format_0_1_t *uci_pdu_format0 = &gNB->uci_pdu_list[num_ucis].pucch_pdu_format_0_1; nfapi_nr_uci_pucch_pdu_format_0_1_t *uci_pdu_format0 = &gNB->uci_pdu_list[num_ucis].pucch_pdu_format_0_1;
offset = pucch_pdu->start_symbol_index*gNB->frame_parms.ofdm_symbol_size + (gNB->frame_parms.first_carrier_offset+pucch_pdu->prb_start*12); offset = pucch_pdu->start_symbol_index*gNB->frame_parms.ofdm_symbol_size + (gNB->frame_parms.first_carrier_offset+pucch_pdu->prb_start*12);
power_rxF = signal_energy_nodc(&gNB->common_vars.rxdataF[0][offset],12); power_rxF = signal_energy_nodc(&gNB->common_vars.rxdataF[0][soffset+offset],12);
LOG_D(PHY,"frame %d, slot %d: PUCCH signal energy %d\n",frame_rx,slot_rx,power_rxF); LOG_D(PHY,"frame %d, slot %d: PUCCH signal energy %d\n",frame_rx,slot_rx,power_rxF);
nr_decode_pucch0(gNB, nr_decode_pucch0(gNB,
......
...@@ -411,7 +411,6 @@ int8_t nr_ue_scheduled_response(nr_scheduled_response_t *scheduled_response){ ...@@ -411,7 +411,6 @@ int8_t nr_ue_scheduled_response(nr_scheduled_response_t *scheduled_response){
uint8_t pdu_type = ul_config->ul_config_list[i].pdu_type, current_harq_pid, gNB_id = 0; uint8_t pdu_type = ul_config->ul_config_list[i].pdu_type, current_harq_pid, gNB_id = 0;
/* PRACH */ /* PRACH */
//NR_PRACH_RESOURCES_t *prach_resources;
fapi_nr_ul_config_prach_pdu *prach_config_pdu; fapi_nr_ul_config_prach_pdu *prach_config_pdu;
/* PUSCH */ /* PUSCH */
nfapi_nr_ue_pusch_pdu_t *pusch_config_pdu; nfapi_nr_ue_pusch_pdu_t *pusch_config_pdu;
......
...@@ -52,7 +52,6 @@ ...@@ -52,7 +52,6 @@
#include "executables/softmodem-common.h" #include "executables/softmodem-common.h"
#include "executables/nr-uesoftmodem.h" #include "executables/nr-uesoftmodem.h"
#include "LAYER2/NR_MAC_UE/mac_proto.h" #include "LAYER2/NR_MAC_UE/mac_proto.h"
#include "LAYER2/NR_MAC_UE/nr_l1_helpers.h"
//#define DEBUG_PHY_PROC //#define DEBUG_PHY_PROC
#define NR_PDCCH_SCHED #define NR_PDCCH_SCHED
...@@ -391,8 +390,6 @@ static void nr_ue_pbch_procedures(uint8_t gNB_id, ...@@ -391,8 +390,6 @@ static void nr_ue_pbch_procedures(uint8_t gNB_id,
if (ue->UE_mode[gNB_id] == NOT_SYNCHED && ue->no_timing_correction == 1){ if (ue->UE_mode[gNB_id] == NOT_SYNCHED && ue->no_timing_correction == 1){
if (get_softmodem_params()->do_ra) { if (get_softmodem_params()->do_ra) {
ue->UE_mode[gNB_id] = PRACH; ue->UE_mode[gNB_id] = PRACH;
ue->prach_resources[gNB_id]->sync_frame = frame_rx;
ue->prach_resources[gNB_id]->init_msg1 = 0;
} else { } else {
ue->UE_mode[gNB_id] = PUSCH; ue->UE_mode[gNB_id] = PUSCH;
} }
...@@ -1302,44 +1299,25 @@ void nr_ue_prach_procedures(PHY_VARS_NR_UE *ue, UE_nr_rxtx_proc_t *proc, uint8_t ...@@ -1302,44 +1299,25 @@ void nr_ue_prach_procedures(PHY_VARS_NR_UE *ue, UE_nr_rxtx_proc_t *proc, uint8_t
int frame_tx = proc->frame_tx, nr_slot_tx = proc->nr_slot_tx, prach_power; // tx_amp int frame_tx = proc->frame_tx, nr_slot_tx = proc->nr_slot_tx, prach_power; // tx_amp
uint8_t mod_id = ue->Mod_id; uint8_t mod_id = ue->Mod_id;
NR_PRACH_RESOURCES_t * prach_resources = ue->prach_resources[gNB_id];
AssertFatal(prach_resources != NULL, "ue->prach_resources[%u] == NULL\n", gNB_id);
uint8_t nr_prach = 0; uint8_t nr_prach = 0;
VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_UE_TX_PRACH, VCD_FUNCTION_IN); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_PROCEDURES_UE_TX_PRACH, VCD_FUNCTION_IN);
if (ue->mac_enabled == 0){ nr_prach = nr_ue_get_rach(&ue->prach_vars[gNB_id]->prach_pdu, mod_id, ue->CC_id, frame_tx, gNB_id, nr_slot_tx);
LOG_D(PHY, "In %s:[%d.%d] getting PRACH resources : %d\n", __FUNCTION__, frame_tx, nr_slot_tx,nr_prach);
prach_resources->ra_TDD_map_index = 0;
prach_resources->ra_PREAMBLE_RECEIVED_TARGET_POWER = 10;
prach_resources->ra_RNTI = 0x1234;
nr_prach = 1;
prach_resources->init_msg1 = 1;
} else {
nr_prach = nr_ue_get_rach(prach_resources, &ue->prach_vars[0]->prach_pdu, mod_id, ue->CC_id, frame_tx, gNB_id, nr_slot_tx);
LOG_D(PHY, "In %s:[%d.%d] getting PRACH resources : %d\n", __FUNCTION__, frame_tx, nr_slot_tx,nr_prach);
}
if (nr_prach == GENERATE_PREAMBLE) { if (nr_prach == GENERATE_PREAMBLE) {
if (ue->mac_enabled == 1) { fapi_nr_ul_config_prach_pdu *prach_pdu = &ue->prach_vars[gNB_id]->prach_pdu;
int16_t pathloss = get_nr_PL(mod_id, ue->CC_id, gNB_id); ue->tx_power_dBm[nr_slot_tx] = prach_pdu->prach_tx_power;
int16_t ra_preamble_rx_power = (int16_t)(prach_resources->ra_PREAMBLE_RECEIVED_TARGET_POWER - pathloss + 30);
ue->tx_power_dBm[nr_slot_tx] = min(nr_get_Pcmax(mod_id), ra_preamble_rx_power);
LOG_D(PHY, "In %s: [UE %d][RAPROC][%d.%d]: Generating PRACH Msg1 (preamble %d, PL %d dB, P0_PRACH %d, TARGET_RECEIVED_POWER %d dBm, RA-RNTI %x)\n", LOG_D(PHY, "In %s: [UE %d][RAPROC][%d.%d]: Generating PRACH Msg1 (preamble %d, P0_PRACH %d)\n",
__FUNCTION__, __FUNCTION__,
mod_id, mod_id,
frame_tx, frame_tx,
nr_slot_tx, nr_slot_tx,
prach_resources->ra_PreambleIndex, prach_pdu->ra_PreambleIndex,
pathloss, ue->tx_power_dBm[nr_slot_tx]);
ue->tx_power_dBm[nr_slot_tx],
prach_resources->ra_PREAMBLE_RECEIVED_TARGET_POWER,
prach_resources->ra_RNTI);
}
ue->prach_vars[gNB_id]->amp = AMP; ue->prach_vars[gNB_id]->amp = AMP;
...@@ -1358,9 +1336,6 @@ void nr_ue_prach_procedures(PHY_VARS_NR_UE *ue, UE_nr_rxtx_proc_t *proc, uint8_t ...@@ -1358,9 +1336,6 @@ void nr_ue_prach_procedures(PHY_VARS_NR_UE *ue, UE_nr_rxtx_proc_t *proc, uint8_t
dB_fixed(prach_power), dB_fixed(prach_power),
ue->prach_vars[gNB_id]->amp); ue->prach_vars[gNB_id]->amp);
if (ue->mac_enabled == 1)
nr_Msg1_transmitted(mod_id, ue->CC_id, frame_tx, gNB_id);
} else if (nr_prach == WAIT_CONTENTION_RESOLUTION) { } else if (nr_prach == WAIT_CONTENTION_RESOLUTION) {
LOG_D(PHY, "In %s: [UE %d] RA waiting contention resolution\n", __FUNCTION__, mod_id); LOG_D(PHY, "In %s: [UE %d] RA waiting contention resolution\n", __FUNCTION__, mod_id);
ue->UE_mode[gNB_id] = RA_WAIT_CR; ue->UE_mode[gNB_id] = RA_WAIT_CR;
......
...@@ -213,12 +213,8 @@ void pucch_procedures_ue_nr(PHY_VARS_NR_UE *ue, ...@@ -213,12 +213,8 @@ void pucch_procedures_ue_nr(PHY_VARS_NR_UE *ue,
pucch_pdu = &pucch_vars->pucch_pdu[i]; pucch_pdu = &pucch_vars->pucch_pdu[i];
uint16_t nb_of_prbs = pucch_pdu->prb_size; uint16_t nb_of_prbs = pucch_pdu->prb_size;
/* Generate PUCCH signal according to its format and parameters */ /* Generate PUCCH signal according to its format and parameters */
ue->generate_ul_signal[gNB_id] = 1;
int16_t PL = get_nr_PL(ue->Mod_id, ue->CC_id, gNB_id); /* LTE function because NR path loss not yet implemented FFS TODO NR */ int16_t pucch_tx_power = pucch_pdu->pucch_tx_power;
int contributor = (10 * log10((double)(pow(2,(ue->frame_parms.numerology_index)) * nb_of_prbs)));
int16_t pucch_tx_power = pucch_pdu->pucch_tx_power + contributor + PL;
if (pucch_tx_power > ue->tx_power_max_dBm) if (pucch_tx_power > ue->tx_power_max_dBm)
pucch_tx_power = ue->tx_power_max_dBm; pucch_tx_power = ue->tx_power_max_dBm;
......
...@@ -264,7 +264,6 @@ int main(int argc, char **argv){ ...@@ -264,7 +264,6 @@ int main(int argc, char **argv){
int n_bytes=0; int n_bytes=0;
NR_DL_FRAME_PARMS *frame_parms; NR_DL_FRAME_PARMS *frame_parms;
NR_PRACH_RESOURCES_t prach_resources;
nfapi_nr_prach_config_t *prach_config; nfapi_nr_prach_config_t *prach_config;
nfapi_nr_prach_pdu_t *prach_pdu; nfapi_nr_prach_pdu_t *prach_pdu;
fapi_nr_prach_config_t *ue_prach_config; fapi_nr_prach_config_t *ue_prach_config;
...@@ -694,7 +693,6 @@ int main(int argc, char **argv){ ...@@ -694,7 +693,6 @@ int main(int argc, char **argv){
ue_prach_pdu = &UE->prach_vars[0]->prach_pdu; ue_prach_pdu = &UE->prach_vars[0]->prach_pdu;
ue_prach_config = &UE->nrUE_config.prach_config; ue_prach_config = &UE->nrUE_config.prach_config;
UE->prach_resources[0] = &prach_resources;
txdata = UE->common_vars.txdata; txdata = UE->common_vars.txdata;
UE->prach_vars[0]->amp = AMP; UE->prach_vars[0]->amp = AMP;
...@@ -717,8 +715,7 @@ int main(int argc, char **argv){ ...@@ -717,8 +715,7 @@ int main(int argc, char **argv){
if (n_frames == 1) if (n_frames == 1)
printf("raPreamble %d\n",preamble_tx); printf("raPreamble %d\n",preamble_tx);
UE->prach_resources[0]->ra_PreambleIndex = preamble_tx; ue_prach_pdu->ra_PreambleIndex = preamble_tx;
UE->prach_resources[0]->init_msg1 = 1;
// Configure channel // Configure channel
bw = N_RB_UL*(180e3)*(1 << frame_parms->numerology_index); bw = N_RB_UL*(180e3)*(1 << frame_parms->numerology_index);
...@@ -769,14 +766,7 @@ int main(int argc, char **argv){ ...@@ -769,14 +766,7 @@ int main(int argc, char **argv){
ue_prach_config->num_prach_fd_occasions_list[fd_occasion].prach_root_sequence_index, ue_prach_config->num_prach_fd_occasions_list[fd_occasion].prach_root_sequence_index,
UE->X_u); UE->X_u);
/*tx_lev = generate_nr_prach(UE, generate_nr_prach(UE, 0, frame, slot);
0, //gNB_id,
subframe); */ //commented for testing purpose
UE_nr_rxtx_proc_t proc={0};
proc.frame_tx = frame;
proc.nr_slot_tx = slot;
nr_ue_prach_procedures(UE, &proc, 0);
/* tx_lev_dB not used later, no need to set */ /* tx_lev_dB not used later, no need to set */
//tx_lev_dB = (unsigned int) dB_fixed(tx_lev); //tx_lev_dB = (unsigned int) dB_fixed(tx_lev);
...@@ -842,31 +832,31 @@ int main(int argc, char **argv){ ...@@ -842,31 +832,31 @@ int main(int argc, char **argv){
for (trial=0; trial<n_frames; trial++) { for (trial=0; trial<n_frames; trial++) {
if (input_fd==NULL) { if (input_fd==NULL) {
sigma2_dB = 10*log10((double)tx_lev) - SNR - 10*log10(N_RB_UL*12/N_ZC); sigma2_dB = 10*log10((double)tx_lev) - SNR - 10*log10(N_RB_UL*12/N_ZC);
if (n_frames==1) if (n_frames==1)
printf("sigma2_dB %f (SNR %f dB) tx_lev_dB %f\n",sigma2_dB,SNR,10*log10((double)tx_lev)); printf("sigma2_dB %f (SNR %f dB) tx_lev_dB %f\n",sigma2_dB,SNR,10*log10((double)tx_lev));
//AWGN //AWGN
sigma2 = pow(10,sigma2_dB/10); sigma2 = pow(10,sigma2_dB/10);
// printf("Sigma2 %f (sigma2_dB %f)\n",sigma2,sigma2_dB); // printf("Sigma2 %f (sigma2_dB %f)\n",sigma2,sigma2_dB);
if (awgn_flag == 0) { if (awgn_flag == 0) {
multipath_tv_channel(UE2gNB, s_re, s_im, r_re, r_im, frame_parms->samples_per_frame, 0); multipath_tv_channel(UE2gNB, s_re, s_im, r_re, r_im, frame_parms->samples_per_frame, 0);
} }
if (n_frames==1) { if (n_frames==1) {
printf("rx_level data symbol %f, tx_lev %f\n", printf("rx_level data symbol %f, tx_lev %f\n",
10*log10(signal_energy_fp(r_re,r_im,1,OFDM_SYMBOL_SIZE_COMPLEX_SAMPLES,0)), 10*log10(signal_energy_fp(r_re,r_im,1,OFDM_SYMBOL_SIZE_COMPLEX_SAMPLES,0)),
10*log10(tx_lev)); 10*log10(tx_lev));
} }
for (i = 0; i< frame_parms->samples_per_subframe; i++) { for (i = 0; i< frame_parms->samples_per_subframe; i++) {
for (aa = 0; aa < frame_parms->nb_antennas_rx; aa++) { for (aa = 0; aa < frame_parms->nb_antennas_rx; aa++) {
((short*) &ru->common.rxdata[aa][rx_prach_start])[2*i] = (short) (.167*(r_re[aa][i] +sqrt(sigma2/2)*gaussdouble(0.0,1.0))); ((short*) &ru->common.rxdata[aa][rx_prach_start])[2*i] = (short) (.167*(r_re[aa][i] +sqrt(sigma2/2)*gaussdouble(0.0,1.0)));
((short*) &ru->common.rxdata[aa][rx_prach_start])[2*i+1] = (short) (.167*(r_im[aa][i] + (iqim*r_re[aa][i]) + sqrt(sigma2/2)*gaussdouble(0.0,1.0))); ((short*) &ru->common.rxdata[aa][rx_prach_start])[2*i+1] = (short) (.167*(r_im[aa][i] + (iqim*r_re[aa][i]) + sqrt(sigma2/2)*gaussdouble(0.0,1.0)));
}
} }
}
} else { } else {
n_bytes = fread(&ru->common.rxdata[0][rx_prach_start],sizeof(int32_t),frame_parms->samples_per_subframe,input_fd); n_bytes = fread(&ru->common.rxdata[0][rx_prach_start],sizeof(int32_t),frame_parms->samples_per_subframe,input_fd);
printf("fread %d bytes from file %s\n",n_bytes,input_file); printf("fread %d bytes from file %s\n",n_bytes,input_file);
......
...@@ -104,6 +104,7 @@ int main(int argc, char **argv) ...@@ -104,6 +104,7 @@ int main(int argc, char **argv)
int nr_slot_tx=0; int nr_slot_tx=0;
int nr_frame_tx=0; int nr_frame_tx=0;
uint64_t actual_payload=0,payload_received; uint64_t actual_payload=0,payload_received;
bool random_payload = true;
int nr_bit=1; // maximum value possible is 2 int nr_bit=1; // maximum value possible is 2
uint8_t m0=0;// higher layer paramater initial cyclic shift uint8_t m0=0;// higher layer paramater initial cyclic shift
uint8_t nrofSymbols=1; //number of OFDM symbols can be 1-2 for format 1 uint8_t nrofSymbols=1; //number of OFDM symbols can be 1-2 for format 1
...@@ -317,6 +318,7 @@ int main(int argc, char **argv) ...@@ -317,6 +318,7 @@ int main(int argc, char **argv)
break; break;
case 'B': case 'B':
actual_payload=atoi(optarg); actual_payload=atoi(optarg);
random_payload = false;
break; break;
case 'T': case 'T':
//nacktoack_flag=(uint8_t)atoi(optarg); //nacktoack_flag=(uint8_t)atoi(optarg);
...@@ -379,6 +381,10 @@ int main(int argc, char **argv) ...@@ -379,6 +381,10 @@ int main(int argc, char **argv)
int do_DTX=0; int do_DTX=0;
if ((format < 2) && (actual_payload == 4)) do_DTX=1; if ((format < 2) && (actual_payload == 4)) do_DTX=1;
if (random_payload) {
srand(time(NULL)); // Initialization, should only be called once.
actual_payload = rand(); // Returns a pseudo-random integer between 0 and RAND_MAX.
}
actual_payload &= ((1<<nr_bit)-1); actual_payload &= ((1<<nr_bit)-1);
printf("Transmitted payload is %ld, do_DTX = %d\n",actual_payload,do_DTX); printf("Transmitted payload is %ld, do_DTX = %d\n",actual_payload,do_DTX);
...@@ -647,7 +653,7 @@ int main(int argc, char **argv) ...@@ -647,7 +653,7 @@ int main(int argc, char **argv)
if (nr_bit==1 && do_DTX == 0) if (nr_bit==1 && do_DTX == 0)
ack_nack_errors+=(actual_payload^(!harq_list[0].harq_value)); ack_nack_errors+=(actual_payload^(!harq_list[0].harq_value));
else if (do_DTX == 0) else if (do_DTX == 0)
ack_nack_errors+=(((actual_payload&1)^(!harq_list[0].harq_value))+((actual_payload>>1)^(!harq_list[1].harq_value))); ack_nack_errors+=(((actual_payload&1)^(!harq_list[1].harq_value))+((actual_payload>>1)^(!harq_list[0].harq_value)));
else if ((!confidence_lvl && !harq_list[0].harq_value) || else if ((!confidence_lvl && !harq_list[0].harq_value) ||
(!confidence_lvl && nr_bit == 2 && !harq_list[1].harq_value)) (!confidence_lvl && nr_bit == 2 && !harq_list[1].harq_value))
ack_nack_errors++; ack_nack_errors++;
......
...@@ -37,6 +37,8 @@ ...@@ -37,6 +37,8 @@
#include "f1ap_du_interface_management.h" #include "f1ap_du_interface_management.h"
#include "assertions.h" #include "assertions.h"
#include "GNB_APP/gnb_paramdef.h"
int to_NRNRB(int nrb) { int to_NRNRB(int nrb) {
for (int i=0; i<sizeofArray(nrb_lut); i++) for (int i=0; i<sizeofArray(nrb_lut); i++)
if (nrb_lut[i] == nrb) if (nrb_lut[i] == nrb)
...@@ -180,12 +182,30 @@ int DU_send_F1_SETUP_REQUEST(instance_t instance) { ...@@ -180,12 +182,30 @@ int DU_send_F1_SETUP_REQUEST(instance_t instance) {
served_plmns_itemExtIEs->extensionValue.present = F1AP_ServedPLMNs_ItemExtIEs__extensionValue_PR_SliceSupportList; served_plmns_itemExtIEs->extensionValue.present = F1AP_ServedPLMNs_ItemExtIEs__extensionValue_PR_SliceSupportList;
F1AP_SliceSupportList_t *slice_support_list = &served_plmns_itemExtIEs->extensionValue.choice.SliceSupportList; F1AP_SliceSupportList_t *slice_support_list = &served_plmns_itemExtIEs->extensionValue.choice.SliceSupportList;
asn1cSequenceAdd(slice_support_list->list, F1AP_SliceSupportItem_t, SliceSupport_item); /* get list of sst/sd from configuration file */
INT8_TO_OCTET_STRING(1,&SliceSupport_item->sNSSAI.sST); paramdef_t SNSSAIParams[] = GNBSNSSAIPARAMS_DESC;
asn1cCalloc(SliceSupport_item->sNSSAI.sD, tmp); paramlist_def_t SNSSAIParamList = {GNB_CONFIG_STRING_SNSSAI_LIST, NULL, 0};
INT24_TO_OCTET_STRING(10203,tmp); char sstr[100];
//INT24_TO_OCTET_STRING(1,tmp); /* TODO: be sure that %d in the line below is at the right place */
sprintf(sstr, "%s.[%d].%s.[0]", GNB_CONFIG_STRING_GNB_LIST, i, GNB_CONFIG_STRING_PLMN_LIST);
config_getlist(&SNSSAIParamList, SNSSAIParams, sizeof(SNSSAIParams)/sizeof(paramdef_t), sstr);
AssertFatal(SNSSAIParamList.numelt > 0, "no slice configuration found (snssaiList in the configuration file)\n");
AssertFatal(SNSSAIParamList.numelt <= 1024, "maximum size for slice support list is 1024, see F1AP 38.473 9.3.1.37\n");
for (int s = 0; s < SNSSAIParamList.numelt; s++) {
uint32_t sst;
uint32_t sd;
bool has_sd;
sst = *SNSSAIParamList.paramarray[s][GNB_SLICE_SERVICE_TYPE_IDX].uptr;
has_sd = *SNSSAIParamList.paramarray[s][GNB_SLICE_DIFFERENTIATOR_IDX].uptr != 0xffffff;
asn1cSequenceAdd(slice_support_list->list, F1AP_SliceSupportItem_t, slice);
INT8_TO_OCTET_STRING(sst, &slice->sNSSAI.sST);
if (has_sd) {
sd = *SNSSAIParamList.paramarray[s][GNB_SLICE_DIFFERENTIATOR_IDX].uptr;
asn1cCalloc(slice->sNSSAI.sD, tmp);
INT24_TO_OCTET_STRING(sd, tmp);
}
}
if (f1ap_req(false, instance)->fdd_flag) { // FDD if (f1ap_req(false, instance)->fdd_flag) { // FDD
nR_Mode_Info->present = F1AP_NR_Mode_Info_PR_fDD; nR_Mode_Info->present = F1AP_NR_Mode_Info_PR_fDD;
asn1cCalloc(nR_Mode_Info->choice.fDD, fDD_Info); asn1cCalloc(nR_Mode_Info->choice.fDD, fDD_Info);
......
...@@ -96,15 +96,6 @@ void du_task_handle_sctp_data_ind(instance_t instance, sctp_data_ind_t *sctp_dat ...@@ -96,15 +96,6 @@ void du_task_handle_sctp_data_ind(instance_t instance, sctp_data_ind_t *sctp_dat
AssertFatal (result == EXIT_SUCCESS, "Failed to free memory (%d)!\n", result); AssertFatal (result == EXIT_SUCCESS, "Failed to free memory (%d)!\n", result);
} }
static instance_t du_create_gtpu_instance_to_cu(char *CUaddr, uint16_t CUport, char *DUaddr, uint16_t DUport) {
openAddr_t tmp= {0};
strncpy(tmp.originHost, DUaddr, sizeof(tmp.originHost)-1);
strncpy(tmp.destinationHost, CUaddr, sizeof(tmp.destinationHost)-1);
sprintf(tmp.originService, "%d", DUport);
sprintf(tmp.destinationService, "%d", CUport);
return gtpv1Init(tmp);
}
void *F1AP_DU_task(void *arg) { void *F1AP_DU_task(void *arg) {
//sctp_cu_init(); //sctp_cu_init();
LOG_I(F1AP, "Starting F1AP at DU\n"); LOG_I(F1AP, "Starting F1AP at DU\n");
...@@ -126,15 +117,6 @@ void *F1AP_DU_task(void *arg) { ...@@ -126,15 +117,6 @@ void *F1AP_DU_task(void *arg) {
LOG_I(F1AP, "DU Task Received F1AP_SETUP_REQ\n"); LOG_I(F1AP, "DU Task Received F1AP_SETUP_REQ\n");
f1ap_setup_req_t *msgSetup=&F1AP_SETUP_REQ(msg); f1ap_setup_req_t *msgSetup=&F1AP_SETUP_REQ(msg);
createF1inst(false, myInstance, msgSetup); createF1inst(false, myInstance, msgSetup);
getCxt(DUtype, myInstance)->gtpInst=du_create_gtpu_instance_to_cu(msgSetup->CU_f1_ip_address.ipv4_address, //"172.21.6.9", //"172.21.10.9",//"172.21.9.5", //msgSetup->CU_f1_ip_address.ipv4_address, //"192.168.18.91"
msgSetup->CUport,
msgSetup->DU_f1_ip_address.ipv4_address,
msgSetup->DUport);
AssertFatal(getCxt(DUtype, myInstance)->gtpInst>0,"Failed to create CU F1-U UDP listener");
// Fixme: fully inconsistent instances management
// dirty global var is a bad fix
extern instance_t legacyInstanceMapping;
legacyInstanceMapping = DUuniqInstance = getCxt(DUtype, myInstance)->gtpInst;
du_task_send_sctp_association_req(myInstance,msgSetup); du_task_send_sctp_association_req(myInstance,msgSetup);
break; break;
......
...@@ -1078,6 +1078,17 @@ int DU_send_UE_CONTEXT_RELEASE_COMPLETE(instance_t instance, ...@@ -1078,6 +1078,17 @@ int DU_send_UE_CONTEXT_RELEASE_COMPLETE(instance_t instance,
f1ap_remove_ue(DUtype, instance, cplt->rnti); f1ap_remove_ue(DUtype, instance, cplt->rnti);
return 0; return 0;
} }
static instance_t du_create_gtpu_instance_to_cu(char *CUaddr, uint16_t CUport, char *DUaddr, uint16_t DUport)
{
openAddr_t tmp;
strncpy(tmp.originHost, DUaddr, sizeof(tmp.originHost)-1);
strncpy(tmp.destinationHost, CUaddr, sizeof(tmp.destinationHost)-1);
sprintf(tmp.originService, "%d", DUport);
sprintf(tmp.destinationService, "%d", CUport);
return gtpv1Init(tmp);
}
int DU_handle_UE_CONTEXT_MODIFICATION_REQUEST(instance_t instance, int DU_handle_UE_CONTEXT_MODIFICATION_REQUEST(instance_t instance,
uint32_t assoc_id, uint32_t assoc_id,
uint32_t stream, uint32_t stream,
...@@ -1160,6 +1171,26 @@ int DU_handle_UE_CONTEXT_MODIFICATION_REQUEST(instance_t instance, ...@@ -1160,6 +1171,26 @@ int DU_handle_UE_CONTEXT_MODIFICATION_REQUEST(instance_t instance,
// 3GPP assumes GTP-U is on port 2152, but OAI is configurable // 3GPP assumes GTP-U is on port 2152, but OAI is configurable
drb_p->up_ul_tnl[0].port=getCxt(false,instance)->setupReq.CUport; drb_p->up_ul_tnl[0].port=getCxt(false,instance)->setupReq.CUport;
extern instance_t DUuniqInstance;
if (DUuniqInstance == 0) {
char gtp_tunnel_ip_address[128];
sprintf(gtp_tunnel_ip_address, "%d.%d.%d.%d",
drb_p->up_ul_tnl[0].tl_address & 0xff,
(drb_p->up_ul_tnl[0].tl_address >> 8) & 0xff,
(drb_p->up_ul_tnl[0].tl_address >> 16) & 0xff,
(drb_p->up_ul_tnl[0].tl_address >> 24) & 0xff);
getCxt(DUtype, instance)->gtpInst=du_create_gtpu_instance_to_cu(
gtp_tunnel_ip_address,
getCxt(false,instance)->setupReq.CUport,
getCxt(false,instance)->setupReq.DU_f1_ip_address.ipv4_address,
getCxt(false,instance)->setupReq.DUport);
AssertFatal(getCxt(DUtype, instance)->gtpInst>0,"Failed to create CU F1-U UDP listener");
// Fixme: fully inconsistent instances management
// dirty global var is a bad fix
extern instance_t legacyInstanceMapping;
legacyInstanceMapping = DUuniqInstance = getCxt(DUtype, instance)->gtpInst;
}
switch (drbs_tobesetupmod_item_p->rLCMode) { switch (drbs_tobesetupmod_item_p->rLCMode) {
case F1AP_RLCMode_rlc_am: case F1AP_RLCMode_rlc_am:
drb_p->rlc_mode = RLC_MODE_AM; drb_p->rlc_mode = RLC_MODE_AM;
......
...@@ -83,6 +83,7 @@ ...@@ -83,6 +83,7 @@
#include "NR_EUTRA-MBSFN-SubframeConfig.h" #include "NR_EUTRA-MBSFN-SubframeConfig.h"
#include "RRC/NR/MESSAGES/asn1_msg.h" #include "RRC/NR/MESSAGES/asn1_msg.h"
#include "RRC/NR/nr_rrc_extern.h"
#include "openair2/LAYER2/nr_pdcp/nr_pdcp.h" #include "openair2/LAYER2/nr_pdcp/nr_pdcp.h"
extern uint16_t sf_ahead; extern uint16_t sf_ahead;
......
...@@ -27,7 +27,6 @@ ...@@ -27,7 +27,6 @@
#include "common/utils/nr/nr_common.h" #include "common/utils/nr/nr_common.h"
#include <math.h> #include <math.h>
#include "PHY/defs_nr_common.h"
//Table 5.1.2.2-2 //Table 5.1.2.2-2
uint16_t Tbstable_nr[INDEX_MAX_TBS_TABLE] = {24,32,40,48,56,64,72,80,88,96,104,112,120,128,136,144,152,160,168,176,184,192,208,224,240,256,272,288,304,320,336,352,368,384,408,432,456,480,504,528,552,576,608,640,672,704,736,768,808,848,888,928,984,1032,1064,1128,1160,1192,1224,1256,1288,1320,1352,1416,1480,1544,1608,1672,1736,1800,1864,1928,2024,2088,2152,2216,2280,2408,2472,2536,2600,2664,2728,2792,2856,2976,3104,3240,3368,3496,3624,3752,3824}; uint16_t Tbstable_nr[INDEX_MAX_TBS_TABLE] = {24,32,40,48,56,64,72,80,88,96,104,112,120,128,136,144,152,160,168,176,184,192,208,224,240,256,272,288,304,320,336,352,368,384,408,432,456,480,504,528,552,576,608,640,672,704,736,768,808,848,888,928,984,1032,1064,1128,1160,1192,1224,1256,1288,1320,1352,1416,1480,1544,1608,1672,1736,1800,1864,1928,2024,2088,2152,2216,2280,2408,2472,2536,2600,2664,2728,2792,2856,2976,3104,3240,3368,3496,3624,3752,3824};
...@@ -48,7 +47,8 @@ uint32_t nr_compute_tbs(uint16_t Qm, ...@@ -48,7 +47,8 @@ uint32_t nr_compute_tbs(uint16_t Qm,
LOG_D(NR_MAC, "In %s: nb_symb_sch %d, nb_dmrs_prb %d, nb_rb %d, nb_rb_oh %d, tb_scaling %d Nl %d\n", __FUNCTION__, nb_symb_sch, nb_dmrs_prb, nb_rb, nb_rb_oh, tb_scaling, Nl); LOG_D(NR_MAC, "In %s: nb_symb_sch %d, nb_dmrs_prb %d, nb_rb %d, nb_rb_oh %d, tb_scaling %d Nl %d\n", __FUNCTION__, nb_symb_sch, nb_dmrs_prb, nb_rb, nb_rb_oh, tb_scaling, Nl);
const uint32_t nbp_re = NR_NB_SC_PER_RB * nb_symb_sch - nb_dmrs_prb - nb_rb_oh; const int nb_subcarrier_per_rb = 12;
const uint32_t nbp_re = nb_subcarrier_per_rb * nb_symb_sch - nb_dmrs_prb - nb_rb_oh;
const uint32_t nb_re = min(156, nbp_re) * nb_rb; const uint32_t nb_re = min(156, nbp_re) * nb_rb;
// Intermediate number of information bits // Intermediate number of information bits
// Rx1024 is tabulated as 10 times the actual code rate // Rx1024 is tabulated as 10 times the actual code rate
......
...@@ -1386,7 +1386,7 @@ int64_t *get_prach_config_info(frequency_range_t freq_range, ...@@ -1386,7 +1386,7 @@ int64_t *get_prach_config_info(frequency_range_t freq_range,
void find_aggregation_candidates(uint8_t *aggregation_level, void find_aggregation_candidates(uint8_t *aggregation_level,
uint8_t *nr_of_candidates, uint8_t *nr_of_candidates,
NR_SearchSpace_t *ss, const NR_SearchSpace_t *ss,
int L) { int L) {
AssertFatal(L>=1 && L<=16,"L %d not ok\n",L); AssertFatal(L>=1 && L<=16,"L %d not ok\n",L);
*nr_of_candidates = 0; *nr_of_candidates = 0;
...@@ -3931,7 +3931,7 @@ uint8_t get_BG(uint32_t A, uint16_t R) { ...@@ -3931,7 +3931,7 @@ uint8_t get_BG(uint32_t A, uint16_t R) {
return 1; return 1;
} }
uint32_t get_Y(NR_SearchSpace_t *ss, int slot, rnti_t rnti) { uint32_t get_Y(const NR_SearchSpace_t *ss, int slot, rnti_t rnti) {
if(ss->searchSpaceType->present == NR_SearchSpace__searchSpaceType_PR_common) if(ss->searchSpaceType->present == NR_SearchSpace__searchSpaceType_PR_common)
return 0; return 0;
......
...@@ -50,7 +50,7 @@ typedef enum { ...@@ -50,7 +50,7 @@ typedef enum {
typeB = 1 typeB = 1
} mappingType_t; } mappingType_t;
uint32_t get_Y(NR_SearchSpace_t *ss, int slot, rnti_t rnti); uint32_t get_Y(const NR_SearchSpace_t *ss, int slot, rnti_t rnti);
uint8_t get_BG(uint32_t A, uint16_t R); uint8_t get_BG(uint32_t A, uint16_t R);
...@@ -90,7 +90,7 @@ uint16_t nr_dci_size(const NR_BWP_DownlinkCommon_t *initialDLBWP, ...@@ -90,7 +90,7 @@ uint16_t nr_dci_size(const NR_BWP_DownlinkCommon_t *initialDLBWP,
void find_aggregation_candidates(uint8_t *aggregation_level, void find_aggregation_candidates(uint8_t *aggregation_level,
uint8_t *nr_of_candidates, uint8_t *nr_of_candidates,
NR_SearchSpace_t *ss, const NR_SearchSpace_t *ss,
int maxL); int maxL);
void find_monitoring_periodicity_offset_common(NR_SearchSpace_t *ss, void find_monitoring_periodicity_offset_common(NR_SearchSpace_t *ss,
......
...@@ -632,7 +632,6 @@ int nr_rrc_mac_config_req_ue( ...@@ -632,7 +632,6 @@ int nr_rrc_mac_config_req_ue(
build_ssb_to_ro_map(mac);//->scc, mac->phy_config.config_req.cell_config.frame_duplex_type); build_ssb_to_ro_map(mac);//->scc, mac->phy_config.config_req.cell_config.frame_duplex_type);
if (!get_softmodem_params()->emulate_l1) if (!get_softmodem_params()->emulate_l1)
mac->if_module->phy_config_request(&mac->phy_config); mac->if_module->phy_config_request(&mac->phy_config);
mac->common_configuration_complete = 1;
} }
if(scell_group_config != NULL ){ if(scell_group_config != NULL ){
mac->cg = scell_group_config; mac->cg = scell_group_config;
......
...@@ -38,9 +38,6 @@ ...@@ -38,9 +38,6 @@
#include <string.h> #include <string.h>
#include "platform_types.h" #include "platform_types.h"
/* PHY */
#include "PHY/defs_nr_common.h"
/* IF */ /* IF */
#include "NR_IF_Module.h" #include "NR_IF_Module.h"
#include "fapi_nr_ue_interface.h" #include "fapi_nr_ue_interface.h"
...@@ -64,10 +61,7 @@ ...@@ -64,10 +61,7 @@
#include "NR_CellGroupConfig.h" #include "NR_CellGroupConfig.h"
#include "NR_ServingCellConfig.h" #include "NR_ServingCellConfig.h"
#include "NR_MeasConfig.h" #include "NR_MeasConfig.h"
#include "fapi_nr_ue_interface.h"
#include "NR_IF_Module.h"
#include "PHY/defs_nr_common.h"
#include "openair2/LAYER2/NR_MAC_COMMON/nr_mac.h"
// ========== // ==========
// NR UE defs // NR UE defs
...@@ -242,6 +236,31 @@ typedef enum { ...@@ -242,6 +236,31 @@ typedef enum {
RA_FAILED = 5 RA_FAILED = 5
} RA_state_t; } RA_state_t;
typedef struct {
/// PRACH format retrieved from prach_ConfigIndex
uint16_t prach_format;
/// Preamble Tx Counter
uint8_t RA_PREAMBLE_TRANSMISSION_COUNTER;
/// Preamble Power Ramping Counter
uint8_t RA_PREAMBLE_POWER_RAMPING_COUNTER;
/// 2-step RA power offset
int POWER_OFFSET_2STEP_RA;
/// Target received power at gNB. Baseline is range -202..-60 dBm. Depends on delta preamble, power ramping counter and step.
int ra_PREAMBLE_RECEIVED_TARGET_POWER;
/// PRACH index for TDD (0 ... 6) depending on TDD configuration and prachConfigIndex
uint8_t ra_TDD_map_index;
/// RA Preamble Power Ramping Step in dB
uint32_t RA_PREAMBLE_POWER_RAMPING_STEP;
///
uint8_t RA_PREAMBLE_BACKOFF;
///
uint8_t RA_SCALING_FACTOR_BI;
/// Indicating whether it is 2-step or 4-step RA
nr_ra_type_e RA_TYPE;
/// UE configured maximum output power
int RA_PCMAX;
} NR_PRACH_RESOURCES_t;
typedef struct { typedef struct {
// pointer to RACH config dedicated // pointer to RACH config dedicated
...@@ -302,6 +321,8 @@ typedef struct { ...@@ -302,6 +321,8 @@ typedef struct {
/// RA SearchSpace /// RA SearchSpace
NR_SearchSpace_t *ss; NR_SearchSpace_t *ss;
NR_PRACH_RESOURCES_t prach_resources;
} RA_config_t; } RA_config_t;
typedef struct { typedef struct {
...@@ -344,6 +365,14 @@ typedef struct { ...@@ -344,6 +365,14 @@ typedef struct {
int8_t delta_pucch; int8_t delta_pucch;
} PUCCH_sched_t; } PUCCH_sched_t;
typedef struct {
uint32_t ssb_index;
/// SSB RSRP in dBm
short ssb_rsrp_dBm;
} NR_PHY_meas_t;
/*!\brief Top level UE MAC structure */ /*!\brief Top level UE MAC structure */
typedef struct { typedef struct {
...@@ -355,7 +384,7 @@ typedef struct { ...@@ -355,7 +384,7 @@ typedef struct {
NR_CSI_ReportConfig_t *csirc; NR_CSI_ReportConfig_t *csirc;
long physCellId; long physCellId;
//// MAC config //// MAC config
int common_configuration_complete; int first_sync_frame;
NR_DRX_Config_t *drx_Config; NR_DRX_Config_t *drx_Config;
NR_SchedulingRequestConfig_t *schedulingRequestConfig; NR_SchedulingRequestConfig_t *schedulingRequestConfig;
NR_BSR_Config_t *bsr_Config; NR_BSR_Config_t *bsr_Config;
...@@ -396,8 +425,6 @@ typedef struct { ...@@ -396,8 +425,6 @@ typedef struct {
RA_config_t ra; RA_config_t ra;
/// SSB index from MIB decoding /// SSB index from MIB decoding
uint8_t mib_ssb; uint8_t mib_ssb;
/// measured SSB RSRP in dBm
short ssb_rsrp_dBm;
nr_csi_report_t csi_report_template[MAX_CSI_REPORTCONFIG]; nr_csi_report_t csi_report_template[MAX_CSI_REPORTCONFIG];
...@@ -433,6 +460,8 @@ typedef struct { ...@@ -433,6 +460,8 @@ typedef struct {
uint16_t nr_band; uint16_t nr_band;
uint8_t ssb_subcarrier_offset; uint8_t ssb_subcarrier_offset;
NR_PHY_meas_t phy_measurements;
dci_pdu_rel15_t def_dci_pdu_rel15[8]; dci_pdu_rel15_t def_dci_pdu_rel15[8];
// Defined for abstracted mode // Defined for abstracted mode
......
...@@ -309,6 +309,7 @@ void select_pucch_resource(NR_UE_MAC_INST_t *mac, ...@@ -309,6 +309,7 @@ void select_pucch_resource(NR_UE_MAC_INST_t *mac,
PUCCH_sched_t *pucch); PUCCH_sched_t *pucch);
int16_t get_pucch_tx_power_ue(NR_UE_MAC_INST_t *mac, int16_t get_pucch_tx_power_ue(NR_UE_MAC_INST_t *mac,
int scs,
NR_PUCCH_Config_t *pucch_Config, NR_PUCCH_Config_t *pucch_Config,
PUCCH_sched_t *pucch, PUCCH_sched_t *pucch,
uint8_t format_type, uint8_t format_type,
...@@ -392,6 +393,8 @@ void nr_ra_failed(uint8_t mod_id, uint8_t CC_id, NR_PRACH_RESOURCES_t *prach_res ...@@ -392,6 +393,8 @@ void nr_ra_failed(uint8_t mod_id, uint8_t CC_id, NR_PRACH_RESOURCES_t *prach_res
void nr_ra_succeeded(module_id_t mod_id, frame_t frame, int slot); void nr_ra_succeeded(module_id_t mod_id, frame_t frame, int slot);
void nr_get_RA_window(NR_UE_MAC_INST_t *mac);
/* \brief Function called by PHY to retrieve information to be transmitted using the RA procedure. /* \brief Function called by PHY to retrieve information to be transmitted using the RA procedure.
If the UE is not in PUSCH mode for a particular eNB index, this is assumed to be an Msg3 and MAC If the UE is not in PUSCH mode for a particular eNB index, this is assumed to be an Msg3 and MAC
attempts to retrieves the CCCH message from RRC. If the UE is in PUSCH mode for a particular eNB attempts to retrieves the CCCH message from RRC. If the UE is in PUSCH mode for a particular eNB
...@@ -403,8 +406,7 @@ andom-access to transmit a BSR along with the C-RNTI control element (see 5.1.4 ...@@ -403,8 +406,7 @@ andom-access to transmit a BSR along with the C-RNTI control element (see 5.1.4
@param gNB_id gNB index @param gNB_id gNB index
@param nr_slot_tx slot for PRACH transmission @param nr_slot_tx slot for PRACH transmission
@returns indication to generate PRACH to phy */ @returns indication to generate PRACH to phy */
uint8_t nr_ue_get_rach(NR_PRACH_RESOURCES_t *prach_resources, uint8_t nr_ue_get_rach(fapi_nr_ul_config_prach_pdu *prach_pdu,
fapi_nr_ul_config_prach_pdu *prach_pdu,
module_id_t mod_id, module_id_t mod_id,
int CC_id, int CC_id,
frame_t frame, frame_t frame,
...@@ -424,7 +426,17 @@ void nr_get_prach_resources(module_id_t mod_id, ...@@ -424,7 +426,17 @@ void nr_get_prach_resources(module_id_t mod_id,
fapi_nr_ul_config_prach_pdu *prach_pdu, fapi_nr_ul_config_prach_pdu *prach_pdu,
NR_RACH_ConfigDedicated_t * rach_ConfigDedicated); NR_RACH_ConfigDedicated_t * rach_ConfigDedicated);
void nr_Msg1_transmitted(module_id_t mod_id, uint8_t CC_id, frame_t frameP, uint8_t gNB_id); void init_RA(module_id_t mod_id,
NR_PRACH_RESOURCES_t *prach_resources,
NR_RACH_ConfigCommon_t *nr_rach_ConfigCommon,
NR_RACH_ConfigGeneric_t *rach_ConfigGeneric,
NR_RACH_ConfigDedicated_t *rach_ConfigDedicated);
int16_t get_prach_tx_power(module_id_t mod_id);
void set_ra_rnti(NR_UE_MAC_INST_t *mac, fapi_nr_ul_config_prach_pdu *prach_pdu);
void nr_Msg1_transmitted(module_id_t mod_id);
void nr_Msg3_transmitted(module_id_t mod_id, uint8_t CC_id, frame_t frameP, slot_t slotP, uint8_t gNB_id); void nr_Msg3_transmitted(module_id_t mod_id, uint8_t CC_id, frame_t frameP, slot_t slotP, uint8_t gNB_id);
...@@ -451,6 +463,8 @@ fapi_nr_ul_config_request_t *get_ul_config_request(NR_UE_MAC_INST_t *mac, int sl ...@@ -451,6 +463,8 @@ fapi_nr_ul_config_request_t *get_ul_config_request(NR_UE_MAC_INST_t *mac, int sl
void fill_ul_config(fapi_nr_ul_config_request_t *ul_config, frame_t frame_tx, int slot_tx, uint8_t pdu_type); void fill_ul_config(fapi_nr_ul_config_request_t *ul_config, frame_t frame_tx, int slot_tx, uint8_t pdu_type);
int16_t compute_nr_SSB_PL(NR_UE_MAC_INST_t *mac, short ssb_rsrp_dBm);
// PUSCH scheduler: // PUSCH scheduler:
// - Calculate the slot in which ULSCH should be scheduled. This is current slot + K2, // - Calculate the slot in which ULSCH should be scheduled. This is current slot + K2,
// - where K2 is the offset between the slot in which UL DCI is received and the slot // - where K2 is the offset between the slot in which UL DCI is received and the slot
......
...@@ -35,8 +35,6 @@ ...@@ -35,8 +35,6 @@
#include "radio/COMMON/common_lib.h" #include "radio/COMMON/common_lib.h"
//#undef MALLOC //#undef MALLOC
#include "assertions.h" #include "assertions.h"
#include "PHY/types.h"
#include "PHY/defs_UE.h"
#include "openair2/LAYER2/nr_pdcp/nr_pdcp_entity.h" #include "openair2/LAYER2/nr_pdcp/nr_pdcp_entity.h"
#include "executables/softmodem-common.h" #include "executables/softmodem-common.h"
#include "openair2/LAYER2/nr_pdcp/nr_pdcp.h" #include "openair2/LAYER2/nr_pdcp/nr_pdcp.h"
...@@ -52,12 +50,12 @@ NR_UE_MAC_INST_t * nr_l2_init_ue(NR_UE_RRC_INST_t* rrc_inst) { ...@@ -52,12 +50,12 @@ NR_UE_MAC_INST_t * nr_l2_init_ue(NR_UE_RRC_INST_t* rrc_inst) {
//init mac here //init mac here
nr_ue_mac_inst = (NR_UE_MAC_INST_t *)calloc(sizeof(NR_UE_MAC_INST_t),NB_NR_UE_MAC_INST); nr_ue_mac_inst = (NR_UE_MAC_INST_t *)calloc(sizeof(NR_UE_MAC_INST_t),NB_NR_UE_MAC_INST);
nr_ue_mac_inst->first_sync_frame = -1;
for (int j=0;j<NB_NR_UE_MAC_INST;j++) { for (int j=0;j<NB_NR_UE_MAC_INST;j++) {
nr_ue_init_mac(j); nr_ue_init_mac(j);
} }
if (rrc_inst && rrc_inst->scell_group_config) { if (rrc_inst && rrc_inst->scell_group_config) {
nr_rrc_mac_config_req_ue(0,0,0,NULL,NULL,NULL,rrc_inst->scell_group_config); nr_rrc_mac_config_req_ue(0,0,0,NULL,NULL,NULL,rrc_inst->scell_group_config);
......
/*
* 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
*/
/*! \file nr_l1_helper.c
* \brief PHY/MAC helper functions
* \author Guido Casati
* \date 2019
* \version 2.0
* \email guido.casati@iis.fraunhofer.de
* @ingroup _mac
*/
#include "PHY/defs_nr_common.h"
//#include "PHY/impl_defs_top.h"
#include "mac_defs.h"
#include "LAYER2/NR_MAC_COMMON/nr_mac_extern.h"
#include "LAYER2/NR_MAC_UE/mac_proto.h"
#include "LAYER2/NR_MAC_UE/nr_l1_helpers.h"
#include "NR_P-Max.h"
// Implementation of 6.2.4 Configured ransmitted power
// 3GPP TS 38.101-1 version 16.5.0 Release 16
// -
// The UE is allowed to set its configured maximum output power PCMAX,f,c for carrier f of serving cell c in each slot.
// The configured maximum output power PCMAX,f,c is set within the following bounds: PCMAX_L,f,c <= PCMAX,f,c <= PCMAX_H,f,c
// -
// Measurement units:
// - p_max: dBm
// - delta_TC_c: dB
// - P_powerclass: dBm
// - delta_P_powerclass: dB
// - MPR_c: dB
// - delta_MPR_c: dB
// - delta_T_IB_c dB
// - delta_rx_SRS dB
// note:
// - Assuming:
// -- Powerclass 3 capable UE (which is default power class unless otherwise stated)
// -- Maximum power reduction (MPR_c) for power class 3, QPSK, inner RB allocations
// -- no additional MPR (A_MPR_c)
// todo:
// - in current implementation delta_P_powerclass is not handling power classes different from 3
long nr_get_Pcmax(module_id_t mod_id){
NR_UE_MAC_INST_t *mac = get_mac_inst(mod_id);
uint32_t band = (mac->scc!=NULL) ? *mac->scc->downlinkConfigCommon->frequencyInfoDL->frequencyBandList.list.array[0] :
*mac->scc_SIB->downlinkConfigCommon.frequencyInfoDL.frequencyBandList.list.array[0]->freqBandIndicatorNR;
NR_P_Max_t p_max = 0;
uint8_t P_powerclass = 23;
uint8_t delta_P_powerclass = 0;
uint8_t MPR_c = 1.5;
uint8_t delta_MPR_c = 0;
uint8_t A_MPR_c = 0;
uint8_t delta_T_IB_c = 0;
uint8_t delta_TC_c = 0;
uint8_t delta_rx_SRS = 0;
uint8_t P_MPR_c = 0;
long P_cmax_l = 0;
long P_cmax_h = 0;
long P_cmax = 0;
if (band == 28 && mac->phy_config.config_req.carrier_config.uplink_bandwidth == 30){
delta_MPR_c = 0.5;
}
if (mac->cg && mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig->ext1){
if (*mac->cg->spCellConfig->spCellConfigDedicated->uplinkConfig->ext1->powerBoostPi2BPSK == 1){
// TbD: assuming power class 3 capable UE operating in TDD bands n40, n41, n77, n78, and n79 with Pi/2 BPSK modulation
delta_P_powerclass = -3;
p_max += 3;
}
}
NR_P_Max_t *p_Max = (mac->scc!=NULL) ? mac->scc->uplinkConfigCommon->frequencyInfoUL->p_Max : mac->scc_SIB->uplinkConfigCommon->frequencyInfoUL.p_Max;
if (p_Max){
p_max += *p_Max;
LOG_D(MAC, "In %s maximum UL transmission power p_max is %ld dBm \n", __FUNCTION__, p_max);
P_cmax_l = min(p_max - delta_TC_c, (P_powerclass - delta_P_powerclass) - max(max(MPR_c + delta_MPR_c, A_MPR_c) + delta_T_IB_c + delta_TC_c + delta_rx_SRS, P_MPR_c));
P_cmax_h = min(p_max, P_powerclass - delta_P_powerclass);
} else {
P_cmax_l = (P_powerclass - delta_P_powerclass) - max(max(MPR_c + delta_MPR_c, A_MPR_c) + delta_T_IB_c + delta_TC_c + delta_rx_SRS, P_MPR_c);
P_cmax_h = P_powerclass - delta_P_powerclass;
}
P_cmax = (P_cmax_h + P_cmax_l) / 2;
LOG_D(MAC, "In %s configured maximum output power: %ld dBm <= PCMAX %ld dBm <= %ld dBm \n", __FUNCTION__, P_cmax_l, P_cmax, P_cmax_h);
return P_cmax;
}
/*
* 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
*/
/** \brief Function to compute configured maximum output power according to clause 6.2.4 of 3GPP TS 38.101-1 version 16.5.0 Release 16
@param Mod_id Module id of UE
*/
long nr_get_Pcmax(module_id_t mod_id);
/** @}*/
...@@ -374,7 +374,7 @@ int8_t nr_ue_decode_mib(module_id_t module_id, ...@@ -374,7 +374,7 @@ int8_t nr_ue_decode_mib(module_id_t module_id,
else else
ssb_sc_offset_norm = ssb_subcarrier_offset; ssb_sc_offset_norm = ssb_subcarrier_offset;
if (mac->common_configuration_complete == 0) if (mac->first_sync_frame == -1)
nr_ue_sib1_scheduler(module_id, nr_ue_sib1_scheduler(module_id,
cc_id, cc_id,
ssb_start_symbol, ssb_start_symbol,
...@@ -394,6 +394,8 @@ int8_t nr_ue_decode_mib(module_id_t module_id, ...@@ -394,6 +394,8 @@ int8_t nr_ue_decode_mib(module_id_t module_id,
mac->dl_config_request.sfn = frame; mac->dl_config_request.sfn = frame;
mac->dl_config_request.slot = ssb_start_symbol/14; mac->dl_config_request.slot = ssb_start_symbol/14;
if (mac->first_sync_frame == -1)
mac->first_sync_frame = frame;
return 0; return 0;
} }
...@@ -1744,16 +1746,17 @@ void nr_ue_configure_pucch(NR_UE_MAC_INST_t *mac, ...@@ -1744,16 +1746,17 @@ void nr_ue_configure_pucch(NR_UE_MAC_INST_t *mac,
} }
pucch_pdu->pucch_tx_power = get_pucch_tx_power_ue(mac, pucch_pdu->pucch_tx_power = get_pucch_tx_power_ue(mac,
scs,
pucch_Config, pucch_Config,
pucch, pucch,
pucch_pdu->format_type, pucch_pdu->format_type,
pucch_pdu->prb_size, pucch_pdu->prb_size,
pucch_pdu->freq_hop_flag, pucch_pdu->freq_hop_flag,
pucch_pdu->add_dmrs_flag, pucch_pdu->add_dmrs_flag,
pucch_pdu->nr_of_symbols, pucch_pdu->nr_of_symbols,
subframe_number, subframe_number,
O_ACK, O_SR, O_ACK, O_SR,
O_CSI, O_CRC); O_CSI, O_CRC);
} }
else AssertFatal(1==0,"problem with pucch configuration\n"); else AssertFatal(1==0,"problem with pucch configuration\n");
...@@ -1793,6 +1796,7 @@ void nr_ue_configure_pucch(NR_UE_MAC_INST_t *mac, ...@@ -1793,6 +1796,7 @@ void nr_ue_configure_pucch(NR_UE_MAC_INST_t *mac,
int16_t get_pucch_tx_power_ue(NR_UE_MAC_INST_t *mac, int16_t get_pucch_tx_power_ue(NR_UE_MAC_INST_t *mac,
int scs,
NR_PUCCH_Config_t *pucch_Config, NR_PUCCH_Config_t *pucch_Config,
PUCCH_sched_t *pucch, PUCCH_sched_t *pucch,
uint8_t format_type, uint8_t format_type,
...@@ -1899,10 +1903,13 @@ int16_t get_pucch_tx_power_ue(NR_UE_MAC_INST_t *mac, ...@@ -1899,10 +1903,13 @@ int16_t get_pucch_tx_power_ue(NR_UE_MAC_INST_t *mac,
return (PUCCH_POWER_DEFAULT); return (PUCCH_POWER_DEFAULT);
} }
int16_t pucch_power = P_O_PUCCH + delta_F_PUCCH + DELTA_TF + G_b_f_c; int16_t pathloss = compute_nr_SSB_PL(mac, mac->phy_measurements.ssb_rsrp_dBm);
int M_pucch_component = (10 * log10((double)(pow(2,scs) * nb_of_prbs)));
int16_t pucch_power = P_O_PUCCH + M_pucch_component + pathloss + delta_F_PUCCH + DELTA_TF + G_b_f_c;
NR_TST_PHY_PRINTF("PUCCH ( Tx power : %d dBm ) ( 10Log(...) : %d ) ( from Path Loss : %d ) ( delta_F_PUCCH : %d ) ( DELTA_TF : %d ) ( G_b_f_c : %d ) \n", NR_TST_PHY_PRINTF("PUCCH ( Tx power : %d dBm ) ( 10Log(...) : %d ) ( from Path Loss : %d ) ( delta_F_PUCCH : %d ) ( DELTA_TF : %d ) ( G_b_f_c : %d ) \n",
pucch_power, contributor, PL, delta_F_PUCCH, DELTA_TF, G_b_f_c); pucch_power, M_pucch_component, pathloss, delta_F_PUCCH, DELTA_TF, G_b_f_c);
return (pucch_power); return (pucch_power);
} }
...@@ -2635,7 +2642,7 @@ uint8_t get_ssb_rsrp_payload(NR_UE_MAC_INST_t *mac, ...@@ -2635,7 +2642,7 @@ uint8_t get_ssb_rsrp_payload(NR_UE_MAC_INST_t *mac,
} }
} }
AssertFatal(*SSB_resource.list.array[ssb_rsrp[0][0]] == mac->mib_ssb, "Couldn't find corresponding SSB in csi_SSB_ResourceList\n"); AssertFatal(*SSB_resource.list.array[ssb_rsrp[0][0]] == mac->mib_ssb, "Couldn't find corresponding SSB in csi_SSB_ResourceList\n");
ssb_rsrp[1][0] = mac->ssb_rsrp_dBm; ssb_rsrp[1][0] = mac->phy_measurements.ssb_rsrp_dBm;
uint8_t ssbi; uint8_t ssbi;
...@@ -4223,5 +4230,32 @@ int nr_ue_process_rar(nr_downlink_indication_t *dl_info, NR_UL_TIME_ALIGNMENT_t ...@@ -4223,5 +4230,32 @@ int nr_ue_process_rar(nr_downlink_indication_t *dl_info, NR_UL_TIME_ALIGNMENT_t
} }
return ret; return ret;
}
// Returns the pathloss in dB for the active UL BWP on the selected carrier based on the DL RS associated with the PRACH transmission
// computation according to clause 7.4 (Physical random access channel) of 3GPP TS 38.213 version 16.3.0 Release 16
// Assumptions:
// - PRACH transmission from a UE is not in response to a detection of a PDCCH order by the UE
// Measurement units:
// - referenceSignalPower: dBm/RE (average EPRE of the resources elements that carry secondary synchronization signals in dBm)
int16_t compute_nr_SSB_PL(NR_UE_MAC_INST_t *mac, short ssb_rsrp_dBm)
{
long referenceSignalPower;
//TODO improve PL measurements. Probably not correct as it is.
if (mac->scc)
referenceSignalPower = mac->scc->ss_PBCH_BlockPower;
else
referenceSignalPower = mac->scc_SIB->ss_PBCH_BlockPower;
int16_t pathloss = (int16_t)(referenceSignalPower - ssb_rsrp_dBm);
LOG_D(NR_MAC, "pathloss %d dB, referenceSignalPower %ld dBm/RE (%f mW), RSRP %d dBm (%f mW)\n",
pathloss,
referenceSignalPower,
pow(10, referenceSignalPower/10),
ssb_rsrp_dBm,
pow(10, ssb_rsrp_dBm/10));
return pathloss;
} }
...@@ -2699,11 +2699,14 @@ void nr_ue_prach_scheduler(module_id_t module_idP, frame_t frameP, sub_frame_t s ...@@ -2699,11 +2699,14 @@ void nr_ue_prach_scheduler(module_id_t module_idP, frame_t frameP, sub_frame_t s
(int)slotP, (int)slotP,
&prach_occasion_info_p); &prach_occasion_info_p);
if (is_nr_prach_slot && ra->ra_state == RA_UE_IDLE) { if (is_nr_prach_slot && ra->ra_state == GENERATE_PREAMBLE) {
AssertFatal(NULL != prach_occasion_info_p,"PRACH Occasion Info not returned in a valid NR Prach Slot\n"); AssertFatal(NULL != prach_occasion_info_p,"PRACH Occasion Info not returned in a valid NR Prach Slot\n");
ra->generate_nr_prach = GENERATE_PREAMBLE; ra->generate_nr_prach = GENERATE_PREAMBLE;
init_RA(module_idP, &ra->prach_resources, setup, rach_ConfigGeneric, ra->rach_ConfigDedicated);
nr_get_RA_window(mac);
format = prach_occasion_info_p->format; format = prach_occasion_info_p->format;
format0 = format & 0xff; // single PRACH format format0 = format & 0xff; // single PRACH format
format1 = (format >> 8) & 0xff; // dual PRACH format format1 = (format >> 8) & 0xff; // dual PRACH format
...@@ -2733,7 +2736,8 @@ void nr_ue_prach_scheduler(module_id_t module_idP, frame_t frameP, sub_frame_t s ...@@ -2733,7 +2736,8 @@ void nr_ue_prach_scheduler(module_id_t module_idP, frame_t frameP, sub_frame_t s
prach_config_pdu->restricted_set = prach_config->restricted_set_config; prach_config_pdu->restricted_set = prach_config->restricted_set_config;
prach_config_pdu->freq_msg1 = prach_config->num_prach_fd_occasions_list[prach_occasion_info_p->fdm].k1; prach_config_pdu->freq_msg1 = prach_config->num_prach_fd_occasions_list[prach_occasion_info_p->fdm].k1;
LOG_D(NR_MAC,"Selected RO Frame %u, Slot %u, Symbol %u, Fdm %u\n", frameP, prach_config_pdu->prach_slot, prach_config_pdu->prach_start_symbol, prach_config_pdu->num_ra); LOG_D(NR_MAC,"PRACH scheduler: Selected RO Frame %u, Slot %u, Symbol %u, Fdm %u\n",
frameP, prach_config_pdu->prach_slot, prach_config_pdu->prach_start_symbol, prach_config_pdu->num_ra);
// Search which SSB is mapped in the RO (among all the SSBs mapped to this RO) // Search which SSB is mapped in the RO (among all the SSBs mapped to this RO)
for (prach_config_pdu->ssb_nb_in_ro=0; prach_config_pdu->ssb_nb_in_ro<prach_occasion_info_p->nb_mapped_ssb; prach_config_pdu->ssb_nb_in_ro++) { for (prach_config_pdu->ssb_nb_in_ro=0; prach_config_pdu->ssb_nb_in_ro<prach_occasion_info_p->nb_mapped_ssb; prach_config_pdu->ssb_nb_in_ro++) {
...@@ -2796,9 +2800,16 @@ void nr_ue_prach_scheduler(module_id_t module_idP, frame_t frameP, sub_frame_t s ...@@ -2796,9 +2800,16 @@ void nr_ue_prach_scheduler(module_id_t module_idP, frame_t frameP, sub_frame_t s
} }
} // if format1 } // if format1
nr_get_prach_resources(module_idP, 0, 0, &ra->prach_resources, prach_config_pdu, ra->rach_ConfigDedicated);
prach_config_pdu->ra_PreambleIndex = ra->ra_PreambleIndex;
prach_config_pdu->prach_tx_power = get_prach_tx_power(module_idP);
set_ra_rnti(mac, prach_config_pdu);
fill_scheduled_response(&scheduled_response, NULL, ul_config, NULL, module_idP, 0 /*TBR fix*/, frameP, slotP, NULL); fill_scheduled_response(&scheduled_response, NULL, ul_config, NULL, module_idP, 0 /*TBR fix*/, frameP, slotP, NULL);
if(mac->if_module != NULL && mac->if_module->scheduled_response != NULL) if(mac->if_module != NULL && mac->if_module->scheduled_response != NULL)
mac->if_module->scheduled_response(&scheduled_response); mac->if_module->scheduled_response(&scheduled_response);
nr_Msg1_transmitted(module_idP);
} // is_nr_prach_slot } // is_nr_prach_slot
} // if is_nr_UL_slot } // if is_nr_UL_slot
} }
......
...@@ -385,6 +385,7 @@ bool allocate_dl_retransmission(module_id_t module_id, ...@@ -385,6 +385,7 @@ bool allocate_dl_retransmission(module_id_t module_id,
NR_UE_info_t *UE, NR_UE_info_t *UE,
int current_harq_pid) { int current_harq_pid) {
int CC_id = 0;
gNB_MAC_INST *nr_mac = RC.nrmac[module_id]; gNB_MAC_INST *nr_mac = RC.nrmac[module_id];
const NR_ServingCellConfigCommon_t *scc = nr_mac->common_channels->ServingCellConfigCommon; const NR_ServingCellConfigCommon_t *scc = nr_mac->common_channels->ServingCellConfigCommon;
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl; NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
...@@ -400,11 +401,11 @@ bool allocate_dl_retransmission(module_id_t module_id, ...@@ -400,11 +401,11 @@ bool allocate_dl_retransmission(module_id_t module_id,
int pm_index = (curInfo->nrOfLayers < retInfo->nrOfLayers) ? curInfo->pm_index : retInfo->pm_index; int pm_index = (curInfo->nrOfLayers < retInfo->nrOfLayers) ? curInfo->pm_index : retInfo->pm_index;
const int coresetid = sched_ctrl->coreset->controlResourceSetId; const int coresetid = sched_ctrl->coreset->controlResourceSetId;
const uint16_t bwpSize = coresetid == 0 ? RC.nrmac[module_id]->cset0_bwp_size : dl_bwp->BWPSize; const uint16_t bwpSize = coresetid == 0 ? nr_mac->cset0_bwp_size : dl_bwp->BWPSize;
int rbStart = 0; // start wrt BWPstart int rbStart = 0; // start wrt BWPstart
int rbSize = 0; int rbSize = 0;
const int tda = get_dl_tda(RC.nrmac[module_id], scc, slot); const int tda = get_dl_tda(nr_mac, scc, slot);
AssertFatal(tda>=0,"Unable to find PDSCH time domain allocation in list\n"); AssertFatal(tda>=0,"Unable to find PDSCH time domain allocation in list\n");
if (tda == retInfo->time_domain_allocation && if (tda == retInfo->time_domain_allocation &&
...@@ -476,28 +477,13 @@ bool allocate_dl_retransmission(module_id_t module_id, ...@@ -476,28 +477,13 @@ bool allocate_dl_retransmission(module_id_t module_id,
} }
/* Find a free CCE */ /* Find a free CCE */
int CCEIndex = get_cce_index(nr_mac,
const uint32_t Y = get_Y(sched_ctrl->search_space, slot, UE->rnti); CC_id, slot, UE->rnti,
uint8_t nr_of_candidates; &sched_ctrl->aggregation_level,
sched_ctrl->search_space,
for (int i=0; i<5; i++) { sched_ctrl->coreset,
// for now taking the lowest value among the available aggregation levels &sched_ctrl->sched_pdcch,
find_aggregation_candidates(&sched_ctrl->aggregation_level, false);
&nr_of_candidates,
sched_ctrl->search_space,
1<<i);
if(nr_of_candidates>0) break;
}
int CCEIndex = find_pdcch_candidate(RC.nrmac[module_id],
/* CC_id = */ 0,
sched_ctrl->aggregation_level,
nr_of_candidates,
&sched_ctrl->sched_pdcch,
sched_ctrl->coreset,
Y);
if (CCEIndex<0) { if (CCEIndex<0) {
LOG_D(MAC, "%4d.%2d could not find CCE for DL DCI retransmission RNTI %04x\n", LOG_D(MAC, "%4d.%2d could not find CCE for DL DCI retransmission RNTI %04x\n",
frame, slot, UE->rnti); frame, slot, UE->rnti);
...@@ -519,7 +505,7 @@ bool allocate_dl_retransmission(module_id_t module_id, ...@@ -519,7 +505,7 @@ bool allocate_dl_retransmission(module_id_t module_id,
} }
sched_ctrl->cce_index = CCEIndex; sched_ctrl->cce_index = CCEIndex;
fill_pdcch_vrb_map(RC.nrmac[module_id], fill_pdcch_vrb_map(nr_mac,
/* CC_id = */ 0, /* CC_id = */ 0,
&sched_ctrl->sched_pdcch, &sched_ctrl->sched_pdcch,
CCEIndex, CCEIndex,
...@@ -560,6 +546,7 @@ void pf_dl(module_id_t module_id, ...@@ -560,6 +546,7 @@ void pf_dl(module_id_t module_id,
UEsched_t UE_sched[MAX_MOBILES_PER_GNB] = {0}; UEsched_t UE_sched[MAX_MOBILES_PER_GNB] = {0};
int remainUEs = max_num_ue; int remainUEs = max_num_ue;
int curUE = 0; int curUE = 0;
int CC_id = 0;
/* Loop UE_info->list to check retransmission */ /* Loop UE_info->list to check retransmission */
UE_iterator(UE_list, UE) { UE_iterator(UE_list, UE) {
...@@ -569,7 +556,8 @@ void pf_dl(module_id_t module_id, ...@@ -569,7 +556,8 @@ void pf_dl(module_id_t module_id,
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl; NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
NR_UE_DL_BWP_t *current_BWP = &UE->current_DL_BWP; NR_UE_DL_BWP_t *current_BWP = &UE->current_DL_BWP;
if (sched_ctrl->ul_failure==1 && get_softmodem_params()->phy_test==0) continue; if (sched_ctrl->ul_failure==1)
continue;
const NR_mac_dir_stats_t *stats = &UE->mac_stats.dl; const NR_mac_dir_stats_t *stats = &UE->mac_stats.dl;
NR_sched_pdsch_t *sched_pdsch = &sched_ctrl->sched_pdsch; NR_sched_pdsch_t *sched_pdsch = &sched_ctrl->sched_pdsch;
...@@ -580,6 +568,9 @@ void pf_dl(module_id_t module_id, ...@@ -580,6 +568,9 @@ void pf_dl(module_id_t module_id,
const uint32_t b = UE->mac_stats.dl.current_bytes; const uint32_t b = UE->mac_stats.dl.current_bytes;
UE->dl_thr_ue = (1 - a) * UE->dl_thr_ue + a * b; UE->dl_thr_ue = (1 - a) * UE->dl_thr_ue + a * b;
if (remainUEs == 0)
continue;
/* retransmission */ /* retransmission */
if (sched_pdsch->dl_harq_pid >= 0) { if (sched_pdsch->dl_harq_pid >= 0) {
/* Allocate retransmission */ /* Allocate retransmission */
...@@ -589,15 +580,9 @@ void pf_dl(module_id_t module_id, ...@@ -589,15 +580,9 @@ void pf_dl(module_id_t module_id,
LOG_D(NR_MAC, "%4d.%2d retransmission can NOT be allocated\n", frame, slot); LOG_D(NR_MAC, "%4d.%2d retransmission can NOT be allocated\n", frame, slot);
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)
return;
} else { } else {
/* skip this UE if there are no free HARQ processes. This can happen e.g. /* skip this UE if there are no free HARQ processes. This can happen e.g.
* if the UE disconnected in L2sim, in which case the gNB is not notified * if the UE disconnected in L2sim, in which case the gNB is not notified
...@@ -659,7 +644,7 @@ void pf_dl(module_id_t module_id, ...@@ -659,7 +644,7 @@ void pf_dl(module_id_t module_id,
const int coresetid = sched_ctrl->coreset->controlResourceSetId; const int coresetid = sched_ctrl->coreset->controlResourceSetId;
const uint16_t bwpSize = coresetid == 0 ? const uint16_t bwpSize = coresetid == 0 ?
RC.nrmac[module_id]->cset0_bwp_size : mac->cset0_bwp_size :
dl_bwp->BWPSize; dl_bwp->BWPSize;
int rbStart = 0; // start wrt BWPstart int rbStart = 0; // start wrt BWPstart
...@@ -669,28 +654,13 @@ void pf_dl(module_id_t module_id, ...@@ -669,28 +654,13 @@ void pf_dl(module_id_t module_id,
continue; continue;
} }
/* Find a free CCE */ int CCEIndex = get_cce_index(mac,
const uint32_t Y = get_Y(sched_ctrl->search_space, slot, iterator->UE->rnti); CC_id, slot, iterator->UE->rnti,
uint8_t nr_of_candidates; &sched_ctrl->aggregation_level,
sched_ctrl->search_space,
for (int i=0; i<5; i++) { sched_ctrl->coreset,
// for now taking the lowest value among the available aggregation levels &sched_ctrl->sched_pdcch,
find_aggregation_candidates(&sched_ctrl->aggregation_level, false);
&nr_of_candidates,
sched_ctrl->search_space,
1<<i);
if(nr_of_candidates>0) break;
}
int CCEIndex = find_pdcch_candidate(mac,
/* CC_id = */ 0,
sched_ctrl->aggregation_level,
nr_of_candidates,
&sched_ctrl->sched_pdcch,
sched_ctrl->coreset,
Y);
if (CCEIndex<0) { if (CCEIndex<0) {
LOG_D(NR_MAC, "%4d.%2d could not find CCE for DL DCI RNTI %04x\n", frame, slot, rnti); LOG_D(NR_MAC, "%4d.%2d could not find CCE for DL DCI RNTI %04x\n", frame, slot, rnti);
iterator++; iterator++;
...@@ -722,7 +692,7 @@ void pf_dl(module_id_t module_id, ...@@ -722,7 +692,7 @@ void pf_dl(module_id_t module_id,
/* MCS has been set above */ /* MCS has been set above */
NR_sched_pdsch_t *sched_pdsch = &sched_ctrl->sched_pdsch; NR_sched_pdsch_t *sched_pdsch = &sched_ctrl->sched_pdsch;
sched_pdsch->time_domain_allocation = get_dl_tda(RC.nrmac[module_id], scc, slot); sched_pdsch->time_domain_allocation = get_dl_tda(mac, scc, slot);
AssertFatal(sched_pdsch->time_domain_allocation>=0,"Unable to find PDSCH time domain allocation in list\n"); AssertFatal(sched_pdsch->time_domain_allocation>=0,"Unable to find PDSCH time domain allocation in list\n");
sched_pdsch->tda_info = nr_get_pdsch_tda_info(dl_bwp, sched_pdsch->time_domain_allocation); sched_pdsch->tda_info = nr_get_pdsch_tda_info(dl_bwp, sched_pdsch->time_domain_allocation);
......
...@@ -250,27 +250,13 @@ void nr_preprocessor_phytest(module_id_t module_id, ...@@ -250,27 +250,13 @@ void nr_preprocessor_phytest(module_id_t module_id,
0); 0);
sched_ctrl->num_total_bytes += sched_ctrl->rlc_status[lcid].bytes_in_buffer; sched_ctrl->num_total_bytes += sched_ctrl->rlc_status[lcid].bytes_in_buffer;
uint8_t nr_of_candidates; int CCEIndex = get_cce_index(RC.nrmac[module_id],
for (int i=0; i<5; i++) { CC_id, slot, UE->rnti,
// for now taking the lowest value among the available aggregation levels &sched_ctrl->aggregation_level,
find_aggregation_candidates(&sched_ctrl->aggregation_level, sched_ctrl->search_space,
&nr_of_candidates, sched_ctrl->coreset,
sched_ctrl->search_space, &sched_ctrl->sched_pdcch,
1<<i); false);
if(nr_of_candidates>0) break;
}
AssertFatal(nr_of_candidates>0,"nr_of_candidates is 0\n");
const uint32_t Y = get_Y(sched_ctrl->search_space, slot, UE->rnti);
int CCEIndex = find_pdcch_candidate(RC.nrmac[module_id],
CC_id,
sched_ctrl->aggregation_level,
nr_of_candidates,
&sched_ctrl->sched_pdcch,
sched_ctrl->coreset,
Y);
AssertFatal(CCEIndex >= 0, AssertFatal(CCEIndex >= 0,
"%s(): could not find CCE for UE %04x\n", "%s(): could not find CCE for UE %04x\n",
__func__, __func__,
...@@ -412,27 +398,13 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, sub_frame_ ...@@ -412,27 +398,13 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, sub_frame_
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;
uint8_t nr_of_candidates; int CCEIndex = get_cce_index(nr_mac,
for (int i=0; i<5; i++) { CC_id, slot, UE->rnti,
// for now taking the lowest value among the available aggregation levels &sched_ctrl->aggregation_level,
find_aggregation_candidates(&sched_ctrl->aggregation_level, sched_ctrl->search_space,
&nr_of_candidates, sched_ctrl->coreset,
sched_ctrl->search_space, &sched_ctrl->sched_pdcch,
1<<i); false);
if(nr_of_candidates>0) break;
}
AssertFatal(nr_of_candidates>0,"nr_of_candidates is 0\n");
const uint32_t Y = get_Y(sched_ctrl->search_space, slot, UE->rnti);
int CCEIndex = find_pdcch_candidate(nr_mac,
CC_id,
sched_ctrl->aggregation_level,
nr_of_candidates,
&sched_ctrl->sched_pdcch,
sched_ctrl->coreset,
Y);
if (CCEIndex < 0) { if (CCEIndex < 0) {
LOG_E(MAC, "%s(): CCE list not empty, couldn't schedule PUSCH\n", __func__); LOG_E(MAC, "%s(): CCE list not empty, couldn't schedule PUSCH\n", __func__);
return false; return false;
......
...@@ -114,10 +114,6 @@ uint8_t nr_ss_first_symb_idx_scs_240_120_set1_mux2[6] = {0,1,2,3,0,1}; ...@@ -114,10 +114,6 @@ uint8_t nr_ss_first_symb_idx_scs_240_120_set1_mux2[6] = {0,1,2,3,0,1};
// Mux pattern type 3 // Mux pattern type 3
uint8_t nr_ss_first_symb_idx_scs_120_120_mux3[4] = {4,8,2,6}; uint8_t nr_ss_first_symb_idx_scs_120_120_mux3[4] = {4,8,2,6};
/// Search space max values indexed by scs
uint8_t nr_max_number_of_candidates_per_slot[4] = {44, 36, 22, 20};
uint8_t nr_max_number_of_cces_per_slot[4] = {56, 56, 48, 32};
// CQI TABLES (10 times the value in 214 to adequately compare with R) // CQI TABLES (10 times the value in 214 to adequately compare with R)
// Table 1 (38.214 5.2.2.1-2) // Table 1 (38.214 5.2.2.1-2)
uint16_t cqi_table1[16][2] = {{0,0},{2,780},{2,1200},{2,1930},{2,3080},{2,4490},{2,6020},{4,3780}, uint16_t cqi_table1[16][2] = {{0,0},{2,780},{2,1200},{2,1930},{2,3080},{2,4490},{2,6020},{4,3780},
...@@ -132,16 +128,6 @@ uint16_t cqi_table3[16][2] = {{0,0},{2,300},{2,500},{2,780},{2,1200},{2,1930},{2 ...@@ -132,16 +128,6 @@ uint16_t cqi_table3[16][2] = {{0,0},{2,300},{2,500},{2,780},{2,1200},{2,1930},{2
{2,6020},{4,3780},{4,4900},{4,6160},{6,4660},{6,5670},{6,6660},{6,7720}}; {2,6020},{4,3780},{4,4900},{4,6160},{6,4660},{6,5670},{6,6660},{6,7720}};
static inline uint8_t get_max_candidates(uint8_t scs) {
AssertFatal(scs<4, "Invalid PDCCH subcarrier spacing %d\n", scs);
return (nr_max_number_of_candidates_per_slot[scs]);
}
static inline uint8_t get_max_cces(uint8_t scs) {
AssertFatal(scs<4, "Invalid PDCCH subcarrier spacing %d\n", scs);
return (nr_max_number_of_cces_per_slot[scs]);
}
uint8_t get_dl_nrOfLayers(const NR_UE_sched_ctrl_t *sched_ctrl, uint8_t get_dl_nrOfLayers(const NR_UE_sched_ctrl_t *sched_ctrl,
const nr_dci_format_t dci_format) { const nr_dci_format_t dci_format) {
...@@ -431,16 +417,15 @@ NR_sched_pdcch_t set_pdcch_structure(gNB_MAC_INST *gNB_mac, ...@@ -431,16 +417,15 @@ NR_sched_pdcch_t set_pdcch_structure(gNB_MAC_INST *gNB_mac,
return pdcch; return pdcch;
} }
int find_pdcch_candidate(const gNB_MAC_INST *mac,
int find_pdcch_candidate(gNB_MAC_INST *mac,
int cc_id, int cc_id,
int aggregation, int aggregation,
int nr_of_candidates, int nr_of_candidates,
NR_sched_pdcch_t *pdcch, const NR_sched_pdcch_t *pdcch,
NR_ControlResourceSet_t *coreset, const NR_ControlResourceSet_t *coreset,
uint32_t Y){ uint32_t Y){
uint16_t *vrb_map = mac->common_channels[cc_id].vrb_map; const uint16_t *vrb_map = mac->common_channels[cc_id].vrb_map;
const int N_ci = 0; const int N_ci = 0;
const int N_rb = pdcch->n_rb; // nb of rbs of coreset per symbol const int N_rb = pdcch->n_rb; // nb of rbs of coreset per symbol
...@@ -475,6 +460,39 @@ int find_pdcch_candidate(gNB_MAC_INST *mac, ...@@ -475,6 +460,39 @@ int find_pdcch_candidate(gNB_MAC_INST *mac,
return -1; return -1;
} }
int get_cce_index(const gNB_MAC_INST *nrmac,
const int CC_id,
const int slot,
const rnti_t rnti,
uint8_t *aggregation_level,
const NR_SearchSpace_t *ss,
const NR_ControlResourceSet_t *coreset,
NR_sched_pdcch_t *sched_pdcch,
bool is_common)
{
const uint32_t Y = is_common ? 0 : get_Y(ss, slot, rnti);
uint8_t nr_of_candidates;
for (int i=0; i<5; i++) {
// for now taking the lowest value among the available aggregation levels
find_aggregation_candidates(aggregation_level,
&nr_of_candidates,
ss,
1<<i);
if(nr_of_candidates>0)
break;
}
int CCEIndex = find_pdcch_candidate(nrmac,
CC_id,
*aggregation_level,
nr_of_candidates,
sched_pdcch,
coreset,
Y);
return CCEIndex;
}
void fill_pdcch_vrb_map(gNB_MAC_INST *mac, void fill_pdcch_vrb_map(gNB_MAC_INST *mac,
int CC_id, int CC_id,
NR_sched_pdcch_t *pdcch, NR_sched_pdcch_t *pdcch,
......
...@@ -131,17 +131,22 @@ int diff_rsrp_ssb_csi_meas_10_1_6_1_2[16] = { ...@@ -131,17 +131,22 @@ int diff_rsrp_ssb_csi_meas_10_1_6_1_2[16] = {
}; };
int get_pucch_index(int slot, int n_slots_frame, const NR_TDD_UL_DL_Pattern_t *tdd, int sched_pucch_size) int get_pucch_index(int frame, int slot, int n_slots_frame, const NR_TDD_UL_DL_Pattern_t *tdd, int sched_pucch_size)
{ {
// PUCCH structures are indexed by slot in the PUCCH period determined by sched_pucch_size number of UL slots // PUCCH structures are indexed by slot in the PUCCH period determined by sched_pucch_size number of UL slots
// this functions return the index to the structure for slot passed to the function // this functions return the index to the structure for slot passed to the function
const int first_ul_slot_period = tdd ? tdd->nrofDownlinkSlots : 0; const int first_ul_slot_period = tdd ? tdd->nrofDownlinkSlots : 0;
const int n_ul_slots_period = tdd ? tdd->nrofUplinkSlots + (tdd->nrofUplinkSymbols > 0 ? 1 : 0) : n_slots_frame; const int n_ul_slots_period = tdd ? tdd->nrofUplinkSlots + (tdd->nrofUplinkSymbols > 0 ? 1 : 0) : n_slots_frame;
const int nr_slots_period = tdd ? n_slots_frame / get_nb_periods_per_frame(tdd->dl_UL_TransmissionPeriodicity) : n_slots_frame; const int nr_slots_period = tdd ? n_slots_frame / get_nb_periods_per_frame(tdd->dl_UL_TransmissionPeriodicity) : n_slots_frame;
// ((slot % nr_slots_period) - first_ul_slot_period) gives the progressive number of the slot in a TDD period const int n_ul_slots_frame = n_slots_frame / nr_slots_period * n_ul_slots_period;
// ((slot / nr_slots_period) * n_ul_slots_period) adds up the number of UL slots in the previous TDD periods // (frame * n_ul_slots_frame) adds up the number of UL slots in the previous frames
const int frame_start = frame * n_ul_slots_frame;
// ((slot / nr_slots_period) * n_ul_slots_period) adds up the number of UL slots in the previous TDD periods of this frame
const int ul_period_start = (slot / nr_slots_period) * n_ul_slots_period;
// ((slot % nr_slots_period) - first_ul_slot_period) gives the progressive number of the slot in this TDD period
const int ul_period_slot = (slot % nr_slots_period) - first_ul_slot_period;
// the sum gives the index of current UL slot in the frame which is normalized wrt sched_pucch_size // the sum gives the index of current UL slot in the frame which is normalized wrt sched_pucch_size
return ((slot % nr_slots_period) - first_ul_slot_period + (slot / nr_slots_period) * n_ul_slots_period) % sched_pucch_size; return (frame_start + ul_period_start + ul_period_slot) % sched_pucch_size;
} }
...@@ -159,7 +164,7 @@ void nr_schedule_pucch(gNB_MAC_INST *nrmac, ...@@ -159,7 +164,7 @@ void nr_schedule_pucch(gNB_MAC_INST *nrmac,
const NR_ServingCellConfigCommon_t *scc = nrmac->common_channels[0].ServingCellConfigCommon; const NR_ServingCellConfigCommon_t *scc = nrmac->common_channels[0].ServingCellConfigCommon;
const NR_TDD_UL_DL_Pattern_t *tdd = scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL; const NR_TDD_UL_DL_Pattern_t *tdd = scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL;
AssertFatal(tdd || nrmac->common_channels[0].frame_type == FDD, "Dynamic TDD not handled yet\n"); AssertFatal(tdd || nrmac->common_channels[0].frame_type == FDD, "Dynamic TDD not handled yet\n");
const int pucch_index = get_pucch_index(slotP, n_slots_frame, tdd, sched_ctrl->sched_pucch_size); const int pucch_index = get_pucch_index(frameP, slotP, n_slots_frame, tdd, sched_ctrl->sched_pucch_size);
NR_sched_pucch_t *curr_pucch = &UE->UE_sched_ctrl.sched_pucch[pucch_index]; NR_sched_pucch_t *curr_pucch = &UE->UE_sched_ctrl.sched_pucch[pucch_index];
if (!curr_pucch->active) if (!curr_pucch->active)
continue; continue;
...@@ -226,7 +231,7 @@ void nr_csi_meas_reporting(int Mod_idP, ...@@ -226,7 +231,7 @@ void nr_csi_meas_reporting(int Mod_idP,
const NR_ServingCellConfigCommon_t *scc = RC.nrmac[Mod_idP]->common_channels[0].ServingCellConfigCommon; const NR_ServingCellConfigCommon_t *scc = RC.nrmac[Mod_idP]->common_channels[0].ServingCellConfigCommon;
const NR_TDD_UL_DL_Pattern_t *tdd = scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL; const NR_TDD_UL_DL_Pattern_t *tdd = scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL;
AssertFatal(tdd || RC.nrmac[Mod_idP]->common_channels[0].frame_type == FDD, "Dynamic TDD not handled yet\n"); AssertFatal(tdd || RC.nrmac[Mod_idP]->common_channels[0].frame_type == FDD, "Dynamic TDD not handled yet\n");
const int pucch_index = get_pucch_index(sched_slot, n_slots_frame, tdd, sched_ctrl->sched_pucch_size); const int pucch_index = get_pucch_index(sched_frame, sched_slot, n_slots_frame, tdd, sched_ctrl->sched_pucch_size);
NR_sched_pucch_t *curr_pucch = &sched_ctrl->sched_pucch[pucch_index]; NR_sched_pucch_t *curr_pucch = &sched_ctrl->sched_pucch[pucch_index];
AssertFatal(curr_pucch->active == false, "CSI structure is scheduled in advance. It should be free!\n"); AssertFatal(curr_pucch->active == false, "CSI structure is scheduled in advance. It should be free!\n");
curr_pucch->r_pucch = -1; curr_pucch->r_pucch = -1;
...@@ -1118,7 +1123,7 @@ int nr_acknack_scheduling(gNB_MAC_INST *mac, ...@@ -1118,7 +1123,7 @@ int nr_acknack_scheduling(gNB_MAC_INST *mac,
continue; continue;
const int pucch_frame = (frame + ((slot + pdsch_to_harq_feedback[f]) / n_slots_frame)) & 1023; const int pucch_frame = (frame + ((slot + pdsch_to_harq_feedback[f]) / n_slots_frame)) & 1023;
// we store PUCCH resources according to slot, TDD configuration and size of the vector containing PUCCH structures // we store PUCCH resources according to slot, TDD configuration and size of the vector containing PUCCH structures
const int pucch_index = get_pucch_index(pucch_slot, n_slots_frame, tdd, sched_ctrl->sched_pucch_size); const int pucch_index = get_pucch_index(pucch_frame, pucch_slot, n_slots_frame, tdd, sched_ctrl->sched_pucch_size);
NR_sched_pucch_t *curr_pucch = &sched_ctrl->sched_pucch[pucch_index]; NR_sched_pucch_t *curr_pucch = &sched_ctrl->sched_pucch[pucch_index];
if (curr_pucch->active && if (curr_pucch->active &&
curr_pucch->frame == pucch_frame && curr_pucch->frame == pucch_frame &&
...@@ -1228,7 +1233,7 @@ void nr_sr_reporting(gNB_MAC_INST *nrmac, frame_t SFN, sub_frame_t slot) ...@@ -1228,7 +1233,7 @@ void nr_sr_reporting(gNB_MAC_INST *nrmac, frame_t SFN, sub_frame_t slot)
const NR_ServingCellConfigCommon_t *scc = nrmac->common_channels[CC_id].ServingCellConfigCommon; const NR_ServingCellConfigCommon_t *scc = nrmac->common_channels[CC_id].ServingCellConfigCommon;
const NR_TDD_UL_DL_Pattern_t *tdd = scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL; const NR_TDD_UL_DL_Pattern_t *tdd = scc->tdd_UL_DL_ConfigurationCommon ? &scc->tdd_UL_DL_ConfigurationCommon->pattern1 : NULL;
AssertFatal(tdd || nrmac->common_channels[CC_id].frame_type == FDD, "Dynamic TDD not handled yet\n"); AssertFatal(tdd || nrmac->common_channels[CC_id].frame_type == FDD, "Dynamic TDD not handled yet\n");
const int pucch_index = get_pucch_index(slot, n_slots_frame, tdd, sched_ctrl->sched_pucch_size); const int pucch_index = get_pucch_index(SFN, slot, n_slots_frame, tdd, sched_ctrl->sched_pucch_size);
NR_sched_pucch_t *curr_pucch = &sched_ctrl->sched_pucch[pucch_index]; NR_sched_pucch_t *curr_pucch = &sched_ctrl->sched_pucch[pucch_index];
if (curr_pucch->active && if (curr_pucch->active &&
......
...@@ -269,12 +269,12 @@ NR_sched_pdcch_t set_pdcch_structure(gNB_MAC_INST *gNB_mac, ...@@ -269,12 +269,12 @@ NR_sched_pdcch_t set_pdcch_structure(gNB_MAC_INST *gNB_mac,
NR_BWP_t *bwp, NR_BWP_t *bwp,
NR_Type0_PDCCH_CSS_config_t *type0_PDCCH_CSS_config); NR_Type0_PDCCH_CSS_config_t *type0_PDCCH_CSS_config);
int find_pdcch_candidate(gNB_MAC_INST *mac, int find_pdcch_candidate(const gNB_MAC_INST *mac,
int cc_id, int cc_id,
int aggregation, int aggregation,
int nr_of_candidates, int nr_of_candidates,
NR_sched_pdcch_t *pdcch, const NR_sched_pdcch_t *pdcch,
NR_ControlResourceSet_t *coreset, const NR_ControlResourceSet_t *coreset,
uint32_t Y); uint32_t Y);
void fill_pdcch_vrb_map(gNB_MAC_INST *mac, void fill_pdcch_vrb_map(gNB_MAC_INST *mac,
...@@ -473,7 +473,15 @@ void set_sched_pucch_list(NR_UE_sched_ctrl_t *sched_ctrl, ...@@ -473,7 +473,15 @@ void set_sched_pucch_list(NR_UE_sched_ctrl_t *sched_ctrl,
const int get_dl_tda(const gNB_MAC_INST *nrmac, const NR_ServingCellConfigCommon_t *scc, int slot); const int get_dl_tda(const gNB_MAC_INST *nrmac, const NR_ServingCellConfigCommon_t *scc, int slot);
const int get_ul_tda(const gNB_MAC_INST *nrmac, const NR_ServingCellConfigCommon_t *scc, int slot); const int get_ul_tda(const gNB_MAC_INST *nrmac, const NR_ServingCellConfigCommon_t *scc, int slot);
bool find_free_CCE(sub_frame_t slot, NR_UE_info_t *UE); int get_cce_index(const gNB_MAC_INST *nrmac,
const int CC_id,
const int slot,
const rnti_t rnti,
uint8_t *aggregation_level,
const NR_SearchSpace_t *ss,
const NR_ControlResourceSet_t *coreset,
NR_sched_pdcch_t *sched_pdcch,
bool is_common);
bool nr_find_nb_rb(uint16_t Qm, bool nr_find_nb_rb(uint16_t Qm,
uint16_t R, uint16_t R,
......
...@@ -1085,6 +1085,12 @@ int handle_dci(module_id_t module_id, int cc_id, unsigned int gNB_index, frame_t ...@@ -1085,6 +1085,12 @@ int handle_dci(module_id_t module_id, int cc_id, unsigned int gNB_index, frame_t
} }
void handle_ssb_meas(NR_UE_MAC_INST_t *mac, uint8_t ssb_index, int16_t rsrp_dbm)
{
mac->phy_measurements.ssb_index = ssb_index;
mac->phy_measurements.ssb_rsrp_dBm = rsrp_dbm;
}
// L2 Abstraction Layer // L2 Abstraction Layer
// Note: sdu should always be processed because data and timing advance updates are transmitted by the UE // Note: sdu should always be processed because data and timing advance updates are transmitted by the UE
int8_t handle_dlsch(nr_downlink_indication_t *dl_info, NR_UL_TIME_ALIGNMENT_t *ul_time_alignment, int pdu_id){ int8_t handle_dlsch(nr_downlink_indication_t *dl_info, NR_UL_TIME_ALIGNMENT_t *ul_time_alignment, int pdu_id){
...@@ -1223,7 +1229,9 @@ int nr_ue_dl_indication(nr_downlink_indication_t *dl_info, NR_UL_TIME_ALIGNMENT_ ...@@ -1223,7 +1229,9 @@ int nr_ue_dl_indication(nr_downlink_indication_t *dl_info, NR_UL_TIME_ALIGNMENT_
switch(dl_info->rx_ind->rx_indication_body[i].pdu_type){ switch(dl_info->rx_ind->rx_indication_body[i].pdu_type){
case FAPI_NR_RX_PDU_TYPE_SSB: case FAPI_NR_RX_PDU_TYPE_SSB:
mac->ssb_rsrp_dBm = (dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.rsrp_dBm; handle_ssb_meas(mac,
(dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.ssb_index,
(dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.rsrp_dBm);
ret_mask |= (handle_bcch_bch(dl_info->module_id, dl_info->cc_id, dl_info->gNB_index, dl_info->phy_data, ret_mask |= (handle_bcch_bch(dl_info->module_id, dl_info->cc_id, dl_info->gNB_index, dl_info->phy_data,
(dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.pdu, (dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.pdu,
(dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.additional_bits, (dl_info->rx_ind->rx_indication_body+i)->ssb_pdu.additional_bits,
......
...@@ -117,7 +117,8 @@ uint16_t mac_rrc_nr_data_req(const module_id_t Mod_idP, ...@@ -117,7 +117,8 @@ uint16_t mac_rrc_nr_data_req(const module_id_t Mod_idP,
const rb_id_t Srb_id, const rb_id_t Srb_id,
const rnti_t rnti, const rnti_t rnti,
const uint8_t Nb_tb, const uint8_t Nb_tb,
uint8_t *const buffer_pP ){ uint8_t *const buffer_pP)
{
#ifdef DEBUG_RRC #ifdef DEBUG_RRC
LOG_D(RRC,"[eNB %d] mac_rrc_data_req to SRB ID=%ld\n",Mod_idP,Srb_id); LOG_D(RRC,"[eNB %d] mac_rrc_data_req to SRB ID=%ld\n",Mod_idP,Srb_id);
...@@ -162,19 +163,21 @@ uint16_t mac_rrc_nr_data_req(const module_id_t Mod_idP, ...@@ -162,19 +163,21 @@ uint16_t mac_rrc_nr_data_req(const module_id_t Mod_idP,
if ((Srb_id & RAB_OFFSET) == CCCH) { if ((Srb_id & RAB_OFFSET) == CCCH) {
LOG_D(NR_RRC,"[gNB %d] Frame %d CCCH request (Srb_id %ld)\n", Mod_idP, frameP, Srb_id); LOG_D(NR_RRC,"[gNB %d] Frame %d CCCH request (Srb_id %ld)\n", Mod_idP, frameP, Srb_id);
char *payload_pP;
struct rrc_gNB_ue_context_s *ue_context_p = rrc_gNB_get_ue_context(RC.nrrrc[Mod_idP], rnti); struct rrc_gNB_ue_context_s *ue_context_p = rrc_gNB_get_ue_context(RC.nrrrc[Mod_idP], rnti);
LOG_D(NR_RRC,"[gNB %d] Frame %d CCCH request (Srb_id %ld)\n", Mod_idP, frameP, Srb_id); LOG_D(NR_RRC,"[gNB %d] Frame %d CCCH request (Srb_id %ld)\n", Mod_idP, frameP, Srb_id);
if (ue_context_p == NULL) { if (ue_context_p == NULL) {
LOG_E(NR_RRC,"[gNB %d] Frame %d CCCH request but no ue_context\n", Mod_idP, frameP); if(buffer_pP != NULL)
LOG_E(NR_RRC,"[gNB %d] Frame %d CCCH request but no ue_context\n", Mod_idP, frameP);
return 0; return 0;
} }
uint16_t payload_size = ue_context_p->ue_context.Srb0.Tx_buffer.payload_size; uint16_t payload_size = ue_context_p->ue_context.Srb0.Tx_buffer.payload_size;
if (buffer_pP == NULL)
return payload_size;
// check if data is there for MAC // check if data is there for MAC
if (payload_size > 0) { if (payload_size > 0) {
payload_pP = ue_context_p->ue_context.Srb0.Tx_buffer.Payload; char *payload_pP = ue_context_p->ue_context.Srb0.Tx_buffer.Payload;
LOG_D(NR_RRC,"[gNB %d] CCCH has %d bytes (dest: %p, src %p)\n", Mod_idP, payload_size, buffer_pP, payload_pP); LOG_D(NR_RRC,"[gNB %d] CCCH has %d bytes (dest: %p, src %p)\n", Mod_idP, payload_size, buffer_pP, payload_pP);
// Fill buffer // Fill buffer
memcpy((void *)buffer_pP, (void*)payload_pP, payload_size); memcpy((void *)buffer_pP, (void*)payload_pP, payload_size);
......
...@@ -75,7 +75,6 @@ ...@@ -75,7 +75,6 @@
#include "NR_DLInformationTransfer.h" #include "NR_DLInformationTransfer.h"
#include "NR_RRCReestablishmentRequest.h" #include "NR_RRCReestablishmentRequest.h"
#include "NR_UE-CapabilityRequestFilterNR.h" #include "NR_UE-CapabilityRequestFilterNR.h"
#include "PHY/defs_nr_common.h"
#include "common/utils/nr/nr_common.h" #include "common/utils/nr/nr_common.h"
#if defined(NR_Rel16) #if defined(NR_Rel16)
#include "NR_SCS-SpecificCarrier.h" #include "NR_SCS-SpecificCarrier.h"
...@@ -1242,7 +1241,7 @@ void fill_mastercellGroupConfig(NR_CellGroupConfig_t *cellGroupConfig, NR_CellGr ...@@ -1242,7 +1241,7 @@ void fill_mastercellGroupConfig(NR_CellGroupConfig_t *cellGroupConfig, NR_CellGr
// DRB Configuration // DRB Configuration
for (int i = bearer_id_start; i < bearer_id_start + nb_bearers_to_setup; i++ ){ for (int i = bearer_id_start; i < bearer_id_start + nb_bearers_to_setup; i++ ){
const NR_RLC_Config_PR rlc_conf = use_rlc_um_for_drb ? NR_RLC_Config_PR_um_Bi_Directional : NR_RLC_Config_PR_am; const NR_RLC_Config_PR rlc_conf = use_rlc_um_for_drb ? NR_RLC_Config_PR_um_Bi_Directional : NR_RLC_Config_PR_am;
NR_RLC_BearerConfig_t *rlc_BearerConfig = get_DRB_RLC_BearerConfig(3 + i, i, rlc_conf, priority[i-bearer_id_start]); NR_RLC_BearerConfig_t *rlc_BearerConfig = get_DRB_RLC_BearerConfig(3 + i, i, rlc_conf, priority[i-1]);
ASN_SEQUENCE_ADD(&cellGroupConfig->rlc_BearerToAddModList->list, rlc_BearerConfig); ASN_SEQUENCE_ADD(&cellGroupConfig->rlc_BearerToAddModList->list, rlc_BearerConfig);
ASN_SEQUENCE_ADD(&ue_context_mastercellGroup->rlc_BearerToAddModList->list, rlc_BearerConfig); ASN_SEQUENCE_ADD(&ue_context_mastercellGroup->rlc_BearerToAddModList->list, rlc_BearerConfig);
} }
......
...@@ -35,6 +35,8 @@ ...@@ -35,6 +35,8 @@
#include "LAYER2/MAC/mac.h" #include "LAYER2/MAC/mac.h"
#include "LAYER2/RLC/rlc.h" #include "LAYER2/RLC/rlc.h"
#define NR_MAX_SIB_LENGTH 2976 // 3GPP TS 38.331 section 5.2.1 - The physical layer imposes a limit to the maximum size a SIB can take. The maximum SIB1 or SI message size is 2976 bits.
extern UE_RRC_INST *UE_rrc_inst; extern UE_RRC_INST *UE_rrc_inst;
extern uint8_t DRB2LCHAN[8]; extern uint8_t DRB2LCHAN[8];
......
...@@ -784,7 +784,7 @@ rrc_gNB_generate_dedicatedRRCReconfiguration( ...@@ -784,7 +784,7 @@ rrc_gNB_generate_dedicatedRRCReconfiguration(
int qos_flow_index = 0; int qos_flow_index = 0;
int pdu_sessions_done = 0; int pdu_sessions_done = 0;
int i; int i;
uint8_t drb_id_to_setup_start = 1; uint8_t drb_id_to_setup_start = 0;
uint8_t nb_drb_to_setup = rrc->configuration.drbs; uint8_t nb_drb_to_setup = rrc->configuration.drbs;
long drb_priority[NGAP_MAX_DRBS_PER_UE]; long drb_priority[NGAP_MAX_DRBS_PER_UE];
NR_CellGroupConfig_t *cellGroupConfig = NULL; NR_CellGroupConfig_t *cellGroupConfig = NULL;
...@@ -903,6 +903,7 @@ rrc_gNB_generate_dedicatedRRCReconfiguration( ...@@ -903,6 +903,7 @@ rrc_gNB_generate_dedicatedRRCReconfiguration(
rrc->configuration.enable_sdap, rrc->configuration.enable_sdap,
rrc->security.do_drb_integrity, rrc->security.do_drb_integrity,
rrc->security.do_drb_ciphering); rrc->security.do_drb_ciphering);
if (drb_id_to_setup_start == 0) drb_id_to_setup_start = DRB_config->drb_Identity;
ASN_SEQUENCE_ADD(&(*DRB_configList)->list, DRB_config); ASN_SEQUENCE_ADD(&(*DRB_configList)->list, DRB_config);
ASN_SEQUENCE_ADD(&(*DRB_configList2)->list, DRB_config); ASN_SEQUENCE_ADD(&(*DRB_configList2)->list, DRB_config);
} }
...@@ -3238,9 +3239,6 @@ static void rrc_DU_process_ue_context_setup_request(MessageDef *msg_p, const cha ...@@ -3238,9 +3239,6 @@ static void rrc_DU_process_ue_context_setup_request(MessageDef *msg_p, const cha
} }
} }
uint8_t drb_id_to_setup_start = 0;
uint8_t nb_drb_to_setup = 0;
long drb_priority[1] = {13}; // For now, we assume only one drb per pdu sessions with a default preiority (will be dynamique in future)
/* Configure SRB2 */ /* Configure SRB2 */
NR_SRB_ToAddMod_t *SRB2_config = NULL; NR_SRB_ToAddMod_t *SRB2_config = NULL;
...@@ -3264,6 +3262,9 @@ static void rrc_DU_process_ue_context_setup_request(MessageDef *msg_p, const cha ...@@ -3264,6 +3262,9 @@ static void rrc_DU_process_ue_context_setup_request(MessageDef *msg_p, const cha
/* Configure DRB */ /* Configure DRB */
NR_DRB_ToAddMod_t *DRB_config = NULL; NR_DRB_ToAddMod_t *DRB_config = NULL;
NR_DRB_ToAddModList_t *DRB_configList = NULL; NR_DRB_ToAddModList_t *DRB_configList = NULL;
uint8_t drb_id_to_setup_start = 0;
uint8_t nb_drb_to_setup = 0;
long drb_priority[1] = {13}; // For now, we assume only one drb per pdu session with a default priority (will be dynamic in future)
if(req->drbs_to_be_setup_length>0){ if(req->drbs_to_be_setup_length>0){
if(ue_context_p->ue_context.DRB_configList == NULL){ if(ue_context_p->ue_context.DRB_configList == NULL){
ue_context_p->ue_context.DRB_configList = CALLOC(1, sizeof(*ue_context_p->ue_context.DRB_configList)); ue_context_p->ue_context.DRB_configList = CALLOC(1, sizeof(*ue_context_p->ue_context.DRB_configList));
...@@ -3273,13 +3274,13 @@ static void rrc_DU_process_ue_context_setup_request(MessageDef *msg_p, const cha ...@@ -3273,13 +3274,13 @@ static void rrc_DU_process_ue_context_setup_request(MessageDef *msg_p, const cha
for (int i=0; i<req->drbs_to_be_setup_length; i++){ for (int i=0; i<req->drbs_to_be_setup_length; i++){
DRB_config = CALLOC(1, sizeof(*DRB_config)); DRB_config = CALLOC(1, sizeof(*DRB_config));
DRB_config->drb_Identity = req->drbs_to_be_setup[i].drb_id; DRB_config->drb_Identity = req->drbs_to_be_setup[i].drb_id;
if (drb_id_to_setup_start == 0) drb_id_to_setup_start = DRB_config->drb_Identity;
ASN_SEQUENCE_ADD(&DRB_configList->list, DRB_config); ASN_SEQUENCE_ADD(&DRB_configList->list, DRB_config);
f1ap_drb_to_be_setup_t drb_p = req->drbs_to_be_setup[i]; f1ap_drb_to_be_setup_t drb_p = req->drbs_to_be_setup[i];
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;
extern instance_t DUuniqInstance; extern instance_t DUuniqInstance;
if (!drb_id_to_setup_start) drb_id_to_setup_start = drb_p.drb_id;
incoming_teid = newGtpuCreateTunnel(DUuniqInstance, incoming_teid = newGtpuCreateTunnel(DUuniqInstance,
req->rnti, req->rnti,
drb_p.drb_id, drb_p.drb_id,
...@@ -3407,6 +3408,8 @@ static void rrc_DU_process_ue_context_modification_request(MessageDef *msg_p, co ...@@ -3407,6 +3408,8 @@ static void rrc_DU_process_ue_context_modification_request(MessageDef *msg_p, co
/* Configure DRB */ /* Configure DRB */
NR_DRB_ToAddMod_t *DRB_config = NULL; NR_DRB_ToAddMod_t *DRB_config = NULL;
NR_DRB_ToAddModList_t *DRB_configList = NULL; NR_DRB_ToAddModList_t *DRB_configList = NULL;
int drb_id_to_setup_start = 0;
long drb_priority[1] = {13}; // For now, we assume only one drb per pdu session with a default priority (will be dynamic in future)
if(req->drbs_to_be_setup_length>0){ if(req->drbs_to_be_setup_length>0){
if(ue_context_p->ue_context.DRB_configList == NULL){ if(ue_context_p->ue_context.DRB_configList == NULL){
ue_context_p->ue_context.DRB_configList = CALLOC(1, sizeof(*ue_context_p->ue_context.DRB_configList)); ue_context_p->ue_context.DRB_configList = CALLOC(1, sizeof(*ue_context_p->ue_context.DRB_configList));
...@@ -3415,12 +3418,14 @@ static void rrc_DU_process_ue_context_modification_request(MessageDef *msg_p, co ...@@ -3415,12 +3418,14 @@ static void rrc_DU_process_ue_context_modification_request(MessageDef *msg_p, co
for (int i=0; i<req->drbs_to_be_setup_length; i++){ for (int i=0; i<req->drbs_to_be_setup_length; i++){
DRB_config = CALLOC(1, sizeof(*DRB_config)); DRB_config = CALLOC(1, sizeof(*DRB_config));
DRB_config->drb_Identity = req->drbs_to_be_setup[i].drb_id; DRB_config->drb_Identity = req->drbs_to_be_setup[i].drb_id;
if (drb_id_to_setup_start == 0) drb_id_to_setup_start = DRB_config->drb_Identity;
ASN_SEQUENCE_ADD(&DRB_configList->list, DRB_config); ASN_SEQUENCE_ADD(&DRB_configList->list, DRB_config);
f1ap_drb_to_be_setup_t drb_p = req->drbs_to_be_setup[i]; f1ap_drb_to_be_setup_t drb_p = req->drbs_to_be_setup[i];
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;
extern instance_t DUuniqInstance; extern instance_t DUuniqInstance;
if (!drb_id_to_setup_start) drb_id_to_setup_start = drb_p.drb_id;
incoming_teid = newGtpuCreateTunnel(DUuniqInstance, incoming_teid = newGtpuCreateTunnel(DUuniqInstance,
req->rnti, req->rnti,
drb_p.drb_id, drb_p.drb_id,
...@@ -3436,8 +3441,6 @@ static void rrc_DU_process_ue_context_modification_request(MessageDef *msg_p, co ...@@ -3436,8 +3441,6 @@ static void rrc_DU_process_ue_context_modification_request(MessageDef *msg_p, co
if(req->srbs_to_be_setup_length>0 || req->drbs_to_be_setup_length>0){ if(req->srbs_to_be_setup_length>0 || req->drbs_to_be_setup_length>0){
cellGroupConfig = calloc(1, sizeof(NR_CellGroupConfig_t)); cellGroupConfig = calloc(1, sizeof(NR_CellGroupConfig_t));
uint8_t drb_id_to_setup_start = 1;
long drb_priority[1] = {13}; // For now, we assume only one drb per pdu sessions with a default preiority (will be dynamique in future)
fill_mastercellGroupConfig(cellGroupConfig, fill_mastercellGroupConfig(cellGroupConfig,
ue_context_p->ue_context.masterCellGroup, ue_context_p->ue_context.masterCellGroup,
rrc->um_on_default_drb, rrc->um_on_default_drb,
...@@ -3456,7 +3459,7 @@ static void rrc_DU_process_ue_context_modification_request(MessageDef *msg_p, co ...@@ -3456,7 +3459,7 @@ static void rrc_DU_process_ue_context_modification_request(MessageDef *msg_p, co
LOG_I(NR_RRC, "Send first DDD buffer status reporting towards the CU through an ITTI message to gtp-u \n"); LOG_I(NR_RRC, "Send first DDD buffer status reporting towards the CU through an ITTI message to gtp-u \n");
uint8_t drb_id = ue_context_p->ue_context.DRB_configList->list.array[0]->drb_Identity; uint8_t drb_id = ue_context_p->ue_context.DRB_configList->list.array[0]->drb_Identity;
rnti_t rnti = ue_context_p->ue_context.rnti; rnti_t rnti = ue_context_p->ue_context.rnti;
int rlc_tx_buffer_space = nr_rlc_get_available_tx_space(rnti, drb_id); int rlc_tx_buffer_space = nr_rlc_get_available_tx_space(rnti, drb_id + 3);
LOG_I(NR_RRC, "Reported in DDD drb_id:%d, rnti:%d\n", drb_id, rnti); LOG_I(NR_RRC, "Reported in DDD drb_id:%d, rnti:%d\n", drb_id, rnti);
MessageDef *msg = itti_alloc_new_message_sized(TASK_RRC_GNB, 0, GTPV1U_DU_BUFFER_REPORT_REQ, MessageDef *msg = itti_alloc_new_message_sized(TASK_RRC_GNB, 0, GTPV1U_DU_BUFFER_REPORT_REQ,
sizeof(gtpv1u_gnb_tunnel_data_req_t)); sizeof(gtpv1u_gnb_tunnel_data_req_t));
......
...@@ -1115,7 +1115,7 @@ static int Gtpv1uHandleGpdu(int h, ...@@ -1115,7 +1115,7 @@ static int Gtpv1uHandleGpdu(int h,
if(NR_PDCP_PDU_SN > 0 && NR_PDCP_PDU_SN %5 ==0){ if(NR_PDCP_PDU_SN > 0 && NR_PDCP_PDU_SN %5 ==0){
LOG_D (GTPU, "Create and send DL DATA Delivery status for the previously received PDU, NR_PDCP_PDU_SN: %u \n", NR_PDCP_PDU_SN); LOG_D (GTPU, "Create and send DL DATA Delivery status for the previously received PDU, NR_PDCP_PDU_SN: %u \n", NR_PDCP_PDU_SN);
int rlc_tx_buffer_space = nr_rlc_get_available_tx_space(ctxt.rnti, rb_id); int rlc_tx_buffer_space = nr_rlc_get_available_tx_space(ctxt.rnti, rb_id + 3);
LOG_D(GTPU, "Available buffer size in RLC for Tx: %d \n", rlc_tx_buffer_space); LOG_D(GTPU, "Available buffer size in RLC for Tx: %d \n", rlc_tx_buffer_space);
/*Total size of DDD_status PDU = 1 octet to report extension header length /*Total size of DDD_status PDU = 1 octet to report extension header length
* size of mandatory part + 3 octets for highest transmitted/delivered PDCP SN * size of mandatory part + 3 octets for highest transmitted/delivered PDCP SN
......
...@@ -1417,11 +1417,15 @@ extern "C" { ...@@ -1417,11 +1417,15 @@ extern "C" {
s->tx_stream = s->usrp->get_tx_stream(stream_args_tx); s->tx_stream = s->usrp->get_tx_stream(stream_args_tx);
/* Setting TX/RX BW after streamers are created due to USRP calibration issue */ /* Setting TX/RX BW after streamers are created due to USRP calibration issue */
for(int i=0; i<((int) s->usrp->get_tx_num_channels()) && i<openair0_cfg[0].tx_num_channels; i++) // N310 with UHD >= 4.2.0 has issues with changing the BW, which is a NOP on N310 in earlier versions
s->usrp->set_tx_bandwidth(openair0_cfg[0].tx_bw,i+choffset); // see also: https://github.com/EttusResearch/uhd/issues/644
if (device->type != USRP_N300_DEV) {
for(int i=0; i<((int) s->usrp->get_rx_num_channels()) && i<openair0_cfg[0].rx_num_channels; i++) for(int i=0; i<((int) s->usrp->get_tx_num_channels()) && i<openair0_cfg[0].tx_num_channels; i++)
s->usrp->set_rx_bandwidth(openair0_cfg[0].rx_bw,i+choffset); s->usrp->set_tx_bandwidth(openair0_cfg[0].tx_bw,i+choffset);
for(int i=0; i<((int) s->usrp->get_rx_num_channels()) && i<openair0_cfg[0].rx_num_channels; i++)
s->usrp->set_rx_bandwidth(openair0_cfg[0].rx_bw,i+choffset);
}
for (int i=0; i<openair0_cfg[0].rx_num_channels; i++) { for (int i=0; i<openair0_cfg[0].rx_num_channels; i++) {
LOG_I(HW,"RX Channel %d\n",i); LOG_I(HW,"RX Channel %d\n",i);
......
...@@ -18,6 +18,7 @@ gNBs = ...@@ -18,6 +18,7 @@ gNBs =
plmn_list = ({ mcc = 208; mnc = 99; mnc_length = 2; snssaiList = ({ sst = 1 }) }); plmn_list = ({ mcc = 208; mnc = 99; mnc_length = 2; snssaiList = ({ sst = 1 }) });
nr_cellid = 12345678L; nr_cellid = 12345678L;
force_256qam_off = 1;
tr_s_preference = "f1"; tr_s_preference = "f1";
......
...@@ -21,6 +21,7 @@ gNBs = ...@@ -21,6 +21,7 @@ gNBs =
////////// Physical parameters: ////////// Physical parameters:
min_rxtxtime = 6; min_rxtxtime = 6;
force_256qam_off = 1;
pdcch_ConfigSIB1 = ( pdcch_ConfigSIB1 = (
{ {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment