blob: 646cc5239387fb339e5365196de74551b4a49873 [file] [log] [blame]
Irina Tirdeab5f053b2012-09-08 09:17:54 +03001/* $OpenBSD: strerror_r.c,v 1.6 2005/08/08 08:05:37 espie Exp $ */
2/* Public Domain <marc@snafu.org> */
3
4#include <errno.h>
5#include <limits.h>
6#include <signal.h>
7#include <stdio.h>
8#include <string.h>
9
10struct Pair {
11 int code;
12 const char* msg;
13};
14
15static const char* __code_string_lookup(const Pair* strings, int code) {
16 for (size_t i = 0; strings[i].msg != NULL; ++i) {
17 if (strings[i].code == code) {
18 return strings[i].msg;
19 }
20 }
21 return NULL;
22}
23
24static const Pair _sys_error_strings[] = {
25#define __BIONIC_ERRDEF(x,y,z) { x, z },
26#include <sys/_errdefs.h>
27 { 0, NULL }
28};
29
Elliott Hughes95a7a642012-09-21 18:27:40 -070030extern "C" __LIBC_HIDDEN__ const char* __strerror_lookup(int error_number) {
Elliott Hughes4198fa42012-09-17 15:23:35 -070031 return __code_string_lookup(_sys_error_strings, error_number);
32}
33
34static const Pair _sys_signal_strings[] = {
35#define __BIONIC_SIGDEF(x,y,z) { y, z },
36#include <sys/_sigdefs.h>
37 { 0, NULL }
38};
39
Elliott Hughes95a7a642012-09-21 18:27:40 -070040extern "C" __LIBC_HIDDEN__ const char* __strsignal_lookup(int signal_number) {
Elliott Hughes4198fa42012-09-17 15:23:35 -070041 return __code_string_lookup(_sys_signal_strings, signal_number);
42}
43
Irina Tirdeab5f053b2012-09-08 09:17:54 +030044int strerror_r(int error_number, char* buf, size_t buf_len) {
45 int saved_errno = errno;
46 size_t length;
47
Elliott Hughes4198fa42012-09-17 15:23:35 -070048 const char* error_name = __strerror_lookup(error_number);
Irina Tirdeab5f053b2012-09-08 09:17:54 +030049 if (error_name != NULL) {
50 length = snprintf(buf, buf_len, "%s", error_name);
51 } else {
Elliott Hughese6e60062013-01-10 16:01:59 -080052 length = snprintf(buf, buf_len, "Unknown error %d", error_number);
Irina Tirdeab5f053b2012-09-08 09:17:54 +030053 }
54 if (length >= buf_len) {
55 errno = ERANGE;
56 return -1;
57 }
58
59 errno = saved_errno;
60 return 0;
61}
62
Elliott Hughes95a7a642012-09-21 18:27:40 -070063extern "C" __LIBC_HIDDEN__ const char* __strsignal(int signal_number, char* buf, size_t buf_len) {
Elliott Hughes4198fa42012-09-17 15:23:35 -070064 const char* signal_name = __strsignal_lookup(signal_number);
Irina Tirdeab5f053b2012-09-08 09:17:54 +030065 if (signal_name != NULL) {
66 return signal_name;
67 }
68
69 const char* prefix = "Unknown";
70 if (signal_number >= SIGRTMIN && signal_number <= SIGRTMAX) {
71 prefix = "Real-time";
72 signal_number -= SIGRTMIN;
73 }
74 size_t length = snprintf(buf, buf_len, "%s signal %d", prefix, signal_number);
75 if (length >= buf_len) {
76 return NULL;
77 }
78 return buf;
79}