mirror of
https://github.com/klzgrad/naiveproxy.git
synced 2024-12-01 01:36:09 +03:00
302 lines
8.9 KiB
C++
302 lines
8.9 KiB
C++
// Copyright 2016 The Chromium Authors. All rights reserved.
|
|
// Use of this source code is governed by a BSD-style license that can be
|
|
// found in the LICENSE file.
|
|
|
|
#include "tools/gn/create_bundle_target_generator.h"
|
|
|
|
#include <map>
|
|
|
|
#include "base/logging.h"
|
|
#include "tools/gn/filesystem_utils.h"
|
|
#include "tools/gn/label_pattern.h"
|
|
#include "tools/gn/parse_tree.h"
|
|
#include "tools/gn/scope.h"
|
|
#include "tools/gn/substitution_type.h"
|
|
#include "tools/gn/target.h"
|
|
#include "tools/gn/value.h"
|
|
#include "tools/gn/value_extractors.h"
|
|
#include "tools/gn/variables.h"
|
|
|
|
CreateBundleTargetGenerator::CreateBundleTargetGenerator(
|
|
Target* target,
|
|
Scope* scope,
|
|
const FunctionCallNode* function_call,
|
|
Err* err)
|
|
: TargetGenerator(target, scope, function_call, err) {}
|
|
|
|
CreateBundleTargetGenerator::~CreateBundleTargetGenerator() = default;
|
|
|
|
void CreateBundleTargetGenerator::DoRun() {
|
|
target_->set_output_type(Target::CREATE_BUNDLE);
|
|
|
|
BundleData& bundle_data = target_->bundle_data();
|
|
if (!FillBundleDir(SourceDir(), variables::kBundleRootDir,
|
|
&bundle_data.root_dir()))
|
|
return;
|
|
if (!FillBundleDir(bundle_data.root_dir(), variables::kBundleContentsDir,
|
|
&bundle_data.contents_dir()))
|
|
return;
|
|
if (!FillBundleDir(bundle_data.root_dir(), variables::kBundleResourcesDir,
|
|
&bundle_data.resources_dir()))
|
|
return;
|
|
if (!FillBundleDir(bundle_data.root_dir(), variables::kBundleExecutableDir,
|
|
&bundle_data.executable_dir()))
|
|
return;
|
|
if (!FillBundleDir(bundle_data.root_dir(), variables::kBundlePlugInsDir,
|
|
&bundle_data.plugins_dir()))
|
|
return;
|
|
|
|
if (!FillXcodeExtraAttributes())
|
|
return;
|
|
|
|
if (!FillProductType())
|
|
return;
|
|
|
|
if (!FillPartialInfoPlist())
|
|
return;
|
|
|
|
if (!FillXcodeTestApplicationName())
|
|
return;
|
|
|
|
if (!FillCodeSigningScript())
|
|
return;
|
|
|
|
if (!FillCodeSigningSources())
|
|
return;
|
|
|
|
if (!FillCodeSigningOutputs())
|
|
return;
|
|
|
|
if (!FillCodeSigningArgs())
|
|
return;
|
|
|
|
if (!FillBundleDepsFilter())
|
|
return;
|
|
}
|
|
|
|
bool CreateBundleTargetGenerator::FillBundleDir(
|
|
const SourceDir& bundle_root_dir,
|
|
const base::StringPiece& name,
|
|
SourceDir* bundle_dir) {
|
|
const Value* value = scope_->GetValue(name, true);
|
|
if (!value)
|
|
return true;
|
|
if (!value->VerifyTypeIs(Value::STRING, err_))
|
|
return false;
|
|
std::string str = value->string_value();
|
|
if (!str.empty() && str[str.size() - 1] != '/')
|
|
str.push_back('/');
|
|
if (!EnsureStringIsInOutputDir(GetBuildSettings()->build_dir(), str,
|
|
value->origin(), err_))
|
|
return false;
|
|
if (str != bundle_root_dir.value() &&
|
|
!IsStringInOutputDir(bundle_root_dir, str)) {
|
|
*err_ = Err(value->origin(), "Path is not in bundle root dir.",
|
|
"The given file should be in the bundle root directory or below.\n"
|
|
"Normally you would do \"$bundle_root_dir/foo\". I interpreted this\n"
|
|
"as \"" + str + "\".");
|
|
return false;
|
|
}
|
|
bundle_dir->SwapValue(&str);
|
|
return true;
|
|
}
|
|
|
|
bool CreateBundleTargetGenerator::FillXcodeExtraAttributes() {
|
|
// Need to get a mutable value to mark all values in the scope as used. This
|
|
// cannot be done on a const Scope.
|
|
Value* value = scope_->GetMutableValue(variables::kXcodeExtraAttributes,
|
|
Scope::SEARCH_CURRENT, true);
|
|
if (!value)
|
|
return true;
|
|
|
|
if (!value->VerifyTypeIs(Value::SCOPE, err_))
|
|
return false;
|
|
|
|
Scope* scope_value = value->scope_value();
|
|
|
|
Scope::KeyValueMap value_map;
|
|
scope_value->GetCurrentScopeValues(&value_map);
|
|
scope_value->MarkAllUsed();
|
|
|
|
std::map<std::string, std::string> xcode_extra_attributes;
|
|
for (const auto& iter : value_map) {
|
|
if (!iter.second.VerifyTypeIs(Value::STRING, err_))
|
|
return false;
|
|
|
|
xcode_extra_attributes.insert(
|
|
std::make_pair(iter.first.as_string(), iter.second.string_value()));
|
|
}
|
|
|
|
target_->bundle_data().xcode_extra_attributes().swap(xcode_extra_attributes);
|
|
return true;
|
|
}
|
|
|
|
bool CreateBundleTargetGenerator::FillProductType() {
|
|
const Value* value = scope_->GetValue(variables::kProductType, true);
|
|
if (!value)
|
|
return true;
|
|
|
|
if (!value->VerifyTypeIs(Value::STRING, err_))
|
|
return false;
|
|
|
|
target_->bundle_data().product_type().assign(value->string_value());
|
|
return true;
|
|
}
|
|
|
|
bool CreateBundleTargetGenerator::FillPartialInfoPlist() {
|
|
const Value* value = scope_->GetValue(variables::kPartialInfoPlist, true);
|
|
if (!value)
|
|
return true;
|
|
|
|
if (!value->VerifyTypeIs(Value::STRING, err_))
|
|
return false;
|
|
|
|
const BuildSettings* build_settings = scope_->settings()->build_settings();
|
|
SourceFile path = scope_->GetSourceDir().ResolveRelativeFile(
|
|
*value, err_, build_settings->root_path_utf8());
|
|
|
|
if (err_->has_error())
|
|
return false;
|
|
|
|
if (!EnsureStringIsInOutputDir(build_settings->build_dir(), path.value(),
|
|
value->origin(), err_))
|
|
return false;
|
|
|
|
target_->bundle_data().set_partial_info_plist(path);
|
|
return true;
|
|
}
|
|
|
|
bool CreateBundleTargetGenerator::FillXcodeTestApplicationName() {
|
|
const Value* value =
|
|
scope_->GetValue(variables::kXcodeTestApplicationName, true);
|
|
if (!value)
|
|
return true;
|
|
|
|
if (!value->VerifyTypeIs(Value::STRING, err_))
|
|
return false;
|
|
|
|
target_->bundle_data().xcode_test_application_name().assign(
|
|
value->string_value());
|
|
return true;
|
|
}
|
|
|
|
bool CreateBundleTargetGenerator::FillCodeSigningScript() {
|
|
const Value* value = scope_->GetValue(variables::kCodeSigningScript, true);
|
|
if (!value)
|
|
return true;
|
|
|
|
if (!value->VerifyTypeIs(Value::STRING, err_))
|
|
return false;
|
|
|
|
SourceFile script_file = scope_->GetSourceDir().ResolveRelativeFile(
|
|
*value, err_, scope_->settings()->build_settings()->root_path_utf8());
|
|
if (err_->has_error())
|
|
return false;
|
|
|
|
target_->bundle_data().set_code_signing_script(script_file);
|
|
return true;
|
|
}
|
|
|
|
bool CreateBundleTargetGenerator::FillCodeSigningSources() {
|
|
const Value* value = scope_->GetValue(variables::kCodeSigningSources, true);
|
|
if (!value)
|
|
return true;
|
|
|
|
if (target_->bundle_data().code_signing_script().is_null()) {
|
|
*err_ = Err(
|
|
function_call_,
|
|
"No code signing script."
|
|
"You must define code_signing_script if you use code_signing_sources.");
|
|
return false;
|
|
}
|
|
|
|
Target::FileList script_sources;
|
|
if (!ExtractListOfRelativeFiles(scope_->settings()->build_settings(), *value,
|
|
scope_->GetSourceDir(), &script_sources,
|
|
err_))
|
|
return false;
|
|
|
|
target_->bundle_data().code_signing_sources().swap(script_sources);
|
|
return true;
|
|
}
|
|
|
|
bool CreateBundleTargetGenerator::FillCodeSigningOutputs() {
|
|
const Value* value = scope_->GetValue(variables::kCodeSigningOutputs, true);
|
|
if (!value)
|
|
return true;
|
|
|
|
if (target_->bundle_data().code_signing_script().is_null()) {
|
|
*err_ = Err(
|
|
function_call_,
|
|
"No code signing script."
|
|
"You must define code_signing_script if you use code_signing_outputs.");
|
|
return false;
|
|
}
|
|
|
|
if (!value->VerifyTypeIs(Value::LIST, err_))
|
|
return false;
|
|
|
|
SubstitutionList& outputs = target_->bundle_data().code_signing_outputs();
|
|
if (!outputs.Parse(*value, err_))
|
|
return false;
|
|
|
|
if (outputs.list().empty()) {
|
|
*err_ =
|
|
Err(function_call_,
|
|
"Code signing script has no output."
|
|
"If you have no outputs, the build system can not tell when your\n"
|
|
"code signing script needs to be run.");
|
|
return false;
|
|
}
|
|
|
|
// Validate that outputs are in the output dir.
|
|
CHECK_EQ(value->list_value().size(), outputs.list().size());
|
|
for (size_t i = 0; i < value->list_value().size(); ++i) {
|
|
if (!EnsureSubstitutionIsInOutputDir(outputs.list()[i],
|
|
value->list_value()[i]))
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|
|
|
|
bool CreateBundleTargetGenerator::FillCodeSigningArgs() {
|
|
const Value* value = scope_->GetValue(variables::kCodeSigningArgs, true);
|
|
if (!value)
|
|
return true;
|
|
|
|
if (target_->bundle_data().code_signing_script().is_null()) {
|
|
*err_ = Err(
|
|
function_call_,
|
|
"No code signing script."
|
|
"You must define code_signing_script if you use code_signing_args.");
|
|
return false;
|
|
}
|
|
|
|
if (!value->VerifyTypeIs(Value::LIST, err_))
|
|
return false;
|
|
|
|
return target_->bundle_data().code_signing_args().Parse(*value, err_);
|
|
}
|
|
|
|
bool CreateBundleTargetGenerator::FillBundleDepsFilter() {
|
|
const Value* value = scope_->GetValue(variables::kBundleDepsFilter, true);
|
|
if (!value)
|
|
return true;
|
|
|
|
if (!value->VerifyTypeIs(Value::LIST, err_))
|
|
return false;
|
|
|
|
const SourceDir& current_dir = scope_->GetSourceDir();
|
|
std::vector<LabelPattern>& bundle_deps_filter =
|
|
target_->bundle_data().bundle_deps_filter();
|
|
for (const auto& item : value->list_value()) {
|
|
bundle_deps_filter.push_back(
|
|
LabelPattern::GetPattern(current_dir, item, err_));
|
|
if (err_->has_error())
|
|
return false;
|
|
}
|
|
|
|
return true;
|
|
}
|