diff options
author | redbrain <redbrain@gcc.gnu.org> | 2012-04-21 19:12:19 +0100 |
---|---|---|
committer | redbrain <redbrain@gcc.gnu.org> | 2012-04-21 19:12:19 +0100 |
commit | 6bb2994a691ee688ac538c2ac9d382804aad5abe (patch) | |
tree | 9bf8e9a3e0886c75383b07c144be6a157b285c11 | |
parent | 30903ba9eb9e6b3f3d926041cfc438c71377d6f6 (diff) | |
download | gcc-alpha-v0.1.tar.gz |
lots of argument passing work finished and we can compile python nowalpha-v0.1
-rw-r--r-- | gcc/python/py-dot-pass-genericify.c | 217 | ||||
-rw-r--r-- | gcc/python/py-parser.y | 4 | ||||
-rw-r--r-- | gcc/python/py-runtime.c | 20 | ||||
-rw-r--r-- | gcc/python/py-runtime.def | 12 | ||||
-rw-r--r-- | gcc/python/py-runtime.h | 3 | ||||
-rw-r--r-- | gcc/python/py-runtime.tpl | 2 | ||||
-rw-r--r-- | libgpython/include/gpython/objects.h | 5 | ||||
-rw-r--r-- | libgpython/include/gpython/runtime.h | 17 | ||||
-rw-r--r-- | libgpython/runtime/py-obj_class.c | 88 | ||||
-rw-r--r-- | libgpython/runtime/py-obj_classmethod.c | 17 | ||||
-rw-r--r-- | libgpython/runtime/py-obj_staticmethod.c | 6 | ||||
-rw-r--r-- | libgpython/runtime/py-runtime.c | 63 | ||||
-rw-r--r-- | libgpython/runtime/py-type-utils.c | 15 |
13 files changed, 325 insertions, 144 deletions
diff --git a/gcc/python/py-dot-pass-genericify.c b/gcc/python/py-dot-pass-genericify.c index 4546363c240..671b28605c0 100644 --- a/gcc/python/py-dot-pass-genericify.c +++ b/gcc/python/py-dot-pass-genericify.c @@ -195,6 +195,42 @@ void gpy_dot_pass_genericify_class_type (tree type, tree self, } static +void gpy_dot_pass_genericify_arguments_to_context (gpy_context_t context, + gpy_dot_tree_t * parameters, + tree argdecl, tree * block) +{ + gpy_dot_tree_t *pnode = parameters; + if (pnode) + { + int offset = 0; + for (; pnode != NULL_DOT; pnode = DOT_CHAIN (pnode)) + { + const char * parmid = DOT_IDENTIFIER_POINTER (pnode); + debug ("folding parameter <%s>!\n", parmid); + + tree vardecl = build_decl (UNKNOWN_LOCATION, VAR_DECL, get_identifier (parmid), + gpy_object_type_ptr); + + tree element_size = TYPE_SIZE_UNIT (gpy_object_type_ptr_ptr); + tree offs = fold_build2_loc (UNKNOWN_LOCATION, MULT_EXPR, sizetype, + build_int_cst (sizetype, offset), + element_size); + tree addr = fold_build2_loc (UNKNOWN_LOCATION, POINTER_PLUS_EXPR, + gpy_object_type_ptr_ptr, + argdecl, offs); + + append_to_statement_list (build2 (MODIFY_EXPR, gpy_object_type_ptr, + vardecl, + build_fold_indirect_ref (addr)), + block); + gcc_assert (!gpy_dd_hash_insert (gpy_dd_hash_string (parmid), vardecl, + context)); + offset++; + } + } +} + +static tree gpy_dot_pass_genericify_find_addr (const char * id, const char * parent_ident, VEC(tree,gc) * decls) @@ -240,7 +276,8 @@ void gpy_dot_pass_genericify_walk_class (tree * block, tree type, tree offs = fold_build2_loc (UNKNOWN_LOCATION, MULT_EXPR, sizetype, build_int_cst (sizetype, offset), element_size); - tree a = GPY_RR_fold_attrib (gpy_dot_type_const_string_tree (ident), + tree str = gpy_dot_type_const_string_tree (ident); + tree a = GPY_RR_fold_attrib (build_fold_addr_expr (str), gpy_dot_pass_genericify_find_addr (ident, type_name, ldecls), offs); VEC_safe_push (tree, gc, attribs, a); @@ -257,8 +294,9 @@ void gpy_dot_pass_genericify_walk_class (tree * block, tree type, attribs_decl, GPY_RR_fold_attrib_list (args)), block); + tree class_str = gpy_dot_type_const_string_tree (type_name); tree fold_class = GPY_RR_fold_class_decl (attribs_decl, TYPE_SIZE_UNIT (type), - gpy_dot_type_const_string_tree (type_name)); + build_fold_addr_expr (class_str)); switch (TREE_CODE (decl)) { @@ -492,10 +530,11 @@ tree gpy_dot_pass_genericify_modify (gpy_dot_tree_t * decl, tree * block, tree lhs_tree = gpy_dot_pass_lower_expr (xlhs, block, context); char * attrib_ident = DOT_IDENTIFIER_POINTER (xrhs); + tree str = gpy_dot_type_const_string_tree (attrib_ident); append_to_statement_list (build2 (MODIFY_EXPR, gpy_object_type_ptr_ptr, addr_1, GPY_RR_fold_attrib_ref (lhs_tree, - gpy_dot_type_const_string_tree (attrib_ident))), + build_fold_addr_expr (str))), block); tree refer = build_fold_indirect_ref (addr_1); append_to_statement_list (build2 (MODIFY_EXPR, gpy_object_type_ptr_ptr, @@ -606,9 +645,10 @@ tree gpy_dot_pass_lower_expr (gpy_dot_tree_t * decl, tree * block, tree lhs_tree = gpy_dot_pass_lower_expr (xlhs, block, context); char * attrib_ident = DOT_IDENTIFIER_POINTER (xrhs); + tree str = gpy_dot_type_const_string_tree (attrib_ident); tree attrib_ref = build2 (MODIFY_EXPR, gpy_object_type_ptr_ptr, addr_1, GPY_RR_fold_attrib_ref (lhs_tree, - gpy_dot_type_const_string_tree (attrib_ident)) + build_fold_addr_expr (str)) ); append_to_statement_list (attrib_ref, block); retval = build_fold_indirect_ref (addr_1); @@ -618,27 +658,66 @@ tree gpy_dot_pass_lower_expr (gpy_dot_tree_t * decl, tree * block, case D_CALL_EXPR: { gpy_dot_tree_t * callid = DOT_lhs_TT (decl); - tree call_decl = gpy_dot_pass_lower_expr (callid, block, context); - gcc_assert (call_decl != error_mark_node); + if (DOT_TYPE (callid) == D_ATTRIB_REF) + { + tree call_decl = gpy_dot_pass_lower_expr (callid, block, context); + gcc_assert (call_decl != error_mark_node); - gpy_dot_tree_t * argslist; - VEC(tree,gc) * argsvec = VEC_alloc (tree,gc,0); - for (argslist = DOT_rhs_TT (decl); argslist != NULL_DOT; argslist = DOT_CHAIN (argslist)) + /* now we need to find the base of the attribute reference so we can pass self */ + /* lets just assume we only handle x.y for now */ + gpy_dot_tree_t * xlhs = DOT_lhs_TT (callid); + gpy_dot_tree_t * xrhs = DOT_rhs_TT (callid); + + gcc_assert (DOT_TYPE (xlhs) == D_IDENTIFIER); + gcc_assert (DOT_TYPE (xrhs) == D_IDENTIFIER); + + tree basetree = gpy_dot_pass_lower_expr (xlhs, block, context); + + gpy_dot_tree_t * argslist; + VEC(tree,gc) * argsvec = VEC_alloc (tree,gc,0); + VEC_safe_push (tree, gc, argsvec, basetree); + + for (argslist = DOT_rhs_TT (decl); argslist != NULL_DOT; argslist = DOT_CHAIN (argslist)) + { + tree lexpr = gpy_dot_pass_lower_expr (argslist, block, context); + VEC_safe_push (tree, gc, argsvec, lexpr); + } + VEC(tree,gc) * args = VEC_alloc (tree,gc,0); + VEC_safe_push (tree, gc, args, call_decl); + VEC_safe_push (tree, gc, args, build_int_cst (integer_type_node, VEC_length (tree, argsvec))); + GPY_VEC_stmts_append (tree, args, argsvec); + + tree retaddr = build_decl (UNKNOWN_LOCATION, VAR_DECL, create_tmp_var_name ("R"), + gpy_object_type_ptr); + append_to_statement_list (build2 (MODIFY_EXPR, gpy_object_type_ptr, retaddr, + GPY_RR_fold_call (args)), + block); + retval = retaddr; + } + else { - tree lexpr = gpy_dot_pass_lower_expr (argslist, block, context); - VEC_safe_push (tree, gc, argsvec, lexpr); + tree call_decl = gpy_dot_pass_lower_expr (callid, block, context); + gcc_assert (call_decl != error_mark_node); + + gpy_dot_tree_t * argslist; + VEC(tree,gc) * argsvec = VEC_alloc (tree,gc,0); + for (argslist = DOT_rhs_TT (decl); argslist != NULL_DOT; argslist = DOT_CHAIN (argslist)) + { + tree lexpr = gpy_dot_pass_lower_expr (argslist, block, context); + VEC_safe_push (tree, gc, argsvec, lexpr); + } + VEC(tree,gc) * args = VEC_alloc (tree,gc,0); + VEC_safe_push (tree, gc, args, call_decl); + VEC_safe_push (tree, gc, args, build_int_cst (integer_type_node, VEC_length (tree, argsvec))); + GPY_VEC_stmts_append (tree, args, argsvec); + + tree retaddr = build_decl (UNKNOWN_LOCATION, VAR_DECL, create_tmp_var_name ("R"), + gpy_object_type_ptr); + append_to_statement_list (build2 (MODIFY_EXPR, gpy_object_type_ptr, retaddr, + GPY_RR_fold_call (args)), + block); + retval = retaddr; } - VEC(tree,gc) * args = VEC_alloc (tree,gc,0); - VEC_safe_push (tree, gc, args, call_decl); - VEC_safe_push (tree, gc, args, build_int_cst (integer_type_node, VEC_length (tree, argsvec))); - GPY_VEC_stmts_append (tree, args, argsvec); - - tree retaddr = build_decl (UNKNOWN_LOCATION, VAR_DECL, create_tmp_var_name ("R"), - gpy_object_type_ptr); - append_to_statement_list (build2 (MODIFY_EXPR, gpy_object_type_ptr, retaddr, - GPY_RR_fold_call (args)), - block); - retval = retaddr; } break; @@ -672,7 +751,7 @@ tree gpy_dot_pass_genericify_toplevl_functor_decl (gpy_dot_tree_t * decl, VEC(gpy_context_t, gc) * context) { tree fntype = build_function_type_list (void_type_node, - /* Arguments .. */ + gpy_object_type_ptr_ptr, NULL_TREE); tree ident = GPY_dot_pass_genericify_gen_concat_identifier (GPY_current_module_name, DOT_IDENTIFIER_POINTER (DOT_FIELD (decl)) @@ -686,6 +765,19 @@ tree gpy_dot_pass_genericify_toplevl_functor_decl (gpy_dot_tree_t * decl, DECL_ARTIFICIAL(fndecl) = 1; TREE_PUBLIC(fndecl) = 1; + tree arglist = NULL_TREE; + tree self_parm_decl = build_decl (BUILTINS_LOCATION, PARM_DECL, + get_identifier ("__arguments__"), + gpy_object_type_ptr_ptr); + + DECL_CONTEXT (self_parm_decl) = fndecl; + DECL_ARG_TYPE (self_parm_decl) = TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (fndecl))); + TREE_READONLY (self_parm_decl) = 1; + arglist = chainon (arglist, self_parm_decl); + + TREE_USED (self_parm_decl) = 1; + DECL_ARGUMENTS (fndecl) = arglist; + /* Define the return type (represented by RESULT_DECL) for the main functin */ tree resdecl = build_decl(BUILTINS_LOCATION, RESULT_DECL, NULL_TREE, TREE_TYPE(fntype)); @@ -700,8 +792,12 @@ tree gpy_dot_pass_genericify_toplevl_functor_decl (gpy_dot_tree_t * decl, DECL_INITIAL (fndecl) = block; tree stmts = alloc_stmt_list (); + gpy_hash_tab_t ctx; gpy_dd_hash_init_table (&ctx); + gpy_dot_tree_t * pnode = DOT_lhs_TT (decl); + + gpy_dot_pass_genericify_arguments_to_context (&ctx, pnode, self_parm_decl, &stmts); VEC_safe_push (gpy_context_t, gc, context, &ctx); gpy_dot_tree_t * node = decl->opb.t; @@ -757,12 +853,10 @@ tree gpy_dot_pass_genericify_class_method_attrib (gpy_dot_tree_t * decl, const char * parent_ident, VEC(gpy_context_t,gc) * context) { - tree params = NULL_TREE; - gpy_dot_tree_t * pnode; - for (pnode = DOT_lhs_TT (decl); pnode != NULL_DOT; pnode = DOT_CHAIN (pnode)) - chainon (params, tree_cons (NULL_TREE, gpy_object_type_ptr, NULL_TREE)); - - tree fntype = build_function_type (void_type_node, params); + tree fntype = build_function_type_list (void_type_node, + gpy_object_type_ptr, + gpy_object_type_ptr_ptr, + NULL_TREE); tree ident = GPY_dot_pass_genericify_gen_concat_identifier (GPY_current_module_name, parent_ident); ident = GPY_dot_pass_genericify_gen_concat_identifier (IDENTIFIER_POINTER (ident), @@ -776,36 +870,29 @@ tree gpy_dot_pass_genericify_class_method_attrib (gpy_dot_tree_t * decl, DECL_ARTIFICIAL(fndecl) = 1; TREE_PUBLIC(fndecl) = 1; - gpy_hash_tab_t ctx; - gpy_dd_hash_init_table (&ctx); - - tree arglist = NULL_TREE; - tree parm_decl = NULL_TREE; tree self_parm_decl = NULL_TREE; - for (pnode = DOT_lhs_TT (decl); pnode != NULL_DOT; pnode = DOT_CHAIN (pnode)) - { - gcc_assert (DOT_TYPE(pnode) == D_IDENTIFIER); - debug ("processing parameter <%s>!\n", DOT_IDENTIFIER_POINTER (pnode)); + tree arglist = NULL_TREE; + tree parm_decl = build_decl (BUILTINS_LOCATION, PARM_DECL, + get_identifier ("self"), + gpy_object_type_ptr); + + DECL_CONTEXT (parm_decl) = fndecl; + DECL_ARG_TYPE (parm_decl) = TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (fndecl))); + TREE_READONLY (parm_decl) = 1; + arglist = chainon (arglist, parm_decl); + TREE_USED (parm_decl) = 1; + self_parm_decl = parm_decl; + + parm_decl = build_decl (BUILTINS_LOCATION, PARM_DECL, + get_identifier ("__arguments__"), + gpy_object_type_ptr_ptr); + + DECL_CONTEXT (parm_decl) = fndecl; + DECL_ARG_TYPE (parm_decl) = TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (fndecl))); + TREE_READONLY (parm_decl) = 1; + arglist = chainon (arglist, parm_decl); + TREE_USED (parm_decl) = 1; - parm_decl = build_decl (BUILTINS_LOCATION, PARM_DECL, - get_identifier (DOT_IDENTIFIER_POINTER (pnode)), - gpy_object_type_ptr); - - DECL_CONTEXT (parm_decl) = fndecl; - DECL_ARG_TYPE (parm_decl) = gpy_object_type_ptr; - TREE_READONLY (parm_decl) = 1; - arglist = chainon (arglist, parm_decl); - - TREE_USED (parm_decl) = 1; - if (!strcmp ("self", DOT_IDENTIFIER_POINTER (pnode))) - self_parm_decl = parm_decl; - else - { - gcc_assert (!gpy_dd_hash_insert (gpy_dd_hash_string (DOT_IDENTIFIER_POINTER (pnode)), - parm_decl, - &ctx)); - } - } DECL_ARGUMENTS (fndecl) = arglist; /* Define the return type (represented by RESULT_DECL) for the main functin */ @@ -821,15 +908,22 @@ tree gpy_dot_pass_genericify_class_method_attrib (gpy_dot_tree_t * decl, tree block = build_block (NULL_TREE, NULL_TREE, NULL_TREE, NULL_TREE); DECL_INITIAL (fndecl) = block; + tree stmts = alloc_stmt_list (); + + gpy_hash_tab_t ctx; + gpy_dd_hash_init_table (&ctx); + + gpy_dot_tree_t * pnode = DOT_lhs_TT (decl); + // we dont care about self... + pnode = DOT_CHAIN (pnode); + + gpy_dot_pass_genericify_arguments_to_context (&ctx, pnode, parm_decl, &stmts); if (self_parm_decl) gcc_assert (!gpy_dd_hash_insert (gpy_dd_hash_string ("self"), self_parm_decl, &ctx)); else warning(0, "No self parameter declared!\n"); - VEC_safe_push (gpy_context_t, gc, context, &ctx); - - tree stmts = alloc_stmt_list (); /* lower the function suite here and append all initilization */ @@ -1088,9 +1182,10 @@ VEC(tree,gc) * gpy_dot_pass_genericify_TU (gpy_hash_tab_t * modules, /* assign the function to the decl */ const char * funcid = DOT_IDENTIFIER_POINTER (DOT_FIELD (idtx)); tree funcdecl = gpy_dot_pass_decl_lookup (context, funcid); + tree str = gpy_dot_type_const_string_tree (funcid); append_to_statement_list (build2 (MODIFY_EXPR, gpy_object_type_ptr, funcdecl, - GPY_RR_fold_func_decl (gpy_dot_type_const_string_tree (funcid), + GPY_RR_fold_func_decl (build_fold_addr_expr (str), t)), &stmts); } diff --git a/gcc/python/py-parser.y b/gcc/python/py-parser.y index a518fb2501a..eb2f411de97 100644 --- a/gcc/python/py-parser.y +++ b/gcc/python/py-parser.y @@ -222,12 +222,12 @@ parameter_list_stmt: { $$ = VEC_pop (gpydot, gpy_symbol_stack); } ; -parameter_list: parameter_list ',' target +parameter_list: parameter_list ',' ident { DOT_CHAIN($1) = $3; $$ = $3; } - | target + | ident { VEC_safe_push (gpydot, gc, gpy_symbol_stack, $1); diff --git a/gcc/python/py-runtime.c b/gcc/python/py-runtime.c index c9213fac8b5..64834471d4f 100644 --- a/gcc/python/py-runtime.c +++ b/gcc/python/py-runtime.c @@ -315,6 +315,26 @@ tree GPY_RR_fold_call (VEC(tree,gc) * arguments) return build_call_expr_loc_vec (BUILTINS_LOCATION, fndecl, arguments); } +tree GPY_RR_fold_argument (tree args, tree offset) +{ + tree fntype = build_function_type_list (gpy_object_type_ptr, + gpy_object_type_ptr_ptr, + integer_type_node, + NULL_TREE); + tree fndecl = build_decl (BUILTINS_LOCATION, FUNCTION_DECL, + get_identifier ("gpy_rr_fold_argument"), + fntype); + tree restype = TREE_TYPE (fndecl); + tree resdecl = build_decl (BUILTINS_LOCATION, RESULT_DECL, NULL_TREE, + restype); + DECL_CONTEXT (resdecl) = fndecl; + DECL_RESULT (fndecl) = resdecl; + DECL_EXTERNAL (fndecl) = 1; + TREE_PUBLIC (fndecl) = 1; + + return build_call_expr (fndecl, 2, args, offset); +} + static tree gpy_build_py_vector_type (void) diff --git a/gcc/python/py-runtime.def b/gcc/python/py-runtime.def index 81484017119..696ba90a901 100644 --- a/gcc/python/py-runtime.def +++ b/gcc/python/py-runtime.def @@ -172,3 +172,15 @@ py-runtime = { code = GPY_RR_fold_call; build_call = build_call_expr_loc_vec; build_call_args = "BUILTINS_LOCATION, fndecl, arguments"; }; +py-runtime = { code = GPY_RR_fold_argument; + arguments = "tree args, tree offset"; + proto = "tree, tree"; + comment = "/* Eval arg */"; + function_identifier = "gpy_rr_fold_argument"; + fntype = "gpy_object_type_ptr, + gpy_object_type_ptr_ptr, + integer_type_node, + NULL_TREE"; + build_call = build_call_expr; + build_call_args = "fndecl, 2, args, offset"; + };
\ No newline at end of file diff --git a/gcc/python/py-runtime.h b/gcc/python/py-runtime.h index 02a6165a76c..6c8ab6a1460 100644 --- a/gcc/python/py-runtime.h +++ b/gcc/python/py-runtime.h @@ -75,5 +75,8 @@ extern tree GPY_RR_fold_attrib_ref (tree, tree); /* Eval call */ extern tree GPY_RR_fold_call (VEC(tree,gc) *); +/* Eval arg */ +extern tree GPY_RR_fold_argument (tree, tree); + #endif //__GCC_PY_RUNTIME_H__ diff --git a/gcc/python/py-runtime.tpl b/gcc/python/py-runtime.tpl index eb4a9a43b62..75e4f119d51 100644 --- a/gcc/python/py-runtime.tpl +++ b/gcc/python/py-runtime.tpl @@ -288,7 +288,7 @@ void gpy_dot_types_init (void) { gpy_builtin_types_vec = VEC_alloc (tree,gc,0); - tree const_char_type = build_qualified_type (char_type_node, + tree const_char_type = build_qualified_type (unsigned_char_type_node, TYPE_QUAL_CONST); tree ctype = build_pointer_type (const_char_type); diff --git a/libgpython/include/gpython/objects.h b/libgpython/include/gpython/objects.h index 114a551c676..ecc8d72d8a8 100644 --- a/libgpython/include/gpython/objects.h +++ b/libgpython/include/gpython/objects.h @@ -67,7 +67,8 @@ typedef struct gpy_object_t { } o ; } gpy_object_t ; -typedef void (*fndecl)(gpy_object_t **); +typedef void (*staticmethod_fndecl)(gpy_object_t **); +typedef void (*classmethod_fndecl) (gpy_object_t *, gpy_object_t **); typedef gpy_object_t * (*binary_op)(gpy_object_t *, gpy_object_t *); typedef struct gpy_number_prot_t { @@ -119,8 +120,10 @@ extern gpy_object_attrib_t ** gpy_args_lit_parse_attrib_table (gpy_object_t *); extern gpy_object_t * gpy_create_object_state (gpy_typedef_t *, void *); extern gpy_object_t * gpy_create_object_decl (gpy_typedef_t *, void *); extern unsigned char * gpy_object_staticmethod_getaddr (gpy_object_t *); +extern unsigned char * gpy_object_classmethod_getaddr (gpy_object_t *); extern void gpy_obj_integer_mod_init (gpy_vector_t * const); extern void gpy_obj_staticmethod_mod_init (gpy_vector_t * const); +extern void gpy_object_classmethod_inherit_self (gpy_object_t *, gpy_object_t *); #endif //__GCC_OBJECTS_H__ diff --git a/libgpython/include/gpython/runtime.h b/libgpython/include/gpython/runtime.h index cf049237667..11ecfd3597e 100644 --- a/libgpython/include/gpython/runtime.h +++ b/libgpython/include/gpython/runtime.h @@ -17,7 +17,22 @@ along with GCC; see the file COPYING3. If not see #ifndef __GCC_RUNTIME_H__ #define __GCC_RUNTIME_H__ -extern gpy_object_t * gpy_rr_fold_functor_decl (const char *, unsigned char *); +/* + accesors to the internal types... + */ +#define __gpy_integer_type_node \ + (gpy_typedef_t *) __GPY_GLOBL_PRIMITIVES->vector[0] +#define __gpy_staticmethod_type_node \ + (gpy_typedef_t *) __GPY_GLOBL_PRIMITIVES->vector[1] +#define __gpy_class_type_node \ + (gpy_typedef_t *) __GPY_GLOBL_PRIMITIVES->vector[2] +#define __gpy_classmethod_type_node \ + (gpy_typedef_t *) __GPY_GLOBL_PRIMITIVES->vector[3] + +extern gpy_object_t * gpy_rr_fold_staticmethod_decl (const char *, unsigned char *); +extern gpy_object_t * gpy_rr_fold_classmethod_decl (const char *, unsigned char *); extern unsigned char * gpy_rr_eval_attrib_reference (gpy_object_t *, const char *); +extern void gpy_rr_eval_print (int, int, ...); + #endif //__GCC_RUNTIME_H__ diff --git a/libgpython/runtime/py-obj_class.c b/libgpython/runtime/py-obj_class.c index d002f8b2739..ab501809867 100644 --- a/libgpython/runtime/py-obj_class.c +++ b/libgpython/runtime/py-obj_class.c @@ -42,8 +42,32 @@ void gpy_object_classobj_init_decl_attribs (const void * self, for (idx = 0; attribs[idx] != NULL; ++idx) { gpy_object_attrib_t * i = attribs[idx]; - unsigned char * x = selfptr + (i->offset); - x = (unsigned char *) &(i->addr); + unsigned char * typeoffs = selfptr + (i->offset); + + gpy_object_t ** offs = (gpy_object_t **) typeoffs; + if (i->addr) + { + gpy_object_t * attrib = (gpy_object_t *)i->addr; + *offs = i->addr; + } + else + *offs = NULL; + } +} + +static +void gpy_object_classobj_methodattribs_addself (gpy_object_attrib_t ** attribs, + gpy_object_t * self) +{ + int idx; + for (idx = 0; attribs[idx] != NULL; ++idx) + { + gpy_object_attrib_t * i = attribs[idx]; + if (i->addr) + { + gpy_object_t * att = (gpy_object_t *) i->addr; + gpy_object_classmethod_inherit_self (att, self); + } } } @@ -78,10 +102,9 @@ gpy_object_t * gpy_object_classobj_new (gpy_typedef_t * type, /* we need to walk though the field_init here */ unsigned char * __field_init__ = gpy_rr_eval_attrib_reference (retval, "__field_init__"); gpy_object_t * field_init = *((gpy_object_t **) __field_init__); - unsigned char * codeaddr = gpy_object_staticmethod_getaddr (field_init); + unsigned char * codeaddr = gpy_object_classmethod_getaddr (field_init); gpy_assert (codeaddr); - debug ("calling the __init__!\n"); __field_init_ptr c = (__field_init_ptr)codeaddr; c (self); @@ -117,25 +140,58 @@ void gpy_object_classobj_print (gpy_object_t * self, FILE *fd, bool newline) fprintf (fd, "\n"); } +static +gpy_object_t ** gpy_object_classobj_setupargs (gpy_object_t ** args, + gpy_object_t * self) +{ + int idx = 0; + gpy_object_t ** ptr; + for (ptr = args; *ptr != NULL; ++ptr) + idx ++; + + gpy_object_t ** newargs = calloc (idx+2, sizeof (gpy_object_t *)); + *newargs = self; + gpy_object_t ** newargsptr = newargs; + newargsptr++; + + for (ptr = args; *ptr != NULL; ++ptr) + { + *newargsptr = *ptr; + newargsptr++; + } + *newargsptr = NULL; + + return newargs; +} + gpy_object_t * gpy_object_classobj_call (gpy_object_t * self, gpy_object_t ** args) { - gpy_object_t * retval = NULL_OBJECT; - gpy_assert (self->T == TYPE_OBJECT_DECL); + gpy_object_t * retval = NULL_OBJECT; + gpy_assert (self->T == TYPE_OBJECT_DECL); + + gpy_typedef_t * type = self->o.object_state->definition; + void * oldstate = self->o.object_state->state; - gpy_typedef_t * type = self->o.object_state->definition; - void * state = self->o.object_state->state; - retval = gpy_create_object_state (type, state); - gpy_assert (retval); + void * newstate = malloc (type->state_size); + memcpy (newstate, oldstate, type->state_size); + retval = gpy_create_object_state (type, newstate); + gpy_assert (retval); - unsigned char * __init__ = gpy_rr_eval_attrib_reference (retval, "__init__"); - gpy_object_t * init = *((gpy_object_t **)__init__); - unsigned char * codeaddr = gpy_object_staticmethod_getaddr (init); - gpy_assert (codeaddr); + unsigned char * __init__ = gpy_rr_eval_attrib_reference (retval, "__init__"); + gpy_object_t * init = *((gpy_object_t **) __init__); - + gpy_assert (init->T == TYPE_OBJECT_DECL); + gpy_typedef_t * calltype = init->o.object_state->definition; + if (type->tp_call) + { + gpy_object_t ** arguments = gpy_object_classobj_setupargs (args, retval); + calltype->tp_call (init, arguments); + } + else + fatal ("name is not callable!\n"); - return retval; + return retval; } static struct gpy_typedef_t class_obj = { diff --git a/libgpython/runtime/py-obj_classmethod.c b/libgpython/runtime/py-obj_classmethod.c index 815c017b886..b2a80cad1bd 100644 --- a/libgpython/runtime/py-obj_classmethod.c +++ b/libgpython/runtime/py-obj_classmethod.c @@ -31,13 +31,13 @@ along with GCC; see the file COPYING3. If not see #include <gpython/objects.h> struct gpy_object_classmethod_t { - const unsigned char * code; - const char * identifier; + unsigned char * code; + char * identifier; unsigned int nargs; }; gpy_object_t * gpy_object_classmethod_new (gpy_typedef_t * type, - gpy_object_t ** args) + gpy_object_t ** args) { gpy_object_t * retval = NULL_OBJECT; @@ -76,16 +76,19 @@ void gpy_object_classmethod_print (gpy_object_t * self, FILE *fd, bool newline) } gpy_object_t * gpy_object_classmethod_call (gpy_object_t * self, - gpy_object_t ** args) + gpy_object_t ** args) { gpy_object_t * retval = NULL_OBJECT; gpy_assert (self->T == TYPE_OBJECT_DECL); struct gpy_object_classmethod_t * state = self->o.object_state->state; - if (!state->code) + if (state->code) { - fndecl fnptr = (fndecl)state->code; - fnptr (args); + classmethod_fndecl fnptr = (classmethod_fndecl)state->code; + gpy_object_t ** ptr = args; + gpy_object_t * class = *ptr; + ptr++; + fnptr (class, ptr); } return retval; } diff --git a/libgpython/runtime/py-obj_staticmethod.c b/libgpython/runtime/py-obj_staticmethod.c index 0f287e18f9e..c7f791466ad 100644 --- a/libgpython/runtime/py-obj_staticmethod.c +++ b/libgpython/runtime/py-obj_staticmethod.c @@ -31,8 +31,8 @@ along with GCC; see the file COPYING3. If not see #include <gpython/objects.h> struct gpy_object_staticmethod_t { - const unsigned char * code; - const char * identifier; + unsigned char * code; + char * identifier; unsigned int nargs; }; @@ -85,7 +85,7 @@ gpy_object_t * gpy_object_staticmethod_call (gpy_object_t * self, struct gpy_object_staticmethod_t * state = self->o.object_state->state; if (!state->code) { - fndecl fnptr = (fndecl)state->code; + staticmethod_fndecl fnptr = (staticmethod_fndecl)state->code; fnptr (args); } return retval; diff --git a/libgpython/runtime/py-runtime.c b/libgpython/runtime/py-runtime.c index a518ba9db69..6dfcd55f001 100644 --- a/libgpython/runtime/py-runtime.c +++ b/libgpython/runtime/py-runtime.c @@ -81,7 +81,7 @@ void gpy_rr_extend_runtime_stack (int nslots) __GPY_GLOBL_RR_STACK = gpy_realloc (__GPY_GLOBL_RR_STACK, size); __GPY_GLOBL_RR_STACK_POINTER = __GPY_GLOBL_RR_STACK; - __GPY_GLOBL_RR_STACK2_POINTER += 3+nslots; + __GPY_GLOBL_RR_STACK_POINTER += 3 + nslots; } void gpy_rr_init_runtime (void) @@ -97,7 +97,7 @@ void gpy_rr_cleanup_final (void) mpfr_free_cache (); } -gpy_object_attrib_t * gpy_rr_fold_attribute (const char * identifier, +gpy_object_attrib_t * gpy_rr_fold_attribute (const unsigned char * identifier, unsigned char * code_addr, unsigned int offset) { @@ -168,15 +168,10 @@ gpy_object_t * gpy_rr_fold_class_decl (gpy_object_attrib_t ** attribs, args[2] = &a3; args[3] = &a4; - gpy_typedef_t * def = (gpy_typedef_t *) - __GPY_GLOBL_PRIMITIVES->vector[2]; - gpy_assert (def); - + gpy_typedef_t * def = __gpy_class_type_node; retval = def->tp_new (def, args); gpy_free (args); - debug ("initilized class object <%p> to <%s>!\n", - (void*)retval, identifier); gpy_assert (retval->T == TYPE_OBJECT_DECL); return retval; @@ -212,15 +207,10 @@ gpy_object_t * gpy_rr_fold_staticmethod_decl (const char * identifier, args[2] = &a3; args[3] = &a4; - gpy_typedef_t * def = (gpy_typedef_t *) - __GPY_GLOBL_PRIMITIVES->vector[1]; - gpy_assert (def); - + gpy_typedef_t * def = __gpy_staticmethod_type_node; retval = def->tp_new (def, args); gpy_free (args); - debug ("initilized staticmethod object <%p> to <%s>!\n", - (void*)retval, identifier); gpy_assert (retval->T == TYPE_OBJECT_DECL); return retval; @@ -234,9 +224,9 @@ gpy_object_t * gpy_rr_fold_classmethod_decl (const char * identifier, gpy_object_t ** args = (gpy_object_t **) gpy_calloc (4, sizeof(gpy_object_t*)); - gpy_literal_t i; - i.type = TYPE_STRING; - i.literal.string = (char *)identifier; + gpy_literal_t s; + s.type = TYPE_STRING; + s.literal.string = (char *)identifier; gpy_literal_t p; p.type = TYPE_ADDR; @@ -246,7 +236,7 @@ gpy_object_t * gpy_rr_fold_classmethod_decl (const char * identifier, n.type = TYPE_INTEGER; n.literal.integer = 0; - gpy_object_t a1 = { .T = TYPE_OBJECT_LIT, .o.literal = &i }; + gpy_object_t a1 = { .T = TYPE_OBJECT_LIT, .o.literal = &s }; gpy_object_t a2 = { .T = TYPE_OBJECT_LIT, .o.literal = &p }; gpy_object_t a3 = { .T = TYPE_OBJECT_LIT, .o.literal = &n }; gpy_object_t a4 = { .T = TYPE_NULL, .o.literal = NULL }; @@ -256,15 +246,10 @@ gpy_object_t * gpy_rr_fold_classmethod_decl (const char * identifier, args[2] = &a3; args[3] = &a4; - gpy_typedef_t * def = (gpy_typedef_t *) - __GPY_GLOBL_PRIMITIVES->vector[1]; - gpy_assert (def); - + gpy_typedef_t * def = __gpy_classmethod_type_node; retval = def->tp_new (def, args); gpy_free (args); - debug ("initilized classmethod object <%p> to <%s>!\n", - (void*)retval, identifier); gpy_assert (retval->T == TYPE_OBJECT_DECL); return retval; @@ -277,11 +262,21 @@ gpy_object_t * gpy_rr_fold_call (gpy_object_t * decl, int nargs, ...) gpy_assert (decl->T == TYPE_OBJECT_DECL); gpy_typedef_t * type = decl->o.object_state->definition; - gpy_assert (type->members_defintion); + + /* + 1 for sentinal */ + gpy_object_t ** args = calloc (nargs + 1, sizeof (gpy_object_t *)); + va_list ap; + int idx; + va_start (ap, nargs); + for (idx = 0; idx < nargs; ++idx) + { + args[idx] = va_arg (ap, gpy_object_t *); + } + args[idx] = NULL; if (type->tp_call) { - retval = type->tp_call (decl, NULL); + retval = type->tp_call (decl, args); } else fatal ("name is not callable!\n"); @@ -289,17 +284,12 @@ gpy_object_t * gpy_rr_fold_call (gpy_object_t * decl, int nargs, ...) return retval; } - - unsigned char * gpy_rr_eval_attrib_reference (gpy_object_t * base, const char * attrib) { unsigned char * retval = NULL; - gpy_assert (base->T == TYPE_OBJECT_STATE); - gpy_typedef_t * type = base->o.object_state->definition; - gpy_assert (type->members_defintion); - + struct gpy_object_attrib_t ** members = type->members_defintion; gpy_object_state_t * objs = base->o.object_state; @@ -336,15 +326,9 @@ gpy_object_t * gpy_rr_fold_integer (const int x) args[0] = &a1; args[1] = &a2; - gpy_typedef_t * Int_def = (gpy_typedef_t *) - __GPY_GLOBL_PRIMITIVES->vector[0]; - gpy_assert (Int_def); - + gpy_typedef_t * Int_def = __gpy_integer_type_node; retval = Int_def->tp_new (Int_def, args); gpy_free(args); - - debug ("initilized integer object <%p> to <%i>!\n", - (void*)retval, x ); gpy_assert (retval->T == TYPE_OBJECT_STATE); return retval; @@ -370,7 +354,6 @@ void gpy_rr_eval_print (int fd, int count, ...) for (idx = 0; idx<count; ++idx) { it = va_arg (vl, gpy_object_t *); - gpy_assert (it->T == TYPE_OBJECT_STATE); struct gpy_typedef_t * definition = it->o.object_state->definition; switch (fd) diff --git a/libgpython/runtime/py-type-utils.c b/libgpython/runtime/py-type-utils.c index e11923e9a05..dfa4ca54f7a 100644 --- a/libgpython/runtime/py-type-utils.c +++ b/libgpython/runtime/py-type-utils.c @@ -32,7 +32,8 @@ along with GCC; see the file COPYING3. If not see #define GPY_ARG_LIT_CHECK(A,I,X) \ gpy_assert (A[I]->T == TYPE_OBJECT_LIT); \ - gpy_assert (A[I]->o.literal->type == X); + gpy_assert (A[I]->o.literal->type == X); \ + ++I; bool gpy_args_check_fmt (gpy_object_t ** args, const char * fmt) { @@ -53,27 +54,24 @@ bool gpy_args_check_fmt (gpy_object_t ** args, const char * fmt) case 'i': { GPY_ARG_LIT_CHECK (args, idx, TYPE_INTEGER); - debug ("integer check pass!\n"); } break; case 's': { GPY_ARG_LIT_CHECK (args, idx, TYPE_STRING); - debug ("string check pass!\n"); } + break; case 'p': { GPY_ARG_LIT_CHECK (args, idx, TYPE_ADDR); - debug ("pointer check pass!\n"); } break; case 'A': { GPY_ARG_LIT_CHECK (args, idx, TYPE_ATTRIB_L); - debug ("pointer check pass!\n"); } break; @@ -84,9 +82,6 @@ bool gpy_args_check_fmt (gpy_object_t ** args, const char * fmt) } break; } - if (!retval) - break; - idx++; } return retval; } @@ -99,7 +94,6 @@ int gpy_args_lit_parse_int (gpy_object_t * arg) gpy_assert (arg->o.literal->type == TYPE_INTEGER); retval = arg->o.literal->literal.integer; - debug ("parsed int <%i>!\n", retval); return retval; } @@ -111,7 +105,6 @@ char * gpy_args_lit_parse_string (gpy_object_t * arg) gpy_assert (arg->o.literal->type == TYPE_STRING); retval = arg->o.literal->literal.string; - debug ("parsed string <%s>!\n", retval); return retval; } @@ -123,7 +116,6 @@ unsigned char * gpy_args_lit_parse_pointer (gpy_object_t * arg) gpy_assert (arg->o.literal->type == TYPE_ADDR); retval = arg->o.literal->literal.addr; - debug ("parsed pointer <%p>!\n", (void*) retval); return retval; } @@ -135,7 +127,6 @@ gpy_object_attrib_t ** gpy_args_lit_parse_attrib_table (gpy_object_t * arg) gpy_assert (arg->o.literal->type == TYPE_ATTRIB_L); retval = arg->o.literal->literal.attribs; - debug ("parsed attribute table <%p>!\n", (void*) retval); return retval; } |