Skip to content

Commit 0170c4c

Browse files
committed
posix: signal: implement strsignal
Implementation and ztest for strsignal. Signed-off-by: Yong Cong Sin <[email protected]>
1 parent 078d9f7 commit 0170c4c

File tree

9 files changed

+175
-2
lines changed

9 files changed

+175
-2
lines changed

doc/services/portability/posix.rst

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -385,7 +385,8 @@ required for error and event handling.
385385
sigpending(),
386386
sigprocmask(),
387387
igsuspend(),
388-
sigwait()
388+
sigwait(),
389+
strsignal(),yes
389390

390391
.. csv-table:: POSIX_SPIN_LOCKS
391392
:header: API, Supported

include/zephyr/posix/signal.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,7 @@ typedef struct {
5555
unsigned long sig[DIV_ROUND_UP(_NSIG, BITS_PER_LONG)];
5656
} sigset_t;
5757

58+
char *strsignal(int signum);
5859
int sigemptyset(sigset_t *set);
5960
int sigfillset(sigset_t *set);
6061
int sigaddset(sigset_t *set, int signo);

lib/posix/CMakeLists.txt

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
# SPDX-License-Identifier: Apache-2.0
22

3+
set(GEN_DIR ${ZEPHYR_BINARY_DIR}/include/generated)
4+
35
zephyr_syscall_header(
46
${ZEPHYR_BASE}/include/zephyr/posix/time.h
57
)
@@ -10,6 +12,20 @@ if(CONFIG_POSIX_API)
1012
zephyr_include_directories(${ZEPHYR_BASE}/include/zephyr/posix)
1113
endif()
1214

15+
if(CONFIG_POSIX_SIGNAL)
16+
set(STRSIGNAL_TABLE_H ${GEN_DIR}/posix/strsignal_table.h)
17+
18+
add_custom_command(
19+
OUTPUT ${STRSIGNAL_TABLE_H}
20+
COMMAND
21+
${PYTHON_EXECUTABLE}
22+
${ZEPHYR_BASE}/scripts/build/gen_strsignal_table.py
23+
-i ${ZEPHYR_BASE}/include/zephyr/posix/signal.h
24+
-o ${STRSIGNAL_TABLE_H}
25+
DEPENDS ${ZEPHYR_BASE}/include/zephyr/posix/signal.h
26+
)
27+
endif()
28+
1329
if(CONFIG_POSIX_API OR CONFIG_PTHREAD_IPC OR CONFIG_POSIX_CLOCK OR
1430
CONFIG_POSIX_MQUEUE OR CONFIG_POSIX_FS OR CONFIG_EVENTFD OR CONFIG_GETOPT)
1531
# This is a temporary workaround so that Newlib declares the appropriate
@@ -29,7 +45,7 @@ zephyr_library_sources_ifdef(CONFIG_POSIX_CLOCK sleep.c)
2945
zephyr_library_sources_ifdef(CONFIG_POSIX_CLOCK timer.c)
3046
zephyr_library_sources_ifdef(CONFIG_POSIX_FS fs.c)
3147
zephyr_library_sources_ifdef(CONFIG_POSIX_MQUEUE mqueue.c)
32-
zephyr_library_sources_ifdef(CONFIG_POSIX_SIGNAL signal.c)
48+
zephyr_library_sources_ifdef(CONFIG_POSIX_SIGNAL signal.c ${STRSIGNAL_TABLE_H})
3349
zephyr_library_sources_ifdef(CONFIG_POSIX_UNAME uname.c)
3450
zephyr_library_sources_ifdef(CONFIG_PTHREAD_IPC _common.c)
3551
zephyr_library_sources_ifdef(CONFIG_PTHREAD_IPC barrier.c)

lib/posix/Kconfig.signal

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,4 +16,11 @@ config POSIX_RTSIG_MAX
1616
Define the maximum number of realtime signals (RTSIG_MAX).
1717
The range of realtime signals is [SIGRTMIN .. (SIGRTMIN+RTSIG_MAX)]
1818

19+
config POSIX_SIGNAL_STRING_DESC
20+
bool "Use full description for the strsignal API"
21+
default y
22+
help
23+
Use full description for the strsignal API.
24+
Will use 256 bytes of ROM.
25+
1926
endif

lib/posix/signal.c

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,10 @@
33
*
44
* SPDX-License-Identifier: Apache-2.0
55
*/
6+
#include "posix/strsignal_table.h"
7+
68
#include <errno.h>
9+
#include <stdio.h>
710

811
#include <zephyr/posix/signal.h>
912

@@ -68,3 +71,28 @@ int sigismember(const sigset_t *set, int signo)
6871

6972
return 1 & (set->sig[SIGNO_WORD_IDX(signo)] >> SIGNO_WORD_BIT(signo));
7073
}
74+
75+
char *strsignal(int signum)
76+
{
77+
static char buf[sizeof("RT signal " STRINGIFY(SIGRTMAX))];
78+
79+
if (!signo_valid(signum)) {
80+
errno = EINVAL;
81+
return "Invalid signal";
82+
}
83+
84+
if (signo_is_rt(signum)) {
85+
snprintf(buf, sizeof(buf), "RT signal %d", signum - SIGRTMIN);
86+
return buf;
87+
}
88+
89+
if (IS_ENABLED(CONFIG_POSIX_SIGNAL_STRING_DESC)) {
90+
if (strsignal_list[signum] != NULL) {
91+
return (char *)strsignal_list[signum];
92+
}
93+
}
94+
95+
snprintf(buf, sizeof(buf), "Signal %d", signum);
96+
97+
return buf;
98+
}

scripts/build/gen_strsignal_table.py

