1
1
Fork 0
mirror of https://github.com/NixOS/nix.git synced 2025-11-20 17:29:36 +01:00

Always store the children of attribute sets

This commit is contained in:
regnat 2021-02-16 11:38:26 +01:00
parent 357e095a7b
commit 7568cbe344

View file

@ -1385,14 +1385,18 @@ EvalState::AttrAccesResult EvalState::getOptionalAttrField(Value & attrs, const
resultingCursor.addFailedChild(name, e); resultingCursor.addFailedChild(name, e);
throw; throw;
}; };
if (cacheResult.returnCode == ValueCache::CacheMiss) {
resultingCursor = resultingCursor.addChild(name, *currentValue); resultingCursor = resultingCursor.addChild(name, *currentValue);
if (cacheResult.returnCode == ValueCache::CacheMiss && currentValue->type() == nAttrs) {
resultingCursor.addAttrSetChilds(*currentValue->attrs);
}
currentValue->setCache(resultingCursor); currentValue->setCache(resultingCursor);
}
if (countCalls && pos2) attrSelects[*pos2]++; if (countCalls && pos2) attrSelects[*pos2]++;
} }
if (cacheResult.returnCode != ValueCache::CacheMiss) {
resultingCursor = dest.getCache();
currentValue->setCache(resultingCursor);
}
dest = *currentValue; dest = *currentValue;
return { .pos = pos2 }; return { .pos = pos2 };
} }
@ -1410,7 +1414,12 @@ ValueCache ValueCache::addChild(const Symbol& name, const Value& value)
{ {
if (!rawCache) if (!rawCache)
return ValueCache::empty; return ValueCache::empty;
return ValueCache(rawCache->addChild(name, cachedValueFor(value)));
auto cachedValue = cachedValueFor(value);
auto ret = ValueCache(rawCache->addChild(name, cachedValue));
if (value.type() == nAttrs)
ret.addAttrSetChilds(*value.attrs);
return ret;
} }
ValueCache ValueCache::addFailedChild(const Symbol& name, const Error & error) ValueCache ValueCache::addFailedChild(const Symbol& name, const Error & error)
@ -1428,7 +1437,11 @@ void ValueCache::addAttrSetChilds(Bindings & children)
{ {
if (!rawCache) return; if (!rawCache) return;
for (auto & attr : children) { for (auto & attr : children) {
addChild(attr.name, *attr.value); // We could in theory directly store the value, but that would cause
// an infinite recursion in case of a cyclic attrset.
// So in a first time, just store a thunk
rawCache->addChild(attr.name, tree_cache::thunk_t{});
/* addChild(attr.name, *attr.value); */
} }
} }