[ROSTESTS]
[reactos.git] / reactos / lib / sdk / crt / stdlib / errno.c
1 /*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS system libraries
4 * FILE: lib/crt/errno.c
5 * PURPOSE: Unknown
6 * PROGRAMER: Unknown
7 *
8 */
9 #include <precomp.h>
10 #include "doserrmap.h"
11 #include <errno.h>
12 #include <internal/wine/msvcrt.h>
13
14 static _invalid_parameter_handler invalid_parameter_handler = NULL;
15
16 /*
17 * @implemented
18 */
19 unsigned long* __doserrno(void)
20 {
21 return (unsigned long*)(&GetThreadData()->tdoserrno);
22 }
23
24 /*
25 * @implemented
26 */
27 int *_errno(void)
28 {
29 return(&GetThreadData()->terrno);
30 }
31
32
33 int __set_doserrno(int error)
34 {
35 PTHREADDATA ThreadData;
36
37 ThreadData = GetThreadData();
38 if (ThreadData)
39 ThreadData->tdoserrno = error;
40
41 return(error);
42 }
43
44 int __set_errno(int error)
45 {
46 PTHREADDATA ThreadData;
47
48 ThreadData = GetThreadData();
49 if (ThreadData)
50 ThreadData->terrno = error;
51
52 return(error);
53 }
54
55 /*
56 * This function sets both doserrno to the passed in OS error code
57 * and also maps this to an appropriate errno code. The mapping
58 * has been deduced automagically by running this functions, which
59 * exists in MSVCRT but is undocumented, on all the error codes in
60 * winerror.h.
61 */
62 void _dosmaperr(unsigned long oserror)
63 {
64 int pos, base, lim;
65
66 __set_doserrno(oserror);
67
68 /* Use binary chop to find the corresponding errno code */
69 for (base=0, lim=sizeof(doserrmap)/sizeof(doserrmap[0]); lim; lim >>= 1) {
70 pos = base+(lim >> 1);
71 if (doserrmap[pos].winerr == oserror) {
72 __set_errno(doserrmap[pos].en);
73 return;
74 } else if (doserrmap[pos].winerr < oserror) {
75 base = pos + 1;
76 --lim;
77 }
78 }
79 /* EINVAL appears to be the default */
80 __set_errno(EINVAL);
81 }
82
83 /******************************************************************************
84 * _set_error_mode (MSVCRT.@)
85 *
86 * Set the error mode, which describes where the C run-time writes error
87 * messages.
88 *
89 * PARAMS
90 * mode - the new error mode
91 *
92 * RETURNS
93 * The old error mode.
94 *
95 * TODO
96 * This function does not have a proper implementation; the error mode is
97 * never used.
98 */
99 int CDECL _set_error_mode(int mode)
100 {
101 static int current_mode = MSVCRT__OUT_TO_DEFAULT;
102
103 const int old = current_mode;
104 if ( MSVCRT__REPORT_ERRMODE != mode ) {
105 current_mode = mode;
106
107 }
108 return old;
109 }
110
111 /******************************************************************************
112 * _seterrormode (MSVCRT.@)
113 */
114 void CDECL _seterrormode(int mode)
115 {
116 SetErrorMode( mode );
117 }
118
119 /******************************************************************************
120 * _invalid_parameter (MSVCRT.@)
121 */
122 void __cdecl _invalid_parameter(const wchar_t *expr, const wchar_t *func,
123 const wchar_t *file, unsigned int line, uintptr_t arg)
124 {
125 if (invalid_parameter_handler) invalid_parameter_handler( expr, func, file, line, arg );
126 else
127 {
128 ERR( "%s:%u %s: %s %lx\n", debugstr_w(file), line, debugstr_w(func), debugstr_w(expr), arg );
129 RaiseException( STATUS_INVALID_CRUNTIME_PARAMETER, EXCEPTION_NONCONTINUABLE, 0, NULL );
130 }
131 }
132
133 /* _get_invalid_parameter_handler - not exported in native msvcrt, added in msvcr80 */
134 _invalid_parameter_handler CDECL _get_invalid_parameter_handler(void)
135 {
136 TRACE("\n");
137 return invalid_parameter_handler;
138 }
139
140 /* _set_invalid_parameter_handler - not exproted in native msvcrt, added in msvcr80 */
141 _invalid_parameter_handler CDECL _set_invalid_parameter_handler(
142 _invalid_parameter_handler handler)
143 {
144 _invalid_parameter_handler old = invalid_parameter_handler;
145
146 TRACE("(%p)\n", handler);
147
148 invalid_parameter_handler = handler;
149 return old;
150 }
151 /* EOF */