value_extractors.cc revision f2477e01787aa58f445919b809d89e252beef54f
1d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch// Copyright (c) 2013 The Chromium Authors. All rights reserved.
2d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch// Use of this source code is governed by a BSD-style license that can be
3d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch// found in the LICENSE file.
4d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch
5d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch#include "tools/gn/value_extractors.h"
6d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch
73551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)#include "tools/gn/build_settings.h"
8d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch#include "tools/gn/err.h"
9d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch#include "tools/gn/label.h"
10d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch#include "tools/gn/source_dir.h"
11d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch#include "tools/gn/source_file.h"
12d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch
13d3868032626d59662ff73b372b5d584c1d144c53Ben Murdochnamespace {
14d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch
15d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch// This extractor rejects files with system-absolute file paths. If we need
16d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch// that in the future, we'll have to add some flag to control this.
17d3868032626d59662ff73b372b5d584c1d144c53Ben Murdochstruct RelativeFileConverter {
183551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)  RelativeFileConverter(const BuildSettings* build_settings_in,
193551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)                        const SourceDir& current_dir_in)
203551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)      : build_settings(build_settings_in),
213551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)        current_dir(current_dir_in) {
223551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)  }
23d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  bool operator()(const Value& v, SourceFile* out, Err* err) const {
24d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch    if (!v.VerifyTypeIs(Value::STRING, err))
25d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch      return false;
263551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)    *out = current_dir.ResolveRelativeFile(v.string_value(),
273551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)                                           build_settings->root_path_utf8());
28d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch    if (out->is_system_absolute()) {
29d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch      *err = Err(v, "System-absolute file path.",
30d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch          "You can't list a system-absolute file path here. Please include "
31d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch          "only files in\nthe source tree. Maybe you meant to begin with two "
32d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch          "slashes to indicate an\nabsolute path in the source tree?");
33d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch      return false;
34d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch    }
35d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch    return true;
36d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  }
373551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)  const BuildSettings* build_settings;
38d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  const SourceDir& current_dir;
39d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch};
40d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch
41d3868032626d59662ff73b372b5d584c1d144c53Ben Murdochstruct RelativeDirConverter {
423551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)  RelativeDirConverter(const BuildSettings* build_settings_in,
433551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)                       const SourceDir& current_dir_in)
443551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)      : build_settings(build_settings_in),
453551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)        current_dir(current_dir_in) {
463551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)  }
47d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  bool operator()(const Value& v, SourceDir* out, Err* err) const {
48d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch    if (!v.VerifyTypeIs(Value::STRING, err))
49d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch      return false;
503551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)    *out = current_dir.ResolveRelativeDir(v.string_value(),
513551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)                                          build_settings->root_path_utf8());
52d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch    return true;
53d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  }
543551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)  const BuildSettings* build_settings;
55d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  const SourceDir& current_dir;
56d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch};
57d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch
580f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)// Fills the label part of a LabelPtrPair, leaving the pointer null.
590f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)template<typename T> struct LabelResolver {
60d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  LabelResolver(const SourceDir& current_dir_in,
61d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch                const Label& current_toolchain_in)
62d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch      : current_dir(current_dir_in),
63d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch        current_toolchain(current_toolchain_in) {}
640f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  bool operator()(const Value& v, LabelPtrPair<T>* out, Err* err) const {
65d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch    if (!v.VerifyTypeIs(Value::STRING, err))
66d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch      return false;
670f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    out->label = Label::Resolve(current_dir, current_toolchain, v, err);
680f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)    out->origin = v.origin();
69d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch    return !err->has_error();
70d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  }
71d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  const SourceDir& current_dir;
72d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  const Label& current_toolchain;
73d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch};
74d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch
75d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch}  // namespace
76d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch
77d3868032626d59662ff73b372b5d584c1d144c53Ben Murdochbool ExtractListOfStringValues(const Value& value,
78d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch                               std::vector<std::string>* dest,
79d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch                               Err* err) {
80d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  if (!value.VerifyTypeIs(Value::LIST, err))
81d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch    return false;
82d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  const std::vector<Value>& input_list = value.list_value();
83d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  dest->reserve(input_list.size());
84d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  for (size_t i = 0; i < input_list.size(); i++) {
85d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch    if (!input_list[i].VerifyTypeIs(Value::STRING, err))
86d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch      return false;
87d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch    dest->push_back(input_list[i].string_value());
88d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  }
89d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  return true;
90d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch}
91d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch
923551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)bool ExtractListOfRelativeFiles(const BuildSettings* build_settings,
933551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)                                const Value& value,
94d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch                                const SourceDir& current_dir,
95d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch                                std::vector<SourceFile>* files,
96d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch                                Err* err) {
97d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  return ListValueExtractor(value, files, err,
983551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)                            RelativeFileConverter(build_settings, current_dir));
99d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch}
100d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch
1013551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)bool ExtractListOfRelativeDirs(const BuildSettings* build_settings,
1023551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)                               const Value& value,
103d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch                               const SourceDir& current_dir,
104d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch                               std::vector<SourceDir>* dest,
105d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch                               Err* err) {
106d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  return ListValueExtractor(value, dest, err,
1073551c9c881056c480085172ff9840cab31610854Torne (Richard Coles)                            RelativeDirConverter(build_settings, current_dir));
108d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch}
109d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch
110d3868032626d59662ff73b372b5d584c1d144c53Ben Murdochbool ExtractListOfLabels(const Value& value,
111d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch                         const SourceDir& current_dir,
112d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch                         const Label& current_toolchain,
1130f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                         LabelConfigVector* dest,
114d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch                         Err* err) {
115d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch  return ListValueExtractor(value, dest, err,
1160f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                            LabelResolver<Config>(current_dir,
1170f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                                                  current_toolchain));
1180f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)}
1190f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)
1200f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)bool ExtractListOfLabels(const Value& value,
1210f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                         const SourceDir& current_dir,
1220f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                         const Label& current_toolchain,
1230f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                         LabelTargetVector* dest,
1240f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                         Err* err) {
1250f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)  return ListValueExtractor(value, dest, err,
1260f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                            LabelResolver<Target>(current_dir,
1270f1bc08d4cfcc34181b0b5cbf065c40f687bf740Torne (Richard Coles)                                                  current_toolchain));
128d3868032626d59662ff73b372b5d584c1d144c53Ben Murdoch}
129f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
130f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)bool ExtractRelativeFile(const BuildSettings* build_settings,
131f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)                         const Value& value,
132f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)                         const SourceDir& current_dir,
133f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)                         SourceFile* file,
134f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)                         Err* err) {
135f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  RelativeFileConverter converter(build_settings, current_dir);
136f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  return converter(value, file, err);
137f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)}
138