1 // Copyright (c) 2011 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 "chrome/browser/chromeos/name_value_pairs_parser.h"
6
7 #include "base/command_line.h"
8 #include "base/logging.h"
9 #include "base/process_util.h"
10 #include "base/string_tokenizer.h"
11 #include "base/string_util.h"
12 #include "base/threading/thread_restrictions.h"
13
14 namespace chromeos { // NOLINT
15
16 namespace {
17
18 const char kQuoteChars[] = "\"";
19
20 } // namespace
21
NameValuePairsParser(NameValueMap * map)22 NameValuePairsParser::NameValuePairsParser(NameValueMap* map)
23 : map_(map) {
24 }
25
AddNameValuePair(const std::string & key,const std::string & value)26 void NameValuePairsParser::AddNameValuePair(const std::string& key,
27 const std::string& value) {
28 (*map_)[key] = value;
29 VLOG(1) << "name: " << key << ", value: " << value;
30 }
31
ParseNameValuePairs(const std::string & in_string,const std::string & eq,const std::string & delim)32 bool NameValuePairsParser::ParseNameValuePairs(const std::string& in_string,
33 const std::string& eq,
34 const std::string& delim) {
35 // Set up the pair tokenizer.
36 StringTokenizer pair_toks(in_string, delim);
37 pair_toks.set_quote_chars(kQuoteChars);
38 // Process token pairs.
39 while (pair_toks.GetNext()) {
40 std::string pair(pair_toks.token());
41 if (pair.find(eq) == 0) {
42 LOG(WARNING) << "Empty key: '" << pair << "'. Aborting.";
43 return false;
44 }
45 StringTokenizer keyvalue(pair, eq);
46 std::string key,value;
47 if (keyvalue.GetNext()) {
48 TrimString(keyvalue.token(), kQuoteChars, &key);
49 if (keyvalue.GetNext()) {
50 TrimString(keyvalue.token(), kQuoteChars, &value);
51 if (keyvalue.GetNext()) {
52 LOG(WARNING) << "Multiple key tokens: '" << pair << "'. Aborting.";
53 return false;
54 }
55 }
56 }
57 if (key.empty()) {
58 LOG(WARNING) << "Invalid token pair: '" << pair << "'. Aborting.";
59 return false;
60 }
61 AddNameValuePair(key, value);
62 }
63 return true;
64 }
65
GetSingleValueFromTool(int argc,const char * argv[],const std::string & key)66 bool NameValuePairsParser::GetSingleValueFromTool(int argc,
67 const char* argv[],
68 const std::string& key) {
69 CommandLine command_line(argc, argv);
70 std::string output_string;
71 // TODO(stevenjb,satorux): Make this non blocking: crosbug.com/5603.
72 base::ThreadRestrictions::ScopedAllowIO allow_io_for_thread_join;
73 if (argc < 1 || !base::GetAppOutput(command_line, &output_string)) {
74 LOG(WARNING) << "Error excuting: " << command_line.command_line_string();
75 return false;
76 }
77 TrimWhitespaceASCII(output_string, TRIM_ALL, &output_string);
78 AddNameValuePair(key, output_string);
79 return true;
80 }
81
ParseNameValuePairsFromTool(int argc,const char * argv[],const std::string & eq,const std::string & delim)82 bool NameValuePairsParser::ParseNameValuePairsFromTool(
83 int argc,
84 const char* argv[],
85 const std::string& eq,
86 const std::string& delim) {
87 CommandLine command_line(argc, argv);
88 std::string output_string;
89 // TODO(stevenjb,satorux): Make this non blocking: crosbug.com/5603.
90 base::ThreadRestrictions::ScopedAllowIO allow_io_for_thread_join;
91 if (argc < 1 || !base::GetAppOutput(command_line, &output_string)) {
92 LOG(WARNING) << "Error excuting: " << command_line.command_line_string();
93 return false;
94 }
95 if (!ParseNameValuePairs(output_string, eq, delim)) {
96 LOG(WARNING) << "Error parsing values while excuting: "
97 << command_line.command_line_string();
98 return false;
99 }
100 return true;
101 }
102
103 } // namespace chromeos
104