osmith submitted this change.

View Change

Approvals: daniel: Looks good to me, but someone else must approve Jenkins Builder: Verified fixeria: Looks good to me, approved
testenv: coredump: support core_pattern=core

Support getting core files from a typical core_pattern=core where the
coredump just gets stored in the current working dir, instead of always
retrieving it from coredumpctl. This is what we will use with jenkins in
the future, as it makes getting core files in other jobs easier. Remove
support for the custom testenv-coredump-helper code that isn't needed
anymore.

Change-Id: Ia765b01432e4cb4cd36c45de874b966e3ebf55bc
---
M _testenv/README.md
M _testenv/testenv/coredump.py
M _testenv/testenv/daemons.py
M _testenv/testenv/requirements.py
4 files changed, 46 insertions(+), 65 deletions(-)

diff --git a/_testenv/README.md b/_testenv/README.md
index 072dcd2..b62295e 100644
--- a/_testenv/README.md
+++ b/_testenv/README.md
@@ -202,15 +202,6 @@
available but doesn't work in podman. QEMU runs a bit slower when this is
set.

-* `TESTENV_COREDUMP_FROM_LXC_HOST`:
- Instead of using coredumpctl to retrieve the coredump, assume testenv is
- running inside an LXC and try to retrieve the coredump from the LXC host
- (OS#6769). This is used in jenkins.
-
-* `TESTENV_COREDUMP_FROM_LXC_HOST_IP`:
- Instead of attempting to automatically detect the LXC host IP, use this IP.
- This can be set to 127.0.0.1 for testing.
-
### Environment variables set by testenv

Testenv sets the following variables while running shell commands from
diff --git a/_testenv/testenv/coredump.py b/_testenv/testenv/coredump.py
index 0343c67..d3fa35f 100644
--- a/_testenv/testenv/coredump.py
+++ b/_testenv/testenv/coredump.py
@@ -2,63 +2,20 @@
# SPDX-License-Identifier: GPL-3.0-or-later
import datetime
import fnmatch
+import glob
import json
import logging
-import os
+import re
import shlex
import shutil
import subprocess
import testenv
import testenv.daemons
import testenv.testdir
-import urllib
-import urllib.request

+core_path = None
executable_path = None

-lxc_netdev = "eth0"
-lxc_ip_pattern = "10.0.*"
-lxc_port = 8042
-
-
-def find_lxc_host_ip():
- cmd = ["ip", "-j", "-o", "-4", "addr", "show", "dev", lxc_netdev]
- p = testenv.cmd.run(cmd, check=False, no_podman=True, capture_output=True, text=True)
- ret = json.loads(p.stdout)[0]["addr_info"][0]["local"]
- if fnmatch.fnmatch(ret, lxc_ip_pattern):
- ret = ret.split(".")
- ret = f"{ret[0]}.{ret[1]}.{ret[2]}.1"
- return ret
- return None
-
-
-def get_from_coredumpctl_lxc_host():
- # Server implementation: osmo-ci, ansible/roles/testenv-coredump-helper
- global executable_path
-
- logging.info("Looking for a coredump on lxc host")
-
- ip = os.environ.get("TESTENV_COREDUMP_FROM_LXC_HOST_IP") or find_lxc_host_ip()
- if not ip:
- logging.warning("Failed to get lxc host ip, can't look for coredump")
- return
-
- try:
- with urllib.request.urlopen(f"http://{ip}:{lxc_port}/core") as response:
- executable_path = dict(response.getheaders())["X-Executable-Path"]
- with open(f"{testenv.testdir.testdir}/core", "wb") as h:
- shutil.copyfileobj(response, h)
- logging.debug("Coredump found and copied to log dir")
- except urllib.error.HTTPError as e:
- executable_path = None
- if e.code == 404:
- logging.debug("No coredump found")
- else:
- logging.error(f"Unexpected error while attempting to fetch the coredump: {e}")
- except urllib.error.URLError as e:
- executable_path = None
- logging.error(f"Unexpected error while attempting to fetch the coredump: {e}")
-

def executable_is_relevant(exe):
if testenv.args.binary_repo:
@@ -77,10 +34,11 @@
return False


-def get_from_coredumpctl_local():
+def get_from_coredumpctl():
+ global core_path
global executable_path

- logging.info("Looking for a coredump")
+ logging.info("Looking for a coredump with coredumpctl")

if not shutil.which("coredumpctl"):
logging.debug("coredumpctl is not available, won't try to get coredump")
@@ -113,18 +71,49 @@
executable_path = coredump["exe"]


-def get_from_coredumpctl():
- if os.environ.get("TESTENV_COREDUMP_FROM_LXC_HOST"):
- get_from_coredumpctl_lxc_host()
+def get_from_file():
+ global core_path
+ global executable_path
+
+ logging.info("Looking for a coredump file")
+
+ glob_matches = glob.glob(f"{testenv.testdir.testdir}/*/core*")
+ if not glob_matches:
+ return
+
+ core_path = glob_matches[0]
+ p = testenv.cmd.run(
+ ["file", core_path],
+ no_podman=True,
+ capture_output=True,
+ text=True,
+ )
+ print(p.stdout, end="")
+
+ execfn_match = re.search(r"execfn: '(.*?)'", p.stdout)
+ if execfn_match:
+ executable_path = execfn_match.group(1)
+ logging.debug("Coredump file and execfn found")
else:
- get_from_coredumpctl_local()
+ logging.debug("Failed to get execfn path from coredump file")
+
+
+def get_coredump():
+ with open("/proc/sys/kernel/core_pattern") as f:
+ pattern = f.readline().rstrip()
+
+ if "systemd-coredump" in pattern:
+ get_from_coredumpctl()
+ elif pattern.startswith("core"):
+ get_from_file()
+ else:
+ logging.debug(f"Unsupported core_pattern, won't try to get coredump: {pattern}")


def get_backtrace():
global executable_path

- core_path = f"{testenv.testdir.testdir}/core"
- if not executable_path or not os.path.exists(core_path):
+ if not executable_path or not core_path:
return

logging.info("Running gdb to get a backtrace")
diff --git a/_testenv/testenv/daemons.py b/_testenv/testenv/daemons.py
index 3a38850..f57b4b4 100644
--- a/_testenv/testenv/daemons.py
+++ b/_testenv/testenv/daemons.py
@@ -68,7 +68,7 @@
# Wait 200ms and check if it is still running
time.sleep(0.2)
if daemons[section].poll() is not None:
- testenv.coredump.get_from_coredumpctl()
+ testenv.coredump.get_coredump()
raise testenv.NoTraceException(f"program failed to start: {program}")

# Run setup script
@@ -118,7 +118,7 @@
return

current_test = testenv.testsuite.get_current_test()
- testenv.coredump.get_from_coredumpctl()
+ testenv.coredump.get_coredump()

if current_test:
logging.error(f"{daemon_name} unexpected exit during {current_test}! rc={returncode}")
diff --git a/_testenv/testenv/requirements.py b/_testenv/testenv/requirements.py
index 97fae0c..2e53081 100644
--- a/_testenv/testenv/requirements.py
+++ b/_testenv/testenv/requirements.py
@@ -11,6 +11,7 @@

def check_programs():
programs = [
+ "file",
"git",
]


To view, visit change 41152. To unsubscribe, or for help writing mail filters, visit settings.

Gerrit-MessageType: merged
Gerrit-Project: osmo-ttcn3-hacks
Gerrit-Branch: master
Gerrit-Change-Id: Ia765b01432e4cb4cd36c45de874b966e3ebf55bc
Gerrit-Change-Number: 41152
Gerrit-PatchSet: 2
Gerrit-Owner: osmith <osmith@sysmocom.de>
Gerrit-Reviewer: Jenkins Builder
Gerrit-Reviewer: daniel <dwillmann@sysmocom.de>
Gerrit-Reviewer: fixeria <vyanitskiy@sysmocom.de>
Gerrit-Reviewer: osmith <osmith@sysmocom.de>