Merge branch 'develop' of https://gitlab.eurecom.fr/oai/openairinterface5g into NR_F1C_F1U_extensions
This commit is contained in:
@@ -198,6 +198,26 @@ pipeline {
|
||||
}
|
||||
}
|
||||
}
|
||||
stage ("RF Simulators") {
|
||||
when { expression {doMandatoryTests} }
|
||||
steps {
|
||||
script {
|
||||
triggerSlaveJob ('RAN-RF-Sim-Test', 'Test-RF-Sim-Container')
|
||||
}
|
||||
}
|
||||
post {
|
||||
always {
|
||||
script {
|
||||
finalizeSlaveJob('RAN-RF-Sim-Test')
|
||||
}
|
||||
}
|
||||
failure {
|
||||
script {
|
||||
currentBuild.result = 'FAILURE'
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -369,7 +369,7 @@ pipeline {
|
||||
[$class: 'UsernamePasswordMultiBinding', credentialsId: "${params.eNB_Credentials}", usernameVariable: 'eNB_Username', passwordVariable: 'eNB_Password']
|
||||
]) {
|
||||
echo '\u2705 \u001B[32mLog Collection (eNB - Run)\u001B[0m'
|
||||
sh "python3 ci-scripts/main.py --mode=LogCollecteNB --eNBIPAddress=${params.eNB_IPAddress} --eNBUserName=${eNB_Username} --eNBPassword=${eNB_Password} --eNBSourceCodePath=${params.eNB_SourceCodePath}"
|
||||
sh "python3 ci-scripts/main.py --mode=LogCollecteNB --eNBIPAddress=${params.eNB_IPAddress} --eNBUserName=${eNB_Username} --eNBPassword=${eNB_Password} --eNBSourceCodePath=${params.eNB_SourceCodePath} --BuildId=${env.BUILD_ID}"
|
||||
|
||||
echo '\u2705 \u001B[32mLog Transfer (eNB - Run)\u001B[0m'
|
||||
sh "sshpass -p \'${eNB_Password}\' scp -o 'StrictHostKeyChecking no' -o 'ConnectTimeout 10' ${eNB_Username}@${params.eNB_IPAddress}:${eNB_SourceCodePath}/cmake_targets/enb.log.zip ./enb.log.${env.BUILD_ID}.zip || true"
|
||||
|
||||
@@ -266,6 +266,9 @@ def ArgsParse(argvs,CiTestObj,RAN,HTML,EPC,ldpc,CONTAINERS,HELP,SCA,PHYSIM):
|
||||
elif re.match('^\-\-OCProjectName=(.+)$', myArgv, re.IGNORECASE):
|
||||
matchReg = re.match('^\-\-OCProjectName=(.+)$', myArgv, re.IGNORECASE)
|
||||
PHYSIM.OCProjectName = matchReg.group(1)
|
||||
elif re.match('^\-\-BuildId=(.+)$', myArgv, re.IGNORECASE):
|
||||
matchReg = re.match('^\-\-BuildId=(.+)$', myArgv, re.IGNORECASE)
|
||||
RAN.BuildId = matchReg.group(1)
|
||||
else:
|
||||
HELP.GenericHelp(CONST.Version)
|
||||
sys.exit('Invalid Parameter: ' + myArgv)
|
||||
|
||||
@@ -36,6 +36,7 @@ import re # reg
|
||||
import logging
|
||||
import os
|
||||
import shutil
|
||||
import subprocess
|
||||
import time
|
||||
from multiprocessing import Process, Lock, SimpleQueue
|
||||
from zipfile import ZipFile
|
||||
@@ -76,6 +77,9 @@ class Containerize():
|
||||
self.eNB_instance = 0
|
||||
self.eNB_serverId = ['', '', '']
|
||||
self.yamlPath = ['', '', '']
|
||||
self.services = ['', '', '']
|
||||
self.nb_healthy = [0, 0, 0]
|
||||
self.exitStatus = 0
|
||||
self.eNB_logFile = ['', '', '']
|
||||
|
||||
self.testCase_id = ''
|
||||
@@ -89,6 +93,14 @@ class Containerize():
|
||||
self.allImagesSize = {}
|
||||
self.collectInfo = {}
|
||||
|
||||
self.pingContName = ''
|
||||
self.pingOptions = ''
|
||||
self.pingLossThreshold = ''
|
||||
self.svrContName = ''
|
||||
self.svrOptions = ''
|
||||
self.cliContName = ''
|
||||
self.cliOptions = ''
|
||||
|
||||
#-----------------------------------------------------------
|
||||
# Container management functions
|
||||
#-----------------------------------------------------------
|
||||
@@ -476,7 +488,6 @@ class Containerize():
|
||||
HTML.CreateHtmlTestRow('N/A', 'KO', CONST.ALL_PROCESSES_OK)
|
||||
|
||||
def UndeployObject(self, HTML, RAN):
|
||||
logging.info('\u001B[1m Undeploying OAI Object Pass\u001B[0m')
|
||||
if self.eNB_serverId[self.eNB_instance] == '0':
|
||||
lIpAddr = self.eNBIPAddress
|
||||
lUserName = self.eNBUserName
|
||||
@@ -529,4 +540,307 @@ class Containerize():
|
||||
HTML.CreateHtmlTestRow(RAN.runtime_stats, 'KO', logStatus)
|
||||
else:
|
||||
HTML.CreateHtmlTestRow(RAN.runtime_stats, 'OK', CONST.ALL_PROCESSES_OK)
|
||||
logging.info('\u001B[1m Undeploying OAI Object Pass\u001B[0m')
|
||||
|
||||
def DeployGenObject(self, HTML):
|
||||
self.exitStatus = 0
|
||||
logging.info('\u001B[1m Checking Services to deploy\u001B[0m')
|
||||
cmd = 'cd ' + self.yamlPath[0] + ' && docker-compose config --services'
|
||||
logging.debug(cmd)
|
||||
try:
|
||||
listServices = subprocess.check_output(cmd, shell=True, universal_newlines=True)
|
||||
except Exception as e:
|
||||
self.exitStatus = 1
|
||||
HTML.CreateHtmlTestRow('SVC not Found', 'KO', CONST.ALL_PROCESSES_OK)
|
||||
return
|
||||
for reqSvc in self.services[0].split(' '):
|
||||
res = re.search(reqSvc, listServices)
|
||||
if res is None:
|
||||
logging.error(reqSvc + ' not found in specified docker-compose')
|
||||
self.exitStatus = 1
|
||||
if (self.exitStatus == 1):
|
||||
HTML.CreateHtmlTestRow('SVC not Found', 'KO', CONST.ALL_PROCESSES_OK)
|
||||
return
|
||||
|
||||
if (self.ranAllowMerge):
|
||||
cmd = 'cd ' + self.yamlPath[0] + ' && sed -e "s@develop@ci-temp@" docker-compose.y*ml > docker-compose-ci.yml'
|
||||
else:
|
||||
cmd = 'cd ' + self.yamlPath[0] + ' && sed -e "s@develop@develop@" docker-compose.y*ml > docker-compose-ci.yml'
|
||||
logging.debug(cmd)
|
||||
subprocess.run(cmd, shell=True)
|
||||
|
||||
cmd = 'cd ' + self.yamlPath[0] + ' && docker-compose -f docker-compose-ci.yml up -d ' + self.services[0]
|
||||
logging.debug(cmd)
|
||||
try:
|
||||
deployStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=30)
|
||||
except Exception as e:
|
||||
self.exitStatus = 1
|
||||
logging.error('Could not deploy')
|
||||
HTML.CreateHtmlTestRow('Could not deploy', 'KO', CONST.ALL_PROCESSES_OK)
|
||||
return
|
||||
|
||||
logging.info('\u001B[1m Checking if all deployed healthy\u001B[0m')
|
||||
cmd = 'cd ' + self.yamlPath[0] + ' && docker-compose -f docker-compose-ci.yml ps -a'
|
||||
count = 0
|
||||
healthy = 0
|
||||
while (count < 10):
|
||||
count += 1
|
||||
deployStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=10)
|
||||
healthy = 0
|
||||
for state in deployStatus.split('\n'):
|
||||
res = re.search('Up \(healthy\)', state)
|
||||
if res is not None:
|
||||
healthy += 1
|
||||
if healthy == self.nb_healthy[0]:
|
||||
count = 100
|
||||
else:
|
||||
time.sleep(10)
|
||||
|
||||
# HACK TO REMOVE LATER WHEN FIX
|
||||
res = re.search('oai-nr-ue', self.services[0])
|
||||
if res is not None:
|
||||
cmd = 'docker exec rfsim5g-oai-nr-ue /bin/bash -c "ip route del default"'
|
||||
logging.debug(cmd)
|
||||
deployStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=10)
|
||||
cmd = 'docker exec rfsim5g-oai-nr-ue /bin/bash -c "ip route del 12.1.1.0/24"'
|
||||
logging.debug(cmd)
|
||||
deployStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=10)
|
||||
cmd = 'docker exec rfsim5g-oai-nr-ue /bin/bash -c "ip route add default via 12.1.1.2 dev oaitun_ue1"'
|
||||
logging.debug(cmd)
|
||||
deployStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=10)
|
||||
# END OF HACK TO REMOVE LATER WHEN FIX
|
||||
|
||||
if count == 100 and healthy == self.nb_healthy[0]:
|
||||
HTML.CreateHtmlTestRow('n/a', 'OK', CONST.ALL_PROCESSES_OK)
|
||||
logging.info('\u001B[1m Deploying OAI Object(s) PASS\u001B[0m')
|
||||
else:
|
||||
self.exitStatus = 1
|
||||
HTML.CreateHtmlTestRow('Could not deploy in time', 'KO', CONST.ALL_PROCESSES_OK)
|
||||
logging.error('\u001B[1m Deploying OAI Object(s) FAILED\u001B[0m')
|
||||
|
||||
def UndeployGenObject(self, HTML):
|
||||
self.exitStatus = 0
|
||||
|
||||
if (self.ranAllowMerge):
|
||||
cmd = 'cd ' + self.yamlPath[0] + ' && sed -e "s@develop@ci-temp@" docker-compose.y*ml > docker-compose-ci.yml'
|
||||
else:
|
||||
cmd = 'cd ' + self.yamlPath[0] + ' && sed -e "s@develop@develop@" docker-compose.y*ml > docker-compose-ci.yml'
|
||||
logging.debug(cmd)
|
||||
subprocess.run(cmd, shell=True)
|
||||
|
||||
# if the containers are running, recover the logs!
|
||||
cmd = 'cd ' + self.yamlPath[0] + ' && docker-compose -f docker-compose-ci.yml ps --all'
|
||||
logging.debug(cmd)
|
||||
deployStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=10)
|
||||
anyLogs = False
|
||||
for state in deployStatus.split('\n'):
|
||||
res = re.search('Name|----------', state)
|
||||
if res is not None:
|
||||
continue
|
||||
if len(state) == 0:
|
||||
continue
|
||||
res = re.search('^(?P<container_name>[a-zA-Z0-9\-\_]+) ', state)
|
||||
if res is not None:
|
||||
anyLogs = True
|
||||
cName = res.group('container_name')
|
||||
cmd = 'cd ' + self.yamlPath[0] + ' && docker logs ' + cName + ' > ' + cName + '.log 2>&1'
|
||||
logging.debug(cmd)
|
||||
deployStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=10)
|
||||
if anyLogs:
|
||||
cmd = 'mkdir -p ../cmake_targets/log && mv ' + self.yamlPath[0] + '/*.log ../cmake_targets/log'
|
||||
logging.debug(cmd)
|
||||
deployStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=10)
|
||||
|
||||
cmd = 'cd ' + self.yamlPath[0] + ' && docker-compose -f docker-compose-ci.yml down'
|
||||
logging.debug(cmd)
|
||||
try:
|
||||
deployStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=100)
|
||||
except Exception as e:
|
||||
self.exitStatus = 1
|
||||
logging.error('Could not undeploy')
|
||||
HTML.CreateHtmlTestRow('Could not undeploy', 'KO', CONST.ALL_PROCESSES_OK)
|
||||
logging.error('\u001B[1m Undeploying OAI Object(s) FAILED\u001B[0m')
|
||||
return
|
||||
|
||||
HTML.CreateHtmlTestRow('n/a', 'OK', CONST.ALL_PROCESSES_OK)
|
||||
logging.info('\u001B[1m Undeploying OAI Object(s) PASS\u001B[0m')
|
||||
|
||||
def PingFromContainer(self, HTML):
|
||||
self.exitStatus = 0
|
||||
cmd = 'mkdir -p ../cmake_targets/log'
|
||||
deployStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=10)
|
||||
|
||||
cmd = 'docker exec ' + self.pingContName + ' /bin/bash -c "ping ' + self.pingOptions + '" 2>&1 | tee ../cmake_targets/log/ping_' + HTML.testCase_id + '.log'
|
||||
logging.debug(cmd)
|
||||
deployStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=100)
|
||||
|
||||
result = re.search(', (?P<packetloss>[0-9\.]+)% packet loss, time [0-9\.]+ms', deployStatus)
|
||||
if result is None:
|
||||
self.PingExit(HTML, False, 'Packet Loss Not Found')
|
||||
return
|
||||
|
||||
packetloss = result.group('packetloss')
|
||||
if float(packetloss) == 100:
|
||||
self.PingExit(HTML, False, 'Packet Loss is 100%')
|
||||
return
|
||||
|
||||
result = re.search('rtt min\/avg\/max\/mdev = (?P<rtt_min>[0-9\.]+)\/(?P<rtt_avg>[0-9\.]+)\/(?P<rtt_max>[0-9\.]+)\/[0-9\.]+ ms', deployStatus)
|
||||
if result is None:
|
||||
self.PingExit(HTML, False, 'Ping RTT_Min RTT_Avg RTT_Max Not Found!')
|
||||
return
|
||||
|
||||
rtt_min = result.group('rtt_min')
|
||||
rtt_avg = result.group('rtt_avg')
|
||||
rtt_max = result.group('rtt_max')
|
||||
pal_msg = 'Packet Loss : ' + packetloss + '%'
|
||||
min_msg = 'RTT(Min) : ' + rtt_min + ' ms'
|
||||
avg_msg = 'RTT(Avg) : ' + rtt_avg + ' ms'
|
||||
max_msg = 'RTT(Max) : ' + rtt_max + ' ms'
|
||||
|
||||
message = 'ping result\n'
|
||||
message += ' ' + pal_msg + '\n'
|
||||
message += ' ' + min_msg + '\n'
|
||||
message += ' ' + avg_msg + '\n'
|
||||
message += ' ' + max_msg + '\n'
|
||||
packetLossOK = True
|
||||
if float(packetloss) > float(self.pingLossThreshold):
|
||||
message += '\nPacket Loss too high'
|
||||
packetLossOK = False
|
||||
elif float(packetloss) > 0:
|
||||
message += '\nPacket Loss is not 0%'
|
||||
self.PingExit(HTML, packetLossOK, message)
|
||||
|
||||
if packetLossOK:
|
||||
logging.debug('\u001B[1;37;44m ping result \u001B[0m')
|
||||
logging.debug('\u001B[1;34m ' + pal_msg + '\u001B[0m')
|
||||
logging.debug('\u001B[1;34m ' + min_msg + '\u001B[0m')
|
||||
logging.debug('\u001B[1;34m ' + avg_msg + '\u001B[0m')
|
||||
logging.debug('\u001B[1;34m ' + max_msg + '\u001B[0m')
|
||||
logging.info('\u001B[1m Ping Test PASS\u001B[0m')
|
||||
|
||||
def PingExit(self, HTML, status, message):
|
||||
html_queue = SimpleQueue()
|
||||
html_cell = '<pre style="background-color:white">UE\n' + message + '</pre>'
|
||||
html_queue.put(html_cell)
|
||||
if status:
|
||||
HTML.CreateHtmlTestRowQueue(self.pingOptions, 'OK', 1, html_queue)
|
||||
else:
|
||||
self.exitStatus = 1
|
||||
logging.error('\u001B[1;37;41m ' + message + ' \u001B[0m')
|
||||
HTML.CreateHtmlTestRowQueue(self.pingOptions, 'KO', 1, html_queue)
|
||||
|
||||
def IperfFromContainer(self, HTML):
|
||||
self.exitStatus = 0
|
||||
|
||||
cmd = 'mkdir -p ../cmake_targets/log'
|
||||
logStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=10)
|
||||
|
||||
# Start the server process
|
||||
cmd = 'docker exec -d ' + self.svrContName + ' /bin/bash -c "nohup iperf ' + self.svrOptions + ' > /tmp/iperf_server.log 2>&1"'
|
||||
logging.debug(cmd)
|
||||
serverStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=10)
|
||||
time.sleep(5)
|
||||
|
||||
# Start the client process
|
||||
cmd = 'docker exec ' + self.cliContName + ' /bin/bash -c "iperf ' + self.cliOptions + '" 2>&1 | tee ../cmake_targets/log/iperf_client_' + HTML.testCase_id + '.log'
|
||||
logging.debug(cmd)
|
||||
clientStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=100)
|
||||
|
||||
# Stop the server process
|
||||
cmd = 'docker exec ' + self.svrContName + ' /bin/bash -c "pkill iperf"'
|
||||
logging.debug(cmd)
|
||||
serverStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=10)
|
||||
time.sleep(5)
|
||||
cmd = 'docker cp ' + self.svrContName + ':/tmp/iperf_server.log ../cmake_targets/log/iperf_server_' + HTML.testCase_id + '.log'
|
||||
logging.debug(cmd)
|
||||
serverStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=10)
|
||||
|
||||
# Analyze client output
|
||||
result = re.search('Server Report:', clientStatus)
|
||||
if result is None:
|
||||
result = re.search('read failed: Connection refused', clientStatus)
|
||||
if result is not None:
|
||||
message = 'Could not connect to iperf server!'
|
||||
else:
|
||||
message = 'Server Report and Connection refused Not Found!'
|
||||
self.IperfExit(HTML, False, message)
|
||||
return
|
||||
|
||||
# Computing the requested bandwidth in float
|
||||
result = re.search('-b (?P<iperf_bandwidth>[0-9\.]+)[KMG]', self.cliOptions)
|
||||
if result is not None:
|
||||
req_bandwidth = result.group('iperf_bandwidth')
|
||||
req_bw = float(req_bandwidth)
|
||||
result = re.search('-b [0-9\.]+K', self.cliOptions)
|
||||
if result is not None:
|
||||
req_bandwidth = '%.1f Kbits/sec' % req_bw
|
||||
req_bw = req_bw * 1000
|
||||
result = re.search('-b [0-9\.]+M', self.cliOptions)
|
||||
if result is not None:
|
||||
req_bandwidth = '%.1f Mbits/sec' % req_bw
|
||||
req_bw = req_bw * 1000000
|
||||
|
||||
reportLine = None
|
||||
reportLineFound = False
|
||||
for iLine in clientStatus.split('\n'):
|
||||
if reportLineFound:
|
||||
reportLine = iLine
|
||||
reportLineFound = False
|
||||
res = re.search('Server Report:', iLine)
|
||||
if res is not None:
|
||||
reportLineFound = True
|
||||
result = None
|
||||
if reportLine is not None:
|
||||
result = re.search('(?:|\[ *\d+\].*) (?P<bitrate>[0-9\.]+ [KMG]bits\/sec) +(?P<jitter>[0-9\.]+ ms) +(\d+\/ ..\d+) +(\((?P<packetloss>[0-9\.]+)%\))', reportLine)
|
||||
iperfStatus = True
|
||||
if result is not None:
|
||||
bitrate = result.group('bitrate')
|
||||
packetloss = result.group('packetloss')
|
||||
jitter = result.group('jitter')
|
||||
logging.debug('\u001B[1;37;44m iperf result \u001B[0m')
|
||||
iperfStatus = True
|
||||
msg = 'Req Bitrate : ' + req_bandwidth + '\n'
|
||||
logging.debug('\u001B[1;34m Req Bitrate : ' + req_bandwidth + '\u001B[0m')
|
||||
if bitrate is not None:
|
||||
msg += 'Bitrate : ' + bitrate + '\n'
|
||||
logging.debug('\u001B[1;34m Bitrate : ' + bitrate + '\u001B[0m')
|
||||
result = re.search('(?P<real_bw>[0-9\.]+) [KMG]bits/sec', str(bitrate))
|
||||
if result is not None:
|
||||
actual_bw = float(str(result.group('real_bw')))
|
||||
result = re.search('[0-9\.]+ K', bitrate)
|
||||
if result is not None:
|
||||
actual_bw = actual_bw * 1000
|
||||
result = re.search('[0-9\.]+ M', bitrate)
|
||||
if result is not None:
|
||||
actual_bw = actual_bw * 1000000
|
||||
br_loss = 100 * actual_bw / req_bw
|
||||
if br_loss < 90:
|
||||
iperfStatus = False
|
||||
bitperf = '%.2f ' % br_loss
|
||||
msg += 'Bitrate Perf: ' + bitperf + '%\n'
|
||||
logging.debug('\u001B[1;34m Bitrate Perf: ' + bitperf + '%\u001B[0m')
|
||||
if packetloss is not None:
|
||||
msg += 'Packet Loss : ' + packetloss + '%\n'
|
||||
logging.debug('\u001B[1;34m Packet Loss : ' + packetloss + '%\u001B[0m')
|
||||
if float(packetloss) > float(5):
|
||||
msg += 'Packet Loss too high!\n'
|
||||
logging.debug('\u001B[1;37;41m Packet Loss too high \u001B[0m')
|
||||
iperfStatus = False
|
||||
if jitter is not None:
|
||||
msg += 'Jitter : ' + jitter + '\n'
|
||||
logging.debug('\u001B[1;34m Jitter : ' + jitter + '\u001B[0m')
|
||||
self.IperfExit(HTML, iperfStatus, msg)
|
||||
else:
|
||||
logging.error('problem?')
|
||||
if iperfStatus:
|
||||
logging.info('\u001B[1m Iperf Test PASS\u001B[0m')
|
||||
|
||||
def IperfExit(self, HTML, status, message):
|
||||
html_queue = SimpleQueue()
|
||||
html_cell = '<pre style="background-color:white">UE\n' + message + '</pre>'
|
||||
html_queue.put(html_cell)
|
||||
if status:
|
||||
HTML.CreateHtmlTestRowQueue(self.cliOptions, 'OK', 1, html_queue)
|
||||
else:
|
||||
self.exitStatus = 1
|
||||
HTML.CreateHtmlTestRowQueue(self.cliOptions, 'KO', 1, html_queue)
|
||||
|
||||
+63
-2
@@ -65,6 +65,7 @@ import xml.etree.ElementTree as ET
|
||||
import logging
|
||||
import datetime
|
||||
import signal
|
||||
import subprocess
|
||||
from multiprocessing import Process, Lock, SimpleQueue
|
||||
logging.basicConfig(
|
||||
level=logging.DEBUG,
|
||||
@@ -372,6 +373,41 @@ def GetParametersFromXML(action):
|
||||
if (string_field is not None):
|
||||
CONTAINERS.yamlPath[CONTAINERS.eNB_instance] = string_field
|
||||
|
||||
elif action == 'DeployGenObject' or action == 'UndeployGenObject':
|
||||
string_field=test.findtext('yaml_path')
|
||||
if (string_field is not None):
|
||||
CONTAINERS.yamlPath[0] = string_field
|
||||
string_field=test.findtext('services')
|
||||
if (string_field is not None):
|
||||
CONTAINERS.services[0] = string_field
|
||||
string_field=test.findtext('nb_healthy')
|
||||
if (string_field is not None):
|
||||
CONTAINERS.nb_healthy[0] = int(string_field)
|
||||
|
||||
elif action == 'PingFromContainer':
|
||||
string_field = test.findtext('container_name')
|
||||
if (string_field is not None):
|
||||
CONTAINERS.pingContName = string_field
|
||||
string_field = test.findtext('options')
|
||||
if (string_field is not None):
|
||||
CONTAINERS.pingOptions = string_field
|
||||
string_field = test.findtext('loss_threshold')
|
||||
if (string_field is not None):
|
||||
CONTAINERS.pingLossThreshold = string_field
|
||||
|
||||
elif action == 'IperfFromContainer':
|
||||
string_field = test.findtext('server_container_name')
|
||||
if (string_field is not None):
|
||||
CONTAINERS.svrContName = string_field
|
||||
string_field = test.findtext('server_options')
|
||||
if (string_field is not None):
|
||||
CONTAINERS.svrOptions = string_field
|
||||
string_field = test.findtext('client_container_name')
|
||||
if (string_field is not None):
|
||||
CONTAINERS.cliContName = string_field
|
||||
string_field = test.findtext('client_options')
|
||||
if (string_field is not None):
|
||||
CONTAINERS.cliOptions = string_field
|
||||
|
||||
else: # ie action == 'Run_PhySim':
|
||||
ldpc.runargs = test.findtext('physim_run_args')
|
||||
@@ -479,6 +515,8 @@ if re.match('^TerminateeNB$', mode, re.IGNORECASE):
|
||||
if RAN.eNBIPAddress == '' or RAN.eNBUserName == '' or RAN.eNBPassword == '':
|
||||
HELP.GenericHelp(CONST.Version)
|
||||
sys.exit('Insufficient Parameter')
|
||||
if RAN.eNBIPAddress == 'none':
|
||||
sys.exit(0)
|
||||
RAN.eNB_instance=0
|
||||
RAN.eNB_serverId[0]='0'
|
||||
RAN.eNBSourceCodePath='/tmp/'
|
||||
@@ -514,11 +552,18 @@ elif re.match('^LogCollectBuild$', mode, re.IGNORECASE):
|
||||
if (RAN.eNBIPAddress == '' or RAN.eNBUserName == '' or RAN.eNBPassword == '' or RAN.eNBSourceCodePath == '') and (CiTestObj.UEIPAddress == '' or CiTestObj.UEUserName == '' or CiTestObj.UEPassword == '' or CiTestObj.UESourceCodePath == ''):
|
||||
HELP.GenericHelp(CONST.Version)
|
||||
sys.exit('Insufficient Parameter')
|
||||
if RAN.eNBIPAddress == 'none':
|
||||
sys.exit(0)
|
||||
CiTestObj.LogCollectBuild(RAN)
|
||||
elif re.match('^LogCollecteNB$', mode, re.IGNORECASE):
|
||||
if RAN.eNBIPAddress == '' or RAN.eNBUserName == '' or RAN.eNBPassword == '' or RAN.eNBSourceCodePath == '':
|
||||
HELP.GenericHelp(CONST.Version)
|
||||
sys.exit('Insufficient Parameter')
|
||||
if RAN.eNBIPAddress == 'none':
|
||||
cmd = 'zip -r enb.log.' + RAN.BuildId + '.zip cmake_targets/log'
|
||||
logging.debug(cmd)
|
||||
zipStatus = subprocess.check_output(cmd, shell=True, stderr=subprocess.STDOUT, universal_newlines=True, timeout=60)
|
||||
sys.exit(0)
|
||||
RAN.LogCollecteNB()
|
||||
elif re.match('^LogCollectHSS$', mode, re.IGNORECASE):
|
||||
if EPC.IPAddress == '' or EPC.UserName == '' or EPC.Password == '' or EPC.Type == '' or EPC.SourceCodePath == '':
|
||||
@@ -802,7 +847,7 @@ elif re.match('^TesteNB$', mode, re.IGNORECASE) or re.match('^TestUE$', mode, re
|
||||
elif action == 'Build_PhySim':
|
||||
HTML=ldpc.Build_PhySim(HTML,CONST)
|
||||
if ldpc.exitStatus==1:
|
||||
RAN.prematureExit = False
|
||||
RAN.prematureExit = True
|
||||
elif action == 'Run_PhySim':
|
||||
HTML=ldpc.Run_PhySim(HTML,CONST,id)
|
||||
elif action == 'Build_Image':
|
||||
@@ -815,9 +860,25 @@ elif re.match('^TesteNB$', mode, re.IGNORECASE) or re.match('^TestUE$', mode, re
|
||||
SCA.CppCheckAnalysis(HTML)
|
||||
elif action == 'Deploy_Run_PhySim':
|
||||
PHYSIM.Deploy_PhySim(HTML, RAN)
|
||||
elif action == 'DeployGenObject':
|
||||
CONTAINERS.DeployGenObject(HTML)
|
||||
if CONTAINERS.exitStatus==1:
|
||||
RAN.prematureExit = True
|
||||
elif action == 'UndeployGenObject':
|
||||
CONTAINERS.UndeployGenObject(HTML)
|
||||
if CONTAINERS.exitStatus==1:
|
||||
RAN.prematureExit = True
|
||||
elif action == 'PingFromContainer':
|
||||
CONTAINERS.PingFromContainer(HTML)
|
||||
if CONTAINERS.exitStatus==1:
|
||||
RAN.prematureExit = True
|
||||
elif action == 'IperfFromContainer':
|
||||
CONTAINERS.IperfFromContainer(HTML)
|
||||
if CONTAINERS.exitStatus==1:
|
||||
RAN.prematureExit = True
|
||||
else:
|
||||
sys.exit('Invalid class (action) from xml')
|
||||
if not RAN.prematureExit:
|
||||
if RAN.prematureExit:
|
||||
if CiTestObj.testCase_id == CiTestObj.testMinStableId:
|
||||
logging.debug('Scenario has reached minimal stability point')
|
||||
CiTestObj.testStabilityPointReached = True
|
||||
|
||||
@@ -41,3 +41,7 @@
|
||||
- Undeploy_Object
|
||||
- Cppcheck_Analysis
|
||||
- Deploy_Run_PhySim
|
||||
- DeployGenObject
|
||||
- UndeployGenObject
|
||||
- PingFromContainer
|
||||
- IperfFromContainer
|
||||
|
||||
@@ -0,0 +1,103 @@
|
||||
<!--
|
||||
|
||||
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>rfsim-5gnr</htmlTabRef>
|
||||
<htmlTabName>Testing 5G NR RF sim in containers</htmlTabName>
|
||||
<htmlTabIcon>wrench</htmlTabIcon>
|
||||
<TestCaseRequestedList>
|
||||
000001
|
||||
000002
|
||||
000003
|
||||
020001
|
||||
020002
|
||||
030001
|
||||
030002
|
||||
100001
|
||||
</TestCaseRequestedList>
|
||||
<TestCaseExclusionList></TestCaseExclusionList>
|
||||
|
||||
<testCase id="000001">
|
||||
<class>DeployGenObject</class>
|
||||
<desc>Deploy OAI 5G CoreNetwork</desc>
|
||||
<yaml_path>yaml_files/5g_rfsimulator</yaml_path>
|
||||
<services>mysql oai-nrf oai-amf oai-smf oai-spgwu oai-ext-dn</services>
|
||||
<nb_healthy>6</nb_healthy>
|
||||
</testCase>
|
||||
|
||||
<testCase id="000002">
|
||||
<class>DeployGenObject</class>
|
||||
<desc>Deploy OAI 5G gNB RF sim SA</desc>
|
||||
<yaml_path>yaml_files/5g_rfsimulator</yaml_path>
|
||||
<services>oai-gnb</services>
|
||||
<nb_healthy>7</nb_healthy>
|
||||
</testCase>
|
||||
|
||||
<testCase id="000003">
|
||||
<class>DeployGenObject</class>
|
||||
<desc>Deploy OAI 5G NR-UE RF sim SA</desc>
|
||||
<yaml_path>yaml_files/5g_rfsimulator</yaml_path>
|
||||
<services>oai-nr-ue</services>
|
||||
<nb_healthy>8</nb_healthy>
|
||||
</testCase>
|
||||
|
||||
<testCase id="020001">
|
||||
<class>PingFromContainer</class>
|
||||
<desc>Ping ext-dn from NR-UE</desc>
|
||||
<container_name>rfsim5g-oai-nr-ue</container_name>
|
||||
<options>-I oaitun_ue1 -c 20 192.168.72.135</options>
|
||||
<loss_threshold>5</loss_threshold>
|
||||
</testCase>
|
||||
|
||||
<testCase id="020002">
|
||||
<class>PingFromContainer</class>
|
||||
<desc>Ping NR-UE from ext-dn</desc>
|
||||
<container_name>rfsim5g-oai-ext-dn</container_name>
|
||||
<options>-c 20 12.1.1.2</options>
|
||||
<loss_threshold>5</loss_threshold>
|
||||
</testCase>
|
||||
|
||||
<testCase id="030001">
|
||||
<class>IperfFromContainer</class>
|
||||
<desc>Iperf UDP Downlink</desc>
|
||||
<server_container_name>rfsim5g-oai-nr-ue</server_container_name>
|
||||
<client_container_name>rfsim5g-oai-ext-dn</client_container_name>
|
||||
<server_options>-B 12.1.1.2 -u -i 1 -s</server_options>
|
||||
<client_options>-c 12.1.1.2 -u -i 1 -t 30 -b 400K</client_options>
|
||||
</testCase>
|
||||
|
||||
<testCase id="030002">
|
||||
<class>IperfFromContainer</class>
|
||||
<desc>Iperf UDP Uplink</desc>
|
||||
<server_container_name>rfsim5g-oai-ext-dn</server_container_name>
|
||||
<client_container_name>rfsim5g-oai-nr-ue</client_container_name>
|
||||
<server_options>-u -i 1 -s</server_options>
|
||||
<client_options>-B 12.1.1.2 -c 192.168.72.135 -u -i 1 -t 30 -b 20K</client_options>
|
||||
</testCase>
|
||||
|
||||
<testCase id="100001">
|
||||
<class>UndeployGenObject</class>
|
||||
<desc>Undeploy all OAI 5G stack</desc>
|
||||
<yaml_path>yaml_files/5g_rfsimulator</yaml_path>
|
||||
</testCase>
|
||||
|
||||
</testCaseList>
|
||||
@@ -0,0 +1,38 @@
|
||||
<!--
|
||||
|
||||
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>rfsim-5gnr-down</htmlTabRef>
|
||||
<htmlTabName>CleanUp 5G RF</htmlTabName>
|
||||
<htmlTabIcon>trash</htmlTabIcon>
|
||||
<TestCaseRequestedList>
|
||||
100002
|
||||
</TestCaseRequestedList>
|
||||
<TestCaseExclusionList></TestCaseExclusionList>
|
||||
|
||||
<testCase id="100002">
|
||||
<class>UndeployGenObject</class>
|
||||
<desc>Undeploy all OAI 5G stack</desc>
|
||||
<yaml_path>yaml_files/5g_rfsimulator</yaml_path>
|
||||
</testCase>
|
||||
|
||||
</testCaseList>
|
||||
@@ -7,7 +7,7 @@
|
||||
</a>
|
||||
</td>
|
||||
<td style="border-collapse: collapse; border: none; vertical-align: center;">
|
||||
<b><font size = "5">OAI Full Stack RF simulation with containers</font></b>
|
||||
<b><font size = "5">OAI Full Stack 4G-LTE RF simulation with containers</font></b>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
@@ -81,11 +81,14 @@ How to build the Traffic-Generator image is explained [here](https://github.com/
|
||||
|
||||
**Just `docker-compose up -d` WILL NOT WORK!**
|
||||
|
||||
All the following commands **SHALL** be run from the `ci-scripts/yaml_files/4g_rfsimulator` folder.
|
||||
|
||||
## 2.1. Deploy and Configure Cassandra Database ##
|
||||
|
||||
It is very crutial that the Cassandra DB is fully configured before you do anything else!
|
||||
|
||||
```bash
|
||||
$ cd ci-scripts/yaml_files/4g_rfsimulator
|
||||
$ docker-compose up -d db_init
|
||||
Creating network "rfsim4g-oai-private-net" with the default driver
|
||||
Creating network "rfsim4g-oai-public-net" with the default driver
|
||||
|
||||
@@ -0,0 +1,396 @@
|
||||
<table style="border-collapse: collapse; border: none;">
|
||||
<tr style="border-collapse: collapse; border: none;">
|
||||
<td style="border-collapse: collapse; border: none;">
|
||||
<a href="http://www.openairinterface.org/">
|
||||
<img src="../../../doc/images/oai_final_logo.png" alt="" border=3 height=50 width=150>
|
||||
</img>
|
||||
</a>
|
||||
</td>
|
||||
<td style="border-collapse: collapse; border: none; vertical-align: center;">
|
||||
<b><font size = "5">OAI Full Stack 5G-NR RF simulation with containers</font></b>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
This page is only valid for an `Ubuntu18` host.
|
||||
|
||||
**TABLE OF CONTENTS**
|
||||
|
||||
1. [Retrieving the images on Docker-Hub](#1-retrieving-the-images-on-docker-hub)
|
||||
2. [Deploy containers](#2-deploy-containers)
|
||||
1. [Deploy OAI 5G Core Network](#21-deploy-oai-5g-core-network)
|
||||
2. [Deploy OAI gNB in RF simulator mode and in Standalone Mode](#22-deploy-oai-gnb-in-rf-simulator-mode-and-in-standalone-mode)
|
||||
3. [Deploy OAI NR-UE in RF simulator mode and in Standalone Mode](#23-deploy-oai-nr-ue-in-rf-simulator-mode-and-in-standalone-mode)
|
||||
3. [Check traffic](#3-check-traffic)
|
||||
1. [Check your Internet connectivity](#31-check-your-internet-connectivity)
|
||||
2. [Start the iperf server inside the NR-UE container](#32-start-the-iperf-server-inside-the-nr-ue-container)
|
||||
3. [Start the iperf client inside the ext-dn container](#33-start-the-iperf-client-inside-the-ext-dn-container)
|
||||
4. [Un-deployment](#4-un-deployment)
|
||||
|
||||
# 1. Retrieving the images on Docker-Hub #
|
||||
|
||||
Currently the images are hosted under the user account `rdefosseoai`.
|
||||
|
||||
This may change in the future.
|
||||
|
||||
Once again you may need to log on [docker-hub](https://hub.docker.com/) if your organization has reached pulling limit as `anonymous`.
|
||||
|
||||
```bash
|
||||
$ docker login
|
||||
Login with your Docker ID to push and pull images from Docker Hub. If you don't have a Docker ID, head over to https://hub.docker.com to create one.
|
||||
Username:
|
||||
Password:
|
||||
```
|
||||
|
||||
Now pull images.
|
||||
|
||||
```bash
|
||||
$ docker pull mysql:5.7
|
||||
$ docker pull rdefosseoai/oai-amf:latest
|
||||
$ docker pull rdefosseoai/oai-nrf:latest
|
||||
$ docker pull rdefosseoai/oai-smf:latest
|
||||
$ docker pull rdefosseoai/oai-spgwu-tiny:latest
|
||||
|
||||
$ docker pull rdefosseoai/oai-gnb:develop
|
||||
$ docker pull rdefosseoai/oai-nr-ue:develop
|
||||
```
|
||||
|
||||
And **re-tag** them for tutorials' docker-compose file to work.
|
||||
|
||||
```bash
|
||||
$ docker image tag rdefosseoai/oai-amf:latest oai-amf:latest
|
||||
$ docker image tag rdefosseoai/oai-nrf:latest oai-nrf:latest
|
||||
$ docker image tag rdefosseoai/oai-smf:latest oai-smf:latest
|
||||
$ docker image tag rdefosseoai/oai-spgwu-tiny:latest oai-spgwu-tiny:latest
|
||||
|
||||
$ docker image tag rdefosseoai/oai-gnb:develop oai-gnb:develop
|
||||
$ docker image tag rdefosseoai/oai-nr-ue:develop oai-nr-ue:develop
|
||||
```
|
||||
|
||||
```bash
|
||||
$ docker logout
|
||||
```
|
||||
|
||||
# 2. Deploy containers #
|
||||
|
||||

|
||||
|
||||
**CAUTION: this SHALL be done in multiple steps.**
|
||||
|
||||
**Just `docker-compose up -d` WILL NOT WORK!**
|
||||
|
||||
All the following commands **SHALL** be run from the `ci-scripts/yaml_files/5g_rfsimulator` folder.
|
||||
|
||||
## 2.1. Deploy OAI 5G Core Network ##
|
||||
|
||||
```bash
|
||||
$ cd ci-scripts/yaml_files/5g_rfsimulator
|
||||
$ docker-compose up -d mysql oai-nrf oai-amf oai-smf oai-spgwu oai-ext-dn
|
||||
Creating network "rfsim5g-oai-public-net" with driver "bridge"
|
||||
Creating network "rfsim5g-oai-traffic_net-net" with driver "bridge"
|
||||
Creating rfsim5g-oai-nrf ... done
|
||||
Creating rfsim5g-mysql ... done
|
||||
Creating rfsim5g-oai-spgwu ... done
|
||||
Creating rfsim5g-oai-amf ... done
|
||||
Creating rfsim5g-oai-smf ... done
|
||||
Creating rfsim5g-oai-ext-dn ... done
|
||||
```
|
||||
|
||||
Wait for a bit.
|
||||
|
||||
```bash
|
||||
$ docker-compose ps -a
|
||||
Name Command State Ports
|
||||
-------------------------------------------------------------------------------------------------
|
||||
rfsim5g-mysql docker-entrypoint.sh mysqld Up (healthy) 3306/tcp, 33060/tcp
|
||||
rfsim5g-oai-amf /bin/bash /openair-amf/bin ... Up (healthy) 38412/sctp, 80/tcp, 9090/tcp
|
||||
rfsim5g-oai-ext-dn /bin/bash -c apt update; ... Up (healthy)
|
||||
rfsim5g-oai-nrf /bin/bash /openair-nrf/bin ... Up (healthy) 80/tcp, 9090/tcp
|
||||
rfsim5g-oai-smf /bin/bash -c /openair-smf/ ... Up (healthy) 80/tcp, 8805/udp, 9090/tcp
|
||||
rfsim5g-oai-spgwu /openair-spgwu-tiny/bin/en ... Up (healthy) 2152/udp, 8805/udp
|
||||
```
|
||||
|
||||
At this point, you can prepare a capture on the newly-created public docker bridges:
|
||||
|
||||
```bash
|
||||
$ ifconfig
|
||||
...
|
||||
rfsim5g-public: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
|
||||
inet 192.168.71.129 netmask 255.255.255.192 broadcast 192.168.71.191
|
||||
inet6 fe80::42:c4ff:fe2b:3d38 prefixlen 64 scopeid 0x20<link>
|
||||
ether 02:42:c4:2b:3d:38 txqueuelen 0 (Ethernet)
|
||||
RX packets 4 bytes 112 (112.0 B)
|
||||
RX errors 0 dropped 0 overruns 0 frame 0
|
||||
TX packets 7 bytes 626 (626.0 B)
|
||||
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
|
||||
|
||||
rfsim5g-traffic: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
|
||||
inet 192.168.72.129 netmask 255.255.255.192 broadcast 192.168.72.191
|
||||
inet6 fe80::42:b5ff:fed3:e732 prefixlen 64 scopeid 0x20<link>
|
||||
ether 02:42:b5:d3:e7:32 txqueuelen 0 (Ethernet)
|
||||
RX packets 2652 bytes 142335 (142.3 KB)
|
||||
RX errors 0 dropped 0 overruns 0 frame 0
|
||||
TX packets 3999 bytes 23367972 (23.3 MB)
|
||||
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
|
||||
...
|
||||
```
|
||||
|
||||
## 2.2. Deploy OAI gNB in RF simulator mode and in Standalone Mode ##
|
||||
|
||||
```bash
|
||||
$ docker-compose up -d oai-gnb
|
||||
rfsim5g-oai-nrf is up-to-date
|
||||
rfsim5g-oai-spgwu is up-to-date
|
||||
rfsim5g-oai-ext-dn is up-to-date
|
||||
Creating rfsim5g-oai-gnb ... done
|
||||
```
|
||||
|
||||
Wait for a bit.
|
||||
|
||||
```bash
|
||||
$ docker-compose ps -a
|
||||
Name Command State Ports
|
||||
-------------------------------------------------------------------------------------------------
|
||||
rfsim5g-mysql docker-entrypoint.sh mysqld Up (healthy) 3306/tcp, 33060/tcp
|
||||
rfsim5g-oai-amf /bin/bash /openair-amf/bin ... Up (healthy) 38412/sctp, 80/tcp, 9090/tcp
|
||||
rfsim5g-oai-ext-dn /bin/bash -c apt update; ... Up (healthy)
|
||||
rfsim5g-oai-gnb /opt/oai-gnb/bin/entrypoin ... Up (healthy)
|
||||
rfsim5g-oai-nrf /bin/bash /openair-nrf/bin ... Up (healthy) 80/tcp, 9090/tcp
|
||||
rfsim5g-oai-smf /bin/bash -c /openair-smf/ ... Up (healthy) 80/tcp, 8805/udp, 9090/tcp
|
||||
rfsim5g-oai-spgwu /openair-spgwu-tiny/bin/en ... Up (healthy) 2152/udp, 8805/udp
|
||||
```
|
||||
|
||||
## 2.3. Deploy OAI NR-UE in RF simulator mode and in Standalone Mode ##
|
||||
|
||||
```bash
|
||||
$ docker-compose up -d oai-nr-ue
|
||||
rfsim5g-mysql is up-to-date
|
||||
rfsim5g-oai-nrf is up-to-date
|
||||
rfsim5g-oai-spgwu is up-to-date
|
||||
rfsim5g-oai-ext-dn is up-to-date
|
||||
rfsim5g-oai-gnb is up-to-date
|
||||
Creating rfsim5g-oai-nr-ue ... done
|
||||
```
|
||||
|
||||
Wait for a bit.
|
||||
|
||||
```bash
|
||||
$ docker-compose ps -a
|
||||
Name Command State Ports
|
||||
-------------------------------------------------------------------------------------------------
|
||||
rfsim5g-mysql docker-entrypoint.sh mysqld Up (healthy) 3306/tcp, 33060/tcp
|
||||
rfsim5g-oai-amf /bin/bash /openair-amf/bin ... Up (healthy) 38412/sctp, 80/tcp, 9090/tcp
|
||||
rfsim5g-oai-ext-dn /bin/bash -c apt update; ... Up (healthy)
|
||||
rfsim5g-oai-gnb /opt/oai-gnb/bin/entrypoin ... Up (healthy)
|
||||
rfsim5g-oai-nr-ue /opt/oai-nr-ue/bin/entrypo ... Up (healthy)
|
||||
rfsim5g-oai-nrf /bin/bash /openair-nrf/bin ... Up (healthy) 80/tcp, 9090/tcp
|
||||
rfsim5g-oai-smf /bin/bash -c /openair-smf/ ... Up (healthy) 80/tcp, 8805/udp, 9090/tcp
|
||||
rfsim5g-oai-spgwu /openair-spgwu-tiny/bin/en ... Up (healthy) 2152/udp, 8805/udp
|
||||
```
|
||||
|
||||
Making sure the OAI UE is connected:
|
||||
|
||||
```bash
|
||||
$ docker exec -it rfsim5g-oai-nr-ue /bin/bash
|
||||
root@bb4d400a832d:/opt/oai-nr-ue# ifconfig
|
||||
eth0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
|
||||
inet 192.168.71.137 netmask 255.255.255.192 broadcast 192.168.71.191
|
||||
ether 02:42:c0:a8:47:89 txqueuelen 0 (Ethernet)
|
||||
RX packets 224259 bytes 5821372018 (5.8 GB)
|
||||
RX errors 0 dropped 0 overruns 0 frame 0
|
||||
TX packets 235916 bytes 7848786376 (7.8 GB)
|
||||
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
|
||||
|
||||
lo: flags=73<UP,LOOPBACK,RUNNING> mtu 65536
|
||||
inet 127.0.0.1 netmask 255.0.0.0
|
||||
loop txqueuelen 1000 (Local Loopback)
|
||||
RX packets 0 bytes 0 (0.0 B)
|
||||
RX errors 0 dropped 0 overruns 0 frame 0
|
||||
TX packets 0 bytes 0 (0.0 B)
|
||||
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
|
||||
|
||||
oaitun_ue1: flags=4305<UP,POINTOPOINT,RUNNING,NOARP,MULTICAST> mtu 1500
|
||||
inet 12.1.1.2 netmask 255.255.255.0 destination 12.1.1.2
|
||||
unspec 00-00-00-00-00-00-00-00-00-00-00-00-00-00-00-00 txqueuelen 500 (UNSPEC)
|
||||
RX packets 0 bytes 0 (0.0 B)
|
||||
RX errors 0 dropped 0 overruns 0 frame 0
|
||||
TX packets 0 bytes 0 (0.0 B)
|
||||
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
|
||||
```
|
||||
|
||||
**CAUTION: THESE NEXT FEW COMMANDS ARE A HACK. RAN developers SHALL FIX THIS!**
|
||||
|
||||
```bash
|
||||
$ docker exec -it rfsim5g-oai-nr-ue /bin/bash
|
||||
|
||||
# Check the current routes
|
||||
|
||||
root@bb4d400a832d:/opt/oai-nr-ue# ip route
|
||||
default via 192.168.71.129 dev eth0
|
||||
12.1.1.0/24 dev oaitun_ue1 proto kernel scope link src 12.1.1.2
|
||||
192.168.71.128/26 dev eth0 proto kernel scope link src 192.168.71.137
|
||||
|
||||
# Remove the default and PDN routes
|
||||
|
||||
root@bb4d400a832d:/opt/oai-nr-ue# ip route del default
|
||||
root@bb4d400a832d:/opt/oai-nr-ue# ip route del 12.1.1.0/24
|
||||
|
||||
# Force the default route through oaitun_ue1 tunnel
|
||||
|
||||
root@bb4d400a832d:/opt/oai-nr-ue# ip route add default via 12.1.1.2 dev oaitun_ue1
|
||||
|
||||
# Check the new routes
|
||||
|
||||
root@bb4d400a832d:/opt/oai-nr-ue# ip route
|
||||
default via 12.1.1.2 dev oaitun_ue1
|
||||
192.168.71.128/26 dev eth0 proto kernel scope link src 192.168.71.137
|
||||
```
|
||||
|
||||
# 3. Check traffic #
|
||||
|
||||
## 3.1. Check your Internet connectivity ##
|
||||
|
||||
```bash
|
||||
$ docker exec -it rfsim5g-oai-nr-ue /bin/bash
|
||||
root@bb4d400a832d:/opt/oai-nr-ue# ping -I oaitun_ue1 -c 10 www.lemonde.fr
|
||||
PING s2.shared.global.fastly.net (151.101.122.217) from 12.1.1.2 oaitun_ue1: 56(84) bytes of data.
|
||||
64 bytes from 151.101.122.217 (151.101.122.217): icmp_seq=1 ttl=53 time=64.5 ms
|
||||
64 bytes from 151.101.122.217 (151.101.122.217): icmp_seq=2 ttl=53 time=37.0 ms
|
||||
64 bytes from 151.101.122.217 (151.101.122.217): icmp_seq=3 ttl=53 time=43.2 ms
|
||||
64 bytes from 151.101.122.217 (151.101.122.217): icmp_seq=4 ttl=53 time=43.2 ms
|
||||
64 bytes from 151.101.122.217 (151.101.122.217): icmp_seq=5 ttl=53 time=54.3 ms
|
||||
64 bytes from 151.101.122.217 (151.101.122.217): icmp_seq=6 ttl=53 time=24.0 ms
|
||||
64 bytes from 151.101.122.217 (151.101.122.217): icmp_seq=7 ttl=53 time=32.5 ms
|
||||
64 bytes from 151.101.122.217 (151.101.122.217): icmp_seq=8 ttl=53 time=37.0 ms
|
||||
64 bytes from 151.101.122.217 (151.101.122.217): icmp_seq=9 ttl=53 time=41.2 ms
|
||||
64 bytes from 151.101.122.217 (151.101.122.217): icmp_seq=10 ttl=53 time=50.3 ms
|
||||
|
||||
--- s2.shared.global.fastly.net ping statistics ---
|
||||
10 packets transmitted, 10 received, 0% packet loss, time 9011ms
|
||||
rtt min/avg/max/mdev = 24.035/42.765/64.557/10.904 ms
|
||||
```
|
||||
|
||||
If it does not work, certainly you need to modify the DNS values in the docker-compose.
|
||||
|
||||
But you can also check with the `ext-dn` container (IP address is `192.168.72.135` in docker-compose)
|
||||
|
||||
```bash
|
||||
$ docker exec -it rfsim5g-oai-nr-ue /bin/bash
|
||||
root@bb4d400a832d# ping -I oaitun_ue1 -c 2 192.168.72.135
|
||||
PING 192.168.72.135 (192.168.72.135) from 12.1.1.2 oaitun_ue1: 56(84) bytes of data.
|
||||
64 bytes from 192.168.72.135: icmp_seq=1 ttl=63 time=10.9 ms
|
||||
64 bytes from 192.168.72.135: icmp_seq=2 ttl=63 time=16.5 ms
|
||||
|
||||
--- 192.168.72.135 ping statistics ---
|
||||
2 packets transmitted, 2 received, 0% packet loss, time 1001ms
|
||||
rtt min/avg/max/mdev = 10.939/13.747/16.556/2.810 ms
|
||||
```
|
||||
|
||||
Let now try to check UDP traffic in Downlink.
|
||||
|
||||
You will need 2 terminals: one in the NR-UE container, one in the ext-dn container.
|
||||
|
||||
## 3.2. Start the `iperf` server inside the NR-UE container ##
|
||||
|
||||
```bash
|
||||
$ docker exec -it rfsim5g-oai-nr-ue /bin/bash
|
||||
root@bb4d400a832d:/opt/oai-nr-ue# iperf -B 12.1.1.2 -u -i 1 -s
|
||||
------------------------------------------------------------
|
||||
Server listening on UDP port 5001
|
||||
Binding to local address 12.1.1.2
|
||||
Receiving 1470 byte datagrams
|
||||
UDP buffer size: 208 KByte (default)
|
||||
------------------------------------------------------------
|
||||
```
|
||||
|
||||
## 3.3. Start the `iperf` client inside the ext-dn container ##
|
||||
|
||||
```bash
|
||||
$ docker exec -it rfsim5g-oai-ext-dn /bin/bash
|
||||
root@f239e31a0bd0:/# iperf -c 12.1.1.2 -u -i 1 -t 20 -b 500K
|
||||
------------------------------------------------------------
|
||||
Client connecting to 12.1.1.2, UDP port 5001
|
||||
Sending 1470 byte datagrams, IPG target: 22968.75 us (kalman adjust)
|
||||
UDP buffer size: 208 KByte (default)
|
||||
------------------------------------------------------------
|
||||
[ 3] local 192.168.72.135 port 58800 connected with 12.1.1.2 port 5001
|
||||
[ ID] Interval Transfer Bandwidth
|
||||
[ 3] 0.0- 1.0 sec 64.6 KBytes 529 Kbits/sec
|
||||
[ 3] 1.0- 2.0 sec 63.2 KBytes 517 Kbits/sec
|
||||
[ 3] 2.0- 3.0 sec 61.7 KBytes 506 Kbits/sec
|
||||
[ 3] 3.0- 4.0 sec 63.2 KBytes 517 Kbits/sec
|
||||
[ 3] 4.0- 5.0 sec 61.7 KBytes 506 Kbits/sec
|
||||
[ 3] 5.0- 6.0 sec 63.2 KBytes 517 Kbits/sec
|
||||
[ 3] 6.0- 7.0 sec 61.7 KBytes 506 Kbits/sec
|
||||
[ 3] 7.0- 8.0 sec 63.2 KBytes 517 Kbits/sec
|
||||
[ 3] 8.0- 9.0 sec 61.7 KBytes 506 Kbits/sec
|
||||
[ 3] 9.0-10.0 sec 63.2 KBytes 517 Kbits/sec
|
||||
[ 3] 10.0-11.0 sec 61.7 KBytes 506 Kbits/sec
|
||||
[ 3] 11.0-12.0 sec 63.2 KBytes 517 Kbits/sec
|
||||
[ 3] 12.0-13.0 sec 61.7 KBytes 506 Kbits/sec
|
||||
[ 3] 13.0-14.0 sec 63.2 KBytes 517 Kbits/sec
|
||||
[ 3] 14.0-15.0 sec 63.2 KBytes 517 Kbits/sec
|
||||
[ 3] 15.0-16.0 sec 61.7 KBytes 506 Kbits/sec
|
||||
[ 3] 16.0-17.0 sec 63.2 KBytes 517 Kbits/sec
|
||||
[ 3] 17.0-18.0 sec 61.7 KBytes 506 Kbits/sec
|
||||
[ 3] 18.0-19.0 sec 63.2 KBytes 517 Kbits/sec
|
||||
[ 3] 19.0-20.0 sec 61.7 KBytes 506 Kbits/sec
|
||||
[ 3] 0.0-20.0 sec 1.22 MBytes 512 Kbits/sec
|
||||
[ 3] Sent 872 datagrams
|
||||
[ 3] Server Report:
|
||||
[ 3] 0.0-20.0 sec 1.22 MBytes 510 Kbits/sec 0.000 ms 3/ 872 (0%)
|
||||
```
|
||||
|
||||
Back on your NR-UE terminal you shall see:
|
||||
|
||||
```bash
|
||||
[ 3] local 12.1.1.2 port 5001 connected with 192.168.72.135 port 58800
|
||||
[ ID] Interval Transfer Bandwidth Jitter Lost/Total Datagrams
|
||||
[ 3] 0.0- 1.0 sec 63.2 KBytes 517 Kbits/sec 1.113 ms 0/ 44 (0%)
|
||||
[ 3] 1.0- 2.0 sec 61.7 KBytes 506 Kbits/sec 1.466 ms 0/ 43 (0%)
|
||||
[ 3] 2.0- 3.0 sec 63.2 KBytes 517 Kbits/sec 1.770 ms 0/ 44 (0%)
|
||||
[ 3] 3.0- 4.0 sec 61.7 KBytes 506 Kbits/sec 1.378 ms 0/ 43 (0%)
|
||||
[ 3] 4.0- 5.0 sec 63.2 KBytes 517 Kbits/sec 1.614 ms 0/ 44 (0%)
|
||||
[ 3] 5.0- 6.0 sec 63.2 KBytes 517 Kbits/sec 1.427 ms 0/ 44 (0%)
|
||||
[ 3] 6.0- 7.0 sec 60.3 KBytes 494 Kbits/sec 1.507 ms 1/ 43 (2.3%)
|
||||
[ 3] 7.0- 8.0 sec 63.2 KBytes 517 Kbits/sec 1.409 ms 0/ 44 (0%)
|
||||
[ 3] 8.0- 9.0 sec 61.7 KBytes 506 Kbits/sec 1.525 ms 0/ 43 (0%)
|
||||
[ 3] 9.0-10.0 sec 63.2 KBytes 517 Kbits/sec 1.393 ms 0/ 44 (0%)
|
||||
[ 3] 10.0-11.0 sec 61.7 KBytes 506 Kbits/sec 1.377 ms 0/ 43 (0%)
|
||||
[ 3] 11.0-12.0 sec 63.2 KBytes 517 Kbits/sec 1.501 ms 0/ 44 (0%)
|
||||
[ 3] 12.0-13.0 sec 61.7 KBytes 506 Kbits/sec 1.788 ms 0/ 43 (0%)
|
||||
[ 3] 13.0-14.0 sec 63.2 KBytes 517 Kbits/sec 1.466 ms 0/ 44 (0%)
|
||||
[ 3] 14.0-15.0 sec 61.7 KBytes 506 Kbits/sec 1.381 ms 0/ 43 (0%)
|
||||
[ 3] 15.0-16.0 sec 61.7 KBytes 506 Kbits/sec 1.417 ms 1/ 44 (2.3%)
|
||||
[ 3] 16.0-17.0 sec 61.7 KBytes 506 Kbits/sec 1.569 ms 0/ 43 (0%)
|
||||
[ 3] 17.0-18.0 sec 63.2 KBytes 517 Kbits/sec 1.492 ms 1/ 45 (2.2%)
|
||||
[ 3] 18.0-19.0 sec 61.7 KBytes 506 Kbits/sec 1.376 ms 0/ 43 (0%)
|
||||
[ 3] 19.0-20.0 sec 61.7 KBytes 506 Kbits/sec 1.589 ms 0/ 43 (0%)
|
||||
[ 3] 0.0-20.0 sec 1.22 MBytes 510 Kbits/sec 1.551 ms 3/ 872 (0.34%)
|
||||
```
|
||||
|
||||
The `500 Kbits/sec` value may change depending on your CPU power!
|
||||
|
||||
# 4. Un-deployment #
|
||||
|
||||
```bash
|
||||
$ docker-compose down
|
||||
Stopping rfsim5g-oai-nr-ue ... done
|
||||
Stopping rfsim5g-oai-gnb ... done
|
||||
Stopping rfsim5g-oai-ext-dn ... done
|
||||
Stopping rfsim5g-oai-smf ... done
|
||||
Stopping rfsim5g-oai-amf ... done
|
||||
Stopping rfsim5g-oai-spgwu ... done
|
||||
Stopping rfsim5g-oai-nrf ... done
|
||||
Stopping rfsim5g-mysql ... done
|
||||
Removing rfsim5g-oai-nr-ue ... done
|
||||
Removing rfsim5g-oai-gnb ... done
|
||||
Removing rfsim5g-oai-ext-dn ... done
|
||||
Removing rfsim5g-oai-smf ... done
|
||||
Removing rfsim5g-oai-amf ... done
|
||||
Removing rfsim5g-oai-spgwu ... done
|
||||
Removing rfsim5g-oai-nrf ... done
|
||||
Removing rfsim5g-mysql ... done
|
||||
Removing network rfsim5g-oai-public-net
|
||||
Removing network rfsim5g-oai-traffic_net-net
|
||||
```
|
||||
@@ -206,7 +206,7 @@ services:
|
||||
privileged: true
|
||||
container_name: rfsim5g-oai-ext-dn
|
||||
entrypoint: /bin/bash -c \
|
||||
"apt update; apt install -y iptables iproute2 iperf iputils-ping;"\
|
||||
"apt update; apt install -y procps iptables iproute2 iperf iputils-ping;"\
|
||||
"iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE;"\
|
||||
"ip route add 12.1.1.0/24 via 192.168.72.134 dev eth0; sleep infinity"
|
||||
depends_on:
|
||||
@@ -220,7 +220,7 @@ services:
|
||||
timeout: 5s
|
||||
retries: 5
|
||||
oai-gnb:
|
||||
image: oai-gnb:int-w32
|
||||
image: oai-gnb:develop
|
||||
privileged: true
|
||||
container_name: rfsim5g-oai-gnb
|
||||
environment:
|
||||
@@ -251,7 +251,7 @@ services:
|
||||
timeout: 5s
|
||||
retries: 5
|
||||
oai-nr-ue:
|
||||
image: oai-nr-ue:int-w32
|
||||
image: oai-nr-ue:develop
|
||||
privileged: true
|
||||
container_name: rfsim5g-oai-nr-ue
|
||||
environment:
|
||||
|
||||
Binary file not shown.
|
After Width: | Height: | Size: 55 KiB |
@@ -37,9 +37,7 @@ RUN /bin/sh oaienv && \
|
||||
mkdir -p log && \
|
||||
./build_oai --eNB --ninja -w USRP --verbose-ci
|
||||
|
||||
RUN yum install -y python3-pip && \
|
||||
pip3 install --ignore-installed pyyaml && \
|
||||
python3 ./docker/scripts/generateTemplate.py ./docker/scripts/enb_parameters.yaml
|
||||
RUN python3 ./docker/scripts/generateTemplate.py ./docker/scripts/enb_parameters.yaml
|
||||
|
||||
#start from scratch for target executable
|
||||
FROM registry.access.redhat.com/ubi8/ubi:latest as oai-enb
|
||||
|
||||
@@ -37,9 +37,7 @@ RUN /bin/sh oaienv && \
|
||||
mkdir -p log && \
|
||||
./build_oai --eNB --ninja -w USRP --verbose-ci
|
||||
|
||||
RUN apt-get install -y python3-pip && \
|
||||
pip3 install --ignore-installed pyyaml && \
|
||||
python3 ./docker/scripts/generateTemplate.py ./docker/scripts/enb_parameters.yaml
|
||||
RUN python3 ./docker/scripts/generateTemplate.py ./docker/scripts/enb_parameters.yaml
|
||||
|
||||
#start from scratch for target executable
|
||||
FROM ubuntu:bionic as oai-enb
|
||||
|
||||
@@ -37,9 +37,7 @@ RUN /bin/sh oaienv && \
|
||||
mkdir -p log && \
|
||||
./build_oai --gNB --ninja -w USRP --verbose-ci
|
||||
|
||||
RUN yum install -y python3-pip && \
|
||||
pip3 install --ignore-installed pyyaml && \
|
||||
python3 ./docker/scripts/generateTemplate.py ./docker/scripts/gnb_parameters.yaml
|
||||
RUN python3 ./docker/scripts/generateTemplate.py ./docker/scripts/gnb_parameters.yaml
|
||||
|
||||
#start from scratch for target executable
|
||||
FROM registry.access.redhat.com/ubi8/ubi:latest as oai-gnb
|
||||
|
||||
@@ -37,9 +37,7 @@ RUN /bin/sh oaienv && \
|
||||
mkdir -p log && \
|
||||
./build_oai --gNB --ninja -w USRP --verbose-ci
|
||||
|
||||
RUN apt-get install -y python3-pip && \
|
||||
pip3 install --ignore-installed pyyaml && \
|
||||
python3 ./docker/scripts/generateTemplate.py ./docker/scripts/gnb_parameters.yaml
|
||||
RUN python3 ./docker/scripts/generateTemplate.py ./docker/scripts/gnb_parameters.yaml
|
||||
|
||||
#start from scratch for target executable
|
||||
FROM ubuntu:bionic as oai-gnb
|
||||
|
||||
@@ -37,9 +37,7 @@ RUN /bin/sh oaienv && \
|
||||
mkdir -p log && \
|
||||
./build_oai --RU --ninja -w USRP --verbose-ci
|
||||
|
||||
RUN yum install -y python3-pip && \
|
||||
pip3 install --ignore-installed pyyaml && \
|
||||
python3 ./docker/scripts/generateTemplate.py ./docker/scripts/enb_parameters.yaml
|
||||
RUN python3 ./docker/scripts/generateTemplate.py ./docker/scripts/enb_parameters.yaml
|
||||
|
||||
#start from scratch for target executable
|
||||
FROM registry.access.redhat.com/ubi8/ubi:latest as oai-lte-ru
|
||||
|
||||
@@ -37,9 +37,7 @@ RUN /bin/sh oaienv && \
|
||||
mkdir -p log && \
|
||||
./build_oai --RU --ninja -w USRP --verbose-ci
|
||||
|
||||
RUN apt-get install -y python3-pip && \
|
||||
pip3 install --ignore-installed pyyaml && \
|
||||
python3 ./docker/scripts/generateTemplate.py ./docker/scripts/enb_parameters.yaml
|
||||
RUN python3 ./docker/scripts/generateTemplate.py ./docker/scripts/enb_parameters.yaml
|
||||
|
||||
#start from scratch for target executable
|
||||
FROM ubuntu:bionic as oai-lte-ru
|
||||
|
||||
@@ -45,7 +45,7 @@ RUN rm -f /etc/rhsm-host && \
|
||||
psmisc \
|
||||
git \
|
||||
# python3-pip and pyyaml are used for conf template generation
|
||||
python3-pip
|
||||
python3-pip \
|
||||
#unzip is needed for protobuf
|
||||
unzip && \
|
||||
pip3 install --ignore-installed pyyaml && \
|
||||
|
||||
Reference in New Issue
Block a user