]>
git.saurik.com Git - wxWidgets.git/blob - wxPython/wxSWIG/SWIG/types.cxx
1 /*******************************************************************************
2 * Simplified Wrapper and Interface Generator (SWIG)
4 * Author : David Beazley
6 * Department of Computer Science
7 * University of Chicago
10 * beazley@cs.uchicago.edu
12 * Please read the file LICENSE for the copyright and terms by which SWIG
13 * can be used and distributed.
14 *******************************************************************************/
16 /***********************************************************************
21 * This file contains functions for dealing with datatypes. This
22 * is a combination of the file typedef.cc (now obsolete) and functions
23 * that used to be in the swig.h header.
25 ***********************************************************************/
29 // -------------------------------------------------------------------
30 // class DataType member functions.
31 // -------------------------------------------------------------------
33 DataType::DataType() {
45 // Create a data type only from the type code (used to form constants)
47 DataType::DataType(int t
) {
52 case T_INT
: case T_SINT
:
56 strcpy(name
,"unsigned int");
58 case T_SHORT
: case T_SSHORT
:
62 strcpy(name
,"unsigned short");
64 case T_LONG
: case T_SLONG
:
68 strcpy(name
,"unsigned long");
71 strcpy(name
, "float");
74 strcpy(name
, "double");
76 case T_CHAR
: case T_SCHAR
:
80 strcpy(name
,"unsigned char");
89 strcpy(name
,"UNKNOWN");
102 DataType::DataType(DataType
*t
) {
104 strcpy(name
,t
->name
);
105 is_pointer
= t
->is_pointer
;
106 implicit_ptr
= t
->implicit_ptr
;
107 qualifier
= copy_string(t
->qualifier
);
108 is_reference
= t
->is_reference
;
110 arraystr
= copy_string(t
->arraystr
);
114 DataType::~DataType() {
115 if (qualifier
) delete qualifier
;
116 if (arraystr
) delete arraystr
;
119 // --------------------------------------------------------------------
120 // DataType::primitive()
122 // Turns a datatype into its bare-bones primitive type. Rarely used,
123 // but sometimes used for typemaps. Permanently alters the datatype!
124 // --------------------------------------------------------------------
126 void DataType::primitive() {
131 case T_INT
: case T_SINT
:
134 case T_SHORT
: case T_SSHORT
:
135 strcpy(name
,"short");
137 case T_LONG
: case T_SLONG
:
144 strcpy(name
,"signed char");
147 strcpy(name
,"unsigned int");
150 strcpy(name
,"unsigned short");
153 strcpy(name
,"unsigned long");
156 strcpy(name
,"unsigned char");
159 strcpy(name
,"float");
162 strcpy(name
,"double");
171 strcpy(name
,"UNKNOWN");
175 // if (!((is_pointer == 1) && (type == T_CHAR))) {
177 // strcpy(name,"POINTER");
181 implicit_ptr
= 0; // Gets rid of typedef'd pointers
183 // Ditch qualifiers (const, volatile, etc...)
193 // --------------------------------------------------------------------
194 // char *print_type()
196 // Print the datatype, but without qualifiers (ie. const, volatile)
197 // Returns a string containing the result.
199 // If a datatype is marked as an implicit ptr it means that is_pointer
200 // is at least one, but we don't print '*'.
202 // If the type status is STAT_REPLACETYPE, it means that we can't
203 // use this type as a valid type. We'll substitute it's old name in.
204 // --------------------------------------------------------------------
206 char *DataType::print_type() {
207 static String result
[8];
212 if (status
& STAT_REPLACETYPE
) {
213 t
= new DataType(this);
214 t
->typedef_replace(); // Upgrade type
219 result
[ri
] << t
->name
<< " ";
220 for (int i
= 0; i
< (t
->is_pointer
-t
->implicit_ptr
); i
++)
223 if (status
& STAT_REPLACETYPE
) {
227 return result
[ri
++].get();
231 // --------------------------------------------------------------------
232 // char *print_full()
234 // Prints full type, with qualifiers.
235 // --------------------------------------------------------------------
237 char *DataType::print_full() {
238 static String result
[8];
244 result
[ri
] << qualifier
<< " " << print_type();
246 result
[ri
] << print_type();
248 return result
[ri
++].get();
252 // --------------------------------------------------------------------
253 // char *print_real()
255 // Prints real type, with qualifiers and arrays if necessary.
256 // --------------------------------------------------------------------
258 char *DataType::print_real(char *local
) {
259 static String result
[8];
264 status
= status
& (~STAT_REPLACETYPE
);
267 if (arraystr
) is_pointer
--;
268 result
[ri
] << print_full();
269 if (local
) result
[ri
] << local
;
271 result
[ri
] << arraystr
;
275 return result
[ri
++].get();
278 // --------------------------------------------------------------------
279 // char *print_cast()
281 // Prints a cast. (Basically just a type but with parens added).
282 // --------------------------------------------------------------------
284 char *DataType::print_cast() {
285 static String result
[8];
290 result
[ri
] << "(" << print_type() << ")";
291 return result
[ri
++].get();
295 // --------------------------------------------------------------------
296 // char *print_arraycast()
298 // Prints a cast, but for array datatypes. Super ugly, but necessary
299 // for multidimensional arrays.
300 // --------------------------------------------------------------------
302 char *DataType::print_arraycast() {
303 static String result
[8];
310 if (status
& STAT_REPLACETYPE
) {
311 t
= new DataType(this);
312 t
->typedef_replace(); // Upgrade type
322 if (*c
== '[') ndim
++;
326 // a Multidimensional array. Provide a special cast for it
327 int oldstatus
= status
;
328 t
->status
= t
->status
& (~STAT_REPLACETYPE
);
330 result
[ri
] << "(" << t
->print_type();
332 t
->status
= oldstatus
;
333 result
[ri
] << " (*)";
336 if (*c
== ']') break;
340 result
[ri
] << c
<< ")";
343 if (status
& STAT_REPLACETYPE
) {
346 return result
[ri
++].get();
349 // --------------------------------------------------------------------
350 // char *print_mangle_default()
352 // Prints a mangled version of this datatype. Used for run-time type
353 // checking in order to print out a "language friendly" version (ie. no
354 // spaces and no weird characters).
355 // --------------------------------------------------------------------
357 char *DataType::print_mangle_default() {
358 static String result
[8];
369 if (*c
== ' ') result
[ri
] << '_';
370 else result
[ri
] << *c
;
372 if ((is_pointer
-implicit_ptr
)) result
[ri
] << '_';
373 for (i
= 0; i
< (is_pointer
-implicit_ptr
); i
++)
376 return result
[ri
++].get();
379 // This is kind of ugly but needed for each language to support a
380 // custom name mangling mechanism. (ie. Perl5).
382 char *DataType::print_mangle() {
384 // Call into target language for name mangling.
385 return lang
->type_mangle(this);
388 // --------------------------------------------------------------------
389 // int DataType::array_dimensions()
391 // Returns the number of dimensions in an array or 0 if not an array.
392 // --------------------------------------------------------------------
393 int DataType::array_dimensions() {
397 if (!arraystr
) return 0;
408 // --------------------------------------------------------------------
409 // char *DataType::get_dimension(int n)
411 // Returns a string containing the value specified for dimension n.
412 // --------------------------------------------------------------------
414 char *DataType::get_dimension(int n
) {
419 if (n
>= array_dimensions()) return dim
;
421 // Attemp to locate the right dimension
424 while ((*c
) && (n
>= 0)) {
429 // c is now at start of array dimension
431 while ((*c
) && (*c
!= ']')) {
439 // --------------------------------------------------------------------
440 // char *DataType::get_array()
442 // Returns the array string for a datatype.
443 // --------------------------------------------------------------------
445 char *DataType::get_array() {
449 // --------------------------------------------------------------------
450 // typedef support. This needs to be scoped.
451 // --------------------------------------------------------------------
453 Hash
*DataType::typedef_hash
[MAXSCOPE
];
454 int DataType::scope
= 0; // Current scope
456 static Hash undefined_types
; // Hash table containing undefined datatypes.
458 // -----------------------------------------------------------------------------
459 // int DataType::check_defined()
461 // Checks to see if a datatype is defined. If not, returns -1 and puts an entry
462 // into an internal hash table
463 // -----------------------------------------------------------------------------
465 int DataType::check_defined() {
466 if (type
== T_USER
) {
468 // Type might be in typedef hash. Check for that
471 if (typedef_hash
[s
]->lookup(name
)) return 0;
475 // Nope. Add as an undefined type and continue.
478 st
= copy_string(name
);
479 undefined_types
.add(st
,st
);
485 // -----------------------------------------------------------------------------
486 // void DataType::init_typedef()
492 // Side Effects : Initializes the typedef hash tables
493 // -----------------------------------------------------------------------------
495 void DataType::init_typedef() {
497 for (i
= 0; i
< MAXSCOPE
; i
++)
501 typedef_hash
[scope
] = new Hash
;
504 // --------------------------------------------------------------------
505 // void DataType::typedef_add(char *typename, int mode = 0)
507 // Adds this datatype to the typedef hash table. mode is an optional
508 // flag that can be used to only add the symbol as a typedef, but not
509 // generate any support code for the SWIG typechecker. This is used
510 // for some of the more obscure datatypes like function pointers,
511 // arrays, and enums.
512 // --------------------------------------------------------------------
514 void DataType::typedef_add(char *tname
, int mode
) {
517 void typeeq_addtypedef(char *name
, char *eqname
);
519 // Check to see if this typedef already defined
520 // We only check in the local scope. C++ classes may make typedefs
521 // that shadow global ones.
523 if (typedef_hash
[scope
]->lookup(tname
)) {
524 fprintf(stderr
,"%s : Line %d. Warning. Datatype %s already defined (2nd definition ignored).\n",
525 input_file
, line_number
, tname
);
529 // Make a new datatype that we will place in our hash table
531 nt
= new DataType(this);
532 nt
->implicit_ptr
= (is_pointer
-implicit_ptr
); // Record if mapped type is a pointer
533 nt
->is_pointer
= (is_pointer
-implicit_ptr
); // Adjust pointer value to be correct
534 nt
->typedef_resolve(); // Resolve any other mappings of this type
535 // strcpy(nt->name,tname); // Copy over the new name
537 // Add this type to our hash table
538 typedef_hash
[scope
]->add(tname
,(void *) nt
);
540 // Now add this type mapping to our type-equivalence table
543 if ((type
!= T_VOID
) && (strcmp(name
,tname
) != 0)) {
544 strcpy(t1
.name
,tname
);
545 name2
<< t1
.print_mangle();
546 name1
<< print_mangle();
547 typeeq_addtypedef(name1
,name2
);
548 typeeq_addtypedef(name2
,name1
);
551 // Call into the target language with this typedef
552 lang
->add_typedef(this,tname
);
556 // --------------------------------------------------------------------
557 // void DataType::typedef_resolve(int level = 0)
559 // Checks to see if this datatype is in the typedef hash and
560 // resolves it if necessary. This will check all of the typedef
561 // hash tables we know about.
563 // level is an optional parameter that determines which scope to use.
564 // Usually this is only used with a bare :: operator in a datatype.
566 // The const headache :
568 // Normally SWIG will fail if a const variable is used in a typedef
571 // typedef const char *String;
573 // This is because future occurrences of "String" will be treated like
574 // a char *, but without regard to the "constness". To work around
575 // this problem. The resolve() method checks to see if these original
576 // data type is const. If so, we'll substitute the name of the original
577 // datatype instead. Got it? Whew. In a nutshell, this means that
578 // all future occurrences of "String" will really be "const char *".
579 // --------------------------------------------------------------------
581 void DataType::typedef_resolve(int level
) {
584 int s
= scope
- level
;
587 if ((td
= (DataType
*) typedef_hash
[s
]->lookup(name
))) {
589 is_pointer
+= td
->is_pointer
;
590 implicit_ptr
+= td
->implicit_ptr
;
591 status
= status
| td
->status
;
593 // Check for constness, and replace type name if necessary
596 if (strcmp(td
->qualifier
,"const") == 0) {
597 strcpy(name
,td
->name
);
598 qualifier
= copy_string(td
->qualifier
);
599 implicit_ptr
-= td
->implicit_ptr
;
606 // Not found, do nothing
610 // --------------------------------------------------------------------
611 // void DataType::typedef_replace()
613 // Checks to see if this datatype is in the typedef hash and
614 // replaces it with the hash entry. Only applies to current scope.
615 // --------------------------------------------------------------------
617 void DataType::typedef_replace () {
621 if ((td
= (DataType
*) typedef_hash
[scope
]->lookup(name
))) {
623 is_pointer
= td
->is_pointer
;
624 implicit_ptr
-= td
->implicit_ptr
;
625 strcpy(name
, td
->name
);
631 temp
<< td
->arraystr
;
632 arraystr
= copy_string(temp
);
635 // Not found, do nothing
639 // ---------------------------------------------------------------
640 // int DataType::is_typedef(char *t)
642 // Checks to see whether t is the name of a datatype we know
643 // about. Returns 1 if there's a match, 0 otherwise
644 // ---------------------------------------------------------------
646 int DataType::is_typedef(char *t
) {
649 if (typedef_hash
[s
]->lookup(t
)) return 1;
655 // ---------------------------------------------------------------
656 // void DataType::typedef_updatestatus(int newstatus)
658 // Checks to see if this datatype is in the hash table. If
659 // so, we'll update its status. This is sometimes used with
660 // typemap handling. Only applies to current scope.
661 // ---------------------------------------------------------------
663 void DataType::typedef_updatestatus(int newstatus
) {
666 if ((t
= (DataType
*) typedef_hash
[scope
]->lookup(name
))) {
667 t
->status
= newstatus
;
672 // -----------------------------------------------------------------------------
673 // void DataType::merge_scope(Hash *h)
675 // Copies all of the entries in scope h into the current scope. This is
676 // primarily done with C++ inheritance.
678 // Inputs : Hash table h.
682 // Side Effects : Copies all of the entries in h to current scope.
683 // -----------------------------------------------------------------------------
685 void DataType::merge_scope(Hash
*h
) {
690 // Copy all of the entries in the given hash table to this new one
693 // printf("%s\n", key);
694 t
= (DataType
*) h
->lookup(key
);
695 nt
= new DataType(t
);
696 typedef_hash
[scope
]->add(key
,(void *) nt
);
702 // -----------------------------------------------------------------------------
703 // void DataType::new_scope(Hash *h = 0)
705 // Creates a new scope for handling typedefs. This is used in C++ handling
706 // to create typedef local to a class definition.
708 // Inputs : h = Optional hash table scope (Used for C++ inheritance).
712 // Side Effects : Creates a new hash table and increments the scope counter
713 // -----------------------------------------------------------------------------
715 void DataType::new_scope(Hash
*h
) {
717 typedef_hash
[scope
] = new Hash
;
724 // -----------------------------------------------------------------------------
725 // Hash *DataType::collapse_scope(char *prefix)
727 // Collapses the current scope into the previous one, but applies a prefix to
728 // all of the datatypes. This is done in order to properly handle C++ stuff.
733 // typedef double Real;
736 // will have a type mapping of "double --> Real" within the class itself.
737 // When we collapse the scope, this mapping will become "double --> Foo::Real"
743 // Side Effects : Returns the hash table corresponding to the current scope
744 // -----------------------------------------------------------------------------
746 Hash
*DataType::collapse_scope(char *prefix
) {
754 key
= typedef_hash
[scope
]->firstkey();
756 t
= (DataType
*) typedef_hash
[scope
]->lookup(key
);
757 nt
= new DataType(t
);
758 temp
= new char[strlen(prefix
)+strlen(key
)+3];
759 sprintf(temp
,"%s::%s",prefix
,key
);
760 // printf("creating %s\n", temp);
761 typedef_hash
[scope
-1]->add(temp
,(void *) nt
);
763 key
= typedef_hash
[scope
]->nextkey();
766 h
= typedef_hash
[scope
];
767 typedef_hash
[scope
] = 0;
774 // -------------------------------------------------------------
775 // Class equivalency lists
777 // These are used to keep track of which datatypes are equivalent.
778 // This information can be dumped in tabular form upon completion
779 // for use in the pointer type checker.
781 // cast is an extension needed to properly handle multiple inheritance
782 // --------------------------------------------------------------
791 static Hash typeeq_hash
;
792 static int te_init
= 0;
795 void typeeq_standard();
801 // --------------------------------------------------------------
802 // typeeq_add(char *name, char *eqname, char *cast)
804 // Adds a new name to the type-equivalence tables.
805 // Creates a new entry if it doesn't exit.
807 // Cast is an optional name for a pointer casting function.
808 // --------------------------------------------------------------
810 void typeeq_add(char *name
, char *eqname
, char *cast
= 0) {
813 if (!te_init
) typeeq_init();
815 if (strcmp(name
,eqname
) == 0) return; // If they're the same, forget it.
817 // Search for "name" entry in the hash table
819 e1
= (EqEntry
*) typeeq_hash
.lookup(name
);
822 // Create a new entry
824 e1
->name
= copy_string(name
);
827 // Add it to the hash table
828 typeeq_hash
.add(name
,(void *) e1
);
833 // Add new type to the list
834 // We'll first check to see if it's already been added
838 if (strcmp(e2
->name
, eqname
) == 0) {
840 e2
->cast
= copy_string(cast
);
847 e2
->name
= copy_string(eqname
);
848 e2
->cast
= copy_string(cast
);
849 e2
->next
= e1
->next
; // Add onto the linked list for name
854 // --------------------------------------------------------------
855 // typeeq_addtypedef(char *name, char *eqname)
857 // Adds a new typedef declaration to the equivelency list.
858 // --------------------------------------------------------------
860 void typeeq_addtypedef(char *name
, char *eqname
) {
863 if (!te_init
) typeeq_init();
865 // First we're going to add the equivalence, no matter what
867 typeeq_add(name
,eqname
);
869 // Now find the hash entry
871 e1
= (EqEntry
*) typeeq_hash
.lookup(name
);
874 // Walk down the list and make other equivalences
878 if (strcmp(e2
->name
, eqname
) != 0) {
879 typeeq_add(e2
->name
, eqname
,e2
->cast
);
880 typeeq_add(eqname
, e2
->name
,e2
->cast
);
886 // ----------------------------------------------------------------
887 // void emit_ptr_equivalence(FILE *f)
889 // Dump out the pointer equivalence table to file.
891 // Changed to register datatypes with the type checker in order
892 // to support proper type-casting (needed for multiple inheritance)
893 // ----------------------------------------------------------------
895 void emit_ptr_equivalence(FILE *f
) {
898 void typeeq_standard();
901 if (!te_init
) typeeq_init();
905 * This table is used by the pointer type-checker\n\
907 static struct { char *n1; char *n2; void *(*pcnv)(void *); } _swig_mapping[] = {\n";
909 e1
= (EqEntry
*) typeeq_hash
.first();
912 // Walk through the equivalency list
915 ttable
<< tab4
<< "{ \"" << e1
->name
<< "\",\"" << e2
->name
<< "\"," << e2
->cast
<< "},\n";
917 ttable
<< tab4
<< "{ \"" << e1
->name
<< "\",\"" << e2
->name
<< "\",0},\n";
920 e1
= (EqEntry
*) typeeq_hash
.next();
922 ttable
<< "{0,0,0}};\n";
923 fprintf(f_wrappers
,"%s\n", ttable
.get());
925 fprintf(f
," int i;\n");
926 fprintf(f
," for (i = 0; _swig_mapping[i].n1; i++)\n");
927 fprintf(f
," SWIG_RegisterMapping(_swig_mapping[i].n1,_swig_mapping[i].n2,_swig_mapping[i].pcnv);\n");
931 // ------------------------------------------------------------------------------
932 // typeeq_derived(char *n1, char *n2, char *cast=)
934 // Adds a one-way mapping between datatypes.
935 // ------------------------------------------------------------------------------
937 void typeeq_derived(char *n1
, char *n2
, char *cast
=0) {
942 if (!te_init
) typeeq_init();
946 name
<< t
.print_mangle();
947 name2
<< t1
.print_mangle();
948 typeeq_add(name
,name2
,cast
);
950 // Now find the hash entry
952 e1
= (EqEntry
*) typeeq_hash
.lookup(name
);
954 // Walk down the list and make other equivalences
956 /* I don't think this is necessary, but we'll keep this code in case
960 if (strcmp(e2->name, name2) != 0) {
961 typeeq_add(e2->name, name2,e2->cast);
969 // ------------------------------------------------------------------------------
970 // typeeq_mangle(char *n1, char *n2, char *cast=)
972 // Adds a single type equivalence
973 // ------------------------------------------------------------------------------
975 void typeeq_mangle(char *n1
, char *n2
, char *cast
=0) {
979 if (!te_init
) typeeq_init();
983 name
<< t
.print_mangle();
984 name2
<< t1
.print_mangle();
985 typeeq_add(name
,name2
,cast
);
988 // ------------------------------------------------------------------------------
989 // typeeq_standard(void)
991 // Generate standard type equivalences (well, pointers that can map into
992 // other pointers naturally).
994 // -------------------------------------------------------------------------------
996 void typeeq_standard(void) {
998 typeeq_mangle("int", "signed int");
999 typeeq_mangle("int", "unsigned int");
1000 typeeq_mangle("signed int", "int");
1001 typeeq_mangle("unsigned int", "int");
1002 typeeq_mangle("short","signed short");
1003 typeeq_mangle("signed short","short");
1004 typeeq_mangle("short","unsigned short");
1005 typeeq_mangle("unsigned short","short");
1006 typeeq_mangle("long","signed long");
1007 typeeq_mangle("signed long","long");
1008 typeeq_mangle("long","unsigned long");
1009 typeeq_mangle("unsigned long","long");
1013 // ------------------------------------------------------------------------------
1014 // type_undefined_check(void)
1016 // Checks the hash table for undefined datatypes and prints a warning message.
1017 // -------------------------------------------------------------------------------
1019 void type_undefined_check(void) {
1022 s
= (char *) undefined_types
.first();
1024 fprintf(stderr
,"The following datatypes were used, but undefined.\n");
1026 fprintf(stderr
," %s\n",s
);
1027 s
= (char *) undefined_types
.next();