1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
|
// file : libbuild2/config/module.hxx -*- C++ -*-
// license : MIT; see accompanying LICENSE file
#ifndef LIBBUILD2_CONFIG_MODULE_HXX
#define LIBBUILD2_CONFIG_MODULE_HXX
#include <map>
#include <libbutl/prefix-map.mxx>
#include <libbuild2/types.hxx>
#include <libbuild2/utility.hxx>
#include <libbuild2/module.hxx>
#include <libbuild2/variable.hxx>
namespace build2
{
namespace config
{
// An ordered list of build system modules each with an ordered list of
// list of config.* variables and their "save flags" (see save_variable())
// that are used (as opposed to just being specified) in this
// configuration. Populated by the config utility functions (required(),
// optional()) and saved in the order populated.
//
struct saved_variable
{
reference_wrapper<const variable> var;
uint64_t flags;
};
struct saved_variables: vector<saved_variable>
{
// Normally each module only have a handful of config variables and we
// only do this during configuration so for now we do linear search
// instead of adding a map.
//
const_iterator
find (const variable& var) const
{
return std::find_if (
begin (),
end (),
[&var] (const saved_variable& v) {return var == v.var;});
}
};
struct saved_modules: butl::prefix_map<string, saved_variables, '.'>
{
// Priority order with INT32_MIN being the highest. Modules with the
// same priority are saved in the order inserted.
//
// Generally, the idea is that we want higher-level modules at the top
// of the file since that's the configuration that we usualy want to
// change. So we have the following priority bands/defaults:
//
// 101-200/150 - code generators (e.g., yacc, bison)
// 201-300/250 - compilers (e.g., C, C++),
// 301-400/350 - binutils (ar, ld)
//
std::multimap<std::int32_t, const_iterator> order;
pair<iterator, bool>
insert (string name, int prio = 0)
{
auto p (emplace (move (name), saved_variables ()));
if (p.second)
order.emplace (prio, p.first);
return p;
}
};
struct module: build2::module
{
config::saved_modules saved_modules;
// Return true if variable/module were newly inserted.
//
bool
save_variable (const variable&, uint64_t flags = 0);
bool
save_module (const char* name, int prio = 0);
// Return true if the variable is already saved.
//
bool
saved (const variable& var)
{
auto i (saved_modules.find_sup (var.name));
return i != saved_modules.end () &&
i->second.find (var) != i->second.end ();
}
// Cached (during init) config.config.persist value, if defined.
//
const vector<pair<string, string>>* persist = nullptr;
static const string name;
static const uint64_t version;
};
}
}
#endif // LIBBUILD2_CONFIG_MODULE_HXX
|