Added/Updated .gitignore files
[mono.git] / mono / io-layer / error.c
blob41356f4f69b186c653fac5efa8a28df31d239124
1 /*
2 * error.c: Error reporting
4 * Author:
5 * Dick Porter (dick@ximian.com)
7 * (C) 2002 Ximian, Inc.
8 */
10 #include <config.h>
11 #include <glib.h>
12 #include <pthread.h>
13 #include <string.h>
14 #include <errno.h>
16 #include "mono/io-layer/wapi.h"
18 static pthread_key_t error_key;
19 static mono_once_t error_key_once=MONO_ONCE_INIT;
21 static void error_init(void)
23 int ret;
25 ret = pthread_key_create(&error_key, NULL);
26 g_assert (ret == 0);
29 void _wapi_error_cleanup (void)
31 int ret;
33 ret = pthread_key_delete (error_key);
34 g_assert (ret == 0);
37 /**
38 * GetLastError:
40 * Retrieves the last error that occurred in the calling thread.
42 * Return value: The error code for the last error that happened on
43 * the calling thread.
45 guint32 GetLastError(void)
47 guint32 err;
48 void *errptr;
50 mono_once(&error_key_once, error_init);
51 errptr=pthread_getspecific(error_key);
52 err=GPOINTER_TO_UINT(errptr);
54 return(err);
57 /**
58 * SetLastError:
59 * @code: The error code.
61 * Sets the error code in the calling thread.
63 void SetLastError(guint32 code)
65 int ret;
67 /* Set the thread-local error code */
68 mono_once(&error_key_once, error_init);
69 ret = pthread_setspecific(error_key, GUINT_TO_POINTER(code));
70 g_assert (ret == 0);
73 guint32
74 errno_to_WSA (guint32 code, const gchar *function_name)
76 gint result = -1;
77 char *sys_error;
78 gchar *msg;
80 switch (code) {
81 case 0: result = ERROR_SUCCESS; break;
82 case EACCES: result = WSAEACCES; break;
83 #ifdef EADDRINUSE
84 case EADDRINUSE: result = WSAEADDRINUSE; break;
85 #endif
86 #ifdef EAFNOSUPPORT
87 case EAFNOSUPPORT: result = WSAEAFNOSUPPORT; break;
88 #endif
89 #if EAGAIN != EWOULDBLOCK
90 case EAGAIN: result = WSAEWOULDBLOCK; break;
91 #endif
92 #ifdef EALREADY
93 case EALREADY: result = WSAEALREADY; break;
94 #endif
95 case EBADF: result = WSAENOTSOCK; break;
96 #ifdef ECONNABORTED
97 case ECONNABORTED: result = WSAENETDOWN; break;
98 #endif
99 #ifdef ECONNREFUSED
100 case ECONNREFUSED: result = WSAECONNREFUSED; break;
101 #endif
102 #ifdef ECONNRESET
103 case ECONNRESET: result = WSAECONNRESET; break;
104 #endif
105 case EFAULT: result = WSAEFAULT; break;
106 #ifdef EHOSTUNREACH
107 case EHOSTUNREACH: result = WSAEHOSTUNREACH; break;
108 #endif
109 #ifdef EINPROGRESS
110 case EINPROGRESS: result = WSAEINPROGRESS; break;
111 #endif
112 case EINTR: result = WSAEINTR; break;
113 case EINVAL: result = WSAEINVAL; break;
114 /*FIXME: case EIO: result = WSAE????; break; */
115 #ifdef EISCONN
116 case EISCONN: result = WSAEISCONN; break;
117 #endif
118 /* FIXME: case ELOOP: result = WSA????; break; */
119 case EMFILE: result = WSAEMFILE; break;
120 #ifdef EMSGSIZE
121 case EMSGSIZE: result = WSAEMSGSIZE; break;
122 #endif
123 /* FIXME: case ENAMETOOLONG: result = WSAEACCES; break; */
124 #ifdef ENETUNREACH
125 case ENETUNREACH: result = WSAENETUNREACH; break;
126 #endif
127 #ifdef ENOBUFS
128 case ENOBUFS: result = WSAENOBUFS; break; /* not documented */
129 #endif
130 /* case ENOENT: result = WSAE????; break; */
131 case ENOMEM: result = WSAENOBUFS; break;
132 #ifdef ENOPROTOOPT
133 case ENOPROTOOPT: result = WSAENOPROTOOPT; break;
134 #endif
135 #ifdef ENOSR
136 case ENOSR: result = WSAENETDOWN; break;
137 #endif
138 #ifdef ENOTCONN
139 case ENOTCONN: result = WSAENOTCONN; break;
140 #endif
141 /*FIXME: case ENOTDIR: result = WSAE????; break; */
142 #ifdef ENOTSOCK
143 case ENOTSOCK: result = WSAENOTSOCK; break;
144 #endif
145 case ENOTTY: result = WSAENOTSOCK; break;
146 #ifdef EOPNOTSUPP
147 case EOPNOTSUPP: result = WSAEOPNOTSUPP; break;
148 #endif
149 case EPERM: result = WSAEACCES; break;
150 case EPIPE: result = WSAESHUTDOWN; break;
151 #ifdef EPROTONOSUPPORT
152 case EPROTONOSUPPORT: result = WSAEPROTONOSUPPORT; break;
153 #endif
154 #if ERESTARTSYS
155 case ERESTARTSYS: result = WSAENETDOWN; break;
156 #endif
157 /*FIXME: case EROFS: result = WSAE????; break; */
158 #ifdef ESOCKTNOSUPPORT
159 case ESOCKTNOSUPPORT: result = WSAESOCKTNOSUPPORT; break;
160 #endif
161 #ifdef ETIMEDOUT
162 case ETIMEDOUT: result = WSAETIMEDOUT; break;
163 #endif
164 #ifdef EWOULDBLOCK
165 case EWOULDBLOCK: result = WSAEWOULDBLOCK; break;
166 #endif
167 #ifdef EADDRNOTAVAIL
168 case EADDRNOTAVAIL: result = WSAEADDRNOTAVAIL; break;
169 #endif
170 /* This might happen with unix sockets */
171 case ENOENT: result = WSAECONNREFUSED; break;
172 #ifdef EDESTADDRREQ
173 case EDESTADDRREQ: result = WSAEDESTADDRREQ; break;
174 #endif
175 case ENODEV: result = WSAENETDOWN; break;
176 default:
177 sys_error = strerror (code);
178 msg = g_locale_to_utf8 (sys_error, strlen (sys_error), NULL, NULL, NULL);
179 if (function_name == NULL)
180 function_name = __func__;
182 g_warning ("%s: Need to translate %d [%s] into winsock error",
183 function_name, code, msg);
185 g_free (msg);
186 result = WSASYSCALLFAILURE;
189 return result;
192 gint
193 _wapi_get_win32_file_error (gint err)
195 gint ret;
196 /* mapping ideas borrowed from wine. they may need some work */
198 switch (err) {
199 case EACCES: case EPERM: case EROFS:
200 ret = ERROR_ACCESS_DENIED;
201 break;
203 case EAGAIN:
204 ret = ERROR_SHARING_VIOLATION;
205 break;
207 case EBUSY:
208 ret = ERROR_LOCK_VIOLATION;
209 break;
211 case EEXIST:
212 ret = ERROR_FILE_EXISTS;
213 break;
215 case EINVAL: case ESPIPE:
216 ret = ERROR_SEEK;
217 break;
219 case EISDIR:
220 ret = ERROR_CANNOT_MAKE;
221 break;
223 case ENFILE: case EMFILE:
224 ret = ERROR_TOO_MANY_OPEN_FILES;
225 break;
227 case ENOENT: case ENOTDIR:
228 ret = ERROR_FILE_NOT_FOUND;
229 break;
231 case ENOSPC:
232 ret = ERROR_HANDLE_DISK_FULL;
233 break;
235 case ENOTEMPTY:
236 ret = ERROR_DIR_NOT_EMPTY;
237 break;
239 case ENOEXEC:
240 ret = ERROR_BAD_FORMAT;
241 break;
243 case ENAMETOOLONG:
244 ret = ERROR_FILENAME_EXCED_RANGE;
245 break;
247 #ifdef EINPROGRESS
248 case EINPROGRESS:
249 ret = ERROR_IO_PENDING;
250 break;
251 #endif
253 case ENOSYS:
254 ret = ERROR_NOT_SUPPORTED;
255 break;
257 case EBADF:
258 ret = ERROR_INVALID_HANDLE;
259 break;
261 case EIO:
262 ret = ERROR_INVALID_HANDLE;
263 break;
265 case EINTR:
266 ret = ERROR_IO_PENDING; /* best match I could find */
267 break;
269 case EPIPE:
270 ret = ERROR_WRITE_FAULT;
271 break;
273 default:
274 g_message ("Unknown errno: %s\n", g_strerror (err));
275 ret = ERROR_GEN_FAILURE;
276 break;
279 return ret;