The Battle for Wesnoth  1.19.0+dev
config_cache.hpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2008 - 2024
3  by Pauli Nieminen <paniemin@cc.hut.fi>
4  Part of the Battle for Wesnoth Project https://www.wesnoth.org/
5 
6  This program is free software; you can redistribute it and/or modify
7  it under the terms of the GNU General Public License as published by
8  the Free Software Foundation; either version 2 of the License, or
9  (at your option) any later version.
10  This program is distributed in the hope that it will be useful,
11  but WITHOUT ANY WARRANTY.
12 
13  See the COPYING file for more details.
14 */
15 
16 /**
17  * this file implements game config caching
18  * to speed up startup
19  ***/
20 
21 #pragma once
22 
23 #include <cassert>
24 #include <memory>
25 
27 
28 class config;
29 class abstract_validator;
30 
31 namespace game_config
32 {
33 
34 /**
35  * Used to set and unset scoped defines to preproc_map
36  *
37  * This is preferred form to set defines that aren't global
38  **/
39 template<typename T>
41 {
42 public:
45 
46  /**
47  * Adds normal preproc define.
48  *
49  * @param name name of preproc define to add.
50  * @param add true if we should add this.
51  */
52  scoped_preproc_define_internal(const std::string& name, bool add = true) : name_(name), add_(add)
53  {
54  if(add_) {
55  T::instance().add_define(name_);
56  }
57  }
58 
59  /**
60  * This removes preproc define from cacher
61  */
63  {
64  if(add_) {
65  T::instance().remove_define(name_);
66  }
67  }
68 
69 protected:
70  //
71  // Protected to let test code access
72  //
73 
74  std::string name_;
75  bool add_;
76 
77 };
78 
79 class config_cache;
80 
82 
83 /**
84  * Singleton class to manage game config file caching.
85  * It uses paths to config files as key to find correct cache
86  * @todo Make smarter filetree checksum caching so only required parts
87  * of tree are checked at startup. Trees are overlapping so have
88  * to split trees to subtrees to only do check once per file.
89  * @todo Make cache system easily allow validation of in memory cache objects
90  * using hash checksum of preproc_map.
91  **/
93 {
94 public:
95  /**
96  * Get reference to the singleton object
97  */
98  static config_cache& instance();
99 
100  config_cache(const config_cache&) = delete;
102 
103  const preproc_map& get_preproc_map() const;
104 
105  /**
106  * Gets a config object from given @a path.
107  * @param path file to load. Should be _main.cfg.
108  * @param cfg config object that is written to. Should be empty on entry.
109  * @param validator the WML schema validator, if provided.
110  */
111  void get_config(const std::string& path, config& cfg, abstract_validator* validator = nullptr);
112 
113  /**
114  * Clear stored defines map to default values
115  */
116  void clear_defines();
117 
118  /**
119  * Add a entry to preproc defines map
120  */
121  void add_define(const std::string& define);
122 
123  /**
124  * Remove a entry to preproc defines map
125  */
126  void remove_define(const std::string& define);
127 
128  /**
129  * Enable/disable caching
130  */
131  void set_use_cache(bool use);
132 
133  /**
134  * Enable/disable cache validation
135  */
136  void set_force_valid_cache(bool force);
137 
138  /**
139  * Force cache checksum validation.
140  */
142 
143  /**
144  * Deletes stale cache files not in use by the game.
145  */
146  bool clean_cache();
147 
148  /**
149  * Deletes all cache files.
150  */
151  bool purge_cache();
152 
153 private:
157 
159 
160  std::string cache_file_prefix_;
161 
162  void read_file(const std::string& file, config& cfg);
163  void write_file(std::string file, const config& cfg);
164  void write_file(std::string file, const preproc_map& defines);
165 
166  void read_cache(const std::string& path, config& cfg, abstract_validator* validator = nullptr);
167 
168  void read_configs(const std::string& path, config& cfg, preproc_map& defines, abstract_validator* validator = nullptr);
169  void load_configs(const std::string& path, config& cfg, abstract_validator* validator = nullptr);
170  void read_defines_queue();
171  void read_defines_file(const std::string& path);
172 
175 
176  bool delete_cache_files(const std::vector<std::string>& paths,
177  const std::string& exclude_pattern = "");
178 
179 protected:
180  //
181  // Protected to let test code access
182  //
183 
184  config_cache();
185 
186  void set_force_invalid_cache(bool);
187 };
188 
189 /**
190  * Used to share macros between cache objects
191  * You have to create transaction object to load all
192  * macros to memory and share them subsequent cache loads.
193  * If transaction is locked all stored macros are still
194  * available but new macros aren't added.
195  **/
197 {
198 public:
201 
204 
205  /**
206  * Lock the transaction so no more macros are added
207  */
208  void lock();
209 
210  /**
211  * Used to let std::for_each insert new defines to active_map
212  * map to active
213  */
214  void insert_to_active(const preproc_map::value_type& def);
215 
216  enum state
217  {
221  LOCKED
222  };
223 
224 private:
225  friend class config_cache;
226  friend class fake_transaction;
227 
228  static state state_;
230 
231  std::vector<std::string> define_filenames_;
233 
234  static state get_state()
235  {
236  return state_;
237  }
238 
239  static bool is_active()
240  {
241  return active_ != 0;
242  }
243 
245  {
246  assert(active_);
247  return *active_;
248  }
249 
250  const std::vector<std::string>& get_define_files() const;
251 
252  void add_define_file(const std::string& file);
253 
254  preproc_map& get_active_map(const preproc_map& defines_map);
255 
256  void add_defines_map_diff(preproc_map& defines_map);
257 };
258 
259 /**
260  * Holds a fake cache transaction if no real one is used
261  **/
263 {
266 
267  friend class config_cache;
268 
269  typedef std::unique_ptr<config_cache_transaction> value_type;
271 
273  {
275  trans_.reset(new config_cache_transaction());
276  }
277  }
278 };
279 
280 }
Used in parsing config file.
Definition: validator.hpp:38
A config object defines a single node in a WML file, with access to child nodes.
Definition: config.hpp:159
Used to share macros between cache objects You have to create transaction object to load all macros t...
void add_defines_map_diff(preproc_map &defines_map)
std::vector< std::string > define_filenames_
static config_cache_transaction & instance()
const std::vector< std::string > & get_define_files() const
void lock()
Lock the transaction so no more macros are added.
preproc_map & get_active_map(const preproc_map &defines_map)
void insert_to_active(const preproc_map::value_type &def)
Used to let std::for_each insert new defines to active_map map to active.
config_cache_transaction(const config_cache_transaction &)=delete
static config_cache_transaction * active_
void add_define_file(const std::string &file)
config_cache_transaction & operator=(const config_cache_transaction &)=delete
Singleton class to manage game config file caching.
void load_configs(const std::string &path, config &cfg, abstract_validator *validator=nullptr)
void add_define(const std::string &define)
Add a entry to preproc defines map.
config_cache & operator=(const config_cache &)=delete
void recheck_filetree_checksum()
Force cache checksum validation.
config_cache(const config_cache &)=delete
void read_cache(const std::string &path, config &cfg, abstract_validator *validator=nullptr)
bool purge_cache()
Deletes all cache files.
void set_use_cache(bool use)
Enable/disable caching.
static config_cache & instance()
Get reference to the singleton object.
preproc_map & make_copy_map()
const preproc_map & get_preproc_map() const
void remove_define(const std::string &define)
Remove a entry to preproc defines map.
void clear_defines()
Clear stored defines map to default values.
void write_file(std::string file, const config &cfg)
void read_configs(const std::string &path, config &cfg, preproc_map &defines, abstract_validator *validator=nullptr)
bool clean_cache()
Deletes stale cache files not in use by the game.
void read_file(const std::string &file, config &cfg)
bool delete_cache_files(const std::vector< std::string > &paths, const std::string &exclude_pattern="")
void read_defines_file(const std::string &path)
void add_defines_map_diff(preproc_map &)
void set_force_valid_cache(bool force)
Enable/disable cache validation.
void get_config(const std::string &path, config &cfg, abstract_validator *validator=nullptr)
Gets a config object from given path.
Holds a fake cache transaction if no real one is used.
fake_transaction & operator=(const fake_transaction &)=delete
std::unique_ptr< config_cache_transaction > value_type
fake_transaction(const fake_transaction &)=delete
Used to set and unset scoped defines to preproc_map.
~scoped_preproc_define_internal()
This removes preproc define from cacher.
scoped_preproc_define_internal(const scoped_preproc_define_internal &)=delete
scoped_preproc_define_internal & operator=(const scoped_preproc_define_internal &)=delete
scoped_preproc_define_internal(const std::string &name, bool add=true)
Adds normal preproc define.
Game configuration data as global variables.
Definition: build_info.cpp:61
std::string path
Definition: filesystem.cpp:84
scoped_preproc_define_internal< config_cache > scoped_preproc_define
std::map< std::string, struct preproc_define > preproc_map