cvsuser 04/07/23 01:29:24
Modified: languages/python pie-thon.pl
languages/python/t/basic oo_attr.t
languages/python/t/pie b3.t
src objects.c py_func.c
Log:
Pie-thon 91 - builtin __new__; default arguments; methoc call trace
Revision Changes Path
1.63 +12 -2 parrot/languages/python/pie-thon.pl
Index: pie-thon.pl
===================================================================
RCS file: /cvs/public/parrot/languages/python/pie-thon.pl,v
retrieving revision 1.62
retrieving revision 1.63
diff -u -w -r1.62 -r1.63
--- pie-thon.pl 22 Jul 2004 16:19:40 -0000 1.62
+++ pie-thon.pl 23 Jul 2004 08:29:13 -0000 1.63
@@ -9,7 +9,7 @@
use Getopt::Std;
my ($DIS, @dis, @source, $file, %opt, $DEFVAR, $cur_func, $lambda_count,
- %main_names, %namespace);
+ %main_names, %namespace, %may_be_none);
$DIS = 'python mydis.py';
$DEFVAR = 'PerlInt';
@@ -261,7 +261,8 @@
my $self;
if ($meth ne '') {
$self = shift @params;
- shift @{$def_args{$arg}};
+ #shift @{$def_args{$arg}};
+ $arg_count{$arg}--;
}
$params = join("\n\t", map {".param pmc $_"} @params);
@@ -304,6 +305,7 @@
my $reg = 4 + $i;
my $d = pop @{$def_args{$arg}};
my $arg_name = pop @params;
+ $may_be_none{$arg_name} = 1;
print <<EOC;
if argcP >= $i goto arg_ok
find_global $arg_name, "${arg}_$d"
@@ -1353,6 +1355,14 @@
EOC
}
else {
+ if ($may_be_none{$c}) {
+ delete $may_be_none{$c};
+ print <<"EOC";
+ ne_addr $c, None, temp_$code_l
+ $c = new $DEFVAR
+temp_$code_l:
+EOC
+ }
print <<"EOC";
# assign $c, $tos->[1] $cmt
set $p, $tos->[1] $cmt
1.9 +17 -2 parrot/languages/python/t/basic/oo_attr.t
Index: oo_attr.t
===================================================================
RCS file: /cvs/public/parrot/languages/python/t/basic/oo_attr.t,v
retrieving revision 1.8
retrieving revision 1.9
diff -u -w -r1.8 -r1.9
--- oo_attr.t 22 Jul 2004 12:48:32 -0000 1.8
+++ oo_attr.t 23 Jul 2004 08:29:18 -0000 1.9
@@ -1,9 +1,9 @@
-# $Id: oo_attr.t,v 1.8 2004/07/22 12:48:32 leo Exp $
+# $Id: oo_attr.t,v 1.9 2004/07/23 08:29:18 leo Exp $
use strict;
use lib '../../lib';
-use Parrot::Test tests => 12;
+use Parrot::Test tests => 13;
sub test {
language_output_is('python', $_[0], '', $_[1]);
@@ -168,3 +168,18 @@
main()
CODE
+
+test(<<'CODE', 'repr in parent');
+
+class C(int):
+ def __repr__(self):
+ return "C(%d)" % self.i
+class D(C):
+ pass
+def main():
+ d = D()
+ d.i = 2
+ print `d`
+
+main()
+CODE
1.3 +25 -2 parrot/languages/python/t/pie/b3.t
Index: b3.t
===================================================================
RCS file: /cvs/public/parrot/languages/python/t/pie/b3.t,v
retrieving revision 1.2
retrieving revision 1.3
diff -u -w -r1.2 -r1.3
--- b3.t 22 Jul 2004 16:19:46 -0000 1.2
+++ b3.t 23 Jul 2004 08:29:21 -0000 1.3
@@ -1,9 +1,9 @@
-# $Id: b3.t,v 1.2 2004/07/22 16:19:46 leo Exp $
+# $Id: b3.t,v 1.3 2004/07/23 08:29:21 leo Exp $
use strict;
use lib '../../lib';
-use Parrot::Test tests => 4;
+use Parrot::Test tests => 5;
sub test {
language_output_is('python', $_[0], '', $_[1]);
@@ -101,3 +101,26 @@
main()
CODE
+
+test(<<'CODE', 'Int __new__');
+T = int
+
+class TT(T):
+ def __repr__(self):
+ return "T(%d)" % self
+
+class Int(TT):
+ def __new__(cls, value=None):
+ if value is None:
+ value = 42
+ return TT.__new__(cls, value)
+
+def main():
+ i = Int(5)
+ print i, `i`
+ i = Int()
+ print i, `i`
+
+main()
+
+CODE
1.111 +88 -34 parrot/src/objects.c
Index: objects.c
===================================================================
RCS file: /cvs/public/parrot/src/objects.c,v
retrieving revision 1.110
retrieving revision 1.111
diff -u -w -r1.110 -r1.111
--- objects.c 22 Jul 2004 16:19:49 -0000 1.110
+++ objects.c 23 Jul 2004 08:29:24 -0000 1.111
@@ -1,6 +1,6 @@
/*
Copyright: 2001-2003 The Perl Foundation. All Rights Reserved.
-$Id: objects.c,v 1.110 2004/07/22 16:19:49 leo Exp $
+$Id: objects.c,v 1.111 2004/07/23 08:29:24 leo Exp $
=head1 NAME
@@ -201,7 +201,7 @@
if (!*meth)
continue;
meth_str.strstart = const_cast(meth);
- meth_str.strlen = strlen(meth);
+ meth_str.strlen = meth_str.bufused = strlen(meth);
meth_str.hashval = 0;
if (Parrot_find_global(interpreter, class_name, &meth_str)) {
/*
@@ -209,7 +209,10 @@
* slot
*/
LVALUE_CAST(void **,vtable)[i] = ((void**)object_vtable)[i];
- /* printf("deleg_pmc found '%s'\n", meth); */
+#if 0
+ PIO_eprintf(interpreter, "deleg_pmc class '%Ss' found '%s'\n",
+ class_name, meth);
+#endif
}
else {
/*
@@ -278,7 +281,7 @@
/*
* ParrotClass is the baseclass anyway, so build just a new class
*/
- if (base_class->vtable->base_type == enum_class_ParrotClass) {
+ if (base_class == Parrot_base_vtables[enum_class_ParrotClass]->data) {
PMC* class = pmc_new(interpreter, enum_class_ParrotClass);
Parrot_new_class(interpreter, class, child_class_name);
if (is_python)
@@ -320,19 +323,10 @@
/* Our penultimate parent list is a clone of our parent's parent
list, with our parent unshifted onto the beginning */
if (parent_is_class) {
- PMC *all_parents, *last;
+ PMC *all_parents;
all_parents = get_attrib_num((SLOTTYPE *)PMC_data(base_class),
PCD_ALL_PARENTS);
temp_pmc = clone_array(interpreter, all_parents);
- /*
- * if any of the parent is a PMC, we need a deleg_pmc vtable
- * XXX - we always use the parents vtable XXX
- */
- if (0 && VTABLE_elements(interpreter, all_parents)) {
- last = VTABLE_get_pmc_keyed_int(interpreter, all_parents, -1);
- if (!PObj_is_class_TEST(last))
- parent_is_class = 0;
- }
}
else {
@@ -574,7 +568,7 @@
if (!PObj_is_class_TEST(parent_class)) {
PMC *attr;
SLOTTYPE *obj_data = PMC_data(object);
- if (!parent_class->vtable->base_type == enum_class_ParrotClass)
+ if (parent_class->vtable->base_type != enum_class_ParrotClass)
VTABLE_invoke(interpreter, parent_class, NULL);
attr = REG_PMC(5);
set_attrib_num(obj_data, POD_FIRST_ATTRIB, attr);
@@ -733,10 +727,12 @@
void *data = Parrot_save_register_frames(interpreter, meth);
REG_STR(0) = meth_str;
REG_PMC(2) = class;
+#if 0
/* args are just passed on */
PIO_eprintf(interpreter, "__new__ class %Ss nargs = %d\n",
VTABLE_name(interpreter, class),
(int)REG_INT(3));
+#endif
Parrot_runops_fromc(interpreter, meth);
object = REG_PMC(5);
Parrot_restore_register_frames(interpreter, data);
@@ -1159,8 +1155,42 @@
return found;
}
+#ifdef NDEBUG
+# define TRACE_FM(i, c, m, sub)
+#else
+static void
+debug_trace_find_meth(Interp* interpreter, PMC *class, STRING *name, PMC *sub)
+{
+ STRING *class_name;
+ const char *result;
+ if (!Interp_flags_TEST(interpreter, PARROT_TRACE_FLAG))
+ return;
+ if (PObj_is_class_TEST(class)) {
+ SLOTTYPE *class_array = PMC_data(class);
+ PMC *class_name_pmc = get_attrib_num(class_array, PCD_CLASS_NAME);
+ class_name = PMC_str_val(class_name_pmc);
+ }
+ else
+ class_name = class->vtable->whoami;
+ if (sub) {
+ if (sub->vtable->base_type == enum_class_NCI)
+ result = "NCI";
+ else
+ result = "Sub";
+ }
+ else
+ result = "no";
+ PIO_eprintf(interpreter,
+ "# find_method class '%Ss' method '%Ss': %s\n",
+ class_name, name, result);
+}
+
+# define TRACE_FM(i, c, m, sub) \
+ debug_trace_find_meth(i, c, m, sub)
+#endif
+
static PMC *
-find_method_direct(Parrot_Interp interpreter, PMC *class,
+find_method_direct_1(Parrot_Interp interpreter, PMC *class,
STRING *method_name)
{
PMC* method = NULL; /* The method we ultimately return */
@@ -1187,8 +1217,10 @@
method = Parrot_find_global(interpreter,
class_name,
method_name);
- if (method)
+ TRACE_FM(interpreter, class, method_name, method);
+ if (method) {
return method;
+ }
/*
* now look into that PMCs parents
* the parent classes are in vtable->isa_str as blank
@@ -1207,16 +1239,20 @@
string_substr(interpreter, isa, start,
isa->strlen - start, NULL, 0),
method_name);
- if (method)
+ TRACE_FM(interpreter, class, method_name, method);
+ if (method) {
return method;
}
+ }
/* TODO */
break;
}
/* finally look in namespace "object" */
- return Parrot_find_global(interpreter,
+ method = Parrot_find_global(interpreter,
CONST_STRING(interpreter, "object"),
method_name);
+ TRACE_FM(interpreter, class, method_name, method);
+ return method;
}
/* The order of operations:
@@ -1236,6 +1272,7 @@
method_name);
/* Bail immediately if we got something */
+ TRACE_FM(interpreter, class, method_name, method);
if (method) {
return method;
}
@@ -1259,14 +1296,31 @@
get_attrib_num((SLOTTYPE *)PMC_data(curclass),
PCD_CLASS_NAME)),
method_name);
+ TRACE_FM(interpreter, curclass, method_name, method);
if (method) {
Parrot_note_method_offset(interpreter, searchoffset, method);
return method;
}
}
+ TRACE_FM(interpreter, class, method_name, method);
return method;
}
+static PMC *
+find_method_direct(Parrot_Interp interpreter, PMC *class,
+ STRING *method_name)
+{
+ PMC *found = find_method_direct_1(interpreter, class, method_name);
+ STRING * s1, *s2;
+ if (found)
+ return found;
+ s1 = CONST_STRING(interpreter, "__get_string");
+ s2 = CONST_STRING(interpreter, "__get_repr");
+ if (string_equal(interpreter, method_name, s1) == 0)
+ return find_method_direct_1(interpreter, class, s2);
+ return NULL;
+}
+
/*
=item C<void
Parrot_note_method_offset(Parrot_Interp interpreter, UINTVAL offset, PMC *method)>
1.40 +17 -5 parrot/src/py_func.c
Index: py_func.c
===================================================================
RCS file: /cvs/public/parrot/src/py_func.c,v
retrieving revision 1.39
retrieving revision 1.40
diff -u -w -r1.39 -r1.40
--- py_func.c 22 Jul 2004 16:19:49 -0000 1.39
+++ py_func.c 23 Jul 2004 08:29:24 -0000 1.40
@@ -1,6 +1,6 @@
/*
Copyright: 2001-2004 The Perl Foundation. All Rights Reserved.
-$Id: py_func.c,v 1.39 2004/07/22 16:19:49 leo Exp $
+$Id: py_func.c,v 1.40 2004/07/23 08:29:24 leo Exp $
=head1 NAME
@@ -710,9 +710,20 @@
VTABLE_set_integer_native(interp, destination, result);
}
+/*
+ * __new__(class, args...)
+ * when its overridden, the call is treated as a method call with
+ * the class in P2
+ *
+ * This is the internal function, if the __new__ isn't present.
+ * We shift down arguments by one and instantiate the object
+ */
+
static PMC*
-parrot_py_instantiate_new(Parrot_Interp interpreter, PMC *class)
+parrot_py_instantiate_new(Parrot_Interp interpreter, PMC *class, PMC*arg)
{
+ REG_PMC(5) = arg; /* XXX shift down more */
+ --REG_INT(3);
if (PObj_is_class_TEST(class)) {
/* init calls instantiate */
return pmc_new_init(interpreter, class->vtable->base_type, (void*) -1);
@@ -727,6 +738,7 @@
parrot_py_create_default_meths(Interp *interpreter)
{
STRING *pio = CONST_STRING(interpreter, "PIO");
+ STRING *piop = CONST_STRING(interpreter, "PIPP");
STRING *class = CONST_STRING(interpreter, "object");
STRING *repr = CONST_STRING(interpreter, "__get_repr");
@@ -739,7 +751,7 @@
F2DPTR(parrot_py_str), str, pio);
*/
parrot_py_global(interpreter,
- F2DPTR(parrot_py_instantiate_new), new__, pio);
+ F2DPTR(parrot_py_instantiate_new), new__, piop);
mmd_register(interpreter, MMD_DIVIDE,
enum_class_PerlInt, enum_class_PerlInt,
@@ -938,7 +950,7 @@
*/
Hash *h;
HashBucket *b;
- PMC *p, *class;
+ PMC *p, *class = NULL;
STRING *class_name;
INTVAL offs;
SLOTTYPE *class_array;
@@ -984,7 +996,7 @@
*/
real_exception(interpreter, NULL, E_AttributeError,
"'%Ss' object has no attribute '%Ss'",
- class, /* TODO demangle */
+ class ? class : object, /* TODO demangle */
name);
return PMCNULL;