add ci run on sim
Signed-off-by: nietingting <nietingting@xiaomi.com>
This commit is contained in:
parent
8b7d2d3da4
commit
70053700b8
76
boards/sim/sim/sim/configs/citest/defconfig
Normal file
76
boards/sim/sim/sim/configs/citest/defconfig
Normal file
@ -0,0 +1,76 @@
|
||||
#
|
||||
# This file is autogenerated: PLEASE DO NOT EDIT IT.
|
||||
#
|
||||
# You can use "make menuconfig" to make any modifications to the installed .config file.
|
||||
# You can then do "make savedefconfig" to generate a new defconfig file that includes your
|
||||
# modifications.
|
||||
#
|
||||
# CONFIG_NSH_CMDOPT_HEXDUMP is not set
|
||||
CONFIG_ALLSYMS=y
|
||||
CONFIG_ARCH="sim"
|
||||
CONFIG_ARCH_BOARD="sim"
|
||||
CONFIG_ARCH_BOARD_SIM=y
|
||||
CONFIG_ARCH_CHIP="sim"
|
||||
CONFIG_ARCH_SIM=y
|
||||
CONFIG_BOARDCTL_APP_SYMTAB=y
|
||||
CONFIG_BOARDCTL_POWEROFF=y
|
||||
CONFIG_BOARD_LOOPSPERMSEC=0
|
||||
CONFIG_BOOT_RUNFROMEXTSRAM=y
|
||||
CONFIG_BUILTIN=y
|
||||
CONFIG_DEBUG_SYMBOLS=y
|
||||
CONFIG_DEV_GPIO=y
|
||||
CONFIG_DEV_LOOP=y
|
||||
CONFIG_DEV_ZERO=y
|
||||
CONFIG_EXAMPLES_GPIO=y
|
||||
CONFIG_EXAMPLES_HELLO=y
|
||||
CONFIG_FAT_LCNAMES=y
|
||||
CONFIG_FAT_LFN=y
|
||||
CONFIG_FSUTILS_PASSWD=y
|
||||
CONFIG_FSUTILS_PASSWD_READONLY=y
|
||||
CONFIG_FS_BINFS=y
|
||||
CONFIG_FS_FAT=y
|
||||
CONFIG_FS_PROCFS=y
|
||||
CONFIG_FS_RAMMAP=y
|
||||
CONFIG_FS_ROMFS=y
|
||||
CONFIG_GPIO_LOWER_HALF=y
|
||||
CONFIG_HAVE_CXX=y
|
||||
CONFIG_IDLETHREAD_STACKSIZE=4096
|
||||
CONFIG_INIT_ENTRYPOINT="nsh_main"
|
||||
CONFIG_IOEXPANDER=y
|
||||
CONFIG_IOEXPANDER_DUMMY=y
|
||||
CONFIG_LIBCXX=y
|
||||
CONFIG_LIBC_ENVPATH=y
|
||||
CONFIG_LIBC_EXECFUNCS=y
|
||||
CONFIG_LIBC_LOCALE_CATALOG=y
|
||||
CONFIG_LIBC_LOCALE_GETTEXT=y
|
||||
CONFIG_LIBC_MAX_EXITFUNS=1
|
||||
CONFIG_LIBC_NUMBERED_ARGS=y
|
||||
CONFIG_NSH_ARCHINIT=y
|
||||
CONFIG_NSH_ARCHROMFS=y
|
||||
CONFIG_NSH_BUILTIN_APPS=y
|
||||
CONFIG_NSH_FATDEVNO=2
|
||||
CONFIG_NSH_FILE_APPS=y
|
||||
CONFIG_NSH_MOTD=y
|
||||
CONFIG_NSH_MOTD_STRING="MOTD: username=admin password=Administrator"
|
||||
CONFIG_NSH_READLINE=y
|
||||
CONFIG_NSH_ROMFSDEVNO=1
|
||||
CONFIG_NSH_ROMFSETC=y
|
||||
CONFIG_PATH_INITIAL="/bin"
|
||||
CONFIG_POSIX_SPAWN_PROXY_STACKSIZE=2048
|
||||
CONFIG_PSEUDOFS_ATTRIBUTES=y
|
||||
CONFIG_PSEUDOFS_SOFTLINKS=y
|
||||
CONFIG_READLINE_TABCOMPLETION=y
|
||||
CONFIG_SCHED_BACKTRACE=y
|
||||
CONFIG_SCHED_HAVE_PARENT=y
|
||||
CONFIG_SCHED_HPWORK=y
|
||||
CONFIG_SCHED_WAITPID=y
|
||||
CONFIG_START_MONTH=6
|
||||
CONFIG_START_YEAR=2008
|
||||
CONFIG_SYSTEM_DUMPSTACK=y
|
||||
CONFIG_SYSTEM_NSH=y
|
||||
CONFIG_TESTING_CXXTEST=y
|
||||
CONFIG_TESTING_FSTEST=y
|
||||
CONFIG_TESTING_GETPRIME=y
|
||||
CONFIG_TESTING_MM=y
|
||||
CONFIG_TESTING_OSTEST=y
|
||||
CONFIG_TESTING_SCANFTEST=y
|
29
boards/sim/sim/sim/configs/citest/run
Normal file
29
boards/sim/sim/sim/configs/citest/run
Normal file
@ -0,0 +1,29 @@
|
||||
#!/usr/bin/env bash
|
||||
|
||||
set -e
|
||||
set -o xtrace
|
||||
|
||||
WD=$(cd $(dirname $0) && pwd)
|
||||
WORKSPACE=$(cd $WD/../../../../../../.. && pwd -P)
|
||||
nuttx=$WORKSPACE/nuttx
|
||||
logs=${WD}/logs
|
||||
target="sim"
|
||||
BOARD="sim"
|
||||
core="sim"
|
||||
|
||||
echo $WD
|
||||
echo $WORKSPACE
|
||||
|
||||
image=`find ${nuttx} -type f -name 'nuttx'`
|
||||
path=${image%/*}
|
||||
cd ${nuttx}/tools/ci/testrun/script
|
||||
python3 -m pytest -m "common" ./ -B ${BOARD} -P ${path} -L ${logs}/${BOARD}/${core} -R ${target} -C --json=${logs}/${BOARD}/${core}/pytest.json
|
||||
ret="$?"
|
||||
|
||||
#clean
|
||||
find ${nuttx}/tools/ci/testrun -name '__pycache__' |xargs rm -rf
|
||||
find ${nuttx}/tools/ci/testrun -name '.pytest_cache' |xargs rm -rf
|
||||
rm -rf ${logs}
|
||||
|
||||
echo $ret
|
||||
exit $ret
|
@ -1,32 +0,0 @@
|
||||
#
|
||||
# This file is autogenerated: PLEASE DO NOT EDIT IT.
|
||||
#
|
||||
# You can use "make menuconfig" to make any modifications to the installed .config file.
|
||||
# You can then do "make savedefconfig" to generate a new defconfig file that includes your
|
||||
# modifications.
|
||||
#
|
||||
CONFIG_ARCH="sim"
|
||||
CONFIG_ARCH_BOARD="sim"
|
||||
CONFIG_ARCH_BOARD_SIM=y
|
||||
CONFIG_ARCH_CHIP="sim"
|
||||
CONFIG_ARCH_SIM=y
|
||||
CONFIG_BOARDCTL=y
|
||||
CONFIG_BOARDCTL_POWEROFF=y
|
||||
CONFIG_BOARD_LOOPSPERMSEC=100
|
||||
CONFIG_CANCELLATION_POINTS=y
|
||||
CONFIG_DEBUG_SYMBOLS=y
|
||||
CONFIG_FS_NAMED_SEMAPHORES=y
|
||||
CONFIG_IDLETHREAD_STACKSIZE=4096
|
||||
CONFIG_INIT_ENTRYPOINT="ostest_main"
|
||||
CONFIG_PTHREAD_CLEANUP=y
|
||||
CONFIG_PTHREAD_CLEANUP_STACKSIZE=3
|
||||
CONFIG_PTHREAD_MUTEX_TYPES=y
|
||||
CONFIG_RAM_START=0x00000000
|
||||
CONFIG_SCHED_HAVE_PARENT=y
|
||||
CONFIG_SCHED_WAITPID=y
|
||||
CONFIG_START_DAY=27
|
||||
CONFIG_START_MONTH=2
|
||||
CONFIG_START_YEAR=2007
|
||||
CONFIG_TESTING_OSTEST=y
|
||||
CONFIG_TESTING_OSTEST_LOOPS=5
|
||||
CONFIG_TESTING_OSTEST_POWEROFF=y
|
@ -1,3 +0,0 @@
|
||||
#! /bin/sh
|
||||
|
||||
./nuttx
|
@ -5,6 +5,7 @@
|
||||
|
||||
# clang doesn't -fsanitize=kernel-address
|
||||
-Darwin,sim:kasan
|
||||
-Darwin,sim:citest
|
||||
|
||||
# macOS doesn't support ELF loading
|
||||
-Darwin,sim:elf
|
||||
|
43
tools/ci/testrun/README.md
Normal file
43
tools/ci/testrun/README.md
Normal file
@ -0,0 +1,43 @@
|
||||
# Requirements
|
||||
- Python 3.6 or above
|
||||
- pexpect + minicom
|
||||
- pytest
|
||||
```bash
|
||||
sudo apt-get install minicom
|
||||
cd env
|
||||
pip3 install -r requirements.txt
|
||||
```
|
||||
# Pytest Original Parameter useage refer to help
|
||||
# Customized Parameters
|
||||
```bash
|
||||
pytest
|
||||
-D specify device, for example: /dev/ttyUSB0
|
||||
-B specify board, for example: sim,best1600_ep
|
||||
-P specify nuttx path
|
||||
-F specify filesystem, for example: /data
|
||||
-L specify log path
|
||||
-O specify ota version, for example: VELA-2.0
|
||||
-S enable sudo as run sim
|
||||
-C enable pre-checkin run
|
||||
-U specify core: ap, audio, cp, sensor, tee
|
||||
-M serial or minicom
|
||||
-R specify target type: target|sim|qemu|module
|
||||
|
||||
```
|
||||
# Example
|
||||
```bash
|
||||
cd script
|
||||
# testsuite
|
||||
pytest test_[testsuite].py -D /dev/ttyUSBx -B <board> -L <logpath> -F <filesystem folder> -P <nuttx path> -R <target|sim|qemu|module>
|
||||
# mark
|
||||
pytest -m <mark_name> ./ -D /dev/ttyUSBx -B <board> -L <logpath> -F <filesystem folder> -P <nuttx path> -R <target|sim|qemu|module> --json=<logpath>/pytest.json
|
||||
# sim
|
||||
pytest -m sim ./ -B sim -P <nuttx path> -L <logpath> -F <filesystem folder> -P <nuttx path> -R <target|sim|qemu|module> --json=<logpath>/pytest.json
|
||||
# stress test
|
||||
pytest -m miwear ./ -B miwear -P <nuttx path> -L <logpath> -F <filesystem path> --json=<logpath>/pytest.json --count=100 --repeat-scope=session
|
||||
```
|
||||
# Generate Report
|
||||
```bash
|
||||
cd utils/report
|
||||
python3 report_gen.py -l <json log path> -b <branch>
|
||||
```
|
6
tools/ci/testrun/env/requirements.txt
vendored
Normal file
6
tools/ci/testrun/env/requirements.txt
vendored
Normal file
@ -0,0 +1,6 @@
|
||||
pexpect==4.8.0
|
||||
pytest==6.2.5
|
||||
pytest-repeat==0.9.1
|
||||
pytest-json==0.4.0
|
||||
pytest-ordering==0.6
|
||||
pyserial==3.5
|
17
tools/ci/testrun/pytest.ini
Normal file
17
tools/ci/testrun/pytest.ini
Normal file
@ -0,0 +1,17 @@
|
||||
# pytest.ini
|
||||
[pytest]
|
||||
# -p : Disable warning capture -p no:warnings
|
||||
# -s : Capture print of the script
|
||||
# -v : --verbose
|
||||
# --html=../report/reports.html --self-contained-html
|
||||
# --alluredir=../report/allure
|
||||
# --count=5 --repeat-scope=session
|
||||
# --capture=sys
|
||||
# --json=pytest_ota_m33.json
|
||||
addopts = -sv --capture=sys
|
||||
|
||||
markers =
|
||||
common : 'marks tests as common'
|
||||
sim : 'marks tests as simulator'
|
||||
qemu : 'marks tests as qemu'
|
||||
disable_autouse : 'disable autouse'
|
2
tools/ci/testrun/script/__init__.py
Normal file
2
tools/ci/testrun/script/__init__.py
Normal file
@ -0,0 +1,2 @@
|
||||
#!/usr/bin/python3
|
||||
# encoding: utf-8
|
135
tools/ci/testrun/script/conftest.py
Normal file
135
tools/ci/testrun/script/conftest.py
Normal file
@ -0,0 +1,135 @@
|
||||
#!/usr/bin/python3
|
||||
# encoding: utf-8
|
||||
|
||||
import pytest
|
||||
from utils.common import connectNuttx
|
||||
|
||||
|
||||
def pytest_addoption(parser):
|
||||
parser.addoption(
|
||||
"-D",
|
||||
action="store",
|
||||
default=None,
|
||||
help="specify device, for example: /dev/ttyUSB0",
|
||||
)
|
||||
parser.addoption(
|
||||
"-B", action="store", default="sim", help="specify board, for example: sim"
|
||||
)
|
||||
parser.addoption(
|
||||
"-P",
|
||||
action="store",
|
||||
default=None,
|
||||
help="specify vela path, for example: /home/root/vela",
|
||||
)
|
||||
parser.addoption(
|
||||
"-F",
|
||||
action="store",
|
||||
default="/data",
|
||||
help="specify filesystem, for example: /data or /tmp",
|
||||
)
|
||||
parser.addoption(
|
||||
"-L",
|
||||
action="store",
|
||||
default=None,
|
||||
help="specify log path, for example: /home/root/vela/logs",
|
||||
)
|
||||
parser.addoption("-O", action="store", default=None, help="specify ota version")
|
||||
parser.addoption(
|
||||
"-S", action="store_true", default=False, help="enable sudo as run sim"
|
||||
)
|
||||
parser.addoption(
|
||||
"-C", action="store_true", default=False, help="enable pre-checkin run"
|
||||
)
|
||||
parser.addoption(
|
||||
"-U",
|
||||
action="store",
|
||||
default=None,
|
||||
help="specify core: ap, audio, cp, sensor, tee",
|
||||
)
|
||||
parser.addoption(
|
||||
"-M",
|
||||
action="store",
|
||||
default="minicom",
|
||||
help="serial open method:serial or minicom",
|
||||
)
|
||||
parser.addoption(
|
||||
"-R",
|
||||
action="store",
|
||||
default="sim",
|
||||
help="specify the target type: target|qemu|sim|module, default is sim",
|
||||
)
|
||||
|
||||
|
||||
@pytest.fixture(scope="session")
|
||||
def get_option(pytestconfig):
|
||||
dev = pytestconfig.getoption("-D")
|
||||
board = pytestconfig.getoption("-B")
|
||||
vela_path = pytestconfig.getoption("-P")
|
||||
fs = pytestconfig.getoption("-F")
|
||||
log_path = pytestconfig.getoption("-L")
|
||||
ota_version = pytestconfig.getoption("-O")
|
||||
sudo = pytestconfig.getoption("-S")
|
||||
ci = pytestconfig.getoption("-C")
|
||||
core = pytestconfig.getoption("-U")
|
||||
method = pytestconfig.getoption("-M")
|
||||
target = pytestconfig.getoption("-R")
|
||||
yield dev, board, vela_path, fs, log_path, ota_version, core, sudo, ci, method, target
|
||||
|
||||
|
||||
@pytest.fixture(scope="session", name="p")
|
||||
def connect_nuttx_session(get_option):
|
||||
(
|
||||
dev,
|
||||
board,
|
||||
vela_path,
|
||||
fs,
|
||||
log_path,
|
||||
ota_version,
|
||||
core,
|
||||
sudo,
|
||||
ci,
|
||||
method,
|
||||
target,
|
||||
) = get_option
|
||||
print(get_option)
|
||||
p = connectNuttx(
|
||||
board, vela_path, dev, log_path, fs, ota_version, core, sudo, ci, method, target
|
||||
)
|
||||
p.setup()
|
||||
yield p
|
||||
p.cleanup()
|
||||
|
||||
|
||||
@pytest.fixture(scope="function", autouse=True)
|
||||
def do_free_ps(request, p):
|
||||
if "disable_autouse" in request.keywords:
|
||||
yield
|
||||
else:
|
||||
yield
|
||||
p.sendCommand("free", "total", flag=">")
|
||||
p.sendCommand("ps", "PID", flag=">")
|
||||
p.sendCommand("ls %s" % p.fs, flag=">")
|
||||
|
||||
|
||||
@pytest.fixture(scope="function", name="pp")
|
||||
def connect_nuttx_function(get_option):
|
||||
(
|
||||
dev,
|
||||
board,
|
||||
vela_path,
|
||||
fs,
|
||||
log_path,
|
||||
ota_version,
|
||||
core,
|
||||
sudo,
|
||||
ci,
|
||||
method,
|
||||
target,
|
||||
) = get_option
|
||||
print(get_option)
|
||||
p = connectNuttx(
|
||||
board, vela_path, dev, log_path, fs, ota_version, core, sudo, ci, method, target
|
||||
)
|
||||
p.setup()
|
||||
yield p
|
||||
# p.cleanup()
|
2
tools/ci/testrun/script/test_os/__init__.py
Normal file
2
tools/ci/testrun/script/test_os/__init__.py
Normal file
@ -0,0 +1,2 @@
|
||||
#!/usr/bin/python3
|
||||
# encoding: utf-8
|
61
tools/ci/testrun/script/test_os/test_os.py
Normal file
61
tools/ci/testrun/script/test_os/test_os.py
Normal file
@ -0,0 +1,61 @@
|
||||
#!/usr/bin/python3
|
||||
# encoding: utf-8
|
||||
import pytest
|
||||
|
||||
pytestmark = [pytest.mark.common, pytest.mark.qemu]
|
||||
do_not_support = ["sabre-6quad", "rv-virt", "rv-virt64", "esp32c3-devkit", "bl602evb"]
|
||||
|
||||
|
||||
def test_ostest(p):
|
||||
ret = p.sendCommand("ostest", "Exiting with status", 300)
|
||||
assert ret == 0
|
||||
|
||||
|
||||
def test_mm(p):
|
||||
if p.board in do_not_support:
|
||||
pytest.skip("unsupported at {}".format(p.board))
|
||||
ret = p.sendCommand("mm", "TEST COMPLETE", 120)
|
||||
assert ret == 0
|
||||
|
||||
|
||||
def test_cxxtest(p):
|
||||
if p.board in do_not_support:
|
||||
pytest.skip("unsupported at {}".format(p.board))
|
||||
ret = p.sendCommand("cxxtest", "Test std::map")
|
||||
assert ret == 0
|
||||
|
||||
|
||||
def test_scanftest(p):
|
||||
if p.board in do_not_support:
|
||||
pytest.skip("unsupported at {}".format(p.board))
|
||||
ret = p.sendCommand("scanftest", "Test #25")
|
||||
assert ret == 0
|
||||
|
||||
|
||||
def test_getprime(p):
|
||||
if p.board in ["rv-virt", "rv-virt64"]:
|
||||
pytest.skip("unsupported at {}".format(p.board))
|
||||
ret = p.sendCommand("getprime", "getprime took")
|
||||
assert ret == 0
|
||||
|
||||
|
||||
@pytest.mark.second_to_last
|
||||
def test_fs_test(p):
|
||||
if p.board in do_not_support:
|
||||
pytest.skip("unsupported at {}".format(p.board))
|
||||
fstest_dir = "{}/{}_fstest".format(p.fs, p.core)
|
||||
p.sendCommand("mkdir %s" % fstest_dir)
|
||||
ret = p.sendCommand("fstest -n 10 -m %s" % fstest_dir, "Final memory usage", 2000)
|
||||
p.sendCommand("ls %s" % fstest_dir)
|
||||
p.sendCommand("rmdir %s" % fstest_dir)
|
||||
assert ret == 0
|
||||
|
||||
|
||||
@pytest.mark.last
|
||||
def test_psram_test(p):
|
||||
if p.board in do_not_support:
|
||||
pytest.skip("unsupported at {}".format(p.board))
|
||||
if p.sendCommand("ls /", "tmp/") == 0:
|
||||
ret = p.sendCommand("fstest -n 10 -m /tmp", "Final memory usage", 500)
|
||||
p.sendCommand("ls /tmp")
|
||||
assert ret == 0
|
2
tools/ci/testrun/utils/__init__.py
Normal file
2
tools/ci/testrun/utils/__init__.py
Normal file
@ -0,0 +1,2 @@
|
||||
#!/usr/bin/python3
|
||||
# encoding: utf-8
|
336
tools/ci/testrun/utils/common.py
Normal file
336
tools/ci/testrun/utils/common.py
Normal file
@ -0,0 +1,336 @@
|
||||
#!/usr/bin/python3
|
||||
|
||||
import os
|
||||
import re
|
||||
import subprocess
|
||||
import time
|
||||
|
||||
import pexpect
|
||||
import pexpect.fdpexpect
|
||||
import serial
|
||||
|
||||
rootPath = os.path.dirname(os.path.abspath(__file__))
|
||||
|
||||
|
||||
class connectNuttx(object):
|
||||
def __init__(
|
||||
self,
|
||||
board,
|
||||
vela_path,
|
||||
dev,
|
||||
log_path,
|
||||
fs,
|
||||
ota_version,
|
||||
core,
|
||||
sudo,
|
||||
ci,
|
||||
method,
|
||||
target,
|
||||
):
|
||||
self.board = board
|
||||
self.path = vela_path
|
||||
self.dev = dev
|
||||
self.log_path = log_path
|
||||
self.fs = fs
|
||||
self.version = ota_version
|
||||
self.sudo = sudo
|
||||
self.ci = ci
|
||||
self.core = core
|
||||
self.method = method
|
||||
self.target = target
|
||||
self.enter = "\r"
|
||||
self.debug_flag = 0
|
||||
# get PROMPT value and rate value
|
||||
self.PROMPT = getConfigValue(
|
||||
self.path, self.board, core=self.core, flag="NSH_PROMPT_STRING"
|
||||
)
|
||||
self.rate = getConfigValue(
|
||||
self.path, self.board, core=self.core, flag="UART0_BAUD"
|
||||
)
|
||||
|
||||
if not os.path.exists(self.log_path):
|
||||
os.makedirs(self.log_path)
|
||||
|
||||
def setup(self):
|
||||
self.start_time = time.strftime("%Y%m%d_%H%M%S", time.localtime())
|
||||
print("============ start at %s ============" % self.start_time)
|
||||
if self.target == "sim":
|
||||
# start nuttx for sim
|
||||
start.startNuttx(self, self.path, self.log_path, self.board, self.sudo)
|
||||
if self.target == "qemu":
|
||||
start.startQemu(self, self.path, self.log_path, self.board, self.sudo)
|
||||
if self.target in ["target", "module"]:
|
||||
# start minicom
|
||||
if self.method == "minicom":
|
||||
start.startMinicom(
|
||||
self, self.dev, self.board, self.log_path, self.core, self.rate
|
||||
)
|
||||
else:
|
||||
start.startSerial(
|
||||
self, self.dev, self.board, self.log_path, self.core, self.rate
|
||||
)
|
||||
|
||||
def sendcontrol(self, char):
|
||||
char = char.lower()
|
||||
a = ord(char)
|
||||
if 97 <= a <= 122:
|
||||
a = a - ord("a") + 1
|
||||
byte = bytes([a])
|
||||
return byte
|
||||
d = {
|
||||
"@": 0,
|
||||
"`": 0,
|
||||
"[": 27,
|
||||
"{": 27,
|
||||
"\\": 28,
|
||||
"|": 28,
|
||||
"]": 29,
|
||||
"}": 29,
|
||||
"^": 30,
|
||||
"~": 30,
|
||||
"_": 31,
|
||||
"?": 127,
|
||||
}
|
||||
if char not in d:
|
||||
return b""
|
||||
byte = bytes(d[char])
|
||||
return byte
|
||||
|
||||
def sendControlCmd(self, cmd, expect="ap>", timeout=10):
|
||||
if self.method == "minicom":
|
||||
self.process.sendcontrol(cmd)
|
||||
time.sleep(1)
|
||||
self.process.sendcontrol(cmd)
|
||||
else:
|
||||
byte = self.sendcontrol(cmd)
|
||||
time.sleep(1)
|
||||
self.process.send(byte)
|
||||
time.sleep(1)
|
||||
self.process.send(byte)
|
||||
time.sleep(1)
|
||||
self.process.sendline("\n")
|
||||
ret = self.process.expect_exact(expect)
|
||||
return ret
|
||||
|
||||
# send command to nsh
|
||||
def sendCommand(self, cmd, expect="", timeout=10, flag=""):
|
||||
if self.method != "minicom":
|
||||
time.sleep(0.5)
|
||||
if not expect:
|
||||
expect = self.PROMPT
|
||||
self.process.buffer = b""
|
||||
self.process.sendline(cmd)
|
||||
try:
|
||||
ret = self.process.expect(expect, timeout=timeout)
|
||||
except pexpect.TIMEOUT:
|
||||
print("Debug: TIMEOUT '%s' exist and run next test case" % cmd)
|
||||
ret = -1
|
||||
except pexpect.EOF:
|
||||
print("Debug: EOF raise exception")
|
||||
ret = -2
|
||||
finally:
|
||||
if self.debug_flag:
|
||||
self.debug(cmd, ret)
|
||||
self.process.buffer = b""
|
||||
self.process.sendline("\n")
|
||||
if flag:
|
||||
is_newline = self.process.expect_exact(flag, timeout=timeout)
|
||||
else:
|
||||
is_newline = self.process.expect_exact(self.PROMPT, timeout=timeout)
|
||||
if self.debug_flag:
|
||||
self.debug("NEWLINE", is_newline)
|
||||
if self.method != "minicom":
|
||||
time.sleep(0.5)
|
||||
return ret
|
||||
|
||||
def switch_to_original_core(self):
|
||||
if self.target == "target":
|
||||
self.sendControlCmd("c")
|
||||
if self.core != "ap":
|
||||
self.process.sendline("cu -l /dev/tty%s\n" % self.core.upper())
|
||||
self.process.expect_exact(self.PROMPT)
|
||||
|
||||
def debug(self, cmd, ret):
|
||||
print("********************* DEBUG START ********************")
|
||||
if cmd == "\n":
|
||||
cmd = r"\n"
|
||||
print("cmd: %s\n" % cmd)
|
||||
print("ret: %s\n" % str(ret))
|
||||
print("before: %s\n" % repr(self.process.before))
|
||||
print("after: %s\n" % repr(self.process.after))
|
||||
print("buffer: %s\n" % repr(self.process.buffer))
|
||||
print("********************** DEBUG END **********************")
|
||||
|
||||
def cleanup(self):
|
||||
if self.target == "sim":
|
||||
self.process.sendline("poweroff")
|
||||
if self.target == "qemu":
|
||||
self.sendControlCmd("a", self.PROMPT)
|
||||
self.process.sendline("x")
|
||||
|
||||
|
||||
class start:
|
||||
def startMinicom(self, dev, board, log_path, core, rate):
|
||||
self.log = "{}/{}_{}.cap".format(log_path, dev[-4:], self.start_time)
|
||||
self.process = pexpect.spawn(
|
||||
r"sudo minicom -D {} -b {} -o -C {}".format(dev, rate, self.log),
|
||||
maxread=200000,
|
||||
)
|
||||
self.process.expect("Welcome to minicom")
|
||||
self.switch_to_original_core()
|
||||
|
||||
def startSerial(self, dev, board, log_path, core, rate):
|
||||
self.log = "{}/{}_{}.cap".format(log_path, dev[-4:], self.start_time)
|
||||
self.logFile = open(self.log, "ab+")
|
||||
self.ser = serial.Serial(port=dev, baudrate=int(rate))
|
||||
self.process = pexpect.fdpexpect.fdspawn(
|
||||
self.ser, "wb", maxread=20000, logfile=self.logFile
|
||||
)
|
||||
self.switch_to_original_core()
|
||||
|
||||
def startNuttx(self, path, log_path, board="sim", sudo=False):
|
||||
os.chdir(path)
|
||||
self.log = "{}/{}_{}.log".format(log_path, board, self.start_time)
|
||||
if sudo:
|
||||
if board in ["sim_rpserver", "sim_rpproxy"]:
|
||||
os.chdir(path)
|
||||
self.process = pexpect.spawn(
|
||||
"bash", ["-c", "sudo ./rpserver/nuttx/nuttx | tee %s" % self.log]
|
||||
)
|
||||
else:
|
||||
self.process = pexpect.spawn(
|
||||
"bash", ["-c", "sudo ./nuttx | tee %s" % self.log]
|
||||
)
|
||||
else:
|
||||
self.process = pexpect.spawn("bash", ["-c", "./nuttx | tee %s" % self.log])
|
||||
self.process.expect(self.PROMPT)
|
||||
|
||||
def startQemu(self, path, log_path, board="qemu", sudo=False):
|
||||
os.chdir(path)
|
||||
self.log = "{}/{}_{}.log".format(log_path, board, self.start_time)
|
||||
flag1 = getConfigValue(path, board, core=None, flag="ARCH_CHIP")
|
||||
if flag1 == "imx6":
|
||||
self.process = pexpect.spawn(
|
||||
"bash",
|
||||
[
|
||||
"-c",
|
||||
"qemu-system-arm -M sabrelite -smp 1 -bios none -kernel ./nuttx -nographic | tee %s"
|
||||
% self.log,
|
||||
],
|
||||
)
|
||||
if flag1 == "qemu-rv":
|
||||
flag2 = getConfigValue(path, board, core=None, flag="ARCH_RV64")
|
||||
if flag2:
|
||||
riscv = "qemu-system-riscv64"
|
||||
else:
|
||||
riscv = "qemu-system-riscv32"
|
||||
self.process = pexpect.spawn(
|
||||
"bash",
|
||||
[
|
||||
"-c",
|
||||
"%s -M virt -bios ./nuttx -nographic | tee %s" % (riscv, self.log),
|
||||
],
|
||||
)
|
||||
self.process.expect(self.PROMPT)
|
||||
|
||||
|
||||
def runCmd(cmd):
|
||||
p = subprocess.Popen(
|
||||
cmd,
|
||||
shell=True,
|
||||
stdin=subprocess.PIPE,
|
||||
stdout=subprocess.PIPE,
|
||||
stderr=subprocess.PIPE,
|
||||
)
|
||||
|
||||
stdout, stderr = p.communicate()
|
||||
recode = p.returncode
|
||||
|
||||
if recode != 0:
|
||||
print("Debug: run command '%s' failed" % cmd)
|
||||
|
||||
return stdout
|
||||
|
||||
|
||||
# find file
|
||||
def findFile(path, flag, board, core=None, match=True):
|
||||
fList = []
|
||||
for root, dirs, files in os.walk(path):
|
||||
for name in files:
|
||||
if not match and flag in name:
|
||||
fList.append(os.path.join(root, name))
|
||||
if match and name == flag and ".o" not in name:
|
||||
fList.append(os.path.join(root, name))
|
||||
if len(fList) != 1:
|
||||
fList = [x for x in fList if board in x and core + "/" in x]
|
||||
print(fList)
|
||||
return fList
|
||||
|
||||
|
||||
# get CONFIG_NSH_PROMPT_STRING value
|
||||
def getConfigValue(path, board, core, flag):
|
||||
value = ""
|
||||
l1 = findFile(path, ".config", board, core=core)
|
||||
with open(l1[0], "r+") as f:
|
||||
lines = f.readlines()
|
||||
f.close()
|
||||
print(lines)
|
||||
print(flag)
|
||||
for line in lines:
|
||||
if flag + "=" in line:
|
||||
value = line.split("=")[1]
|
||||
if '"' in value:
|
||||
value = value.strip('"').strip()
|
||||
print(value)
|
||||
return value
|
||||
|
||||
|
||||
# read log and extract timestamp
|
||||
def getTimestamp(filename, str1, str2, pattern):
|
||||
with open(filename, "r") as f:
|
||||
buff = f.read()
|
||||
pat = re.compile(str1 + "(.*?)" + str2, re.S)
|
||||
result = pat.findall(buff)
|
||||
timestamp = re.findall(pattern, str(result)) # extract timestamp
|
||||
return timestamp
|
||||
|
||||
|
||||
# calculate the time difference for each time
|
||||
def getDif(timestamp, rateANDinterance):
|
||||
lst = []
|
||||
for i in range(1, len(timestamp)):
|
||||
difts = int(timestamp[i]) - int(timestamp[i - 1])
|
||||
float_num = (difts / 1000000) - rateANDinterance
|
||||
lst.append(float_num)
|
||||
return lst
|
||||
|
||||
|
||||
# read log
|
||||
def getLog(filename, str1, str2):
|
||||
l1 = []
|
||||
with open(filename, "r", encoding="utf-8", errors="ignore") as f:
|
||||
buff = f.read()
|
||||
f.close()
|
||||
pat = re.compile(str1 + "(.*?)" + str2, re.S)
|
||||
result = pat.findall(buff)
|
||||
|
||||
if "gtest" in str1:
|
||||
return result[0].strip("\n")
|
||||
else:
|
||||
# add line to l1
|
||||
for i in result[0].strip("\n").split("\n"):
|
||||
l1.append(i)
|
||||
return l1
|
||||
|
||||
|
||||
def rmfile(p, core, file):
|
||||
if p.core == core:
|
||||
p.sendCommand("rm -r" + file)
|
||||
else:
|
||||
p.process.sendline("cu -l /dev/tty" + core.upper())
|
||||
p.sendCommand("\n", core, flag=core + ">")
|
||||
p.sendCommand("rm -r " + file, core, flag=core + ">")
|
||||
if p.core == "ap":
|
||||
p.sendControlCmd("c")
|
||||
else:
|
||||
p.switch_to_original_core(p)
|
Loading…
Reference in New Issue
Block a user