Logo AND Algorithmique Numérique Distribuée

Public GIT Repository
36c10b7ab0e9c5e89a2e2ebf1fc46e5cecbb891d
[simgrid.git] / include / xbt / Lib.hpp
1 /* Copyright (c) 2015. The SimGrid Team.
2  * All rights reserved.                                                     */
3
4 /* This program is free software; you can redistribute it and/or modify it
5  * under the terms of the license (GNU LGPL) which comes with this package. */
6
7 #ifndef SIMGRID_XBT_LIB_HPP
8 #define SIMGRID_XBT_LIB_HPP
9
10 #include <cstddef>
11
12 #include <vector>
13
14 namespace simgrid {
15 namespace xbt {
16
17 template<class T>
18 class Lib {
19 private:
20   static std::vector<void(*)(void*)> deleters_;
21 protected:
22   std::vector<void*> facets_;
23 public:
24   static std::size_t add_level(void (*deleter)(void*))
25   {
26     std::size_t res = deleters_.size();
27     deleters_.push_back(deleter);
28     return res;
29   }
30   template<class U> static
31   std::size_t add_level()
32   {
33     return add_level([](void* p){ delete (U*)p; });
34   }
35   Lib() : facets_(deleters_.size(), nullptr) {}
36   ~Lib()
37   {
38     for (std::size_t i = 0; i < facets_.size(); ++i)
39       if (facets_[i] != nullptr)
40         deleters_[i](facets_[i]);
41   }
42
43   // TODO, make type-safe versions of this
44   void* facet(std::size_t level)
45   {
46     if (level >= facets_.size())
47       return nullptr;
48     else
49       return facets_.at(level);
50   }
51   void set_facet(std::size_t level, void* value, bool use_dtor = true)
52   {
53     if (level >= facets_.size())
54       facets_.resize(level + 1, nullptr);
55     void* old_value = this->facet(level);
56     facets_.at(level) = value;
57     if (use_dtor && old_value != nullptr && deleters_[level])
58       deleters_[level](old_value);
59   }
60 };
61
62 template<class T>
63 std::vector<void(*)(void*)> Lib<T>::deleters_ = {};
64
65 }
66 }
67
68 #endif