bool JSObject::getPropertyAttributes(const Identifier& propertyName, unsigned& attributes) const { if (_prop.get(propertyName, attributes)) return true; // Look in the static hashtable of properties const HashEntry* e = findPropertyHashEntry(propertyName); if (e) { attributes = e->attr; return true; } return false; }
bool JSObject::getPropertyAttributes(ExecState* exec, const Identifier& propertyName, unsigned& attributes) const { if (m_structureID->get(propertyName, attributes) != WTF::notFound) return true; // Look in the static hashtable of properties const HashEntry* entry = findPropertyHashEntry(exec, propertyName); if (entry) { attributes = entry->attributes(); return true; } return false; }
bool TiObject::getPropertyAttributes(TiExcState* exec, const Identifier& propertyName, unsigned& attributes) const { TiCell* specificValue; if (m_structure->get(propertyName, attributes, specificValue) != WTI::notFound) return true; // Look in the static hashtable of properties const HashEntry* entry = findPropertyHashEntry(exec, propertyName); if (entry) { attributes = entry->attributes(); return true; } return false; }
// ECMA 8.6.2.5 bool JSObject::deleteProperty(ExecState* exec, const Identifier& propertyName) { unsigned attributes; if (m_structureID->get(propertyName, attributes) != WTF::notFound) { if ((attributes & DontDelete)) return false; removeDirect(propertyName); return true; } // Look in the static hashtable of properties const HashEntry* entry = findPropertyHashEntry(exec, propertyName); if (entry && entry->attributes() & DontDelete) return false; // this builtin property can't be deleted // FIXME: Should the code here actually do some deletion? return true; }
// ECMA 8.6.2.5 bool JSObject::deleteProperty(ExecState * /*exec*/, const Identifier &propertyName) { unsigned attributes; JSValue *v = _prop.get(propertyName, attributes); if (v) { if ((attributes & DontDelete)) return false; _prop.remove(propertyName); if (attributes & GetterSetter) _prop.setHasGetterSetterProperties(_prop.containsGettersOrSetters()); return true; } // Look in the static hashtable of properties const HashEntry* entry = findPropertyHashEntry(propertyName); if (entry && entry->attr & DontDelete) return false; // this builtin property can't be deleted return true; }
// ECMA 8.6.2.2 void JSObject::put(ExecState *exec, const Identifier &propertyName, JSValue *value, int attr) { assert(value); // non-standard netscape extension if (propertyName == exec->propertyNames().underscoreProto) { JSObject* proto = value->getObject(); while (proto) { if (proto == this) { throwError(exec, GeneralError, "cyclic __proto__ value"); return; } proto = proto->prototype() ? proto->prototype()->getObject() : 0; } setPrototype(value); return; } // putValue() is used for JS assignemnts. It passes no attribute. // Assume that a C++ implementation knows what it is doing // and don't spend time doing a read-only check for it. bool checkRO = (attr == None || attr == DontDelete); if (checkRO) { // Check for static properties that are ReadOnly; the property map will check the dynamic properties. // We don't have to worry about setters being read-only as they can't be added with such an attribute. // We also need to inherit any attributes we have from the entry const HashEntry* entry = findPropertyHashEntry(propertyName); if (entry) { if (entry->attr & ReadOnly) { #ifdef KJS_VERBOSE fprintf( stderr, "WARNING: static property %s is ReadOnly\n", propertyName.ascii() ); #endif return; } attr = entry->attr; } } // Check if there are any setters or getters in the prototype chain JSObject *obj = this; bool hasGettersOrSetters = false; while (true) { if (obj->_prop.hasGetterSetterProperties()) { hasGettersOrSetters = true; break; } if (!obj->_proto->isObject()) break; obj = static_cast<JSObject *>(obj->_proto); } if (hasGettersOrSetters) { obj = this; while (true) { unsigned attributes; if (JSValue *gs = obj->_prop.get(propertyName, attributes)) { if (attributes & GetterSetter) { JSObject *setterFunc = static_cast<GetterSetterImp *>(gs)->getSetter(); if (!setterFunc) { throwSetterError(exec); return; } List args; args.append(value); setterFunc->call(exec, this, args); return; } else { // If there's an existing property on the object or one of its // prototype it should be replaced, so we just break here. break; } } if (!obj->_proto->isObject()) break; obj = static_cast<JSObject *>(obj->_proto); } } _prop.put(propertyName,value,attr,checkRO); }