Lines changed: 92 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,92 @@
1+
#!/usr/bin/env python3
2+
#
3+
# Copyright (c) 2023 Meta
4+
#
5+
# SPDX-License-Identifier: Apache-2.0
6+
7+
import argparse
8+
import os
9+
import re
10+
11+
12+
def front_matter():
13+
return f'''
14+
/*
15+
* This file is generated by {__file__}
16+
*/
17+
18+
#include <zephyr/posix/signal.h>
19+
'''
20+
21+
22+
def gen_strsignal_table(input, output):
23+
with open(input, 'r') as inf:
24+
25+
highest_signo = 0
26+
symbols = []
27+
msgs = {}
28+
29+
for line in inf.readlines():
30+
# Select items of the form below (note: SIGNO is numeric)
31+
# #define SYMBOL SIGNO /**< MSG */
32+
pat = r'^#define[\s]+(SIG[A-Z_]*)[\s]+([1-9][0-9]*)[\s]+/\*\*<[\s]+(.*)[\s]+\*/[\s]*$'
33+
match = re.match(pat, line)
34+
35+
if not match:
36+
continue
37+
38+
symbol = match[1]
39+
signo = int(match[2])
40+
msg = match[3]
41+
42+
symbols.append(symbol)
43+
msgs[symbol] = msg
44+
45+
highest_signo = max(int(signo), highest_signo)
46+
47+
try:
48+
os.makedirs(os.path.dirname(output))
49+
except BaseException:
50+
# directory already present
51+
pass
52+
53+
with open(output, 'w') as outf:
54+
55+
print(front_matter(), file=outf)
56+
57+
# Generate string table
58+
print(
59+
f'static const char *const strsignal_list[{highest_signo + 1}] = {{', file=outf)
60+
for symbol in symbols:
61+
print(f'\t[{symbol}] = "{msgs[symbol]}",', file=outf)
62+
63+
print('};', file=outf)
64+
65+
66+
def parse_args():
67+
parser = argparse.ArgumentParser(allow_abbrev=False)
68+
parser.add_argument(
69+
'-i',
70+
'--input',
71+
dest='input',
72+
required=True,
73+
help='input file (e.g. include/zephyr/posix/signal.h)')
74+
parser.add_argument(
75+
'-o',
76+
'--output',
77+
dest='output',
78+
required=True,
79+
help='output file (e.g. build/zephyr/misc/generated/lib/posix/strsignal_table.h)')
80+
81+
args = parser.parse_args()
82+
83+
return args
84+
85+
86+
def main():
87+
args = parse_args()
88+
gen_strsignal_table(args.input, args.output)
89+
90+
91+
if __name__ == '__main__':
92+
main()

tests/posix/common/src/signal.c

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66

77
#include <errno.h>
88
#include <signal.h>
9+
#include <stdio.h>
910

1011
#include <zephyr/kernel.h>
1112
#include <zephyr/ztest.h>
@@ -192,3 +193,26 @@ ZTEST(posix_apis, test_signal_ismember)
192193
zassert_equal(sigismember(&set, SIGKILL), 0, "%s not expected to be member", "SIGKILL");
193194
zassert_equal(sigismember(&set, SIGTERM), 0, "%s not expected to be member", "SIGTERM");
194195
}
196+
197+
ZTEST(posix_apis, test_signal_strsignal)
198+
{
199+
char buf[sizeof("RT signal " STRINGIFY(SIGRTMAX))] = {0};
200+
201+
zassert_mem_equal(strsignal(-1), "Invalid signal", sizeof("Invalid signal"));
202+
zassert_mem_equal(strsignal(0), "Invalid signal", sizeof("Invalid signal"));
203+
zassert_mem_equal(strsignal(_NSIG), "Invalid signal", sizeof("Invalid signal"));
204+
205+
zassert_mem_equal(strsignal(30), "Signal 30", sizeof("Signal 30"));
206+
snprintf(buf, sizeof(buf), "RT signal %d", SIGRTMIN - SIGRTMIN);
207+
zassert_mem_equal(strsignal(SIGRTMIN), buf, strlen(buf));
208+
snprintf(buf, sizeof(buf), "RT signal %d", SIGRTMAX - SIGRTMIN);
209+
zassert_mem_equal(strsignal(SIGRTMAX), buf, strlen(buf));
210+
211+
#ifdef CONFIG_POSIX_SIGNAL_STRING_DESC
212+
zassert_mem_equal(strsignal(SIGHUP), "Hangup", sizeof("Hangup"));
213+
zassert_mem_equal(strsignal(SIGSYS), "Bad system call", sizeof("Bad system call"));
214+
#else
215+
zassert_mem_equal(strsignal(SIGHUP), "Signal 1", sizeof("Signal 1"));
216+
zassert_mem_equal(strsignal(SIGSYS), "Signal 31", sizeof("Signal 31"));
217+
#endif
218+
}

tests/posix/common/testcase.yaml

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -80,3 +80,6 @@ tests:
8080
- CONFIG_SPIN_VALIDATE=n
8181
integration_platforms:
8282
- mps2_an385
83+
portability.posix.common.signal.strsignal_no_desc:
84+
extra_configs:
85+
- CONFIG_POSIX_SIGNAL_STRING_DESC=n

tests/posix/headers/src/signal_h.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -163,6 +163,7 @@ ZTEST(posix_headers, test_signal_h)
163163
zassert_not_null(sigaddset);
164164
zassert_not_null(sigdelset);
165165
zassert_not_null(sigismember);
166+
zassert_not_null(strsignal);
166167
#endif /* CONFIG_POSIX_SIGNAL */
167168

168169
if (IS_ENABLED(CONFIG_POSIX_API)) {

0 commit comments

Comments
 (0)