void* nsPropertyTable::GetPropertyInternal(nsPropertyOwner aObject, nsIAtom *aPropertyName, bool aRemove, nsresult *aResult) { NS_PRECONDITION(aPropertyName && aObject, "unexpected null param"); nsresult rv = NS_PROPTABLE_PROP_NOT_THERE; void *propValue = nullptr; PropertyList* propertyList = GetPropertyListFor(aPropertyName); if (propertyList) { auto entry = static_cast<PropertyListMapEntry*> (propertyList->mObjectValueMap.Search(aObject)); if (entry) { propValue = entry->value; if (aRemove) { // don't call propertyList->mDtorFunc. That's the caller's job now. propertyList->mObjectValueMap.RemoveEntry(entry); } rv = NS_OK; } } if (aResult) *aResult = rv; return propValue; }
void* nsPropertyTable::GetPropertyInternal(nsPropertyOwner aObject, nsIAtom *aPropertyName, bool aRemove, nsresult *aResult) { NS_PRECONDITION(aPropertyName && aObject, "unexpected null param"); nsresult rv = NS_PROPTABLE_PROP_NOT_THERE; void *propValue = nullptr; PropertyList* propertyList = GetPropertyListFor(aPropertyName); if (propertyList) { PropertyListMapEntry *entry = static_cast<PropertyListMapEntry*> (PL_DHashTableOperate(&propertyList->mObjectValueMap, aObject, PL_DHASH_LOOKUP)); if (PL_DHASH_ENTRY_IS_BUSY(entry)) { propValue = entry->value; if (aRemove) { // don't call propertyList->mDtorFunc. That's the caller's job now. PL_DHashTableRawRemove(&propertyList->mObjectValueMap, entry); } rv = NS_OK; } } if (aResult) *aResult = rv; return propValue; }
nsresult nsPropertyTable::SetPropertyInternal(nsPropertyOwner aObject, nsIAtom *aPropertyName, void *aPropertyValue, NSPropertyDtorFunc aPropDtorFunc, void *aPropDtorData, bool aTransfer, void **aOldValue) { NS_PRECONDITION(aPropertyName && aObject, "unexpected null param"); PropertyList* propertyList = GetPropertyListFor(aPropertyName); if (propertyList) { // Make sure the dtor function and data and the transfer flag match if (aPropDtorFunc != propertyList->mDtorFunc || aPropDtorData != propertyList->mDtorData || aTransfer != propertyList->mTransfer) { NS_WARNING("Destructor/data mismatch while setting property"); return NS_ERROR_INVALID_ARG; } } else { propertyList = new PropertyList(aPropertyName, aPropDtorFunc, aPropDtorData, aTransfer); if (!propertyList || !propertyList->mObjectValueMap.ops) { delete propertyList; return NS_ERROR_OUT_OF_MEMORY; } propertyList->mNext = mPropertyList; mPropertyList = propertyList; } // The current property value (if there is one) is replaced and the current // value is destroyed nsresult result = NS_OK; PropertyListMapEntry *entry = static_cast<PropertyListMapEntry*> (PL_DHashTableOperate(&propertyList->mObjectValueMap, aObject, PL_DHASH_ADD)); if (!entry) return NS_ERROR_OUT_OF_MEMORY; // A nullptr entry->key is the sign that the entry has just been allocated // for us. If it's non-nullptr then we have an existing entry. if (entry->key) { if (aOldValue) *aOldValue = entry->value; else if (propertyList->mDtorFunc) propertyList->mDtorFunc(const_cast<void*>(entry->key), aPropertyName, entry->value, propertyList->mDtorData); result = NS_PROPTABLE_PROP_OVERWRITTEN; } else if (aOldValue) { *aOldValue = nullptr; } entry->key = aObject; entry->value = aPropertyValue; return result; }
nsresult nsPropertyTable::DeleteProperty(nsPropertyOwner aObject, nsIAtom *aPropertyName) { NS_PRECONDITION(aPropertyName && aObject, "unexpected null param"); PropertyList* propertyList = GetPropertyListFor(aPropertyName); if (propertyList) { if (propertyList->DeletePropertyFor(aObject)) return NS_OK; } return NS_PROPTABLE_PROP_NOT_THERE; }