Allow super calls in static methods.

This commit is contained in:
Bob Nystrom
2015-09-19 15:19:41 -07:00
parent 19f70b4035
commit 8ef4ea6186
3 changed files with 10 additions and 12 deletions

View File

@ -2150,11 +2150,6 @@ static void super_(Compiler* compiler, bool allowAssignment)
{ {
error(compiler, "Cannot use 'super' outside of a method."); error(compiler, "Cannot use 'super' outside of a method.");
} }
else if (enclosingClass->inStatic)
{
// TODO: Why not?
error(compiler, "Cannot use 'super' in a static method.");
}
loadThis(compiler); loadThis(compiler);

View File

@ -300,13 +300,16 @@ static WrenForeignMethodFn findForeignMethod(WrenVM* vm,
static Value bindMethod(WrenVM* vm, int methodType, int symbol, static Value bindMethod(WrenVM* vm, int methodType, int symbol,
ObjModule* module, ObjClass* classObj, Value methodValue) ObjModule* module, ObjClass* classObj, Value methodValue)
{ {
const char* className = classObj->name->value;
if (methodType == CODE_METHOD_STATIC) classObj = classObj->obj.classObj;
Method method; Method method;
if (IS_STRING(methodValue)) if (IS_STRING(methodValue))
{ {
const char* name = AS_CSTRING(methodValue); const char* name = AS_CSTRING(methodValue);
method.type = METHOD_FOREIGN; method.type = METHOD_FOREIGN;
method.fn.foreign = findForeignMethod(vm, module->name->value, method.fn.foreign = findForeignMethod(vm, module->name->value,
classObj->name->value, className,
methodType == CODE_METHOD_STATIC, methodType == CODE_METHOD_STATIC,
name); name);
@ -322,16 +325,13 @@ static Value bindMethod(WrenVM* vm, int methodType, int symbol,
ObjFn* methodFn = IS_FN(methodValue) ? AS_FN(methodValue) ObjFn* methodFn = IS_FN(methodValue) ? AS_FN(methodValue)
: AS_CLOSURE(methodValue)->fn; : AS_CLOSURE(methodValue)->fn;
// Methods are always bound against the class, and not the metaclass, even // Patch up the bytecode now that we know the superclass.
// for static methods, because static methods don't have instance fields
// anyway.
wrenBindMethodCode(classObj, methodFn); wrenBindMethodCode(classObj, methodFn);
method.type = METHOD_BLOCK; method.type = METHOD_BLOCK;
method.fn.obj = AS_OBJ(methodValue); method.fn.obj = AS_OBJ(methodValue);
} }
if (methodType == CODE_METHOD_STATIC) classObj = classObj->obj.classObj;
wrenBindMethod(vm, classObj, symbol, method); wrenBindMethod(vm, classObj, symbol, method);
return NULL_VAL; return NULL_VAL;
} }

View File

@ -1,5 +1,8 @@
class Foo { class Foo {
static method { static name {
super // expect error System.print("Foo.name") // expect: Foo.name
System.print(super) // expect: Foo
} }
} }
Foo.name