fujuntang
2021-09-07 b984dac55bdd0a5b694837fb8fb2ceb07ce9808f
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
#include "usg_common.h"
#include "bus_error.h"
 
#define MAX_ERROR_LEN 256           /* Maximum length of string in per-thread
                                       buffer returned by strerror() */
#define _bus_nerr  256
 
int bus_errno;
 
static pthread_once_t once = PTHREAD_ONCE_INIT;
static pthread_key_t strerrorKey;
 
 
static const char *_bus_errlist[_bus_nerr] = {
  "\0",
  "Timed out",
  "The other end is not inline",
  "Key already in use",
  "Network fault",
  "Send to self error",
  "Receive from wrong end",
  "Service stoped",
  "Exceed resource limit",
  "Service not supported",
  "Resource busy",
  "Resource not provide",
  "Invalid parameters",
  "No enough memory"
 
};
 
static void                         /* Free thread-specific data buffer */
destructor(void *buf)
{
  free(buf);
}
 
static void                         /* One-time key creation function */
createKey(void)
{
  int s;
 
  /* Allocate a unique thread-specific data key and save the address
     of the destructor for thread-specific data buffers */
 
  s = pthread_key_create(&strerrorKey, destructor);
  if (s != 0)
    err_exit(s, "pthread_key_create");
}
 
char *
bus_strerror(int err)
{
  int s;
  char *buf;
  /* Make first caller allocate key for thread-specific data */
 
  if (err == 0) {
    err = EBUS_BASE;
  }
 
  s = pthread_once(&once, createKey);
  if (s != 0)
    err_exit(s, "pthread_once");
 
  buf = (char *)pthread_getspecific(strerrorKey);
  if (buf == NULL)
  {
    /* If first call from this thread, allocate
                                   buffer for thread, and save its location */
    buf = (char *)malloc(MAX_ERROR_LEN);
    if (buf == NULL)
      err_exit(errno, "malloc");
 
    s = pthread_setspecific(strerrorKey, buf);
    if (s != 0)
      err_exit(s, "pthread_setspecific");
  }
 
 
  if(err < EBUS_BASE) {
    // libc错误
    if (err < 0 || err >= _sys_nerr || _sys_errlist[err] == NULL)
    {
      snprintf(buf, MAX_ERROR_LEN, "Unknown error %d", err);
    }
    else
    {
      strncpy(buf, _sys_errlist[err], MAX_ERROR_LEN - 1);
      buf[MAX_ERROR_LEN - 1] = '\0';          /* Ensure null termination */
    }
  } else {
    //自定义错误
    err -= EBUS_BASE;
    if (err < 0 || err >= _bus_nerr || _bus_errlist[err] == NULL)
    {
      snprintf(buf, MAX_ERROR_LEN, "Unknown error %d", err);
    }
    else
    {
      strncpy(buf, _bus_errlist[err], MAX_ERROR_LEN - 1);
      buf[MAX_ERROR_LEN - 1] = '\0';          /* Ensure null termination */
    }
 
  }
 
  return buf;
}