forked from lix-project/lix
parent
832e111494
commit
da3aea291d
|
@ -19,6 +19,8 @@ create table if not exists Attributes (
|
||||||
|
|
||||||
struct AttrDb
|
struct AttrDb
|
||||||
{
|
{
|
||||||
|
std::atomic_bool failed{false};
|
||||||
|
|
||||||
struct State
|
struct State
|
||||||
{
|
{
|
||||||
SQLite db;
|
SQLite db;
|
||||||
|
@ -64,36 +66,53 @@ struct AttrDb
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
auto state(_state->lock());
|
auto state(_state->lock());
|
||||||
state->txn->commit();
|
if (!failed)
|
||||||
|
state->txn->commit();
|
||||||
state->txn.reset();
|
state->txn.reset();
|
||||||
} catch (...) {
|
} catch (...) {
|
||||||
ignoreException();
|
ignoreException();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename F>
|
||||||
|
AttrId doSQLite(F && fun)
|
||||||
|
{
|
||||||
|
if (failed) return 0;
|
||||||
|
try {
|
||||||
|
return fun();
|
||||||
|
} catch (SQLiteError &) {
|
||||||
|
ignoreException();
|
||||||
|
failed = true;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
AttrId setAttrs(
|
AttrId setAttrs(
|
||||||
AttrKey key,
|
AttrKey key,
|
||||||
const std::vector<Symbol> & attrs)
|
const std::vector<Symbol> & attrs)
|
||||||
{
|
{
|
||||||
auto state(_state->lock());
|
return doSQLite([&]()
|
||||||
|
{
|
||||||
|
auto state(_state->lock());
|
||||||
|
|
||||||
state->insertAttribute.use()
|
|
||||||
(key.first)
|
|
||||||
(key.second)
|
|
||||||
(AttrType::FullAttrs)
|
|
||||||
(0, false).exec();
|
|
||||||
|
|
||||||
AttrId rowId = state->db.getLastInsertedRowId();
|
|
||||||
assert(rowId);
|
|
||||||
|
|
||||||
for (auto & attr : attrs)
|
|
||||||
state->insertAttribute.use()
|
state->insertAttribute.use()
|
||||||
(rowId)
|
(key.first)
|
||||||
(attr)
|
(key.second)
|
||||||
(AttrType::Placeholder)
|
(AttrType::FullAttrs)
|
||||||
(0, false).exec();
|
(0, false).exec();
|
||||||
|
|
||||||
return rowId;
|
AttrId rowId = state->db.getLastInsertedRowId();
|
||||||
|
assert(rowId);
|
||||||
|
|
||||||
|
for (auto & attr : attrs)
|
||||||
|
state->insertAttribute.use()
|
||||||
|
(rowId)
|
||||||
|
(attr)
|
||||||
|
(AttrType::Placeholder)
|
||||||
|
(0, false).exec();
|
||||||
|
|
||||||
|
return rowId;
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
AttrId setString(
|
AttrId setString(
|
||||||
|
@ -101,96 +120,114 @@ struct AttrDb
|
||||||
std::string_view s,
|
std::string_view s,
|
||||||
const char * * context = nullptr)
|
const char * * context = nullptr)
|
||||||
{
|
{
|
||||||
auto state(_state->lock());
|
return doSQLite([&]()
|
||||||
|
{
|
||||||
|
auto state(_state->lock());
|
||||||
|
|
||||||
if (context) {
|
if (context) {
|
||||||
std::string ctx;
|
std::string ctx;
|
||||||
for (const char * * p = context; *p; ++p) {
|
for (const char * * p = context; *p; ++p) {
|
||||||
if (p != context) ctx.push_back(' ');
|
if (p != context) ctx.push_back(' ');
|
||||||
ctx.append(*p);
|
ctx.append(*p);
|
||||||
}
|
}
|
||||||
state->insertAttributeWithContext.use()
|
state->insertAttributeWithContext.use()
|
||||||
(key.first)
|
(key.first)
|
||||||
(key.second)
|
(key.second)
|
||||||
(AttrType::String)
|
(AttrType::String)
|
||||||
(s)
|
(s)
|
||||||
(ctx).exec();
|
(ctx).exec();
|
||||||
} else {
|
} else {
|
||||||
state->insertAttribute.use()
|
state->insertAttribute.use()
|
||||||
(key.first)
|
(key.first)
|
||||||
(key.second)
|
(key.second)
|
||||||
(AttrType::String)
|
(AttrType::String)
|
||||||
(s).exec();
|
(s).exec();
|
||||||
}
|
}
|
||||||
|
|
||||||
return state->db.getLastInsertedRowId();
|
return state->db.getLastInsertedRowId();
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
AttrId setBool(
|
AttrId setBool(
|
||||||
AttrKey key,
|
AttrKey key,
|
||||||
bool b)
|
bool b)
|
||||||
{
|
{
|
||||||
auto state(_state->lock());
|
return doSQLite([&]()
|
||||||
|
{
|
||||||
|
auto state(_state->lock());
|
||||||
|
|
||||||
state->insertAttribute.use()
|
state->insertAttribute.use()
|
||||||
(key.first)
|
(key.first)
|
||||||
(key.second)
|
(key.second)
|
||||||
(AttrType::Bool)
|
(AttrType::Bool)
|
||||||
(b ? 1 : 0).exec();
|
(b ? 1 : 0).exec();
|
||||||
|
|
||||||
return state->db.getLastInsertedRowId();
|
return state->db.getLastInsertedRowId();
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
AttrId setPlaceholder(AttrKey key)
|
AttrId setPlaceholder(AttrKey key)
|
||||||
{
|
{
|
||||||
auto state(_state->lock());
|
return doSQLite([&]()
|
||||||
|
{
|
||||||
|
auto state(_state->lock());
|
||||||
|
|
||||||
state->insertAttribute.use()
|
state->insertAttribute.use()
|
||||||
(key.first)
|
(key.first)
|
||||||
(key.second)
|
(key.second)
|
||||||
(AttrType::Placeholder)
|
(AttrType::Placeholder)
|
||||||
(0, false).exec();
|
(0, false).exec();
|
||||||
|
|
||||||
return state->db.getLastInsertedRowId();
|
return state->db.getLastInsertedRowId();
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
AttrId setMissing(AttrKey key)
|
AttrId setMissing(AttrKey key)
|
||||||
{
|
{
|
||||||
auto state(_state->lock());
|
return doSQLite([&]()
|
||||||
|
{
|
||||||
|
auto state(_state->lock());
|
||||||
|
|
||||||
state->insertAttribute.use()
|
state->insertAttribute.use()
|
||||||
(key.first)
|
(key.first)
|
||||||
(key.second)
|
(key.second)
|
||||||
(AttrType::Missing)
|
(AttrType::Missing)
|
||||||
(0, false).exec();
|
(0, false).exec();
|
||||||
|
|
||||||
return state->db.getLastInsertedRowId();
|
return state->db.getLastInsertedRowId();
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
AttrId setMisc(AttrKey key)
|
AttrId setMisc(AttrKey key)
|
||||||
{
|
{
|
||||||
auto state(_state->lock());
|
return doSQLite([&]()
|
||||||
|
{
|
||||||
|
auto state(_state->lock());
|
||||||
|
|
||||||
state->insertAttribute.use()
|
state->insertAttribute.use()
|
||||||
(key.first)
|
(key.first)
|
||||||
(key.second)
|
(key.second)
|
||||||
(AttrType::Misc)
|
(AttrType::Misc)
|
||||||
(0, false).exec();
|
(0, false).exec();
|
||||||
|
|
||||||
return state->db.getLastInsertedRowId();
|
return state->db.getLastInsertedRowId();
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
AttrId setFailed(AttrKey key)
|
AttrId setFailed(AttrKey key)
|
||||||
{
|
{
|
||||||
auto state(_state->lock());
|
return doSQLite([&]()
|
||||||
|
{
|
||||||
|
auto state(_state->lock());
|
||||||
|
|
||||||
state->insertAttribute.use()
|
state->insertAttribute.use()
|
||||||
(key.first)
|
(key.first)
|
||||||
(key.second)
|
(key.second)
|
||||||
(AttrType::Failed)
|
(AttrType::Failed)
|
||||||
(0, false).exec();
|
(0, false).exec();
|
||||||
|
|
||||||
return state->db.getLastInsertedRowId();
|
return state->db.getLastInsertedRowId();
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
std::optional<std::pair<AttrId, AttrValue>> getAttr(
|
std::optional<std::pair<AttrId, AttrValue>> getAttr(
|
||||||
|
@ -237,12 +274,22 @@ struct AttrDb
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static std::shared_ptr<AttrDb> makeAttrDb(const Hash & fingerprint)
|
||||||
|
{
|
||||||
|
try {
|
||||||
|
return std::make_shared<AttrDb>(fingerprint);
|
||||||
|
} catch (SQLiteError &) {
|
||||||
|
ignoreException();
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
EvalCache::EvalCache(
|
EvalCache::EvalCache(
|
||||||
bool useCache,
|
bool useCache,
|
||||||
const Hash & fingerprint,
|
const Hash & fingerprint,
|
||||||
EvalState & state,
|
EvalState & state,
|
||||||
RootLoader rootLoader)
|
RootLoader rootLoader)
|
||||||
: db(useCache ? std::make_shared<AttrDb>(fingerprint) : nullptr)
|
: db(useCache ? makeAttrDb(fingerprint) : nullptr)
|
||||||
, state(state)
|
, state(state)
|
||||||
, rootLoader(rootLoader)
|
, rootLoader(rootLoader)
|
||||||
{
|
{
|
||||||
|
|
|
@ -63,7 +63,6 @@ static std::tuple<fetchers::Tree, FlakeRef, FlakeRef> fetchOrSubstituteTree(
|
||||||
debug("got tree '%s' from '%s'",
|
debug("got tree '%s' from '%s'",
|
||||||
state.store->printStorePath(tree.storePath), lockedRef);
|
state.store->printStorePath(tree.storePath), lockedRef);
|
||||||
|
|
||||||
|
|
||||||
if (state.allowedPaths)
|
if (state.allowedPaths)
|
||||||
state.allowedPaths->insert(tree.actualPath);
|
state.allowedPaths->insert(tree.actualPath);
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue