clover: Use conversion operator to initialize build log from compat::string.
[mesa.git] / src / gallium / state_trackers / clover / core / module.cpp
1 //
2 // Copyright 2012 Francisco Jerez
3 //
4 // Permission is hereby granted, free of charge, to any person obtaining a
5 // copy of this software and associated documentation files (the "Software"),
6 // to deal in the Software without restriction, including without limitation
7 // the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 // and/or sell copies of the Software, and to permit persons to whom the
9 // Software is furnished to do so, subject to the following conditions:
10 //
11 // The above copyright notice and this permission notice shall be included in
12 // all copies or substantial portions of the Software.
13 //
14 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 // THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
18 // OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
19 // ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
20 // OTHER DEALINGS IN THE SOFTWARE.
21 //
22
23 #include <type_traits>
24
25 #include "core/module.hpp"
26
27 using namespace clover;
28
29 namespace {
30 template<typename T, typename = void>
31 struct _serializer;
32
33 /// Serialize the specified object.
34 template<typename T>
35 void
36 _proc(compat::ostream &os, const T &x) {
37 _serializer<T>::proc(os, x);
38 }
39
40 /// Deserialize the specified object.
41 template<typename T>
42 void
43 _proc(compat::istream &is, T &x) {
44 _serializer<T>::proc(is, x);
45 }
46
47 template<typename T>
48 T
49 _proc(compat::istream &is) {
50 T x;
51 _serializer<T>::proc(is, x);
52 return x;
53 }
54
55 /// Calculate the size of the specified object.
56 template<typename T>
57 void
58 _proc(module::size_t &sz, const T &x) {
59 _serializer<T>::proc(sz, x);
60 }
61
62 /// (De)serialize a scalar value.
63 template<typename T>
64 struct _serializer<T, typename std::enable_if<
65 std::is_scalar<T>::value>::type> {
66 static void
67 proc(compat::ostream &os, const T &x) {
68 os.write(reinterpret_cast<const char *>(&x), sizeof(x));
69 }
70
71 static void
72 proc(compat::istream &is, T &x) {
73 is.read(reinterpret_cast<char *>(&x), sizeof(x));
74 }
75
76 static void
77 proc(module::size_t &sz, const T &x) {
78 sz += sizeof(x);
79 }
80 };
81
82 /// (De)serialize a vector.
83 template<typename T>
84 struct _serializer<compat::vector<T>,
85 typename std::enable_if<
86 !std::is_scalar<T>::value>::type> {
87 static void
88 proc(compat::ostream &os, const compat::vector<T> &v) {
89 _proc<uint32_t>(os, v.size());
90
91 for (size_t i = 0; i < v.size(); i++)
92 _proc<T>(os, v[i]);
93 }
94
95 static void
96 proc(compat::istream &is, compat::vector<T> &v) {
97 v.reserve(_proc<uint32_t>(is));
98
99 for (size_t i = 0; i < v.size(); i++)
100 new(&v[i]) T(_proc<T>(is));
101 }
102
103 static void
104 proc(module::size_t &sz, const compat::vector<T> &v) {
105 sz += sizeof(uint32_t);
106
107 for (size_t i = 0; i < v.size(); i++)
108 _proc<T>(sz, v[i]);
109 }
110 };
111
112 template<typename T>
113 struct _serializer<compat::vector<T>,
114 typename std::enable_if<
115 std::is_scalar<T>::value>::type> {
116 static void
117 proc(compat::ostream &os, const compat::vector<T> &v) {
118 _proc<uint32_t>(os, v.size());
119 os.write(reinterpret_cast<const char *>(v.begin()),
120 v.size() * sizeof(T));
121 }
122
123 static void
124 proc(compat::istream &is, compat::vector<T> &v) {
125 v.reserve(_proc<uint32_t>(is));
126 is.read(reinterpret_cast<char *>(v.begin()),
127 v.size() * sizeof(T));
128 }
129
130 static void
131 proc(module::size_t &sz, const compat::vector<T> &v) {
132 sz += sizeof(uint32_t) + sizeof(T) * v.size();
133 }
134 };
135
136 /// (De)serialize a module::section.
137 template<>
138 struct _serializer<module::section> {
139 template<typename S, typename QT>
140 static void
141 proc(S &s, QT &x) {
142 _proc(s, x.id);
143 _proc(s, x.type);
144 _proc(s, x.size);
145 _proc(s, x.data);
146 }
147 };
148
149 /// (De)serialize a module::argument.
150 template<>
151 struct _serializer<module::argument> {
152 template<typename S, typename QT>
153 static void
154 proc(S &s, QT &x) {
155 _proc(s, x.type);
156 _proc(s, x.size);
157 _proc(s, x.target_size);
158 _proc(s, x.target_align);
159 _proc(s, x.ext_type);
160 }
161 };
162
163 /// (De)serialize a module::symbol.
164 template<>
165 struct _serializer<module::symbol> {
166 template<typename S, typename QT>
167 static void
168 proc(S &s, QT &x) {
169 _proc(s, x.name);
170 _proc(s, x.section);
171 _proc(s, x.offset);
172 _proc(s, x.args);
173 }
174 };
175
176 /// (De)serialize a module.
177 template<>
178 struct _serializer<module> {
179 template<typename S, typename QT>
180 static void
181 proc(S &s, QT &x) {
182 _proc(s, x.syms);
183 _proc(s, x.secs);
184 }
185 };
186 };
187
188 namespace clover {
189 void
190 module::serialize(compat::ostream &os) const {
191 _proc(os, *this);
192 }
193
194 module
195 module::deserialize(compat::istream &is) {
196 return _proc<module>(is);
197 }
198
199 module::size_t
200 module::size() const {
201 size_t sz = 0;
202 _proc(sz, *this);
203 return sz;
204 }
205 }