1.1 --- a/templates/ops.c Sat Nov 26 23:07:09 2016 +0100
1.2 +++ b/templates/ops.c Sun Nov 27 00:33:50 2016 +0100
1.3 @@ -41,6 +41,14 @@
1.4 return 1;
1.5 }
1.6
1.7 +int __get_class_and_store(__ref obj, int pos, __attr value)
1.8 +{
1.9 + /* Forbid class-relative assignments. */
1.10 +
1.11 + __raise_type_error();
1.12 + return 0;
1.13 +}
1.14 +
1.15 /* Introspection. */
1.16
1.17 int __is_instance(__ref obj)
1.18 @@ -124,6 +132,14 @@
1.19
1.20 /* Attribute testing and storage operations. */
1.21
1.22 +int __check_and_store_via_class(__ref obj, int pos, int code, __attr value)
1.23 +{
1.24 + /* Forbid class-relative assignments. */
1.25 +
1.26 + __raise_type_error();
1.27 + return 0;
1.28 +}
1.29 +
1.30 int __check_and_store_via_object(__ref obj, int pos, int code, __attr value)
1.31 {
1.32 if (__HASATTR(obj, pos, code))
1.33 @@ -131,6 +147,10 @@
1.34 __store_via_object(obj, pos, value);
1.35 return 1;
1.36 }
1.37 +
1.38 + /* No suitable attribute. */
1.39 +
1.40 + __raise_type_error();
1.41 return 0;
1.42 }
1.43
1.44 @@ -138,7 +158,11 @@
1.45 {
1.46 if (__check_and_store_via_object(obj, pos, code, value))
1.47 return 1;
1.48 - return __check_and_store_via_object(__get_class(obj), pos, code, value);
1.49 +
1.50 + /* Forbid class-relative assignments. */
1.51 +
1.52 + __raise_type_error();
1.53 + return 0;
1.54 }
1.55
1.56 /* Context-related operations. */
2.1 --- a/templates/ops.h Sat Nov 26 23:07:09 2016 +0100
2.2 +++ b/templates/ops.h Sun Nov 27 00:33:50 2016 +0100
2.3 @@ -19,6 +19,7 @@
2.4 /* Direct storage operations. */
2.5
2.6 int __store_via_object(__ref obj, int pos, __attr value);
2.7 +int __get_class_and_store(__ref obj, int pos, __attr value);
2.8
2.9 /* Introspection. */
2.10
2.11 @@ -43,6 +44,7 @@
2.12
2.13 /* Attribute testing and storage operations. */
2.14
2.15 +int __check_and_store_via_class(__ref obj, int pos, int code, __attr value);
2.16 int __check_and_store_via_object(__ref obj, int pos, int code, __attr value);
2.17 int __check_and_store_via_any(__ref obj, int pos, int code, __attr value);
2.18
3.1 --- a/tests/attr_providers.py Sat Nov 26 23:07:09 2016 +0100
3.2 +++ b/tests/attr_providers.py Sun Nov 27 00:33:50 2016 +0100
3.3 @@ -1,6 +1,7 @@
3.4 class C:
3.5 def __init__(self):
3.6 self.a = 1
3.7 + self.c = 3
3.8
3.9 b = 2
3.10
3.11 @@ -22,11 +23,35 @@
3.12
3.13 x.a = 7
3.14 x.b = 8
3.15 + return f(x)
3.16 +
3.17 +def h(x):
3.18 + x.c
3.19 + x.a = 4
3.20 + x.b
3.21 + return f(x)
3.22
3.23 c = C()
3.24 d = D()
3.25 e = E()
3.26
3.27 -result1 = f(c) # (1, 2)
3.28 -result2 = f(d) # (3, 4)
3.29 -result3 = f(e) # (5, 6)
3.30 +print f(c) # (1, 2)
3.31 +print f(d) # (3, 4)
3.32 +print f(e) # (5, 6)
3.33 +print f(E) # (5, 6)
3.34 +
3.35 +try:
3.36 + print g(c) # should fail with an error caused by a test
3.37 +except TypeError:
3.38 + print "g(c): c is not a suitable argument."
3.39 +
3.40 +print g(d) # (7, 8)
3.41 +
3.42 +try:
3.43 + print g(e) # should fail with an error caused by a test
3.44 +except TypeError:
3.45 + print "g(e): e is not a suitable argument."
3.46 +
3.47 +print g(E) # (7, 8)
3.48 +
3.49 +print h(c) # (4, 5)