Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(274)

Side by Side Diff: tools/gn/target_manager.cc

Issue 21114002: Add initial prototype for the GN meta-buildsystem. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: add owners and readme Created 7 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « tools/gn/target_manager.h ('k') | tools/gn/target_manager_unittest.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 // Copyright (c) 2013 The Chromium 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 "tools/gn/target_manager.h"
6
7 #include <deque>
8
9 #include "base/bind.h"
10 #include "base/strings/string_piece.h"
11 #include "tools/gn/build_settings.h"
12 #include "tools/gn/err.h"
13 #include "tools/gn/filesystem_utils.h"
14 #include "tools/gn/item_node.h"
15 #include "tools/gn/scheduler.h"
16 #include "tools/gn/toolchain_manager.h"
17 #include "tools/gn/value.h"
18
19 TargetManager::TargetManager(const BuildSettings* build_settings)
20 : build_settings_(build_settings) {
21 }
22
23 TargetManager::~TargetManager() {
24 }
25
26 Target* TargetManager::GetTarget(const Label& label,
27 const LocationRange& specified_from_here,
28 Target* dep_from,
29 Err* err) {
30 DCHECK(!label.is_null());
31 DCHECK(!label.toolchain_dir().value().empty());
32 DCHECK(!label.toolchain_name().empty());
33
34 base::AutoLock lock(build_settings_->item_tree().lock());
35
36 ItemNode* target_node =
37 build_settings_->item_tree().GetExistingNodeLocked(label);
38 Target* target = NULL;
39 if (!target_node) {
40 // First time we've seen this, may need to load the file.
41
42 // Compute the settings. The common case is that we have a dep_from and
43 // the toolchains match, so we can use the settings from there rather than
44 // querying the toolchain manager (which requires locking, etc.).
45 const Settings* settings;
46 if (dep_from && dep_from->label().ToolchainsEqual(label)) {
47 settings = dep_from->settings();
48 } else {
49 settings =
50 build_settings_->toolchain_manager().GetSettingsForToolchainLocked(
51 specified_from_here, label.GetToolchainLabel(), err);
52 if (!settings)
53 return NULL;
54 }
55
56 target = new Target(settings, label);
57 target_node = new ItemNode(target);
58 target_node->set_originally_referenced_from_here(specified_from_here);
59 build_settings_->item_tree().AddNodeLocked(target_node);
60
61 // We're generating a node when there is no referencing one.
62 if (!dep_from)
63 target_node->set_generated_from_here(specified_from_here);
64
65 // Only schedule loading the given target if somebody is depending on it
66 // (and we optimize by not re-asking it to run the current file).
67 // Otherwise, we're probably generating it right now.
68 if (dep_from && dep_from->label().dir() != label.dir()) {
69 if (!ScheduleInvocationLocked(specified_from_here, label, err))
70 return NULL;
71 }
72 } else if ((target = target_node->item()->AsTarget())) {
73 // Previously saw this item as a target.
74
75 // If we have no dep_from, we're generating it.
76 if (!dep_from) {
77 // In this case, it had better not already be generated.
78 if (target_node->state() != ItemNode::REFERENCED) {
79 *err = Err(specified_from_here,
80 "Duplicate target.",
81 "\"" + label.GetUserVisibleName(true) +
82 "\" being defined here.");
83 err->AppendSubErr(Err(target_node->generated_from_here(),
84 "Originally defined here."));
85 return NULL;
86 } else {
87 target_node->set_generated_from_here(specified_from_here);
88 }
89 }
90 } else {
91 // Error, we previously saw this thing as a non-target.
92 *err = Err(specified_from_here, "Not previously a target.",
93 "The target being declared here was previously seen referenced as a\n"
94 "non-target (like a config)");
95 err->AppendSubErr(Err(target_node->originally_referenced_from_here(),
96 "Originally referenced from here."));
97 return NULL;
98 }
99
100 // Keep a record of the guy asking us for this dependency. We know if
101 // somebody is adding a dependency, that guy it himself not resolved.
102 if (dep_from && target_node->state() != ItemNode::RESOLVED) {
103 build_settings_->item_tree().GetExistingNodeLocked(
104 dep_from->label())->AddDependency(target_node);
105 }
106
107 return target;
108 }
109
110 void TargetManager::TargetGenerationComplete(const Label& label) {
111 base::AutoLock lock(build_settings_->item_tree().lock());
112 build_settings_->item_tree().MarkItemGeneratedLocked(label);
113 }
114
115 void TargetManager::GetAllTargets(
116 std::vector<const Target*>* all_targets) const {
117 base::AutoLock lock(build_settings_->item_tree().lock());
118
119 std::vector<const Item*> all_items;
120 build_settings_->item_tree().GetAllItemsLocked(&all_items);
121 for (size_t i = 0; i < all_items.size(); i++) {
122 const Target* t = all_items[i]->AsTarget();
123 if (t)
124 all_targets->push_back(t);
125 }
126 }
127
128 bool TargetManager::ScheduleInvocationLocked(
129 const LocationRange& specified_from_here,
130 const Label& label,
131 Err* err) {
132 return build_settings_->toolchain_manager().ScheduleInvocationLocked(
133 specified_from_here, label.GetToolchainLabel(), label.dir(), err);
134 }
OLDNEW
« no previous file with comments | « tools/gn/target_manager.h ('k') | tools/gn/target_manager_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698