[Patches] Extension building on Win32 using Gnu C
Rene Liebscher
R.Liebscher@gmx.de
Wed, 14 Jun 2000 13:41:24 +0200
This is a multi-part message in MIME format.
--------------149A4E4C425D8C885F0B8B92
Content-Type: text/plain; charset=us-ascii
Content-Transfer-Encoding: 7bit
Greg Ward wrote:
>
> > --- python.patched/dist/src/Include/object.h Tue May 30 10:34:33 2000
> [...]
> > --- 107,120 ----
> > PyObject_HEAD \
> > int ob_size; /* Number of items in variable part */
> >
> > ! typedef DL_CLASSIMPORT_BEG struct _object {
> > PyObject_HEAD
> > ! } DL_CLASSIMPORT_END PyObject;
> >
> >
> > + typedef DL_CLASSIMPORT_BEG struct {
> > + PyObject_VAR_HEAD
> > + } DL_CLASSIMPORT_END PyVarObject;
>
> This strikes me as really weird style. Do those macros really *have* to
> be wormed into the typedefs in that way? Isn't there a cleaner way to
> do it?
The Gnu-C compilers need these imports, there are two ways to do so
struct name { ... } __declspec(dllimport);
or
struct __declspec(dllimport) name { ... };
Read also
http://gcc.gnu.org/onlinedocs/gcc_4.html#SEC95 (paragraphs 3 and 4)
__declspec is another name for __attribute
They don't mention dllimport and types in the same context, I don't know
why.
(However, MS Visual C++ uses the same import statements for imports of
classes from dll's. egcs 1.1.x uses __declspec() in MS compatible way.)
In typedefs you could have unnamed structs, so I prefer the second.
Even if it seems to work to have such a definition:
typedef struct __declspec(import) { ... } name;
If you don't have these imports in C-mode you get warnings and in C++
mode the compiler chrashs.
Perhaps it would be useful to reduce it to a
"#define DL_IMPORT_TYPE __decspec(dllimport)"
instead of these two. (The attached patch realizes this idea,
if you don't like the name replace it directly in the patch file.)
( I found this DL_CLASSIMPORT stuff (the only part of the patch
I didn't found for myself) at the following website
http://starship.python.net/crew/kernr/mingw32/Notes.html
and I took it almost unchanged.)
> And do these macros have to be used in extensions as well? Eg. if foo.c
> supplies an extension foo, so is compiled/linked to foo.pyd (a DLL in
> disguise), do I have to scatter foo.c with DL_CLASSIMPORT_{BEG,END} tags
> to make it compile with Cygwin?
No, you only need it, if these types are used in the interface of a dll
you want to use (in this case you want to use python??.dll or should I
better say, link against its import library libpython??.a )
(You probably had to use it in your file foo.h if you
want let other people use your extension dll on a direct way. Which also
means these people would need to link their modules against your dll.)
kind regards
Rene Liebscher
--------------149A4E4C425D8C885F0B8B92
Content-Type: text/plain; charset=us-ascii;
name="python_new.patch"
Content-Transfer-Encoding: 7bit
Content-Disposition: inline;
filename="python_new.patch"
diff -BcrN --minimal python/dist/src/Include/Python.h python.patched/dist/src/Include/Python.h
*** python/dist/src/Include/Python.h Sun May 28 22:29:48 2000
--- python.patched/dist/src/Include/Python.h Wed Jun 14 12:45:18 2000
***************
*** 46,51 ****
--- 46,59 ----
#define DL_EXPORT(RTYPE) RTYPE
#endif
+ /* The next is used by the Gnu C-compilers on Win32, for all others
+ it will be defined as empty */
+ /* Definition of every type, variables of which may be imported from DLL,
+ must be imported too */
+ #ifndef DL_IMPORT_TYPE
+ #define DL_IMPORT_TYPE
+ #endif
+
#ifdef SYMANTEC__CFM68K__
#define UsingSharedLibs
#endif
diff -BcrN --minimal python/dist/src/Include/object.h python.patched/dist/src/Include/object.h
*** python/dist/src/Include/object.h Mon Apr 24 17:40:45 2000
--- python.patched/dist/src/Include/object.h Wed Jun 14 12:45:18 2000
***************
*** 109,120 ****
typedef struct _object {
PyObject_HEAD
! } PyObject;
typedef struct {
PyObject_VAR_HEAD
- } PyVarObject;
/*
Type objects contain a string containing the type name (to help somewhat
--- 109,120 ----
typedef struct _object {
PyObject_HEAD
! } DL_IMPORT_TYPE PyObject;
typedef struct {
PyObject_VAR_HEAD
+ } DL_IMPORT_TYPE PyVarObject;
/*
Type objects contain a string containing the type name (to help somewhat
***************
*** 170,176 ****
unaryfunc nb_float;
unaryfunc nb_oct;
unaryfunc nb_hex;
! } PyNumberMethods;
typedef struct {
inquiry sq_length;
--- 170,176 ----
unaryfunc nb_float;
unaryfunc nb_oct;
unaryfunc nb_hex;
! } DL_IMPORT_TYPE PyNumberMethods;
typedef struct {
inquiry sq_length;
***************
*** 181,200 ****
intobjargproc sq_ass_item;
intintobjargproc sq_ass_slice;
objobjproc sq_contains;
! } PySequenceMethods;
typedef struct {
inquiry mp_length;
binaryfunc mp_subscript;
objobjargproc mp_ass_subscript;
! } PyMappingMethods;
typedef struct {
getreadbufferproc bf_getreadbuffer;
getwritebufferproc bf_getwritebuffer;
getsegcountproc bf_getsegcount;
getcharbufferproc bf_getcharbuffer;
! } PyBufferProcs;
typedef void (*destructor) Py_PROTO((PyObject *));
--- 181,200 ----
intobjargproc sq_ass_item;
intintobjargproc sq_ass_slice;
objobjproc sq_contains;
! } DL_IMPORT_TYPE PySequenceMethods;
typedef struct {
inquiry mp_length;
binaryfunc mp_subscript;
objobjargproc mp_ass_subscript;
! } DL_IMPORT_TYPE PyMappingMethods;
typedef struct {
getreadbufferproc bf_getreadbuffer;
getwritebufferproc bf_getwritebuffer;
getsegcountproc bf_getsegcount;
getcharbufferproc bf_getcharbuffer;
! } DL_IMPORT_TYPE PyBufferProcs;
typedef void (*destructor) Py_PROTO((PyObject *));
***************
*** 256,262 ****
int tp_maxalloc;
struct _typeobject *tp_next;
#endif
! } PyTypeObject;
extern DL_IMPORT(PyTypeObject) PyType_Type; /* The type of type objects */
--- 256,262 ----
int tp_maxalloc;
struct _typeobject *tp_next;
#endif
! } DL_IMPORT_TYPE PyTypeObject;
extern DL_IMPORT(PyTypeObject) PyType_Type; /* The type of type objects */
diff -BcrN --minimal python/dist/src/PC/config.h python.patched/dist/src/PC/config.h
*** python/dist/src/PC/config.h Wed May 10 15:25:32 2000
--- python.patched/dist/src/PC/config.h Wed Jun 14 12:45:18 2000
***************
*** 42,47 ****
--- 42,78 ----
#define PREFIX ""
#define EXEC_PREFIX ""
+ /* egcs/gnu-win32 defines __GNUC__ and _WIN32 */
+
+ #if defined(__GNUC__) && defined(_WIN32)
+ #define NT /* NT is obsolete - please use MS_WIN32 instead */
+ #define MS_WIN32
+ #define MS_WINDOWS
+ #define HAVE_CLOCK
+ #define HAVE_STRFTIME
+ #define HAVE_STRERROR
+ #define NT_THREADS
+ #define WITH_THREAD
+ #define WORD_BIT 32
+ #define HAVE_LONG_LONG 1
+ #define LONG_LONG long long
+ #define PYTHONPATH ".\\DLLs;.\\lib;.\\lib\\plat-win;.\\lib\\lib-tk"
+
+ #ifndef MS_NO_COREDLL
+ #define MS_COREDLL /* Python core is in a DLL */
+ #ifndef USE_DL_EXPORT
+ #define USE_DL_IMPORT
+ #endif /* !USE_DL_EXPORT */
+ #endif /* !MS_NO_COREDLL */
+
+ #ifdef USE_DL_IMPORT
+ #define DL_IMPORT(sym) __declspec(dllimport) sym
+ /* Definition of every type, variables of which may be imported from DLL,
+ must be imported too */
+ #define DL_IMPORT_TYPE __declspec(dllimport)
+ #endif /* USE_DL_IMPORT */
+ #endif /* (defined(__GNUC__) && defined(_WIN32)) */
+
/* Microsoft C defines _MSC_VER */
#ifdef _MSC_VER
--------------149A4E4C425D8C885F0B8B92--