source: vendor/python/2.5/Modules/puremodule.c

Last change on this file was 3225, checked in by bird, 18 years ago

Python 2.5

File size: 30.6 KB
Line 
1/* This module exports the C API to such Pure Software Inc. (tm) (now
2 * called Pure Atria Corporation) products as Purify (tm) and Quantify
3 * (tm). Other packages could be added, but I didn't have those products
4 * and thus lack the API documentation.
5 *
6 * Currently supported: Quantify 2.x, Purify 3.x
7 *
8 * You need to decide which products you want to incorporate into the
9 * module when you compile this file. The way to do this is to edit
10 * <Python>/Modules/Setup to pass the appropriate flags to the compiler.
11 * -DWITH_PURIFY compiles in the Purify support, and -DWITH_QUANTIFY
12 * compiles in the Quantify support. -DWITH_ALL_PURE compiles in both.
13 * You can also build a Purify'd or Quantify'd interpreter by passing in
14 * the LINKCC variable to make. E.g. if you want to build a Purify'd
15 * interpreter and are using gcc, build Python with this command:
16 *
17 * make LINKCC='purify gcc'
18 *
19 * It would be nice (and probably easy) to provide this file as a shared
20 * library, however since it doesn't appear that Pure gives us shared
21 * libraries of the stubs, it doesn't really matter. For now, you have to
22 * link this file in statically.
23 *
24 * Major bogosity. The purify.h header file exports purify_exit(), but
25 * guess what? It is not defined in the libpurify_stubs.a file! I tried
26 * to fake one here, hoping the Pure linker would Do The Right Thing when
27 * instrumented for Purify, but it doesn't seem to, so I don't export
28 * purify_exit() to the Python layer. In Python you should raise a
29 * SystemExit exception anyway.
30 *
31 * The actual purify.h and quantify.h files which embody the APIs are
32 * copyrighted by Pure Software, Inc. and are only attainable through them.
33 * This module assumes you have legally installed licenses of their
34 * software. Contact them on the Web via <http://www.pureatria.com/>
35 *
36 * Author: Barry Warsaw <bwarsaw@python.org>
37 * <bwarsaw@cnri.reston.va.us>
38 */
39
40#include "Python.h"
41
42#if defined(WITH_PURIFY) || defined(WITH_ALL_PURE)
43# include <purify.h>
44# define HAS_PURIFY_EXIT 0 /* See note at top of file */
45# define PURE_PURIFY_VERSION 3 /* not provided by purify.h */
46#endif
47#if defined(WITH_QUANTIFY) || defined(WITH_ALL_PURE)
48# include <quantify.h>
49# define PURE_QUANTIFY_VERSION 2 /* not provided by quantify.h */
50#endif
51#if defined(PURIFY_H) || defined(QUANTIFY_H)
52# define COMMON_PURE_FUNCTIONS
53#endif /* PURIFY_H || QUANTIFY_H */
54
55typedef int (*VoidArgFunc)(void);
56typedef int (*StringArgFunc)(char*);
57typedef int (*PrintfishFunc)(const char*, ...);
58typedef int (*StringIntArgFunc)(const char*, int);
59
60
61
62
63static PyObject*
64call_voidarg_function(VoidArgFunc func, PyObject *self, PyObject *args)
65{
66 int status;
67
68 if (!PyArg_ParseTuple(args, ""))
69 return NULL;
70
71 status = func();
72 return Py_BuildValue("i", status);
73}
74
75static PyObject*
76call_stringarg_function(StringArgFunc func, PyObject *self, PyObject *args)
77{
78 int status;
79 char* stringarg;
80
81 if (!PyArg_ParseTuple(args, "s", &stringarg))
82 return NULL;
83
84 status = func(stringarg);
85 return Py_BuildValue("i", status);
86}
87
88static PyObject*
89call_stringorint_function(StringArgFunc func, PyObject *self, PyObject *args)
90{
91 int status;
92 int intarg;
93 char* stringarg;
94
95 /* according to the quantify.h file, the argument to
96 * quantify_*_recording_system_call can be an integer or a string,
97 * but the functions are prototyped as taking a single char*
98 * argument. Yikes!
99 */
100 if (PyArg_ParseTuple(args, "i", &intarg))
101 /* func is prototyped as int(*)(char*)
102 * better shut up the compiler
103 */
104 status = func((char*)intarg);
105
106 else {
107 PyErr_Clear();
108 if (!PyArg_ParseTuple(args, "s", &stringarg))
109 return NULL;
110 else
111 status = func(stringarg);
112 }
113 return Py_BuildValue("i", status);
114}
115
116static PyObject*
117call_printfish_function(PrintfishFunc func, PyObject *self, PyObject *args)
118{
119 /* we support the printf() style vararg functions by requiring the
120 * formatting be done in Python. At the C level we pass just a string
121 * to the printf() style function.
122 */
123 int status;
124 char* argstring;
125
126 if (!PyArg_ParseTuple(args, "s", &argstring))
127 return NULL;
128
129 status = func("%s", argstring);
130 return Py_BuildValue("i", status);
131}
132
133static PyObject*
134call_intasaddr_function(StringArgFunc func, PyObject *self, PyObject *args)
135{
136 long memrep;
137 int id;
138
139 if (!PyArg_ParseTuple(args, "l", &memrep))
140 return NULL;
141
142 id = func((char*)memrep);
143 return Py_BuildValue("i", id);
144}
145
146static PyObject*
147call_stringandint_function(StringIntArgFunc func, PyObject *self,
148 PyObject *args)
149{
150 long srcrep;
151 int size;
152 int status;
153
154 if (!PyArg_ParseTuple(args, "li", &srcrep, &size))
155 return NULL;
156
157 status = func((char*)srcrep, size);
158 return Py_BuildValue("i", status);
159}
160
161
162
163
164/* functions common to all products
165 *
166 * N.B. These printf() style functions are a bit of a kludge. Since the
167 * API doesn't provide vprintf versions of them, we can't call them
168 * directly. They don't support all the standard printf % modifiers
169 * anyway. The way to use these is to use Python's % string operator to do
170 * the formatting. By the time these functions get the thing to print,
171 * it's already a string, and they just use "%s" as the format string.
172 */
173
174#ifdef COMMON_PURE_FUNCTIONS
175
176static PyObject*
177pure_pure_logfile_printf(PyObject* self, PyObject* args)
178{
179 return call_printfish_function(pure_logfile_printf, self, args);
180}
181
182static PyObject*
183pure_pure_printf(PyObject* self, PyObject* args)
184{
185 return call_printfish_function(pure_printf, self, args);
186}
187
188static PyObject*
189pure_pure_printf_with_banner(PyObject* self, PyObject* args)
190{
191 return call_printfish_function(pure_printf_with_banner, self, args);
192}
193
194
195#endif /* COMMON_PURE_FUNCTIONS */
196
197
198
199
200/* Purify functions
201 *
202 * N.B. There are some interfaces described in the purify.h file that are
203 * not described in the manual.
204 *
205 * Unsigned longs purify_report_{address,number,type,result} are not
206 * accessible from the Python layer since they seem mostly useful when
207 * purify_stop_here() is called by the (C) debugger. The same is true of
208 * the purify_stop_here_internal() function so it isn't exported either.
209 * And purify_stop_here() should never be called directly.
210 *
211 * The header file says purify_{new,all,clear_new}_reports() are obsolete
212 * so they aren't exported.
213 *
214 * None of the custom dynamic loader functions are exported.
215 *
216 * purify_unsafe_memcpy() isn't exported.
217 *
218 * purify_{start,size}_of_block() aren't exported.
219 *
220 * The manual that I have says that the prototype for the second argument
221 * to purify_map_pool is:
222 *
223 * void (*fn)(char*)
224 *
225 * but the purify.h file declares it as:
226 *
227 * void (*fn)(char*, int, void*)
228 *
229 * and does not explain what the other arguments are for. I support the
230 * latter but I don't know if I do it right or usefully.
231 *
232 * The header file says that purify_describe() returns a char* which is the
233 * pointer passed to it. The manual says it returns an int, but I believe
234 * that is a typo.
235 */
236#ifdef PURIFY_H
237
238static PyObject*
239pure_purify_all_inuse(PyObject *self, PyObject *args)
240{
241 return call_voidarg_function(purify_all_inuse, self, args);
242}
243static PyObject*
244pure_purify_all_leaks(PyObject *self, PyObject *args)
245{
246 return call_voidarg_function(purify_all_leaks, self, args);
247}
248static PyObject*
249pure_purify_new_inuse(PyObject *self, PyObject *args)
250{
251 return call_voidarg_function(purify_new_inuse, self, args);
252}
253static PyObject*
254pure_purify_new_leaks(PyObject *self, PyObject *args)
255{
256 return call_voidarg_function(purify_new_leaks, self, args);
257}
258static PyObject*
259pure_purify_clear_inuse(PyObject *self, PyObject *args)
260{
261 return call_voidarg_function(purify_clear_inuse, self, args);
262}
263static PyObject*
264pure_purify_clear_leaks(PyObject *self, PyObject *args)
265{
266 return call_voidarg_function(purify_clear_leaks, self, args);
267}
268static PyObject*
269pure_purify_all_fds_inuse(PyObject *self, PyObject *args)
270{
271 return call_voidarg_function(purify_all_fds_inuse, self, args);
272}
273static PyObject*
274pure_purify_new_fds_inuse(PyObject *self, PyObject *args)
275{
276 return call_voidarg_function(purify_new_fds_inuse, self, args);
277}
278static PyObject*
279pure_purify_printf_with_call_chain(PyObject *self, PyObject *args)
280{
281 return call_printfish_function(purify_printf_with_call_chain,
282 self, args);
283}
284static PyObject*
285pure_purify_set_pool_id(PyObject *self, PyObject *args)
286{
287 long memrep;
288 int id;
289
290 if (!PyArg_ParseTuple(args, "li:purify_set_pool_id", &memrep, &id))
291 return NULL;
292
293 purify_set_pool_id((char*)memrep, id);
294 Py_INCREF(Py_None);
295 return Py_None;
296}
297static PyObject*
298pure_purify_get_pool_id(PyObject *self, PyObject *args)
299{
300 return call_intasaddr_function(purify_get_pool_id, self, args);
301}
302static PyObject*
303pure_purify_set_user_data(PyObject *self, PyObject *args)
304{
305 long memrep;
306 long datarep;
307
308 if (!PyArg_ParseTuple(args, "ll:purify_set_user_data", &memrep, &datarep))
309 return NULL;
310
311 purify_set_user_data((char*)memrep, (void*)datarep);
312 Py_INCREF(Py_None);
313 return Py_None;
314}
315static PyObject*
316pure_purify_get_user_data(PyObject *self, PyObject *args)
317{
318 /* can't use call_intasaddr_function() since purify_get_user_data()
319 * returns a void*
320 */
321 long memrep;
322 void* data;
323
324 if (!PyArg_ParseTuple(args, "l:purify_get_user_data", &memrep))
325 return NULL;
326
327 data = purify_get_user_data((char*)memrep);
328 return Py_BuildValue("l", (long)data);
329}
330
331
332
333/* this global variable is shared by both mapping functions:
334 * pure_purify_map_pool() and pure_purify_map_pool_id(). Since they cache
335 * this variable it should be safe in the face of recursion or cross
336 * calling.
337 *
338 * Further note that the prototype for the callback function is wrong in
339 * the Purify manual. The manual says the function takes a single char*,
340 * but the header file says it takes an additional int and void*. I have
341 * no idea what these are for!
342 */
343static PyObject* MapCallable = NULL;
344
345static void
346map_pool_callback(char* mem, int user_size, void *user_aux_data)
347{
348 long memrep = (long)mem;
349 long user_aux_data_rep = (long)user_aux_data;
350 PyObject* result;
351 PyObject* memobj = Py_BuildValue("lil", memrep, user_size,
352 user_aux_data_rep);
353
354 if (memobj == NULL)
355 return;
356
357 result = PyEval_CallObject(MapCallable, memobj);
358 Py_DECREF(result);
359 Py_DECREF(memobj);
360}
361
362static PyObject*
363pure_purify_map_pool(PyObject *self, PyObject *args)
364{
365 /* cache global variable in case of recursion */
366 PyObject* saved_callable = MapCallable;
367 PyObject* arg_callable;
368 int id;
369
370 if (!PyArg_ParseTuple(args, "iO:purify_map_pool", &id, &arg_callable))
371 return NULL;
372
373 if (!PyCallable_Check(arg_callable)) {
374 PyErr_SetString(PyExc_TypeError,
375 "Second argument must be callable");
376 return NULL;
377 }
378 MapCallable = arg_callable;
379 purify_map_pool(id, map_pool_callback);
380 MapCallable = saved_callable;
381
382 Py_INCREF(Py_None);
383 return Py_None;
384}
385
386static void
387PurifyMapPoolIdCallback(int id)
388{
389 PyObject* result;
390 PyObject* intobj = Py_BuildValue("i", id);
391
392 if (intobj == NULL)
393 return;
394
395 result = PyEval_CallObject(MapCallable, intobj);
396 Py_DECREF(result);
397 Py_DECREF(intobj);
398}
399
400static PyObject*
401pure_purify_map_pool_id(PyObject *self, PyObject *args)
402{
403 /* cache global variable in case of recursion */
404 PyObject* saved_callable = MapCallable;
405 PyObject* arg_callable;
406
407 if (!PyArg_ParseTuple(args, "O:purify_map_pool_id", &arg_callable))
408 return NULL;
409
410 if (!PyCallable_Check(arg_callable)) {
411 PyErr_SetString(PyExc_TypeError, "Argument must be callable.");
412 return NULL;
413 }
414
415 MapCallable = arg_callable;
416 purify_map_pool_id(PurifyMapPoolIdCallback);
417 MapCallable = saved_callable;
418
419 Py_INCREF(Py_None);
420 return Py_None;
421}
422
423
424
425
426static PyObject*
427pure_purify_new_messages(PyObject *self, PyObject *args)
428{
429 return call_voidarg_function(purify_new_messages, self, args);
430}
431static PyObject*
432pure_purify_all_messages(PyObject *self, PyObject *args)
433{
434 return call_voidarg_function(purify_all_messages, self, args);
435}
436static PyObject*
437pure_purify_clear_messages(PyObject *self, PyObject *args)
438{
439 return call_voidarg_function(purify_clear_messages, self, args);
440}
441static PyObject*
442pure_purify_clear_new_messages(PyObject *self, PyObject *args)
443{
444 return call_voidarg_function(purify_clear_new_messages, self, args);
445}
446static PyObject*
447pure_purify_start_batch(PyObject *self, PyObject *args)
448{
449 return call_voidarg_function(purify_start_batch, self, args);
450}
451static PyObject*
452pure_purify_start_batch_show_first(PyObject *self, PyObject *args)
453{
454 return call_voidarg_function(purify_start_batch_show_first,
455 self, args);
456}
457static PyObject*
458pure_purify_stop_batch(PyObject *self, PyObject *args)
459{
460 return call_voidarg_function(purify_stop_batch, self, args);
461}
462static PyObject*
463pure_purify_name_thread(PyObject *self, PyObject *args)
464{
465 /* can't strictly use call_stringarg_function since
466 * purify_name_thread takes a const char*, not a char*
467 */
468 int status;
469 char* stringarg;
470
471 if (!PyArg_ParseTuple(args, "s:purify_name_thread", &stringarg))
472 return NULL;
473
474 status = purify_name_thread(stringarg);
475 return Py_BuildValue("i", status);
476}
477static PyObject*
478pure_purify_watch(PyObject *self, PyObject *args)
479{
480 return call_intasaddr_function(purify_watch, self, args);
481}
482static PyObject*
483pure_purify_watch_1(PyObject *self, PyObject *args)
484{
485 return call_intasaddr_function(purify_watch_1, self, args);
486}
487static PyObject*
488pure_purify_watch_2(PyObject *self, PyObject *args)
489{
490 return call_intasaddr_function(purify_watch_2, self, args);
491}
492static PyObject*
493pure_purify_watch_4(PyObject *self, PyObject *args)
494{
495 return call_intasaddr_function(purify_watch_4, self, args);
496}
497static PyObject*
498pure_purify_watch_8(PyObject *self, PyObject *args)
499{
500 return call_intasaddr_function(purify_watch_8, self, args);
501}
502static PyObject*
503pure_purify_watch_w_1(PyObject *self, PyObject *args)
504{
505 return call_intasaddr_function(purify_watch_w_1, self, args);
506}
507static PyObject*
508pure_purify_watch_w_2(PyObject *self, PyObject *args)
509{
510 return call_intasaddr_function(purify_watch_w_2, self, args);
511}
512static PyObject*
513pure_purify_watch_w_4(PyObject *self, PyObject *args)
514{
515 return call_intasaddr_function(purify_watch_w_4, self, args);
516}
517static PyObject*
518pure_purify_watch_w_8(PyObject *self, PyObject *args)
519{
520 return call_intasaddr_function(purify_watch_w_8, self, args);
521}
522static PyObject*
523pure_purify_watch_r_1(PyObject *self, PyObject *args)
524{
525 return call_intasaddr_function(purify_watch_r_1, self, args);
526}
527static PyObject*
528pure_purify_watch_r_2(PyObject *self, PyObject *args)
529{
530 return call_intasaddr_function(purify_watch_r_2, self, args);
531}
532static PyObject*
533pure_purify_watch_r_4(PyObject *self, PyObject *args)
534{
535 return call_intasaddr_function(purify_watch_r_4, self, args);
536}
537static PyObject*
538pure_purify_watch_r_8(PyObject *self, PyObject *args)
539{
540 return call_intasaddr_function(purify_watch_r_8, self, args);
541}
542static PyObject*
543pure_purify_watch_rw_1(PyObject *self, PyObject *args)
544{
545 return call_intasaddr_function(purify_watch_rw_1, self, args);
546}
547static PyObject*
548pure_purify_watch_rw_2(PyObject *self, PyObject *args)
549{
550 return call_intasaddr_function(purify_watch_rw_2, self, args);
551}
552static PyObject*
553pure_purify_watch_rw_4(PyObject *self, PyObject *args)
554{
555 return call_intasaddr_function(purify_watch_rw_4, self, args);
556}
557static PyObject*
558pure_purify_watch_rw_8(PyObject *self, PyObject *args)
559{
560 return call_intasaddr_function(purify_watch_rw_8, self, args);
561}
562
563static PyObject*
564pure_purify_watch_n(PyObject *self, PyObject *args)
565{
566 long addrrep;
567 unsigned int size;
568 char* type;
569 int status;
570
571 if (!PyArg_ParseTuple(args, "lis:purify_watch_n", &addrrep, &size, &type))
572 return NULL;
573
574 status = purify_watch_n((char*)addrrep, size, type);
575 return Py_BuildValue("i", status);
576}
577
578static PyObject*
579pure_purify_watch_info(PyObject *self, PyObject *args)
580{
581 return call_voidarg_function(purify_watch_info, self, args);
582}
583
584static PyObject*
585pure_purify_watch_remove(PyObject *self, PyObject *args)
586{
587 int watchno;
588 int status;
589
590 if (!PyArg_ParseTuple(args, "i:purify_watch_remove", &watchno))
591 return NULL;
592
593 status = purify_watch_remove(watchno);
594 return Py_BuildValue("i", status);
595}
596
597static PyObject*
598pure_purify_watch_remove_all(PyObject *self, PyObject *args)
599{
600 return call_voidarg_function(purify_watch_remove_all, self, args);
601}
602static PyObject*
603pure_purify_describe(PyObject *self, PyObject *args)
604{
605 long addrrep;
606 char* rtn;
607
608 if (!PyArg_ParseTuple(args, "l:purify_describe", &addrrep))
609 return NULL;
610
611 rtn = purify_describe((char*)addrrep);
612 return Py_BuildValue("l", (long)rtn);
613}
614
615static PyObject*
616pure_purify_what_colors(PyObject *self, PyObject *args)
617{
618 long addrrep;
619 unsigned int size;
620 int status;
621
622 if (!PyArg_ParseTuple(args, "li:purify_what_colors", &addrrep, &size))
623 return NULL;
624
625 status = purify_what_colors((char*)addrrep, size);
626 return Py_BuildValue("i", status);
627}
628
629static PyObject*
630pure_purify_is_running(PyObject *self, PyObject *args)
631{
632 return call_voidarg_function(purify_is_running, self, args);
633}
634
635static PyObject*
636pure_purify_assert_is_readable(PyObject *self, PyObject *args)
637{
638 return call_stringandint_function(purify_assert_is_readable,
639 self, args);
640}
641static PyObject*
642pure_purify_assert_is_writable(PyObject *self, PyObject *args)
643{
644 return call_stringandint_function(purify_assert_is_writable,
645 self, args);
646}
647
648#if HAS_PURIFY_EXIT
649
650/* I wish I could include this, but I can't. See the notes at the top of
651 * the file.
652 */
653
654static PyObject*
655pure_purify_exit(PyObject *self, PyObject *args)
656{
657 int status;
658
659 if (!PyArg_ParseTuple(args, "i:purify_exit", &status))
660 return NULL;
661
662 /* purify_exit doesn't always act like exit(). See the manual */
663 purify_exit(status);
664 Py_INCREF(Py_None);
665 return Py_None;
666}
667#endif /* HAS_PURIFY_EXIT */
668
669#endif /* PURIFY_H */
670
671
672
673
674/* Quantify functions
675 *
676 * N.B. Some of these functions are only described in the quantify.h file,
677 * not in the version of the hardcopy manual that I had. If you're not
678 * sure what some of these do, check the header file, it is documented
679 * fairly well.
680 *
681 * None of the custom dynamic loader functions are exported.
682 *
683 */
684#ifdef QUANTIFY_H
685
686static PyObject*
687pure_quantify_is_running(PyObject *self, PyObject *args)
688{
689 return call_voidarg_function(quantify_is_running, self, args);
690}
691static PyObject*
692pure_quantify_help(PyObject *self, PyObject *args)
693{
694 return call_voidarg_function(quantify_help, self, args);
695}
696static PyObject*
697pure_quantify_print_recording_state(PyObject *self, PyObject *args)
698{
699 return call_voidarg_function(quantify_print_recording_state,
700 self, args);
701}
702static PyObject*
703pure_quantify_start_recording_data(PyObject *self, PyObject *args)
704{
705 return call_voidarg_function(quantify_start_recording_data,
706 self, args);
707}
708static PyObject*
709pure_quantify_stop_recording_data(PyObject *self, PyObject *args)
710{
711 return call_voidarg_function(quantify_stop_recording_data, self, args);
712}
713static PyObject*
714pure_quantify_is_recording_data(PyObject *self, PyObject *args)
715{
716 return call_voidarg_function(quantify_is_recording_data, self, args);
717}
718static PyObject*
719pure_quantify_start_recording_system_calls(PyObject *self, PyObject *args)
720{
721 return call_voidarg_function(quantify_start_recording_system_calls,
722 self, args);
723}
724static PyObject*
725pure_quantify_stop_recording_system_calls(PyObject *self, PyObject *args)
726{
727 return call_voidarg_function(quantify_stop_recording_system_calls,
728 self, args);
729}
730static PyObject*
731pure_quantify_is_recording_system_calls(PyObject *self, PyObject *args)
732{
733 return call_voidarg_function(quantify_is_recording_system_calls,
734 self, args);
735}
736static PyObject*
737pure_quantify_start_recording_system_call(PyObject *self, PyObject *args)
738{
739 return call_stringorint_function(quantify_start_recording_system_call,
740 self, args);
741}
742static PyObject*
743pure_quantify_stop_recording_system_call(PyObject *self, PyObject *args)
744{
745 return call_stringorint_function(quantify_stop_recording_system_call,
746 self, args);
747}
748static PyObject*
749pure_quantify_is_recording_system_call(PyObject *self, PyObject *args)
750{
751 return call_stringorint_function(quantify_is_recording_system_call,
752 self, args);
753}
754static PyObject*
755pure_quantify_start_recording_dynamic_library_data(PyObject *self, PyObject *args)
756{
757 return call_voidarg_function(
758 quantify_start_recording_dynamic_library_data,
759 self, args);
760}
761static PyObject*
762pure_quantify_stop_recording_dynamic_library_data(PyObject *self, PyObject *args)
763{
764 return call_voidarg_function(
765 quantify_stop_recording_dynamic_library_data,
766 self, args);
767}
768static PyObject*
769pure_quantify_is_recording_dynamic_library_data(PyObject *self, PyObject *args)
770{
771 return call_voidarg_function(
772 quantify_is_recording_dynamic_library_data,
773 self, args);
774}
775static PyObject*
776pure_quantify_start_recording_register_window_traps(PyObject *self, PyObject *args)
777{
778 return call_voidarg_function(
779 quantify_start_recording_register_window_traps,
780 self, args);
781}
782static PyObject*
783pure_quantify_stop_recording_register_window_traps(PyObject *self, PyObject *args)
784{
785 return call_voidarg_function(
786 quantify_stop_recording_register_window_traps,
787 self, args);
788}
789static PyObject*
790pure_quantify_is_recording_register_window_traps(PyObject *self, PyObject *args)
791{
792 return call_voidarg_function(
793 quantify_is_recording_register_window_traps,
794 self, args);
795}
796static PyObject*
797pure_quantify_disable_recording_data(PyObject *self, PyObject *args)
798{
799 return call_voidarg_function(quantify_disable_recording_data,
800 self, args);
801}
802static PyObject*
803pure_quantify_clear_data(PyObject *self, PyObject *args)
804{
805 return call_voidarg_function(quantify_clear_data, self, args);
806}
807static PyObject*
808pure_quantify_save_data(PyObject *self, PyObject *args)
809{
810 return call_voidarg_function(quantify_save_data, self, args);
811}
812static PyObject*
813pure_quantify_save_data_to_file(PyObject *self, PyObject *args)
814{
815 return call_stringarg_function(quantify_save_data_to_file, self, args);
816}
817static PyObject*
818pure_quantify_add_annotation(PyObject *self, PyObject *args)
819{
820 return call_stringarg_function(quantify_add_annotation, self, args);
821}
822
823#endif /* QUANTIFY_H */
824
825
826
827
828/* external interface
829 */
830static struct PyMethodDef
831pure_methods[] = {
832#ifdef COMMON_PURE_FUNCTIONS
833 {"pure_logfile_printf", pure_pure_logfile_printf, METH_VARARGS},
834 {"pure_printf", pure_pure_printf, METH_VARARGS},
835 {"pure_printf_with_banner", pure_pure_printf_with_banner, METH_VARARGS},
836#endif /* COMMON_PURE_FUNCTIONS */
837#ifdef PURIFY_H
838 {"purify_all_inuse", pure_purify_all_inuse, METH_VARARGS},
839 {"purify_all_leaks", pure_purify_all_leaks, METH_VARARGS},
840 {"purify_new_inuse", pure_purify_new_inuse, METH_VARARGS},
841 {"purify_new_leaks", pure_purify_new_leaks, METH_VARARGS},
842 {"purify_clear_inuse", pure_purify_clear_inuse, METH_VARARGS},
843 {"purify_clear_leaks", pure_purify_clear_leaks, METH_VARARGS},
844 {"purify_all_fds_inuse", pure_purify_all_fds_inuse, METH_VARARGS},
845 {"purify_new_fds_inuse", pure_purify_new_fds_inuse, METH_VARARGS},
846 /* see purify.h */
847 {"purify_logfile_printf", pure_pure_logfile_printf, METH_VARARGS},
848 {"purify_printf", pure_pure_printf, METH_VARARGS},
849 {"purify_printf_with_banner", pure_pure_printf_with_banner, METH_VARARGS},
850 /**/
851 {"purify_printf_with_call_chain", pure_purify_printf_with_call_chain, METH_VARARGS},
852 {"purify_set_pool_id", pure_purify_set_pool_id, METH_VARARGS},
853 {"purify_get_pool_id", pure_purify_get_pool_id, METH_VARARGS},
854 {"purify_set_user_data", pure_purify_set_user_data, METH_VARARGS},
855 {"purify_get_user_data", pure_purify_get_user_data, METH_VARARGS},
856 {"purify_map_pool", pure_purify_map_pool, METH_VARARGS},
857 {"purify_map_pool_id", pure_purify_map_pool_id, METH_VARARGS},
858 {"purify_new_messages", pure_purify_new_messages, METH_VARARGS},
859 {"purify_all_messages", pure_purify_all_messages, METH_VARARGS},
860 {"purify_clear_messages", pure_purify_clear_messages, METH_VARARGS},
861 {"purify_clear_new_messages", pure_purify_clear_new_messages, METH_VARARGS},
862 {"purify_start_batch", pure_purify_start_batch, METH_VARARGS},
863 {"purify_start_batch_show_first", pure_purify_start_batch_show_first, METH_VARARGS},
864 {"purify_stop_batch", pure_purify_stop_batch, METH_VARARGS},
865 {"purify_name_thread", pure_purify_name_thread, METH_VARARGS},
866 {"purify_watch", pure_purify_watch, METH_VARARGS},
867 {"purify_watch_1", pure_purify_watch_1, METH_VARARGS},
868 {"purify_watch_2", pure_purify_watch_2, METH_VARARGS},
869 {"purify_watch_4", pure_purify_watch_4, METH_VARARGS},
870 {"purify_watch_8", pure_purify_watch_8, METH_VARARGS},
871 {"purify_watch_w_1", pure_purify_watch_w_1, METH_VARARGS},
872 {"purify_watch_w_2", pure_purify_watch_w_2, METH_VARARGS},
873 {"purify_watch_w_4", pure_purify_watch_w_4, METH_VARARGS},
874 {"purify_watch_w_8", pure_purify_watch_w_8, METH_VARARGS},
875 {"purify_watch_r_1", pure_purify_watch_r_1, METH_VARARGS},
876 {"purify_watch_r_2", pure_purify_watch_r_2, METH_VARARGS},
877 {"purify_watch_r_4", pure_purify_watch_r_4, METH_VARARGS},
878 {"purify_watch_r_8", pure_purify_watch_r_8, METH_VARARGS},
879 {"purify_watch_rw_1", pure_purify_watch_rw_1, METH_VARARGS},
880 {"purify_watch_rw_2", pure_purify_watch_rw_2, METH_VARARGS},
881 {"purify_watch_rw_4", pure_purify_watch_rw_4, METH_VARARGS},
882 {"purify_watch_rw_8", pure_purify_watch_rw_8, METH_VARARGS},
883 {"purify_watch_n", pure_purify_watch_n, METH_VARARGS},
884 {"purify_watch_info", pure_purify_watch_info, METH_VARARGS},
885 {"purify_watch_remove", pure_purify_watch_remove, METH_VARARGS},
886 {"purify_watch_remove_all", pure_purify_watch_remove_all, METH_VARARGS},
887 {"purify_describe", pure_purify_describe, METH_VARARGS},
888 {"purify_what_colors", pure_purify_what_colors, METH_VARARGS},
889 {"purify_is_running", pure_purify_is_running, METH_VARARGS},
890 {"purify_assert_is_readable", pure_purify_assert_is_readable, METH_VARARGS},
891 {"purify_assert_is_writable", pure_purify_assert_is_writable, METH_VARARGS},
892#if HAS_PURIFY_EXIT
893 /* I wish I could include this, but I can't. See the notes at the
894 * top of the file.
895 */
896 {"purify_exit", pure_purify_exit, METH_VARARGS},
897#endif /* HAS_PURIFY_EXIT */
898#endif /* PURIFY_H */
899#ifdef QUANTIFY_H
900 {"quantify_is_running", pure_quantify_is_running, METH_VARARGS},
901 {"quantify_help", pure_quantify_help, METH_VARARGS},
902 {"quantify_print_recording_state", pure_quantify_print_recording_state, METH_VARARGS},
903 {"quantify_start_recording_data", pure_quantify_start_recording_data, METH_VARARGS},
904 {"quantify_stop_recording_data", pure_quantify_stop_recording_data, METH_VARARGS},
905 {"quantify_is_recording_data", pure_quantify_is_recording_data, METH_VARARGS},
906 {"quantify_start_recording_system_calls",
907 pure_quantify_start_recording_system_calls, METH_VARARGS},
908 {"quantify_stop_recording_system_calls",
909 pure_quantify_stop_recording_system_calls, METH_VARARGS},
910 {"quantify_is_recording_system_calls",
911 pure_quantify_is_recording_system_calls, METH_VARARGS},
912 {"quantify_start_recording_system_call",
913 pure_quantify_start_recording_system_call, METH_VARARGS},
914 {"quantify_stop_recording_system_call",
915 pure_quantify_stop_recording_system_call, METH_VARARGS},
916 {"quantify_is_recording_system_call",
917 pure_quantify_is_recording_system_call, METH_VARARGS},
918 {"quantify_start_recording_dynamic_library_data",
919 pure_quantify_start_recording_dynamic_library_data, METH_VARARGS},
920 {"quantify_stop_recording_dynamic_library_data",
921 pure_quantify_stop_recording_dynamic_library_data, METH_VARARGS},
922 {"quantify_is_recording_dynamic_library_data",
923 pure_quantify_is_recording_dynamic_library_data, METH_VARARGS},
924 {"quantify_start_recording_register_window_traps",
925 pure_quantify_start_recording_register_window_traps, METH_VARARGS},
926 {"quantify_stop_recording_register_window_traps",
927 pure_quantify_stop_recording_register_window_traps, METH_VARARGS},
928 {"quantify_is_recording_register_window_traps",
929 pure_quantify_is_recording_register_window_traps, METH_VARARGS},
930 {"quantify_disable_recording_data",
931 pure_quantify_disable_recording_data, METH_VARARGS},
932 {"quantify_clear_data", pure_quantify_clear_data, METH_VARARGS},
933 {"quantify_save_data", pure_quantify_save_data, METH_VARARGS},
934 {"quantify_save_data_to_file", pure_quantify_save_data_to_file, METH_VARARGS},
935 {"quantify_add_annotation", pure_quantify_add_annotation, METH_VARARGS},
936#endif /* QUANTIFY_H */
937 {NULL, NULL} /* sentinel */
938};
939
940
941
942
943static void
944ins(d, name, val)
945 PyObject *d;
946 char* name;
947 long val;
948{
949 PyObject *v = PyInt_FromLong(val);
950 if (v) {
951 (void)PyDict_SetItemString(d, name, v);
952 Py_DECREF(v);
953 }
954}
955
956
957void
958initpure()
959{
960 PyObject *m, *d;
961
962 m = Py_InitModule("pure", pure_methods);
963 if (m == NULL)
964 return;
965 d = PyModule_GetDict(m);
966
967 /* this is bogus because we should be able to find this information
968 * out from the header files. Pure's current versions don't
969 * include this information!
970 */
971#ifdef PURE_PURIFY_VERSION
972 ins(d, "PURIFY_VERSION", PURE_PURIFY_VERSION);
973#else
974 PyDict_SetItemString(d, "PURIFY_VERSION", Py_None);
975#endif
976
977 /* these aren't terribly useful because purify_exit() isn't
978 * exported correctly. See the note at the top of the file.
979 */
980#ifdef PURIFY_EXIT_ERRORS
981 ins(d, "PURIFY_EXIT_ERRORS", PURIFY_EXIT_ERRORS);
982#endif
983#ifdef PURIFY_EXIT_LEAKS
984 ins(d, "PURIFY_EXIT_LEAKS", PURIFY_EXIT_LEAKS);
985#endif
986#ifdef PURIFY_EXIT_PLEAKS
987 ins(d, "PURIFY_EXIT_PLEAKS", PURIFY_EXIT_PLEAKS);
988#endif
989
990
991#ifdef PURE_QUANTIFY_VERSION
992 ins(d, "QUANTIFY_VERSION", PURE_QUANTIFY_VERSION);
993#else
994 PyDict_SetItemString(d, "QUANTIFY_VERSION", Py_None);
995#endif
996}
Note: See TracBrowser for help on using the repository browser.