Obey strict mode for property getters and setters

Change-Id: I6f51cd72c2607989c55373dfee53130381f5ef75
Reviewed-by: Erik Verbruggen <erik.verbruggen@digia.com>
This commit is contained in:
Lars Knoll 2012-11-27 23:23:04 +01:00 committed by Erik Verbruggen
parent 1dbad2e689
commit 94a344c01a
5 changed files with 18 additions and 17 deletions

View File

@ -118,7 +118,7 @@ void DeclarativeEnvironment::createMutableBinding(ExecutionContext *ctx, String
desc.configurable = deletable ? PropertyDescriptor::Set : PropertyDescriptor::Unset; desc.configurable = deletable ? PropertyDescriptor::Set : PropertyDescriptor::Unset;
desc.writable = PropertyDescriptor::Set; desc.writable = PropertyDescriptor::Set;
desc.enumberable = PropertyDescriptor::Set; desc.enumberable = PropertyDescriptor::Set;
activation->__defineOwnProperty__(ctx, name, &desc, true); activation->__defineOwnProperty__(ctx, name, &desc);
} }
void DeclarativeEnvironment::setMutableBinding(String *name, Value value, bool strict) void DeclarativeEnvironment::setMutableBinding(String *name, Value value, bool strict)
@ -159,9 +159,10 @@ Value DeclarativeEnvironment::getBindingValue(String *name, bool strict) const
bool DeclarativeEnvironment::deleteBinding(ExecutionContext *ctx, String *name) bool DeclarativeEnvironment::deleteBinding(ExecutionContext *ctx, String *name)
{ {
if (activation) if (activation)
activation->__delete__(ctx, name, false); activation->__delete__(ctx, name);
// ### throw in strict mode? if (ctx->lexicalEnvironment->strictMode)
__qmljs_throw_type_error(ctx);
return false; return false;
} }

View File

