Gentoo Archives: gentoo-commits

From: "Petteri Räty" <betelgeuse@g.o>
To: gentoo-commits@l.g.o
Subject: [gentoo-commits] proj/libbash:master commit in: scripts/, src/core/, bashast/
Date: Wed, 20 Apr 2011 14:05:10
Message-Id: 8838cef4a07903791881cc64c8c5de02370eb38b.betelgeuse@gentoo
1 commit: 8838cef4a07903791881cc64c8c5de02370eb38b
2 Author: Mu Qiao <qiaomuf <AT> gentoo <DOT> org>
3 AuthorDate: Tue Apr 19 13:35:06 2011 +0000
4 Commit: Petteri Räty <betelgeuse <AT> gentoo <DOT> org>
5 CommitDate: Wed Apr 20 13:44:30 2011 +0000
6 URL: http://git.overlays.gentoo.org/gitweb/?p=proj/libbash.git;a=commit;h=8838cef4
7
8 Walker: implement replacement expansion for raw string
9
10 ${parameter/pattern/string} is supported for raw string. We haven't
11 provided any advanced pattern matching yet. Array and positional
12 parameter expansion like ${var[@]/foo/bar} and ${*/foo/bar} are not
13 supported for now.
14
15 ---
16 bashast/libbashWalker.g | 34 +++++++++++++++++++++++++-
17 scripts/var_expansion.ebuild | 15 +++++++++++
18 scripts/var_expansion.ebuild.result | 15 +++++++++++
19 src/core/interpreter.cpp | 36 +++++++++++++++++++++++++++
20 src/core/interpreter.h | 46 +++++++++++++++++++++++++++++++++++
21 5 files changed, 145 insertions(+), 1 deletions(-)
22
23 diff --git a/bashast/libbashWalker.g b/bashast/libbashWalker.g
24 index b6c9a7f..752e470 100644
25 --- a/bashast/libbashWalker.g
26 +++ b/bashast/libbashWalker.g
27 @@ -194,7 +194,39 @@ var_expansion returns[std::string libbash_value]
28 |^(libbash_name=name_base ARRAY_SIZE) {
29 libbash_value = boost::lexical_cast<std::string>(walker->get_array_length(libbash_name));
30 }
31 - ));
32 + ))
33 + |^(REPLACE_ALL var_name pattern=string_expr (replacement=string_expr)?) {
34 + libbash_value = walker->do_replace_expansion($var_name.libbash_value,
35 + std::bind(&interpreter::replace_all,
36 + std::placeholders::_1,
37 + pattern.libbash_value,
38 + replacement.libbash_value),
39 + $var_name.index);
40 + }
41 + |^(REPLACE_AT_END var_name pattern=string_expr (replacement=string_expr)?) {
42 + libbash_value = walker->do_replace_expansion($var_name.libbash_value,
43 + std::bind(&interpreter::replace_at_end,
44 + std::placeholders::_1,
45 + pattern.libbash_value,
46 + replacement.libbash_value),
47 + $var_name.index);
48 + }
49 + |^(REPLACE_AT_START var_name pattern=string_expr (replacement=string_expr)?) {
50 + libbash_value = walker->do_replace_expansion($var_name.libbash_value,
51 + std::bind(&interpreter::replace_at_start,
52 + std::placeholders::_1,
53 + pattern.libbash_value,
54 + replacement.libbash_value),
55 + $var_name.index);
56 + }
57 + |^(REPLACE_FIRST var_name pattern=string_expr (replacement=string_expr)?) {
58 + libbash_value = walker->do_replace_expansion($var_name.libbash_value,
59 + std::bind(&interpreter::replace_first,
60 + std::placeholders::_1,
61 + pattern.libbash_value,
62 + replacement.libbash_value),
63 + $var_name.index);
64 + };
65
66 word returns[std::string libbash_value]
67 :(num) => libbash_string=num { $libbash_value = libbash_string; }
68
69 diff --git a/scripts/var_expansion.ebuild b/scripts/var_expansion.ebuild
70 index c45ad1e..9a46277 100644
71 --- a/scripts/var_expansion.ebuild
72 +++ b/scripts/var_expansion.ebuild
73 @@ -37,3 +37,18 @@ FOO035="${#ARRAY[0]}"
74 FOO036="${#ARRAY[@]}"
75 FOO037="${#ARRAY[*]}"
76 FOO038="${#ARRAY}"
77 +FOO039="Hello World"
78 +FOO040=${FOO039/nothing/nothing}
79 +FOO041=${FOO039/o W/ow}
80 +FOO042=${FOO039//o/e}
81 +FOO043=${FOO039/#He/he}
82 +FOO044=${FOO039/#he/he}
83 +FOO045=${FOO039/%rld/rlD}
84 +FOO046=${FOO039/%rlD/rlD}
85 +FOO047=${FOO039/o W}
86 +FOO048=${FOO039//o}
87 +FOO049=${FOO039/#He}
88 +FOO050=${FOO039/#he}
89 +FOO051=${FOO039/%rld}
90 +FOO052=${FOO039/%rlD}
91 +FOO053=${FOO039/aaaaaaaaaaaa}
92
93 diff --git a/scripts/var_expansion.ebuild.result b/scripts/var_expansion.ebuild.result
94 index 8bea3b8..ed5fea3 100644
95 --- a/scripts/var_expansion.ebuild.result
96 +++ b/scripts/var_expansion.ebuild.result
97 @@ -39,3 +39,18 @@ FOO035=2
98 FOO036=5
99 FOO037=5
100 FOO038=2
101 +FOO039=Hello World
102 +FOO040=Hello World
103 +FOO041=Helloworld
104 +FOO042=Helle Werld
105 +FOO043=hello World
106 +FOO044=Hello World
107 +FOO045=Hello WorlD
108 +FOO046=Hello World
109 +FOO047=Hellorld
110 +FOO048=Hell Wrld
111 +FOO049=llo World
112 +FOO050=Hello World
113 +FOO051=Hello Wo
114 +FOO052=Hello World
115 +FOO053=Hello World
116
117 diff --git a/src/core/interpreter.cpp b/src/core/interpreter.cpp
118 index c683315..0ac5699 100644
119 --- a/src/core/interpreter.cpp
120 +++ b/src/core/interpreter.cpp
121 @@ -24,8 +24,11 @@
122
123 #include "core/interpreter.h"
124
125 +#include <functional>
126 +
127 #include <boost/algorithm/string/classification.hpp>
128 #include <boost/algorithm/string/join.hpp>
129 +#include <boost/algorithm/string/replace.hpp>
130 #include <boost/algorithm/string/split.hpp>
131
132 #include "libbashWalker.h"
133 @@ -109,3 +112,36 @@ bool interpreter::call(const std::string& name,
134
135 return true;
136 }
137 +
138 +void interpreter::replace_all(std::string& value,
139 + const std::string& pattern,
140 + const std::string& replacement)
141 +{
142 + boost::replace_all(value, pattern, replacement);
143 +}
144 +
145 +void interpreter::replace_at_end(std::string& value,
146 + const std::string& pattern,
147 + const std::string& replacement)
148 +{
149 + if(value.size() >= pattern.size() &&
150 + value.substr(value.size() - pattern.size()) == pattern)
151 + value.replace(value.size() - pattern.size(),
152 + pattern.size(),
153 + replacement);
154 +}
155 +
156 +void interpreter::replace_at_start(std::string& value,
157 + const std::string& pattern,
158 + const std::string& replacement)
159 +{
160 + if(value.substr(0, pattern.size()) == pattern)
161 + value.replace(0, pattern.size(), replacement);
162 +}
163 +
164 +void interpreter::replace_first(std::string& value,
165 + const std::string& pattern,
166 + const std::string& replacement)
167 +{
168 + boost::replace_first(value, pattern, replacement);
169 +}
170
171 diff --git a/src/core/interpreter.h b/src/core/interpreter.h
172 index 22a083e..72b8e3b 100644
173 --- a/src/core/interpreter.h
174 +++ b/src/core/interpreter.h
175 @@ -563,6 +563,20 @@ public:
176 return value.substr(offset, length);
177 }
178
179 + /// \brief perform replacement expansion
180 + /// \param the name of the varaible that needs to be expanded
181 + /// \param the function object used to perform expansion
182 + /// \param array index, use index=0 if it's not an array
183 + /// \return the expanded value
184 + std::string do_replace_expansion(const std::string& name,
185 + std::function<void(std::string&)> replacer,
186 + const unsigned index) const
187 + {
188 + std::string value = resolve<std::string>(name, index);
189 + replacer(value);
190 + return value;
191 + }
192 +
193 /// \brief get the length of a string variable
194 /// \param the name of the variable
195 /// \return the length
196 @@ -600,5 +614,37 @@ public:
197 /// \param the value of the word
198 //. \param[out] the splitted result
199 void split_word(const std::string& word, std::vector<std::string>& output);
200 +
201 + /// \brief perform expansion like ${var//foo/bar}
202 + /// \param the value to be expanded
203 + /// \param the pattern used to match the value
204 + /// \param the replacement string
205 + static void replace_all(std::string& value,
206 + const std::string& pattern,
207 + const std::string& replacement);
208 +
209 + /// \brief perform expansion like ${var/%foo/bar}
210 + /// \param the value to be expanded
211 + /// \param the pattern used to match the value
212 + /// \param the replacement string
213 + static void replace_at_end(std::string& value,
214 + const std::string& pattern,
215 + const std::string& replacement);
216 +
217 + /// \brief perform expansion like ${var/#foo/bar}
218 + /// \param the value to be expanded
219 + /// \param the pattern used to match the value
220 + /// \param the replacement string
221 + static void replace_at_start(std::string& value,
222 + const std::string& pattern,
223 + const std::string& replacement);
224 +
225 + /// \brief perform expansion like ${var/foo/bar}
226 + /// \param the value to be expanded
227 + /// \param the pattern used to match the value
228 + /// \param the replacement string
229 + static void replace_first(std::string& value,
230 + const std::string& pattern,
231 + const std::string& replacement);
232 };
233 #endif