fix installing of extension modules
[python/dscho.git] / PC / msvcrtmodule.c
blobf441aa386c895fa8d84f084d598d9bd8dc123e2f
1 /*********************************************************
3 msvcrtmodule.c
5 A Python interface to the Microsoft Visual C Runtime
6 Library, providing access to those non-portable, but
7 still useful routines.
9 Only ever compiled with an MS compiler, so no attempt
10 has been made to avoid MS language extensions, etc...
12 This may only work on NT or 95...
14 Author: Mark Hammond and Guido van Rossum.
15 Maintenance: Guido van Rossum.
17 ***********************************************************/
19 #include "Python.h"
20 #include "malloc.h"
21 #include <io.h>
22 #include <conio.h>
23 #include <sys/locking.h>
24 #include <crtdbg.h>
25 #include <windows.h>
27 #ifdef _MSC_VER
28 #if _MSC_VER >= 1500
29 #include <crtassem.h>
30 #endif
31 #endif
33 // Force the malloc heap to clean itself up, and free unused blocks
34 // back to the OS. (According to the docs, only works on NT.)
35 static PyObject *
36 msvcrt_heapmin(PyObject *self, PyObject *args)
38 if (!PyArg_ParseTuple(args, ":heapmin"))
39 return NULL;
41 if (_heapmin() != 0)
42 return PyErr_SetFromErrno(PyExc_IOError);
44 Py_INCREF(Py_None);
45 return Py_None;
48 // Perform locking operations on a C runtime file descriptor.
49 static PyObject *
50 msvcrt_locking(PyObject *self, PyObject *args)
52 int fd;
53 int mode;
54 long nbytes;
55 int err;
57 if (!PyArg_ParseTuple(args, "iil:locking", &fd, &mode, &nbytes))
58 return NULL;
60 Py_BEGIN_ALLOW_THREADS
61 err = _locking(fd, mode, nbytes);
62 Py_END_ALLOW_THREADS
63 if (err != 0)
64 return PyErr_SetFromErrno(PyExc_IOError);
66 Py_INCREF(Py_None);
67 return Py_None;
70 // Set the file translation mode for a C runtime file descriptor.
71 static PyObject *
72 msvcrt_setmode(PyObject *self, PyObject *args)
74 int fd;
75 int flags;
76 if (!PyArg_ParseTuple(args,"ii:setmode", &fd, &flags))
77 return NULL;
79 flags = _setmode(fd, flags);
80 if (flags == -1)
81 return PyErr_SetFromErrno(PyExc_IOError);
83 return PyLong_FromLong(flags);
86 // Convert an OS file handle to a C runtime file descriptor.
87 static PyObject *
88 msvcrt_open_osfhandle(PyObject *self, PyObject *args)
90 long handle;
91 int flags;
92 int fd;
94 if (!PyArg_ParseTuple(args, "li:open_osfhandle", &handle, &flags))
95 return NULL;
97 fd = _open_osfhandle(handle, flags);
98 if (fd == -1)
99 return PyErr_SetFromErrno(PyExc_IOError);
101 return PyLong_FromLong(fd);
104 // Convert a C runtime file descriptor to an OS file handle.
105 static PyObject *
106 msvcrt_get_osfhandle(PyObject *self, PyObject *args)
108 int fd;
109 Py_intptr_t handle;
111 if (!PyArg_ParseTuple(args,"i:get_osfhandle", &fd))
112 return NULL;
114 handle = _get_osfhandle(fd);
115 if (handle == -1)
116 return PyErr_SetFromErrno(PyExc_IOError);
118 /* technically 'handle' is not a pointer, but a integer as
119 large as a pointer, Python's *VoidPtr interface is the
120 most appropriate here */
121 return PyLong_FromVoidPtr((void*)handle);
124 /* Console I/O */
126 static PyObject *
127 msvcrt_kbhit(PyObject *self, PyObject *args)
129 int ok;
131 if (!PyArg_ParseTuple(args, ":kbhit"))
132 return NULL;
134 ok = _kbhit();
135 return PyLong_FromLong(ok);
138 static PyObject *
139 msvcrt_getch(PyObject *self, PyObject *args)
141 int ch;
142 char s[1];
144 if (!PyArg_ParseTuple(args, ":getch"))
145 return NULL;
147 Py_BEGIN_ALLOW_THREADS
148 ch = _getch();
149 Py_END_ALLOW_THREADS
150 s[0] = ch;
151 return PyBytes_FromStringAndSize(s, 1);
154 #ifdef _WCONIO_DEFINED
155 static PyObject *
156 msvcrt_getwch(PyObject *self, PyObject *args)
158 Py_UNICODE ch;
159 Py_UNICODE u[1];
161 if (!PyArg_ParseTuple(args, ":getwch"))
162 return NULL;
164 Py_BEGIN_ALLOW_THREADS
165 ch = _getwch();
166 Py_END_ALLOW_THREADS
167 u[0] = ch;
168 return PyUnicode_FromUnicode(u, 1);
170 #endif
172 static PyObject *
173 msvcrt_getche(PyObject *self, PyObject *args)
175 int ch;
176 char s[1];
178 if (!PyArg_ParseTuple(args, ":getche"))
179 return NULL;
181 Py_BEGIN_ALLOW_THREADS
182 ch = _getche();
183 Py_END_ALLOW_THREADS
184 s[0] = ch;
185 return PyBytes_FromStringAndSize(s, 1);
188 #ifdef _WCONIO_DEFINED
189 static PyObject *
190 msvcrt_getwche(PyObject *self, PyObject *args)
192 Py_UNICODE ch;
193 Py_UNICODE s[1];
195 if (!PyArg_ParseTuple(args, ":getwche"))
196 return NULL;
198 Py_BEGIN_ALLOW_THREADS
199 ch = _getwche();
200 Py_END_ALLOW_THREADS
201 s[0] = ch;
202 return PyUnicode_FromUnicode(s, 1);
204 #endif
206 static PyObject *
207 msvcrt_putch(PyObject *self, PyObject *args)
209 char ch;
211 if (!PyArg_ParseTuple(args, "c:putch", &ch))
212 return NULL;
214 _putch(ch);
215 Py_INCREF(Py_None);
216 return Py_None;
219 #ifdef _WCONIO_DEFINED
220 static PyObject *
221 msvcrt_putwch(PyObject *self, PyObject *args)
223 Py_UNICODE *ch;
224 int size;
226 if (!PyArg_ParseTuple(args, "u#:putwch", &ch, &size))
227 return NULL;
229 if (size == 0) {
230 PyErr_SetString(PyExc_ValueError,
231 "Expected unicode string of length 1");
232 return NULL;
234 _putwch(*ch);
235 Py_RETURN_NONE;
238 #endif
240 static PyObject *
241 msvcrt_ungetch(PyObject *self, PyObject *args)
243 char ch;
245 if (!PyArg_ParseTuple(args, "c:ungetch", &ch))
246 return NULL;
248 if (_ungetch(ch) == EOF)
249 return PyErr_SetFromErrno(PyExc_IOError);
250 Py_INCREF(Py_None);
251 return Py_None;
254 #ifdef _WCONIO_DEFINED
255 static PyObject *
256 msvcrt_ungetwch(PyObject *self, PyObject *args)
258 Py_UNICODE ch;
260 if (!PyArg_ParseTuple(args, "u:ungetwch", &ch))
261 return NULL;
263 if (_ungetch(ch) == EOF)
264 return PyErr_SetFromErrno(PyExc_IOError);
265 Py_INCREF(Py_None);
266 return Py_None;
268 #endif
270 static void
271 insertint(PyObject *d, char *name, int value)
273 PyObject *v = PyLong_FromLong((long) value);
274 if (v == NULL) {
275 /* Don't bother reporting this error */
276 PyErr_Clear();
278 else {
279 PyDict_SetItemString(d, name, v);
280 Py_DECREF(v);
284 #ifdef _DEBUG
286 static PyObject*
287 msvcrt_setreportfile(PyObject *self, PyObject *args)
289 int type, file;
290 _HFILE res;
292 if (!PyArg_ParseTuple(args, "ii", &type, &file))
293 return NULL;
294 res = _CrtSetReportFile(type, (_HFILE)file);
295 return PyLong_FromLong((long)res);
296 Py_INCREF(Py_None);
297 return Py_None;
300 static PyObject*
301 msvcrt_setreportmode(PyObject *self, PyObject *args)
303 int type, mode;
304 int res;
306 if (!PyArg_ParseTuple(args, "ii", &type, &mode))
307 return NULL;
308 res = _CrtSetReportMode(type, mode);
309 if (res == -1)
310 return PyErr_SetFromErrno(PyExc_IOError);
311 return PyLong_FromLong(res);
314 static PyObject*
315 msvcrt_seterrormode(PyObject *self, PyObject *args)
317 int mode, res;
319 if (!PyArg_ParseTuple(args, "i", &mode))
320 return NULL;
321 res = _set_error_mode(mode);
322 return PyLong_FromLong(res);
325 #endif
327 static PyObject*
328 seterrormode(PyObject *self, PyObject *args)
330 unsigned int mode, res;
332 if (!PyArg_ParseTuple(args, "I", &mode))
333 return NULL;
334 res = SetErrorMode(mode);
335 return PyLong_FromUnsignedLong(res);
339 /* List of functions exported by this module */
340 static struct PyMethodDef msvcrt_functions[] = {
341 {"heapmin", msvcrt_heapmin, METH_VARARGS},
342 {"locking", msvcrt_locking, METH_VARARGS},
343 {"setmode", msvcrt_setmode, METH_VARARGS},
344 {"open_osfhandle", msvcrt_open_osfhandle, METH_VARARGS},
345 {"get_osfhandle", msvcrt_get_osfhandle, METH_VARARGS},
346 {"kbhit", msvcrt_kbhit, METH_VARARGS},
347 {"getch", msvcrt_getch, METH_VARARGS},
348 {"getche", msvcrt_getche, METH_VARARGS},
349 {"putch", msvcrt_putch, METH_VARARGS},
350 {"ungetch", msvcrt_ungetch, METH_VARARGS},
351 {"SetErrorMode", seterrormode, METH_VARARGS},
352 #ifdef _DEBUG
353 {"CrtSetReportFile", msvcrt_setreportfile, METH_VARARGS},
354 {"CrtSetReportMode", msvcrt_setreportmode, METH_VARARGS},
355 {"set_error_mode", msvcrt_seterrormode, METH_VARARGS},
356 #endif
357 #ifdef _WCONIO_DEFINED
358 {"getwch", msvcrt_getwch, METH_VARARGS},
359 {"getwche", msvcrt_getwche, METH_VARARGS},
360 {"putwch", msvcrt_putwch, METH_VARARGS},
361 {"ungetwch", msvcrt_ungetwch, METH_VARARGS},
362 #endif
363 {NULL, NULL}
367 static struct PyModuleDef msvcrtmodule = {
368 PyModuleDef_HEAD_INIT,
369 "msvcrt",
370 NULL,
372 msvcrt_functions,
373 NULL,
374 NULL,
375 NULL,
376 NULL
379 PyMODINIT_FUNC
380 PyInit_msvcrt(void)
382 int st;
383 PyObject *d;
384 PyObject *m = PyModule_Create(&msvcrtmodule);
385 if (m == NULL)
386 return NULL;
387 d = PyModule_GetDict(m);
389 /* constants for the locking() function's mode argument */
390 insertint(d, "LK_LOCK", _LK_LOCK);
391 insertint(d, "LK_NBLCK", _LK_NBLCK);
392 insertint(d, "LK_NBRLCK", _LK_NBRLCK);
393 insertint(d, "LK_RLCK", _LK_RLCK);
394 insertint(d, "LK_UNLCK", _LK_UNLCK);
395 insertint(d, "SEM_FAILCRITICALERRORS", SEM_FAILCRITICALERRORS);
396 insertint(d, "SEM_NOALIGNMENTFAULTEXCEPT", SEM_NOALIGNMENTFAULTEXCEPT);
397 insertint(d, "SEM_NOGPFAULTERRORBOX", SEM_NOGPFAULTERRORBOX);
398 insertint(d, "SEM_NOOPENFILEERRORBOX", SEM_NOOPENFILEERRORBOX);
399 #ifdef _DEBUG
400 insertint(d, "CRT_WARN", _CRT_WARN);
401 insertint(d, "CRT_ERROR", _CRT_ERROR);
402 insertint(d, "CRT_ASSERT", _CRT_ASSERT);
403 insertint(d, "CRTDBG_MODE_DEBUG", _CRTDBG_MODE_DEBUG);
404 insertint(d, "CRTDBG_MODE_FILE", _CRTDBG_MODE_FILE);
405 insertint(d, "CRTDBG_MODE_WNDW", _CRTDBG_MODE_WNDW);
406 insertint(d, "CRTDBG_REPORT_MODE", _CRTDBG_REPORT_MODE);
407 insertint(d, "CRTDBG_FILE_STDERR", (int)_CRTDBG_FILE_STDERR);
408 insertint(d, "CRTDBG_FILE_STDOUT", (int)_CRTDBG_FILE_STDOUT);
409 insertint(d, "CRTDBG_REPORT_FILE", (int)_CRTDBG_REPORT_FILE);
410 #endif
412 /* constants for the crt versions */
413 #ifdef _VC_ASSEMBLY_PUBLICKEYTOKEN
414 st = PyModule_AddStringConstant(m, "VC_ASSEMBLY_PUBLICKEYTOKEN",
415 _VC_ASSEMBLY_PUBLICKEYTOKEN);
416 if (st < 0) return NULL;
417 #endif
418 #ifdef _CRT_ASSEMBLY_VERSION
419 st = PyModule_AddStringConstant(m, "CRT_ASSEMBLY_VERSION",
420 _CRT_ASSEMBLY_VERSION);
421 if (st < 0) return NULL;
422 #endif
423 #ifdef __LIBRARIES_ASSEMBLY_NAME_PREFIX
424 st = PyModule_AddStringConstant(m, "LIBRARIES_ASSEMBLY_NAME_PREFIX",
425 __LIBRARIES_ASSEMBLY_NAME_PREFIX);
426 if (st < 0) return NULL;
427 #endif
429 return m;