@ -165,7 +165,7 @@ bool Object::__canPut__(ExecutionContext *ctx, String *name)
} }
// Section 8.12.5 // Section 8.12.5
void Object::__put__(ExecutionContext *ctx, String *name, const Value &value, bool throwException) void Object::__put__(ExecutionContext *ctx, String *name, const Value &value)
{ {
// clause 1 // clause 1
if (!__canPut__(ctx, name)) if (!__canPut__(ctx, name))
@ -183,7 +183,7 @@ void Object::__put__(ExecutionContext *ctx, String *name, const Value &value, bo
// ### to simplify and speed up we should expand the relevant parts here (clauses 6,7,9,10,12,13) // ### to simplify and speed up we should expand the relevant parts here (clauses 6,7,9,10,12,13)
PropertyDescriptor desc = PropertyDescriptor::fromValue(value); PropertyDescriptor desc = PropertyDescriptor::fromValue(value);
__defineOwnProperty__(ctx, name, &desc, throwException); __defineOwnProperty__(ctx, name, &desc);
return; return;
} }
@ -210,7 +210,7 @@ void Object::__put__(ExecutionContext *ctx, String *name, const Value &value, bo
} }
reject: reject:
if (throwException) if (ctx->lexicalEnvironment->strictMode)
__qmljs_throw_type_error(ctx); __qmljs_throw_type_error(ctx);
} }
@ -224,7 +224,7 @@ bool Object::__hasProperty__(ExecutionContext *ctx, String *name) const
} }
// Section 8.12.7 // Section 8.12.7
bool Object::__delete__(ExecutionContext *ctx, String *name, bool throwException) bool Object::__delete__(ExecutionContext *ctx, String *name)
{ {
if (members) { if (members) {
if (PropertyTableEntry *entry = members->findEntry(name)) { if (PropertyTableEntry *entry = members->findEntry(name)) {
@ -232,7 +232,7 @@ bool Object::__delete__(ExecutionContext *ctx, String *name, bool throwException
members->remove(entry); members->remove(entry);
return true; return true;
} }
if (throwException) if (ctx->lexicalEnvironment->strictMode)
__qmljs_throw_type_error(ctx); __qmljs_throw_type_error(ctx);
return false; return false;
} }
@ -241,7 +241,7 @@ bool Object::__delete__(ExecutionContext *ctx, String *name, bool throwException
} }
// Section 8.12.9 // Section 8.12.9
bool Object::__defineOwnProperty__(ExecutionContext *ctx, String *name, PropertyDescriptor *desc, bool throwException) bool Object::__defineOwnProperty__(ExecutionContext *ctx, String *name, PropertyDescriptor *desc)
{ {
if (!members) if (!members)
members = new PropertyTable(); members = new PropertyTable();
@ -315,7 +315,7 @@ bool Object::__defineOwnProperty__(ExecutionContext *ctx, String *name, Property
return true; return true;
reject: reject:
qDebug() << "___put__ rejected" << name->toQString(); qDebug() << "___put__ rejected" << name->toQString();
if (throwException) if (ctx->lexicalEnvironment->strictMode)
__qmljs_throw_type_error(ctx); __qmljs_throw_type_error(ctx);
return false; return false;
} }

View File

@ -408,11 +408,11 @@ struct Object {
virtual Value __get__(ExecutionContext *ctx, String *name); virtual Value __get__(ExecutionContext *ctx, String *name);
virtual PropertyDescriptor *__getOwnProperty__(ExecutionContext *ctx, String *name); virtual PropertyDescriptor *__getOwnProperty__(ExecutionContext *ctx, String *name);
virtual PropertyDescriptor *__getPropertyDescriptor__(ExecutionContext *ctx, String *name, PropertyDescriptor *to_fill); virtual PropertyDescriptor *__getPropertyDescriptor__(ExecutionContext *ctx, String *name, PropertyDescriptor *to_fill);
virtual void __put__(ExecutionContext *ctx, String *name, const Value &value, bool throwException = false); virtual void __put__(ExecutionContext *ctx, String *name, const Value &value);
virtual bool __canPut__(ExecutionContext *ctx, String *name); virtual bool __canPut__(ExecutionContext *ctx, String *name);
virtual bool __hasProperty__(ExecutionContext *ctx, String *name) const; virtual bool __hasProperty__(ExecutionContext *ctx, String *name) const;
virtual bool __delete__(ExecutionContext *ctx, String *name, bool throwException = false); virtual bool __delete__(ExecutionContext *ctx, String *name);
virtual bool __defineOwnProperty__(ExecutionContext *ctx, String *name, PropertyDescriptor *desc, bool throwException = false); virtual bool __defineOwnProperty__(ExecutionContext *ctx, String *name, PropertyDescriptor *desc);
// //
// helpers // helpers

View File

@ -192,7 +192,7 @@ Value __qmljs_delete_subscript(ExecutionContext *ctx, Value base, Value index)
Value __qmljs_delete_member(ExecutionContext *ctx, Value base, String *name) Value __qmljs_delete_member(ExecutionContext *ctx, Value base, String *name)
{ {
Value obj = base.toObject(ctx); Value obj = base.toObject(ctx);
return Value::fromBoolean(obj.objectValue()->__delete__(ctx, name, true)); return Value::fromBoolean(obj.objectValue()->__delete__(ctx, name));
} }
Value __qmljs_delete_name(ExecutionContext *ctx, String *name) Value __qmljs_delete_name(ExecutionContext *ctx, String *name)
@ -543,7 +543,7 @@ Value __qmljs_new_string_object(ExecutionContext *ctx, String *string)
void __qmljs_set_property(ExecutionContext *ctx, Value object, String *name, Value value) void __qmljs_set_property(ExecutionContext *ctx, Value object, String *name, Value value)
{ {
object.objectValue()->__put__(ctx, name, value, /*flags*/ 0); object.objectValue()->__put__(ctx, name, value);
} }
Value __qmljs_get_element(ExecutionContext *ctx, Value object, Value index) Value __qmljs_get_element(ExecutionContext *ctx, Value object, Value index)
@ -583,7 +583,7 @@ void __qmljs_set_element(ExecutionContext *ctx, Value object, Value index, Value
if (! object.isObject()) if (! object.isObject())
object = __qmljs_to_object(object, ctx); object = __qmljs_to_object(object, ctx);
object.objectValue()->__put__(ctx, name, value, /*flags*/ 0); object.objectValue()->__put__(ctx, name, value);
} }
Value __qmljs_foreach_iterator_object(Value in, ExecutionContext *ctx) Value __qmljs_foreach_iterator_object(Value in, ExecutionContext *ctx)

View File

@ -1414,7 +1414,7 @@ Value ArrayPrototype::method_pop(ExecutionContext *ctx)
if (r2) { if (r2) {
String *r6 = Value::fromDouble(r2 - 1).toString(ctx); String *r6 = Value::fromDouble(r2 - 1).toString(ctx);
Value r7 = self.property(ctx, r6); Value r7 = self.property(ctx, r6);
self.objectValue()->__delete__(ctx, r6, 0); self.objectValue()->__delete__(ctx, r6);
self.objectValue()->__put__(ctx, ctx->engine->id_length, Value::fromDouble(2 - 1)); self.objectValue()->__put__(ctx, ctx->engine->id_length, Value::fromDouble(2 - 1));
return r7; return r7;
} }