Bug Summary

File:out/../deps/v8/src/torque/instance-type-generator.cc
Warning:line 240, column 5
Value stored to 'own_type_pending' is never read

Annotated Source Code

Press '?' to see keyboard shortcuts

clang -cc1 -cc1 -triple x86_64-unknown-linux-gnu -analyze -disable-free -clear-ast-before-backend -disable-llvm-verifier -discard-value-names -main-file-name instance-type-generator.cc -analyzer-checker=core -analyzer-checker=apiModeling -analyzer-checker=unix -analyzer-checker=deadcode -analyzer-checker=cplusplus -analyzer-checker=security.insecureAPI.UncheckedReturn -analyzer-checker=security.insecureAPI.getpw -analyzer-checker=security.insecureAPI.gets -analyzer-checker=security.insecureAPI.mktemp -analyzer-checker=security.insecureAPI.mkstemp -analyzer-checker=security.insecureAPI.vfork -analyzer-checker=nullability.NullPassedToNonnull -analyzer-checker=nullability.NullReturnedFromNonnull -analyzer-output plist -w -setup-static-analyzer -mrelocation-model pic -pic-level 2 -pic-is-pie -mframe-pointer=all -relaxed-aliasing -fmath-errno -ffp-contract=on -fno-rounding-math -mconstructor-aliases -funwind-tables=2 -target-cpu x86-64 -tune-cpu generic -debugger-tuning=gdb -ffunction-sections -fdata-sections -fcoverage-compilation-dir=/home/maurizio/node-v18.6.0/out -resource-dir /usr/local/lib/clang/16.0.0 -D _GLIBCXX_USE_CXX11_ABI=1 -D NODE_OPENSSL_CONF_NAME=nodejs_conf -D NODE_OPENSSL_HAS_QUIC -D V8_GYP_BUILD -D V8_TYPED_ARRAY_MAX_SIZE_IN_HEAP=64 -D __STDC_FORMAT_MACROS -D OPENSSL_NO_PINSHARED -D OPENSSL_THREADS -D V8_TARGET_ARCH_X64 -D V8_HAVE_TARGET_OS -D V8_TARGET_OS_LINUX -D V8_EMBEDDER_STRING="-node.8" -D ENABLE_DISASSEMBLER -D V8_PROMISE_INTERNAL_FIELD_COUNT=1 -D V8_SHORT_BUILTIN_CALLS -D OBJECT_PRINT -D V8_INTL_SUPPORT -D V8_ATOMIC_OBJECT_FIELD_WRITES -D V8_ENABLE_LAZY_SOURCE_POSITIONS -D V8_USE_SIPHASH -D V8_SHARED_RO_HEAP -D V8_WIN64_UNWINDING_INFO -D V8_ENABLE_REGEXP_INTERPRETER_THREADED_DISPATCH -D V8_SNAPSHOT_COMPRESSION -D V8_ENABLE_WEBASSEMBLY -D V8_ENABLE_JAVASCRIPT_PROMISE_HOOKS -D V8_ALLOCATION_FOLDING -D V8_ALLOCATION_SITE_TRACKING -D V8_SCRIPTORMODULE_LEGACY_LIFETIME -D V8_ADVANCED_BIGINT_ALGORITHMS -I ../deps/v8 -I ../deps/v8/include -internal-isystem /usr/lib/gcc/x86_64-redhat-linux/8/../../../../include/c++/8 -internal-isystem /usr/lib/gcc/x86_64-redhat-linux/8/../../../../include/c++/8/x86_64-redhat-linux -internal-isystem /usr/lib/gcc/x86_64-redhat-linux/8/../../../../include/c++/8/backward -internal-isystem /usr/local/lib/clang/16.0.0/include -internal-isystem /usr/local/include -internal-isystem /usr/lib/gcc/x86_64-redhat-linux/8/../../../../x86_64-redhat-linux/include -internal-externc-isystem /include -internal-externc-isystem /usr/include -O3 -Wno-unused-parameter -Wno-return-type -std=gnu++17 -fdeprecated-macro -fdebug-compilation-dir=/home/maurizio/node-v18.6.0/out -ferror-limit 19 -fno-rtti -fgnuc-version=4.2.1 -fcxx-exceptions -fexceptions -vectorize-loops -vectorize-slp -analyzer-output=html -faddrsig -D__GCC_HAVE_DWARF2_CFI_ASM=1 -o /tmp/scan-build-2022-08-22-142216-507842-1 -x c++ ../deps/v8/src/torque/instance-type-generator.cc
1// Copyright 2019 the V8 project authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "src/torque/implementation-visitor.h"
6
7namespace v8 {
8namespace internal {
9namespace torque {
10
11namespace {
12
13// Contains all necessary state for a single class type during the process of
14// assigning instance types, and provides a convenient way to access the list of
15// types that inherit from this one.
16struct InstanceTypeTree {
17 explicit InstanceTypeTree(const ClassType* type)
18 : type(type),
19 start(INT_MAX2147483647),
20 end(INT_MIN(-2147483647 -1)),
21 value(-1),
22 num_values(0),
23 num_own_values(0) {}
24 const ClassType* type;
25 std::vector<std::unique_ptr<InstanceTypeTree>> children;
26 int start; // Start of range for this and subclasses, or INT_MAX.
27 int end; // End of range for this and subclasses, or INT_MIN.
28 int value; // Assigned value for this class itself, or -1 when unassigned.
29 int num_values; // Number of values assigned for this and subclasses.
30 int num_own_values; // How many values this needs (not including subclasses).
31};
32
33// Assembles all class types into a tree, but doesn't yet attempt to assign
34// instance types for them.
35std::unique_ptr<InstanceTypeTree> BuildInstanceTypeTree() {
36 // First, build InstanceTypeTree instances for every class but don't try to
37 // attach them to their subclasses yet.
38 std::unordered_map<const ClassType*, InstanceTypeTree*> map_by_type;
39 std::vector<std::unique_ptr<InstanceTypeTree>> unparented_types;
40 for (auto& p : GlobalContext::AllDeclarables()) {
41 if (const TypeAlias* alias = TypeAlias::DynamicCast(p.get())) {
42 const Type* type = alias->type();
43 const ClassType* class_type = ClassType::DynamicCast(type);
44 if (class_type == nullptr) {
45 continue;
46 }
47 auto& map_slot = map_by_type[class_type];
48 if (map_slot != nullptr) {
49 continue; // We already encountered this type.
50 }
51 std::unique_ptr<InstanceTypeTree> type_tree =
52 std::make_unique<InstanceTypeTree>(class_type);
53 map_slot = type_tree.get();
54 unparented_types.push_back(std::move(type_tree));
55 }
56 }
57
58 // Second, assemble them all into a tree following the inheritance hierarchy.
59 std::unique_ptr<InstanceTypeTree> root;
60 for (auto& type_tree : unparented_types) {
61 const ClassType* parent = type_tree->type->GetSuperClass();
62 if (parent == nullptr) {
63 if (root != nullptr)
64 Error("Expected only one root class type. Found: ", root->type->name(),
65 " and ", type_tree->type->name())
66 .Position(type_tree->type->GetPosition());
67 root = std::move(type_tree);
68 } else {
69 map_by_type[parent]->children.push_back(std::move(type_tree));
70 }
71 }
72 return root;
73}
74
75// Propagates constraints about instance types from children to their parents.
76void PropagateInstanceTypeConstraints(InstanceTypeTree* root) {
77 for (auto& child : root->children) {
78 PropagateInstanceTypeConstraints(child.get());
79 if (child->start < root->start) root->start = child->start;
80 if (child->end > root->end) root->end = child->end;
81 root->num_values += child->num_values;
82 }
83 const InstanceTypeConstraints& constraints =
84 root->type->GetInstanceTypeConstraints();
85 if (!root->type->IsAbstract() && !root->type->HasSameInstanceTypeAsParent()) {
86 root->num_own_values = 1;
87 }
88 root->num_values += root->num_own_values;
89 if (constraints.num_flags_bits != -1) {
90 // Children won't get any types assigned; must be done manually in C++.
91 root->children.clear();
92 root->num_values = 1 << constraints.num_flags_bits;
93 root->num_own_values = root->num_values;
94 root->start = 0;
95 root->end = root->num_values - 1;
96 }
97 if (constraints.value != -1) {
98 if (root->num_own_values != 1) {
99 Error("Instance type value requested for abstract class ",
100 root->type->name())
101 .Position(root->type->GetPosition());
102 }
103 root->value = constraints.value;
104 if (constraints.value < root->start) root->start = constraints.value;
105 if (constraints.value > root->end) root->end = constraints.value;
106 }
107}
108
109// Assigns values for the type itself, not including any children. Returns the
110// next available value.
111int SelectOwnValues(InstanceTypeTree* root, int start_value) {
112 if (root->value == -1) {
113 root->value = start_value;
114 } else if (root->value < start_value) {
115 Error("Failed to assign instance type ", root->value, " to ",
116 root->type->name())
117 .Position(root->type->GetPosition());
118 }
119 return root->value + root->num_own_values;
120}
121
122// Sorting function for types that don't have specific values they must include.
123// Prioritizes bigger type ranges (those with more subtypes) first, and
124// then sorts alphabetically within each size category.
125struct CompareUnconstrainedTypes {
126 constexpr bool operator()(const InstanceTypeTree* a,
127 const InstanceTypeTree* b) const {
128 return (a->num_values > b->num_values)
129 ? true
130 : (a->num_values < b->num_values)
131 ? false
132 : std::less<std::string>()(a->type->name(),
133 b->type->name());
134 }
135};
136
137// Assigns concrete values for every instance type range, and sorts the children
138// at each layer of the tree into increasing order. Appends the newly-assigned
139// tree to the destination vector. Returns the first unassigned value after
140// those that have been used.
141int SolveInstanceTypeConstraints(
142 std::unique_ptr<InstanceTypeTree> root, int start_value,
143 std::vector<std::unique_ptr<InstanceTypeTree>>* destination) {
144 if (root->start < start_value) {
145 Error("Failed to assign instance type ", root->start, " to ",
146 root->type->name())
147 .Position(root->type->GetPosition());
148 }
149
150 // First, separate the children into four groups:
151 // - The one child that must go first, if it exists;
152 // - Children with specific value requirements ("constrained");
153 // - Children without specific value requirements ("unconstrained");
154 // - The one child that must go last, if it exists.
155 std::unique_ptr<InstanceTypeTree> lowest_child;
156 std::unique_ptr<InstanceTypeTree> highest_child;
157 std::multimap<int, std::unique_ptr<InstanceTypeTree>>
158 constrained_children_by_start;
159 // Using std::map because you can't std::move out of a std::set until C++17.
160 std::map<InstanceTypeTree*, std::unique_ptr<InstanceTypeTree>,
161 CompareUnconstrainedTypes>
162 unconstrained_children_by_size;
163 for (auto& child : root->children) {
164 if (child->type->IsHighestInstanceTypeWithinParent()) {
165 if (highest_child) {
166 Error("Two classes requested to be the highest instance type: ",
167 highest_child->type->name(), " and ", child->type->name(),
168 " within range for parent class ", root->type->name())
169 .Position(child->type->GetPosition());
170 }
171 if (child->type->IsLowestInstanceTypeWithinParent()) {
172 Error(
173 "Class requested to be both highest and lowest instance type "
174 "within its parent range: ",
175 child->type->name())
176 .Position(child->type->GetPosition());
177 }
178 highest_child = std::move(child);
179 } else if (child->type->IsLowestInstanceTypeWithinParent()) {
180 if (lowest_child) {
181 Error("Two classes requested to be the lowest instance type: ",
182 lowest_child->type->name(), " and ", child->type->name(),
183 " within range for parent class ", root->type->name())
184 .Position(child->type->GetPosition());
185 }
186 lowest_child = std::move(child);
187 } else if (child->start > child->end) {
188 unconstrained_children_by_size.insert(
189 std::make_pair(child.get(), std::move(child)));
190 } else {
191 constrained_children_by_start.insert(
192 std::make_pair(child->start, std::move(child)));
193 }
194 }
195 root->children.clear();
196
197 bool own_type_pending = root->num_own_values > 0;
198
199 // Second, iterate and place the children in ascending order.
200 if (lowest_child != nullptr) {
201 start_value = SolveInstanceTypeConstraints(std::move(lowest_child),
202 start_value, &root->children);
203 }
204 for (auto& constrained_child_pair : constrained_children_by_start) {
205 // Select the next constrained child type in ascending order.
206 std::unique_ptr<InstanceTypeTree> constrained_child =
207 std::move(constrained_child_pair.second);
208
209 // Try to place the root type before the constrained child type if it fits.
210 if (own_type_pending) {
211 if ((root->value != -1 && root->value < constrained_child->start) ||
212 (root->value == -1 &&
213 start_value + root->num_own_values <= constrained_child->start)) {
214 start_value = SelectOwnValues(root.get(), start_value);
215 own_type_pending = false;
216 }
217 }
218
219 // Try to find any unconstrained children that fit before the constrained
220 // one. This simple greedy algorithm just puts the biggest unconstrained
221 // children in first, which might not fill the space as efficiently as
222 // possible but is good enough for our needs.
223 for (auto it = unconstrained_children_by_size.begin();
224 it != unconstrained_children_by_size.end();) {
225 if (it->second->num_values + start_value <= constrained_child->start) {
226 start_value = SolveInstanceTypeConstraints(
227 std::move(it->second), start_value, &root->children);
228 it = unconstrained_children_by_size.erase(it);
229 } else {
230 ++it;
231 }
232 }
233
234 // Place the constrained child type.
235 start_value = SolveInstanceTypeConstraints(std::move(constrained_child),
236 start_value, &root->children);
237 }
238 if (own_type_pending) {
239 start_value = SelectOwnValues(root.get(), start_value);
240 own_type_pending = false;
Value stored to 'own_type_pending' is never read
241 }
242 for (auto& child_pair : unconstrained_children_by_size) {
243 start_value = SolveInstanceTypeConstraints(std::move(child_pair.second),
244 start_value, &root->children);
245 }
246 if (highest_child != nullptr) {
247 start_value = SolveInstanceTypeConstraints(std::move(highest_child),
248 start_value, &root->children);
249 }
250
251 // Finally, set the range for this class to include all placed subclasses.
252 root->end = start_value - 1;
253 root->start =
254 root->children.empty() ? start_value : root->children.front()->start;
255 if (root->value != -1 && root->value < root->start) {
256 root->start = root->value;
257 }
258 root->num_values = root->end - root->start + 1;
259 root->type->InitializeInstanceTypes(
260 root->value == -1 ? base::Optional<int>{} : root->value,
261 std::make_pair(root->start, root->end));
262
263 if (root->num_values > 0) {
264 destination->push_back(std::move(root));
265 }
266 return start_value;
267}
268
269std::unique_ptr<InstanceTypeTree> SolveInstanceTypeConstraints(
270 std::unique_ptr<InstanceTypeTree> root) {
271 std::vector<std::unique_ptr<InstanceTypeTree>> destination;
272 SolveInstanceTypeConstraints(std::move(root), 0, &destination);
273 return destination.empty() ? nullptr : std::move(destination.front());
274}
275
276std::unique_ptr<InstanceTypeTree> AssignInstanceTypes() {
277 std::unique_ptr<InstanceTypeTree> root = BuildInstanceTypeTree();
278 if (root != nullptr) {
279 PropagateInstanceTypeConstraints(root.get());
280 root = SolveInstanceTypeConstraints(std::move(root));
281 }
282 return root;
283}
284
285// Prints items in macro lists for the given type and its descendants.
286// - definitions: This list is pairs of instance type name and assigned value,
287// such as V(ODDBALL_TYPE, 67). It includes FIRST_* and LAST_* items for each
288// type that has more than one associated InstanceType. Items within those
289// ranges are indented for readability.
290// - values: This list is just instance type names, like V(ODDBALL_TYPE). It
291// does not include any FIRST_* and LAST_* range markers.
292// - fully_defined_single_instance_types: This list is pairs of class name and
293// instance type, for classes which have defined layouts and a single
294// corresponding instance type.
295// - fully_defined_multiple_instance_types: This list is pairs of class name and
296// instance type, for classes which have defined layouts and subclasses.
297// - only_declared_single_instance_types: This list is pairs of class name and
298// instance type, for classes which have a single corresponding instance type
299// and do not have layout definitions in Torque.
300// - only_declared_multiple_instance_types: This list is pairs of class name and
301// instance type, for classes which have subclasses but also have a single
302// corresponding instance type, and do not have layout definitions in Torque.
303// - fully_defined_range_instance_types: This list is triples of class name,
304// first instance type, and last instance type, for classes which have defined
305// layouts and multiple corresponding instance types.
306// - only_declared_range_instance_types: This list is triples of class name,
307// first instance type, and last instance type, for classes which have
308// multiple corresponding instance types and do not have layout definitions in
309// Torque.
310void PrintInstanceTypes(InstanceTypeTree* root, std::ostream& definitions,
311 std::ostream& values,
312 std::ostream& fully_defined_single_instance_types,
313 std::ostream& fully_defined_multiple_instance_types,
314 std::ostream& only_declared_single_instance_types,
315 std::ostream& only_declared_multiple_instance_types,
316 std::ostream& fully_defined_range_instance_types,
317 std::ostream& only_declared_range_instance_types,
318 const std::string& indent) {
319 std::string type_name =
320 CapifyStringWithUnderscores(root->type->name()) + "_TYPE";
321 std::string inner_indent = indent;
322
323 if (root->num_values > 1) {
324 definitions << indent << "V(FIRST_" << type_name << ", " << root->start
325 << ") \\\n";
326 inner_indent += " ";
327 }
328 if (root->num_own_values == 1) {
329 definitions << inner_indent << "V(" << type_name << ", " << root->value
330 << ") /* " << root->type->GetPosition() << " */\\\n";
331 values << " V(" << type_name << ") /* " << root->type->GetPosition()
332 << " */\\\n";
333 std::ostream& type_checker_list =
334 root->type->HasUndefinedLayout()
335 ? (root->num_values == 1 ? only_declared_single_instance_types
336 : only_declared_multiple_instance_types)
337 : (root->num_values == 1 ? fully_defined_single_instance_types
338 : fully_defined_multiple_instance_types);
339 type_checker_list << " V(" << root->type->name() << ", " << type_name
340 << ") /* " << root->type->GetPosition() << " */ \\\n";
341 }
342 for (auto& child : root->children) {
343 PrintInstanceTypes(child.get(), definitions, values,
344 fully_defined_single_instance_types,
345 fully_defined_multiple_instance_types,
346 only_declared_single_instance_types,
347 only_declared_multiple_instance_types,
348 fully_defined_range_instance_types,
349 only_declared_range_instance_types, inner_indent);
350 }
351 if (root->num_values > 1) {
352 // We can't emit LAST_STRING_TYPE because it's not a valid flags
353 // combination. So if the class type has multiple own values, which only
354 // happens when using ANNOTATION_RESERVE_BITS_IN_INSTANCE_TYPE, then omit
355 // the end marker.
356 if (root->num_own_values <= 1) {
357 definitions << indent << "V(LAST_" << type_name << ", " << root->end
358 << ") \\\n";
359 }
360
361 // Only output the instance type range for things other than the root type.
362 if (root->type->GetSuperClass() != nullptr) {
363 std::ostream& range_instance_types =
364 root->type->HasUndefinedLayout() ? only_declared_range_instance_types
365 : fully_defined_range_instance_types;
366 range_instance_types << " V(" << root->type->name() << ", FIRST_"
367 << type_name << ", LAST_" << type_name << ") \\\n";
368 }
369 }
370}
371
372} // namespace
373
374void ImplementationVisitor::GenerateInstanceTypes(
375 const std::string& output_directory) {
376 std::stringstream header;
377 std::string file_name = "instance-types.h";
378 {
379 IncludeGuardScope guard(header, file_name);
380
381 header << "// Instance types for all classes except for those that use "
382 "InstanceType as flags.\n";
383 header << "#define TORQUE_ASSIGNED_INSTANCE_TYPES(V) \\\n";
384 std::unique_ptr<InstanceTypeTree> instance_types = AssignInstanceTypes();
385 std::stringstream values_list;
386 std::stringstream fully_defined_single_instance_types;
387 std::stringstream fully_defined_multiple_instance_types;
388 std::stringstream only_declared_single_instance_types;
389 std::stringstream only_declared_multiple_instance_types;
390 std::stringstream fully_defined_range_instance_types;
391 std::stringstream only_declared_range_instance_types;
392 if (instance_types != nullptr) {
393 PrintInstanceTypes(instance_types.get(), header, values_list,
394 fully_defined_single_instance_types,
395 fully_defined_multiple_instance_types,
396 only_declared_single_instance_types,
397 only_declared_multiple_instance_types,
398 fully_defined_range_instance_types,
399 only_declared_range_instance_types, " ");
400 }
401 header << "\n";
402
403 header << "// Instance types for all classes except for those that use\n";
404 header << "// InstanceType as flags.\n";
405 header << "#define TORQUE_ASSIGNED_INSTANCE_TYPE_LIST(V) \\\n";
406 header << values_list.str();
407 header << "\n";
408
409 header << "// Pairs of (ClassName, INSTANCE_TYPE) for classes that have\n";
410 header << "// full Torque definitions.\n";
411 header << "#define TORQUE_INSTANCE_CHECKERS_SINGLE_FULLY_DEFINED(V) \\\n";
412 header << fully_defined_single_instance_types.str();
413 header << "\n";
414
415 header << "// Pairs of (ClassName, INSTANCE_TYPE) for classes that have\n";
416 header << "// full Torque definitions and subclasses.\n";
417 header << "#define TORQUE_INSTANCE_CHECKERS_MULTIPLE_FULLY_DEFINED(V) \\\n";
418 header << fully_defined_multiple_instance_types.str();
419 header << "\n";
420
421 header << "// Pairs of (ClassName, INSTANCE_TYPE) for classes that are\n";
422 header << "// declared but not defined in Torque. These classes may\n";
423 header << "// correspond with actual C++ classes, but they are not\n";
424 header << "// guaranteed to.\n";
425 header << "#define TORQUE_INSTANCE_CHECKERS_SINGLE_ONLY_DECLARED(V) \\\n";
426 header << only_declared_single_instance_types.str();
427 header << "\n";
428
429 header << "// Pairs of (ClassName, INSTANCE_TYPE) for classes that are\n";
430 header << "// declared but not defined in Torque, and have subclasses.\n";
431 header << "// These classes may correspond with actual C++ classes, but\n";
432 header << "// they are not guaranteed to.\n";
433 header << "#define TORQUE_INSTANCE_CHECKERS_MULTIPLE_ONLY_DECLARED(V) \\\n";
434 header << only_declared_multiple_instance_types.str();
435 header << "\n";
436
437 header << "// Triples of (ClassName, FIRST_TYPE, LAST_TYPE) for classes\n";
438 header << "// that have full Torque definitions.\n";
439 header << "#define TORQUE_INSTANCE_CHECKERS_RANGE_FULLY_DEFINED(V) \\\n";
440 header << fully_defined_range_instance_types.str();
441 header << "\n";
442
443 header << "// Triples of (ClassName, FIRST_TYPE, LAST_TYPE) for classes\n";
444 header << "// that are declared but not defined in Torque. These classes\n";
445 header << "// may correspond with actual C++ classes, but they are not\n";
446 header << "// guaranteed to.\n";
447 header << "#define TORQUE_INSTANCE_CHECKERS_RANGE_ONLY_DECLARED(V) \\\n";
448 header << only_declared_range_instance_types.str();
449 header << "\n";
450
451 std::stringstream torque_defined_class_list;
452 std::stringstream torque_defined_varsize_instance_type_list;
453 std::stringstream torque_defined_fixed_instance_type_list;
454 std::stringstream torque_defined_map_csa_list;
455 std::stringstream torque_defined_map_root_list;
456
457 for (const ClassType* type : TypeOracle::GetClasses()) {
458 std::string upper_case_name = type->name();
459 std::string lower_case_name = SnakeifyString(type->name());
460 std::string instance_type_name =
461 CapifyStringWithUnderscores(type->name()) + "_TYPE";
462
463 if (!type->IsExtern()) {
464 torque_defined_class_list << " V(" << upper_case_name << ") \\\n";
465 }
466
467 if (type->ShouldGenerateUniqueMap()) {
468 torque_defined_map_csa_list << " V(_, " << upper_case_name << "Map, "
469 << lower_case_name << "_map, "
470 << upper_case_name << ") \\\n";
471 torque_defined_map_root_list << " V(Map, " << lower_case_name
472 << "_map, " << upper_case_name
473 << "Map) \\\n";
474 std::stringstream& list =
475 type->HasStaticSize() ? torque_defined_fixed_instance_type_list
476 : torque_defined_varsize_instance_type_list;
477 list << " V(" << instance_type_name << ", " << upper_case_name << ", "
478 << lower_case_name << ") \\\n";
479 }
480 }
481
482 header << "// Fully Torque-defined classes (both internal and exported).\n";
483 header << "#define TORQUE_DEFINED_CLASS_LIST(V) \\\n";
484 header << torque_defined_class_list.str();
485 header << "\n";
486 header << "#define TORQUE_DEFINED_VARSIZE_INSTANCE_TYPE_LIST(V) \\\n";
487 header << torque_defined_varsize_instance_type_list.str();
488 header << "\n";
489 header << "#define TORQUE_DEFINED_FIXED_INSTANCE_TYPE_LIST(V) \\\n";
490 header << torque_defined_fixed_instance_type_list.str();
491 header << "\n";
492 header << "#define TORQUE_DEFINED_INSTANCE_TYPE_LIST(V) \\\n";
493 header << " TORQUE_DEFINED_VARSIZE_INSTANCE_TYPE_LIST(V) \\\n";
494 header << " TORQUE_DEFINED_FIXED_INSTANCE_TYPE_LIST(V) \\\n";
495 header << "\n";
496 header << "#define TORQUE_DEFINED_MAP_CSA_LIST_GENERATOR(V, _) \\\n";
497 header << torque_defined_map_csa_list.str();
498 header << "\n";
499 header << "#define TORQUE_DEFINED_MAP_ROOT_LIST(V) \\\n";
500 header << torque_defined_map_root_list.str();
501 header << "\n";
502 }
503 std::string output_header_path = output_directory + "/" + file_name;
504 WriteFile(output_header_path, header.str());
505
506 GlobalContext::SetInstanceTypesInitialized();
507}
508
509} // namespace torque
510} // namespace internal
511} // namespace v8