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 #ifndef TOOLS_GN_TARGET_H_ 6 #define TOOLS_GN_TARGET_H_ 7 8 #include <set> 9 #include <string> 10 #include <vector> 11 12 #include "base/basictypes.h" 13 #include "base/compiler_specific.h" 14 #include "base/logging.h" 15 #include "base/strings/string_piece.h" 16 #include "base/synchronization/lock.h" 17 #include "tools/gn/action_values.h" 18 #include "tools/gn/config_values.h" 19 #include "tools/gn/item.h" 20 #include "tools/gn/label_ptr.h" 21 #include "tools/gn/ordered_set.h" 22 #include "tools/gn/output_file.h" 23 #include "tools/gn/source_file.h" 24 #include "tools/gn/unique_vector.h" 25 26 class InputFile; 27 class Settings; 28 class Token; 29 class Toolchain; 30 31 class Target : public Item { 32 public: 33 enum OutputType { 34 UNKNOWN, 35 GROUP, 36 EXECUTABLE, 37 SHARED_LIBRARY, 38 STATIC_LIBRARY, 39 SOURCE_SET, 40 COPY_FILES, 41 ACTION, 42 ACTION_FOREACH, 43 }; 44 typedef std::vector<SourceFile> FileList; 45 typedef std::vector<std::string> StringVector; 46 47 Target(const Settings* settings, const Label& label); 48 virtual ~Target(); 49 50 // Returns a string naming the output type. 51 static const char* GetStringForOutputType(OutputType type); 52 53 // Item overrides. 54 virtual Target* AsTarget() OVERRIDE; 55 virtual const Target* AsTarget() const OVERRIDE; 56 virtual bool OnResolved(Err* err) OVERRIDE; 57 output_type()58 OutputType output_type() const { return output_type_; } set_output_type(OutputType t)59 void set_output_type(OutputType t) { output_type_ = t; } 60 61 // Can be linked into other targets. 62 bool IsLinkable() const; 63 64 // Can have dependencies linked in. 65 bool IsFinal() const; 66 67 // Will be the empty string to use the target label as the output name. 68 // See GetComputedOutputName(). output_name()69 const std::string& output_name() const { return output_name_; } set_output_name(const std::string & name)70 void set_output_name(const std::string& name) { output_name_ = name; } 71 72 // Returns the output name for this target, which is the output_name if 73 // specified, or the target label if not. If the flag is set, it will also 74 // include any output prefix specified on the tool (often "lib" on Linux). 75 // 76 // Because this depends on the tool for this target, the toolchain must 77 // have been set before calling. 78 std::string GetComputedOutputName(bool include_prefix) const; 79 output_extension()80 const std::string& output_extension() const { return output_extension_; } set_output_extension(const std::string & extension)81 void set_output_extension(const std::string& extension) { 82 output_extension_ = extension; 83 } 84 sources()85 const FileList& sources() const { return sources_; } sources()86 FileList& sources() { return sources_; } 87 88 // Set to true when all sources are public. This is the default. In this case 89 // the public headers list should be empty. all_headers_public()90 bool all_headers_public() const { return all_headers_public_; } set_all_headers_public(bool p)91 void set_all_headers_public(bool p) { all_headers_public_ = p; } 92 93 // When all_headers_public is false, this is the list of public headers. It 94 // could be empty which would mean no headers are public. public_headers()95 const FileList& public_headers() const { return public_headers_; } public_headers()96 FileList& public_headers() { return public_headers_; } 97 98 // Whether this target's includes should be checked by "gn check". check_includes()99 bool check_includes() const { return check_includes_; } set_check_includes(bool ci)100 void set_check_includes(bool ci) { check_includes_ = ci; } 101 102 // Whether this static_library target should have code linked in. complete_static_lib()103 bool complete_static_lib() const { return complete_static_lib_; } set_complete_static_lib(bool complete)104 void set_complete_static_lib(bool complete) { 105 DCHECK_EQ(STATIC_LIBRARY, output_type_); 106 complete_static_lib_ = complete; 107 } 108 testonly()109 bool testonly() const { return testonly_; } set_testonly(bool value)110 void set_testonly(bool value) { testonly_ = value; } 111 112 // Compile-time extra dependencies. inputs()113 const FileList& inputs() const { return inputs_; } inputs()114 FileList& inputs() { return inputs_; } 115 116 // Runtime dependencies. data()117 const FileList& data() const { return data_; } data()118 FileList& data() { return data_; } 119 120 // Returns true if targets depending on this one should have an order 121 // dependency. hard_dep()122 bool hard_dep() const { 123 return output_type_ == ACTION || 124 output_type_ == ACTION_FOREACH || 125 output_type_ == COPY_FILES; 126 } 127 128 // Linked private dependencies. private_deps()129 const LabelTargetVector& private_deps() const { return private_deps_; } private_deps()130 LabelTargetVector& private_deps() { return private_deps_; } 131 132 // Linked public dependencies. public_deps()133 const LabelTargetVector& public_deps() const { return public_deps_; } public_deps()134 LabelTargetVector& public_deps() { return public_deps_; } 135 136 // Non-linked dependencies. data_deps()137 const LabelTargetVector& data_deps() const { return data_deps_; } data_deps()138 LabelTargetVector& data_deps() { return data_deps_; } 139 140 // List of configs that this class inherits settings from. Once a target is 141 // resolved, this will also list all-dependent and public configs. configs()142 const UniqueVector<LabelConfigPair>& configs() const { return configs_; } configs()143 UniqueVector<LabelConfigPair>& configs() { return configs_; } 144 145 // List of configs that all dependencies (direct and indirect) of this 146 // target get. These configs are not added to this target. Note that due 147 // to the way this is computed, there may be duplicates in this list. all_dependent_configs()148 const UniqueVector<LabelConfigPair>& all_dependent_configs() const { 149 return all_dependent_configs_; 150 } all_dependent_configs()151 UniqueVector<LabelConfigPair>& all_dependent_configs() { 152 return all_dependent_configs_; 153 } 154 155 // List of configs that targets depending directly on this one get. These 156 // configs are also added to this target. public_configs()157 const UniqueVector<LabelConfigPair>& public_configs() const { 158 return public_configs_; 159 } public_configs()160 UniqueVector<LabelConfigPair>& public_configs() { 161 return public_configs_; 162 } 163 164 // A list of a subset of deps where we'll re-export public_configs as 165 // public_configs of this target. forward_dependent_configs()166 const UniqueVector<LabelTargetPair>& forward_dependent_configs() const { 167 return forward_dependent_configs_; 168 } forward_dependent_configs()169 UniqueVector<LabelTargetPair>& forward_dependent_configs() { 170 return forward_dependent_configs_; 171 } 172 173 // Dependencies that can include files from this target. allow_circular_includes_from()174 const std::set<Label>& allow_circular_includes_from() const { 175 return allow_circular_includes_from_; 176 } allow_circular_includes_from()177 std::set<Label>& allow_circular_includes_from() { 178 return allow_circular_includes_from_; 179 } 180 inherited_libraries()181 const UniqueVector<const Target*>& inherited_libraries() const { 182 return inherited_libraries_; 183 } 184 185 // This config represents the configuration set directly on this target. config_values()186 ConfigValues& config_values() { return config_values_; } config_values()187 const ConfigValues& config_values() const { return config_values_; } 188 action_values()189 ActionValues& action_values() { return action_values_; } action_values()190 const ActionValues& action_values() const { return action_values_; } 191 all_lib_dirs()192 const OrderedSet<SourceDir>& all_lib_dirs() const { return all_lib_dirs_; } all_libs()193 const OrderedSet<std::string>& all_libs() const { return all_libs_; } 194 recursive_hard_deps()195 const std::set<const Target*>& recursive_hard_deps() const { 196 return recursive_hard_deps_; 197 } 198 199 // The toolchain is only known once this target is resolved (all if its 200 // dependencies are known). They will be null until then. Generally, this can 201 // only be used during target writing. toolchain()202 const Toolchain* toolchain() const { return toolchain_; } 203 204 // Sets the toolchain. The toolchain must include a tool for this target 205 // or the error will be set and the function will return false. Unusually, 206 // this function's "err" output is optional since this is commonly used 207 // frequently by unit tests which become needlessly verbose. 208 bool SetToolchain(const Toolchain* toolchain, Err* err = NULL); 209 210 // Returns outputs from this target. The link output file is the one that 211 // other targets link to when they depend on this target. This will only be 212 // valid for libraries and will be empty for all other target types. 213 // 214 // The dependency output file is the file that should be used to express 215 // a dependency on this one. It could be the same as the link output file 216 // (this will be the case for static libraries). For shared libraries it 217 // could be the same or different than the link output file, depending on the 218 // system. For actions this will be the stamp file. 219 // 220 // These are only known once the target is resolved and will be empty before 221 // that. This is a cache of the files to prevent every target that depends on 222 // a given library from recomputing the same pattern. link_output_file()223 const OutputFile& link_output_file() const { 224 return link_output_file_; 225 } dependency_output_file()226 const OutputFile& dependency_output_file() const { 227 return dependency_output_file_; 228 } 229 230 private: 231 // Pulls necessary information from dependencies to this one when all 232 // dependencies have been resolved. 233 void PullDependentTargetInfo(); 234 235 // These each pull specific things from dependencies to this one when all 236 // deps have been resolved. 237 void PullForwardedDependentConfigs(); 238 void PullForwardedDependentConfigsFrom(const Target* from); 239 void PullRecursiveHardDeps(); 240 241 // Fills the link and dependency output files when a target is resolved. 242 void FillOutputFiles(); 243 244 // Validates the given thing when a target is resolved. 245 bool CheckVisibility(Err* err) const; 246 bool CheckTestonly(Err* err) const; 247 bool CheckNoNestedStaticLibs(Err* err) const; 248 249 OutputType output_type_; 250 std::string output_name_; 251 std::string output_extension_; 252 253 FileList sources_; 254 bool all_headers_public_; 255 FileList public_headers_; 256 bool check_includes_; 257 bool complete_static_lib_; 258 bool testonly_; 259 FileList inputs_; 260 FileList data_; 261 262 bool hard_dep_; 263 264 LabelTargetVector private_deps_; 265 LabelTargetVector public_deps_; 266 LabelTargetVector data_deps_; 267 268 UniqueVector<LabelConfigPair> configs_; 269 UniqueVector<LabelConfigPair> all_dependent_configs_; 270 UniqueVector<LabelConfigPair> public_configs_; 271 UniqueVector<LabelTargetPair> forward_dependent_configs_; 272 273 std::set<Label> allow_circular_includes_from_; 274 275 bool external_; 276 277 // Static libraries and source sets from transitive deps. These things need 278 // to be linked only with the end target (executable, shared library). Source 279 // sets do not get pushed beyond static library boundaries, and neither 280 // source sets nor static libraries get pushed beyond sahred library 281 // boundaries. 282 UniqueVector<const Target*> inherited_libraries_; 283 284 // These libs and dirs are inherited from statically linked deps and all 285 // configs applying to this target. 286 OrderedSet<SourceDir> all_lib_dirs_; 287 OrderedSet<std::string> all_libs_; 288 289 // All hard deps from this target and all dependencies. Filled in when this 290 // target is marked resolved. This will not include the current target. 291 std::set<const Target*> recursive_hard_deps_; 292 293 ConfigValues config_values_; // Used for all binary targets. 294 ActionValues action_values_; // Used for action[_foreach] targets. 295 296 // Toolchain used by this target. Null until target is resolved. 297 const Toolchain* toolchain_; 298 299 // Output files. Null until the target is resolved. 300 OutputFile link_output_file_; 301 OutputFile dependency_output_file_; 302 303 DISALLOW_COPY_AND_ASSIGN(Target); 304 }; 305 306 namespace BASE_HASH_NAMESPACE { 307 308 #if defined(COMPILER_GCC) 309 template<> struct hash<const Target*> { 310 std::size_t operator()(const Target* t) const { 311 return reinterpret_cast<std::size_t>(t); 312 } 313 }; 314 #elif defined(COMPILER_MSVC) 315 inline size_t hash_value(const Target* t) { 316 return reinterpret_cast<size_t>(t); 317 } 318 #endif // COMPILER... 319 320 } // namespace BASE_HASH_NAMESPACE 321 322 #endif // TOOLS_GN_TARGET_H_ 323