sassc 2.0.1 → 2.1.0.pre1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/.gitmodules +1 -1
- data/.travis.yml +7 -3
- data/CHANGELOG.md +3 -0
- data/CODE_OF_CONDUCT.md +1 -1
- data/README.md +1 -1
- data/Rakefile +23 -8
- data/ext/extconf.rb +39 -0
- data/ext/libsass/.gitignore +1 -0
- data/ext/libsass/GNUmakefile.am +23 -39
- data/ext/libsass/Makefile +56 -91
- data/ext/libsass/Makefile.conf +16 -2
- data/ext/libsass/configure.ac +8 -12
- data/ext/libsass/include/sass/base.h +1 -0
- data/ext/libsass/include/sass/context.h +1 -1
- data/ext/libsass/src/GNUmakefile.am +1 -5
- data/ext/libsass/src/ast.cpp +747 -2010
- data/ext/libsass/src/ast.hpp +239 -2383
- data/ext/libsass/src/{to_c.cpp → ast2c.cpp} +22 -16
- data/ext/libsass/src/ast2c.hpp +39 -0
- data/ext/libsass/src/ast_def_macros.hpp +62 -10
- data/ext/libsass/src/ast_fwd_decl.cpp +1 -0
- data/ext/libsass/src/ast_fwd_decl.hpp +43 -165
- data/ext/libsass/src/ast_sel_cmp.cpp +909 -0
- data/ext/libsass/src/ast_sel_unify.cpp +280 -0
- data/ext/libsass/src/ast_selectors.cpp +1475 -0
- data/ext/libsass/src/ast_selectors.hpp +568 -0
- data/ext/libsass/src/ast_supports.cpp +130 -0
- data/ext/libsass/src/ast_supports.hpp +121 -0
- data/ext/libsass/src/ast_values.cpp +967 -0
- data/ext/libsass/src/ast_values.hpp +489 -0
- data/ext/libsass/src/backtrace.cpp +4 -0
- data/ext/libsass/src/base64vlq.cpp +3 -0
- data/ext/libsass/src/bind.cpp +18 -17
- data/ext/libsass/src/bind.hpp +3 -1
- data/ext/libsass/src/c2ast.cpp +64 -0
- data/ext/libsass/src/c2ast.hpp +14 -0
- data/ext/libsass/src/cencode.c +2 -2
- data/ext/libsass/src/check_nesting.cpp +52 -56
- data/ext/libsass/src/check_nesting.hpp +35 -34
- data/ext/libsass/src/color_maps.cpp +156 -153
- data/ext/libsass/src/color_maps.hpp +152 -152
- data/ext/libsass/src/constants.cpp +15 -0
- data/ext/libsass/src/constants.hpp +13 -0
- data/ext/libsass/src/context.cpp +24 -14
- data/ext/libsass/src/context.hpp +6 -6
- data/ext/libsass/src/cssize.cpp +69 -71
- data/ext/libsass/src/cssize.hpp +50 -50
- data/ext/libsass/src/debugger.hpp +117 -110
- data/ext/libsass/src/emitter.cpp +13 -12
- data/ext/libsass/src/emitter.hpp +13 -9
- data/ext/libsass/src/environment.cpp +15 -1
- data/ext/libsass/src/environment.hpp +6 -0
- data/ext/libsass/src/error_handling.cpp +36 -59
- data/ext/libsass/src/error_handling.hpp +29 -16
- data/ext/libsass/src/eval.cpp +302 -323
- data/ext/libsass/src/eval.hpp +64 -55
- data/ext/libsass/src/expand.cpp +94 -88
- data/ext/libsass/src/expand.hpp +33 -37
- data/ext/libsass/src/extend.cpp +38 -36
- data/ext/libsass/src/extend.hpp +15 -15
- data/ext/libsass/src/file.cpp +34 -2
- data/ext/libsass/src/fn_colors.cpp +594 -0
- data/ext/libsass/src/fn_colors.hpp +85 -0
- data/ext/libsass/src/fn_lists.cpp +284 -0
- data/ext/libsass/src/fn_lists.hpp +34 -0
- data/ext/libsass/src/fn_maps.cpp +94 -0
- data/ext/libsass/src/fn_maps.hpp +30 -0
- data/ext/libsass/src/fn_miscs.cpp +256 -0
- data/ext/libsass/src/fn_miscs.hpp +40 -0
- data/ext/libsass/src/fn_numbers.cpp +220 -0
- data/ext/libsass/src/fn_numbers.hpp +45 -0
- data/ext/libsass/src/fn_selectors.cpp +235 -0
- data/ext/libsass/src/fn_selectors.hpp +35 -0
- data/ext/libsass/src/fn_strings.cpp +254 -0
- data/ext/libsass/src/fn_strings.hpp +34 -0
- data/ext/libsass/src/fn_utils.cpp +156 -0
- data/ext/libsass/src/fn_utils.hpp +56 -0
- data/ext/libsass/src/inspect.cpp +101 -152
- data/ext/libsass/src/inspect.hpp +69 -73
- data/ext/libsass/src/json.cpp +2 -2
- data/ext/libsass/src/lexer.cpp +6 -3
- data/ext/libsass/src/listize.cpp +9 -11
- data/ext/libsass/src/listize.hpp +11 -7
- data/ext/libsass/src/memory/SharedPtr.cpp +2 -83
- data/ext/libsass/src/memory/SharedPtr.hpp +127 -143
- data/ext/libsass/src/node.cpp +13 -10
- data/ext/libsass/src/node.hpp +3 -3
- data/ext/libsass/src/operation.hpp +184 -144
- data/ext/libsass/src/operators.cpp +43 -17
- data/ext/libsass/src/operators.hpp +5 -5
- data/ext/libsass/src/output.cpp +21 -18
- data/ext/libsass/src/output.hpp +14 -21
- data/ext/libsass/src/parser.cpp +215 -183
- data/ext/libsass/src/parser.hpp +28 -24
- data/ext/libsass/src/plugins.cpp +5 -1
- data/ext/libsass/src/position.cpp +3 -0
- data/ext/libsass/src/prelexer.cpp +9 -3
- data/ext/libsass/src/prelexer.hpp +9 -9
- data/ext/libsass/src/remove_placeholders.cpp +14 -11
- data/ext/libsass/src/remove_placeholders.hpp +8 -9
- data/ext/libsass/src/sass.cpp +9 -3
- data/ext/libsass/src/sass.hpp +12 -9
- data/ext/libsass/src/sass2scss.cpp +45 -14
- data/ext/libsass/src/sass_context.cpp +18 -15
- data/ext/libsass/src/sass_functions.cpp +6 -3
- data/ext/libsass/src/sass_functions.hpp +1 -1
- data/ext/libsass/src/sass_util.cpp +3 -0
- data/ext/libsass/src/sass_values.cpp +21 -13
- data/ext/libsass/src/source_map.cpp +5 -2
- data/ext/libsass/src/source_map.hpp +2 -2
- data/ext/libsass/src/subset_map.cpp +4 -1
- data/ext/libsass/src/to_value.cpp +23 -21
- data/ext/libsass/src/to_value.hpp +18 -22
- data/ext/libsass/src/units.cpp +4 -0
- data/ext/libsass/src/units.hpp +1 -0
- data/ext/libsass/src/utf8/checked.h +12 -10
- data/ext/libsass/src/utf8/core.h +3 -0
- data/ext/libsass/src/utf8_string.cpp +3 -0
- data/ext/libsass/src/util.cpp +67 -75
- data/ext/libsass/src/util.hpp +64 -19
- data/ext/libsass/src/util_string.cpp +75 -0
- data/ext/libsass/src/util_string.hpp +19 -0
- data/ext/libsass/src/values.cpp +22 -13
- data/ext/libsass/src/values.hpp +2 -2
- data/ext/libsass/win/libsass.targets +30 -4
- data/ext/libsass/win/libsass.vcxproj.filters +82 -4
- data/lib/sassc.rb +24 -0
- data/lib/sassc/engine.rb +2 -2
- data/lib/sassc/native.rb +8 -1
- data/lib/sassc/version.rb +1 -1
- data/sassc.gemspec +19 -11
- data/test/engine_test.rb +26 -1
- data/test/native_test.rb +1 -1
- metadata +66 -72
- data/ext/Rakefile +0 -3
- data/ext/libsass/.github/CONTRIBUTING.md +0 -65
- data/ext/libsass/.github/ISSUE_TEMPLATE.md +0 -54
- data/ext/libsass/.travis.yml +0 -64
- data/ext/libsass/Readme.md +0 -104
- data/ext/libsass/SECURITY.md +0 -10
- data/ext/libsass/appveyor.yml +0 -91
- data/ext/libsass/docs/README.md +0 -20
- data/ext/libsass/docs/api-context-example.md +0 -45
- data/ext/libsass/docs/api-context-internal.md +0 -163
- data/ext/libsass/docs/api-context.md +0 -295
- data/ext/libsass/docs/api-doc.md +0 -215
- data/ext/libsass/docs/api-function-example.md +0 -67
- data/ext/libsass/docs/api-function-internal.md +0 -8
- data/ext/libsass/docs/api-function.md +0 -74
- data/ext/libsass/docs/api-importer-example.md +0 -112
- data/ext/libsass/docs/api-importer-internal.md +0 -20
- data/ext/libsass/docs/api-importer.md +0 -86
- data/ext/libsass/docs/api-value-example.md +0 -55
- data/ext/libsass/docs/api-value-internal.md +0 -76
- data/ext/libsass/docs/api-value.md +0 -154
- data/ext/libsass/docs/build-on-darwin.md +0 -27
- data/ext/libsass/docs/build-on-gentoo.md +0 -55
- data/ext/libsass/docs/build-on-windows.md +0 -139
- data/ext/libsass/docs/build-shared-library.md +0 -35
- data/ext/libsass/docs/build-with-autotools.md +0 -78
- data/ext/libsass/docs/build-with-makefiles.md +0 -68
- data/ext/libsass/docs/build-with-mingw.md +0 -107
- data/ext/libsass/docs/build-with-visual-studio.md +0 -90
- data/ext/libsass/docs/build.md +0 -97
- data/ext/libsass/docs/compatibility-plan.md +0 -48
- data/ext/libsass/docs/contributing.md +0 -17
- data/ext/libsass/docs/custom-functions-internal.md +0 -122
- data/ext/libsass/docs/dev-ast-memory.md +0 -223
- data/ext/libsass/docs/implementations.md +0 -56
- data/ext/libsass/docs/plugins.md +0 -47
- data/ext/libsass/docs/setup-environment.md +0 -68
- data/ext/libsass/docs/source-map-internals.md +0 -51
- data/ext/libsass/docs/trace.md +0 -26
- data/ext/libsass/docs/triage.md +0 -17
- data/ext/libsass/docs/unicode.md +0 -39
- data/ext/libsass/extconf.rb +0 -6
- data/ext/libsass/script/bootstrap +0 -13
- data/ext/libsass/script/branding +0 -10
- data/ext/libsass/script/ci-build-libsass +0 -134
- data/ext/libsass/script/ci-build-plugin +0 -62
- data/ext/libsass/script/ci-install-compiler +0 -6
- data/ext/libsass/script/ci-install-deps +0 -20
- data/ext/libsass/script/ci-report-coverage +0 -42
- data/ext/libsass/script/spec +0 -5
- data/ext/libsass/script/tap-driver +0 -652
- data/ext/libsass/script/tap-runner +0 -1
- data/ext/libsass/script/test-leaks.pl +0 -103
- data/ext/libsass/src/functions.cpp +0 -2234
- data/ext/libsass/src/functions.hpp +0 -198
- data/ext/libsass/src/to_c.hpp +0 -39
- data/ext/libsass/test/test_node.cpp +0 -94
- data/ext/libsass/test/test_paths.cpp +0 -28
- data/ext/libsass/test/test_selector_difference.cpp +0 -25
- data/ext/libsass/test/test_specificity.cpp +0 -25
- data/ext/libsass/test/test_subset_map.cpp +0 -472
- data/ext/libsass/test/test_superselector.cpp +0 -69
- data/ext/libsass/test/test_unification.cpp +0 -31
- data/lib/tasks/libsass.rb +0 -33
data/ext/libsass/src/eval.cpp
CHANGED
@@ -1,4 +1,7 @@
|
|
1
|
+
// sass.hpp must go before all system headers to get the
|
2
|
+
// __EXTENSIONS__ fix on Solaris.
|
1
3
|
#include "sass.hpp"
|
4
|
+
|
2
5
|
#include <cstdlib>
|
3
6
|
#include <cmath>
|
4
7
|
#include <iostream>
|
@@ -17,7 +20,8 @@
|
|
17
20
|
#include "position.hpp"
|
18
21
|
#include "sass/values.h"
|
19
22
|
#include "to_value.hpp"
|
20
|
-
#include "
|
23
|
+
#include "ast2c.hpp"
|
24
|
+
#include "c2ast.hpp"
|
21
25
|
#include "context.hpp"
|
22
26
|
#include "backtrace.hpp"
|
23
27
|
#include "lexer.hpp"
|
@@ -26,6 +30,7 @@
|
|
26
30
|
#include "expand.hpp"
|
27
31
|
#include "color_maps.hpp"
|
28
32
|
#include "sass_functions.hpp"
|
33
|
+
#include "util_string.hpp"
|
29
34
|
|
30
35
|
namespace Sass {
|
31
36
|
|
@@ -47,14 +52,51 @@ namespace Sass {
|
|
47
52
|
return exp.environment();
|
48
53
|
}
|
49
54
|
|
55
|
+
const std::string Eval::cwd()
|
56
|
+
{
|
57
|
+
return ctx.cwd();
|
58
|
+
}
|
59
|
+
|
60
|
+
struct Sass_Inspect_Options& Eval::options()
|
61
|
+
{
|
62
|
+
return ctx.c_options;
|
63
|
+
}
|
64
|
+
|
65
|
+
struct Sass_Compiler* Eval::compiler()
|
66
|
+
{
|
67
|
+
return ctx.c_compiler;
|
68
|
+
}
|
69
|
+
|
70
|
+
EnvStack& Eval::env_stack()
|
71
|
+
{
|
72
|
+
return exp.env_stack;
|
73
|
+
}
|
74
|
+
|
50
75
|
Selector_List_Obj Eval::selector()
|
51
76
|
{
|
52
77
|
return exp.selector();
|
53
78
|
}
|
54
79
|
|
55
|
-
|
80
|
+
std::vector<Sass_Callee>& Eval::callee_stack()
|
81
|
+
{
|
82
|
+
return ctx.callee_stack;
|
83
|
+
}
|
84
|
+
|
85
|
+
|
86
|
+
SelectorStack& Eval::selector_stack()
|
87
|
+
{
|
88
|
+
return exp.selector_stack;
|
89
|
+
}
|
90
|
+
|
91
|
+
bool& Eval::old_at_root_without_rule()
|
92
|
+
{
|
93
|
+
return exp.old_at_root_without_rule;
|
94
|
+
}
|
95
|
+
|
96
|
+
|
97
|
+
Expression* Eval::operator()(Block* b)
|
56
98
|
{
|
57
|
-
|
99
|
+
Expression* val = 0;
|
58
100
|
for (size_t i = 0, L = b->length(); i < L; ++i) {
|
59
101
|
val = b->at(i)->perform(this);
|
60
102
|
if (val) return val;
|
@@ -62,14 +104,14 @@ namespace Sass {
|
|
62
104
|
return val;
|
63
105
|
}
|
64
106
|
|
65
|
-
|
107
|
+
Expression* Eval::operator()(Assignment* a)
|
66
108
|
{
|
67
|
-
Env* env =
|
109
|
+
Env* env = environment();
|
68
110
|
std::string var(a->variable());
|
69
111
|
if (a->is_global()) {
|
70
112
|
if (a->is_default()) {
|
71
113
|
if (env->has_global(var)) {
|
72
|
-
|
114
|
+
Expression* e = Cast<Expression>(env->get_global(var));
|
73
115
|
if (!e || e->concrete_type() == Expression::NULL_VAL) {
|
74
116
|
env->set_global(var, a->value()->perform(this));
|
75
117
|
}
|
@@ -88,7 +130,7 @@ namespace Sass {
|
|
88
130
|
while (cur && cur->is_lexical()) {
|
89
131
|
if (cur->has_local(var)) {
|
90
132
|
if (AST_Node_Obj node = cur->get_local(var)) {
|
91
|
-
|
133
|
+
Expression* e = Cast<Expression>(node);
|
92
134
|
if (!e || e->concrete_type() == Expression::NULL_VAL) {
|
93
135
|
cur->set_local(var, a->value()->perform(this));
|
94
136
|
}
|
@@ -104,7 +146,7 @@ namespace Sass {
|
|
104
146
|
}
|
105
147
|
else if (env->has_global(var)) {
|
106
148
|
if (AST_Node_Obj node = env->get_global(var)) {
|
107
|
-
|
149
|
+
Expression* e = Cast<Expression>(node);
|
108
150
|
if (!e || e->concrete_type() == Expression::NULL_VAL) {
|
109
151
|
env->set_global(var, a->value()->perform(this));
|
110
152
|
}
|
@@ -123,11 +165,11 @@ namespace Sass {
|
|
123
165
|
return 0;
|
124
166
|
}
|
125
167
|
|
126
|
-
|
168
|
+
Expression* Eval::operator()(If* i)
|
127
169
|
{
|
128
|
-
Expression_Obj rv
|
129
|
-
Env env(
|
130
|
-
|
170
|
+
Expression_Obj rv;
|
171
|
+
Env env(environment());
|
172
|
+
env_stack().push_back(&env);
|
131
173
|
Expression_Obj cond = i->predicate()->perform(this);
|
132
174
|
if (!cond->is_false()) {
|
133
175
|
rv = i->block()->perform(this);
|
@@ -136,13 +178,13 @@ namespace Sass {
|
|
136
178
|
Block_Obj alt = i->alternative();
|
137
179
|
if (alt) rv = alt->perform(this);
|
138
180
|
}
|
139
|
-
|
181
|
+
env_stack().pop_back();
|
140
182
|
return rv.detach();
|
141
183
|
}
|
142
184
|
|
143
185
|
// For does not create a new env scope
|
144
186
|
// But iteration vars are reset afterwards
|
145
|
-
|
187
|
+
Expression* Eval::operator()(For* f)
|
146
188
|
{
|
147
189
|
std::string variable(f->variable());
|
148
190
|
Expression_Obj low = f->lower_bound()->perform(this);
|
@@ -168,9 +210,9 @@ namespace Sass {
|
|
168
210
|
double end = sass_end->value();
|
169
211
|
// only create iterator once in this environment
|
170
212
|
Env env(environment(), true);
|
171
|
-
|
213
|
+
env_stack().push_back(&env);
|
172
214
|
Block_Obj body = f->block();
|
173
|
-
|
215
|
+
Expression* val = 0;
|
174
216
|
if (start < end) {
|
175
217
|
if (f->is_inclusive()) ++end;
|
176
218
|
for (double i = start;
|
@@ -192,24 +234,24 @@ namespace Sass {
|
|
192
234
|
if (val) break;
|
193
235
|
}
|
194
236
|
}
|
195
|
-
|
237
|
+
env_stack().pop_back();
|
196
238
|
return val;
|
197
239
|
}
|
198
240
|
|
199
241
|
// Eval does not create a new env scope
|
200
242
|
// But iteration vars are reset afterwards
|
201
|
-
|
243
|
+
Expression* Eval::operator()(Each* e)
|
202
244
|
{
|
203
245
|
std::vector<std::string> variables(e->variables());
|
204
246
|
Expression_Obj expr = e->list()->perform(this);
|
205
247
|
Env env(environment(), true);
|
206
|
-
|
207
|
-
List_Obj list
|
208
|
-
|
248
|
+
env_stack().push_back(&env);
|
249
|
+
List_Obj list;
|
250
|
+
Map* map = nullptr;
|
209
251
|
if (expr->concrete_type() == Expression::MAP) {
|
210
252
|
map = Cast<Map>(expr);
|
211
253
|
}
|
212
|
-
else if (
|
254
|
+
else if (Selector_List* ls = Cast<Selector_List>(expr)) {
|
213
255
|
Listize listize;
|
214
256
|
Expression_Obj rv = ls->perform(&listize);
|
215
257
|
list = Cast<List>(rv);
|
@@ -223,14 +265,14 @@ namespace Sass {
|
|
223
265
|
}
|
224
266
|
|
225
267
|
Block_Obj body = e->block();
|
226
|
-
Expression_Obj val
|
268
|
+
Expression_Obj val;
|
227
269
|
|
228
270
|
if (map) {
|
229
271
|
for (Expression_Obj key : map->keys()) {
|
230
272
|
Expression_Obj value = map->at(key);
|
231
273
|
|
232
274
|
if (variables.size() == 1) {
|
233
|
-
|
275
|
+
List* variable = SASS_MEMORY_NEW(List, map->pstate(), 2, SASS_SPACE);
|
234
276
|
variable->append(key);
|
235
277
|
variable->append(value);
|
236
278
|
env.set_local(variables[0], variable);
|
@@ -248,18 +290,18 @@ namespace Sass {
|
|
248
290
|
list = Cast<List>(list);
|
249
291
|
}
|
250
292
|
for (size_t i = 0, L = list->length(); i < L; ++i) {
|
251
|
-
|
293
|
+
Expression* item = list->at(i);
|
252
294
|
// unwrap value if the expression is an argument
|
253
|
-
if (
|
295
|
+
if (Argument* arg = Cast<Argument>(item)) item = arg->value();
|
254
296
|
// check if we got passed a list of args (investigate)
|
255
|
-
if (
|
297
|
+
if (List* scalars = Cast<List>(item)) {
|
256
298
|
if (variables.size() == 1) {
|
257
|
-
|
299
|
+
Expression* var = scalars;
|
258
300
|
env.set_local(variables[0], var);
|
259
301
|
} else {
|
260
302
|
// XXX: this is never hit via spec tests
|
261
303
|
for (size_t j = 0, K = variables.size(); j < K; ++j) {
|
262
|
-
|
304
|
+
Expression* res = j >= scalars->length()
|
263
305
|
? SASS_MEMORY_NEW(Null, expr->pstate())
|
264
306
|
: scalars->at(j);
|
265
307
|
env.set_local(variables[j], res);
|
@@ -270,7 +312,7 @@ namespace Sass {
|
|
270
312
|
env.set_local(variables.at(0), item);
|
271
313
|
for (size_t j = 1, K = variables.size(); j < K; ++j) {
|
272
314
|
// XXX: this is never hit via spec tests
|
273
|
-
|
315
|
+
Expression* res = SASS_MEMORY_NEW(Null, expr->pstate());
|
274
316
|
env.set_local(variables[j], res);
|
275
317
|
}
|
276
318
|
}
|
@@ -279,46 +321,46 @@ namespace Sass {
|
|
279
321
|
if (val) break;
|
280
322
|
}
|
281
323
|
}
|
282
|
-
|
324
|
+
env_stack().pop_back();
|
283
325
|
return val.detach();
|
284
326
|
}
|
285
327
|
|
286
|
-
|
328
|
+
Expression* Eval::operator()(While* w)
|
287
329
|
{
|
288
330
|
Expression_Obj pred = w->predicate();
|
289
331
|
Block_Obj body = w->block();
|
290
332
|
Env env(environment(), true);
|
291
|
-
|
333
|
+
env_stack().push_back(&env);
|
292
334
|
Expression_Obj cond = pred->perform(this);
|
293
335
|
while (!cond->is_false()) {
|
294
336
|
Expression_Obj val = body->perform(this);
|
295
337
|
if (val) {
|
296
|
-
|
338
|
+
env_stack().pop_back();
|
297
339
|
return val.detach();
|
298
340
|
}
|
299
341
|
cond = pred->perform(this);
|
300
342
|
}
|
301
|
-
|
343
|
+
env_stack().pop_back();
|
302
344
|
return 0;
|
303
345
|
}
|
304
346
|
|
305
|
-
|
347
|
+
Expression* Eval::operator()(Return* r)
|
306
348
|
{
|
307
349
|
return r->value()->perform(this);
|
308
350
|
}
|
309
351
|
|
310
|
-
|
352
|
+
Expression* Eval::operator()(Warning* w)
|
311
353
|
{
|
312
|
-
Sass_Output_Style outstyle =
|
313
|
-
|
354
|
+
Sass_Output_Style outstyle = options().output_style;
|
355
|
+
options().output_style = NESTED;
|
314
356
|
Expression_Obj message = w->message()->perform(this);
|
315
|
-
Env* env =
|
357
|
+
Env* env = environment();
|
316
358
|
|
317
359
|
// try to use generic function
|
318
360
|
if (env->has("@warn[f]")) {
|
319
361
|
|
320
362
|
// add call stack entry
|
321
|
-
|
363
|
+
callee_stack().push_back({
|
322
364
|
"@warn",
|
323
365
|
w->pstate().path,
|
324
366
|
w->pstate().line + 1,
|
@@ -327,18 +369,18 @@ namespace Sass {
|
|
327
369
|
{ env }
|
328
370
|
});
|
329
371
|
|
330
|
-
|
372
|
+
Definition* def = Cast<Definition>((*env)["@warn[f]"]);
|
331
373
|
// Block_Obj body = def->block();
|
332
374
|
// Native_Function func = def->native_function();
|
333
375
|
Sass_Function_Entry c_function = def->c_function();
|
334
376
|
Sass_Function_Fn c_func = sass_function_get_function(c_function);
|
335
377
|
|
336
|
-
|
378
|
+
AST2C ast2c;
|
337
379
|
union Sass_Value* c_args = sass_make_list(1, SASS_COMMA, false);
|
338
|
-
sass_list_set_value(c_args, 0, message->perform(&
|
339
|
-
union Sass_Value* c_val = c_func(c_args, c_function,
|
340
|
-
|
341
|
-
|
380
|
+
sass_list_set_value(c_args, 0, message->perform(&ast2c));
|
381
|
+
union Sass_Value* c_val = c_func(c_args, c_function, compiler());
|
382
|
+
options().output_style = outstyle;
|
383
|
+
callee_stack().pop_back();
|
342
384
|
sass_delete_value(c_args);
|
343
385
|
sass_delete_value(c_val);
|
344
386
|
return 0;
|
@@ -350,23 +392,23 @@ namespace Sass {
|
|
350
392
|
traces.push_back(Backtrace(w->pstate()));
|
351
393
|
std::cerr << traces_to_string(traces, " ");
|
352
394
|
std::cerr << std::endl;
|
353
|
-
|
395
|
+
options().output_style = outstyle;
|
354
396
|
traces.pop_back();
|
355
397
|
return 0;
|
356
398
|
}
|
357
399
|
|
358
|
-
|
400
|
+
Expression* Eval::operator()(Error* e)
|
359
401
|
{
|
360
|
-
Sass_Output_Style outstyle =
|
361
|
-
|
402
|
+
Sass_Output_Style outstyle = options().output_style;
|
403
|
+
options().output_style = NESTED;
|
362
404
|
Expression_Obj message = e->message()->perform(this);
|
363
|
-
Env* env =
|
405
|
+
Env* env = environment();
|
364
406
|
|
365
407
|
// try to use generic function
|
366
408
|
if (env->has("@error[f]")) {
|
367
409
|
|
368
410
|
// add call stack entry
|
369
|
-
|
411
|
+
callee_stack().push_back({
|
370
412
|
"@error",
|
371
413
|
e->pstate().path,
|
372
414
|
e->pstate().line + 1,
|
@@ -375,18 +417,18 @@ namespace Sass {
|
|
375
417
|
{ env }
|
376
418
|
});
|
377
419
|
|
378
|
-
|
420
|
+
Definition* def = Cast<Definition>((*env)["@error[f]"]);
|
379
421
|
// Block_Obj body = def->block();
|
380
422
|
// Native_Function func = def->native_function();
|
381
423
|
Sass_Function_Entry c_function = def->c_function();
|
382
424
|
Sass_Function_Fn c_func = sass_function_get_function(c_function);
|
383
425
|
|
384
|
-
|
426
|
+
AST2C ast2c;
|
385
427
|
union Sass_Value* c_args = sass_make_list(1, SASS_COMMA, false);
|
386
|
-
sass_list_set_value(c_args, 0, message->perform(&
|
387
|
-
union Sass_Value* c_val = c_func(c_args, c_function,
|
388
|
-
|
389
|
-
|
428
|
+
sass_list_set_value(c_args, 0, message->perform(&ast2c));
|
429
|
+
union Sass_Value* c_val = c_func(c_args, c_function, compiler());
|
430
|
+
options().output_style = outstyle;
|
431
|
+
callee_stack().pop_back();
|
390
432
|
sass_delete_value(c_args);
|
391
433
|
sass_delete_value(c_val);
|
392
434
|
return 0;
|
@@ -394,23 +436,23 @@ namespace Sass {
|
|
394
436
|
}
|
395
437
|
|
396
438
|
std::string result(unquote(message->to_sass()));
|
397
|
-
|
439
|
+
options().output_style = outstyle;
|
398
440
|
error(result, e->pstate(), traces);
|
399
441
|
return 0;
|
400
442
|
}
|
401
443
|
|
402
|
-
|
444
|
+
Expression* Eval::operator()(Debug* d)
|
403
445
|
{
|
404
|
-
Sass_Output_Style outstyle =
|
405
|
-
|
446
|
+
Sass_Output_Style outstyle = options().output_style;
|
447
|
+
options().output_style = NESTED;
|
406
448
|
Expression_Obj message = d->value()->perform(this);
|
407
|
-
Env* env =
|
449
|
+
Env* env = environment();
|
408
450
|
|
409
451
|
// try to use generic function
|
410
452
|
if (env->has("@debug[f]")) {
|
411
453
|
|
412
454
|
// add call stack entry
|
413
|
-
|
455
|
+
callee_stack().push_back({
|
414
456
|
"@debug",
|
415
457
|
d->pstate().path,
|
416
458
|
d->pstate().line + 1,
|
@@ -419,37 +461,36 @@ namespace Sass {
|
|
419
461
|
{ env }
|
420
462
|
});
|
421
463
|
|
422
|
-
|
464
|
+
Definition* def = Cast<Definition>((*env)["@debug[f]"]);
|
423
465
|
// Block_Obj body = def->block();
|
424
466
|
// Native_Function func = def->native_function();
|
425
467
|
Sass_Function_Entry c_function = def->c_function();
|
426
468
|
Sass_Function_Fn c_func = sass_function_get_function(c_function);
|
427
469
|
|
428
|
-
|
470
|
+
AST2C ast2c;
|
429
471
|
union Sass_Value* c_args = sass_make_list(1, SASS_COMMA, false);
|
430
|
-
sass_list_set_value(c_args, 0, message->perform(&
|
431
|
-
union Sass_Value* c_val = c_func(c_args, c_function,
|
432
|
-
|
433
|
-
|
472
|
+
sass_list_set_value(c_args, 0, message->perform(&ast2c));
|
473
|
+
union Sass_Value* c_val = c_func(c_args, c_function, compiler());
|
474
|
+
options().output_style = outstyle;
|
475
|
+
callee_stack().pop_back();
|
434
476
|
sass_delete_value(c_args);
|
435
477
|
sass_delete_value(c_val);
|
436
478
|
return 0;
|
437
479
|
|
438
480
|
}
|
439
481
|
|
440
|
-
std::string cwd(ctx.cwd());
|
441
482
|
std::string result(unquote(message->to_sass()));
|
442
|
-
std::string abs_path(Sass::File::rel2abs(d->pstate().path, cwd, cwd));
|
443
|
-
std::string rel_path(Sass::File::abs2rel(d->pstate().path, cwd, cwd));
|
483
|
+
std::string abs_path(Sass::File::rel2abs(d->pstate().path, cwd(), cwd()));
|
484
|
+
std::string rel_path(Sass::File::abs2rel(d->pstate().path, cwd(), cwd()));
|
444
485
|
std::string output_path(Sass::File::path_for_console(rel_path, abs_path, d->pstate().path));
|
445
|
-
|
486
|
+
options().output_style = outstyle;
|
446
487
|
|
447
488
|
std::cerr << output_path << ":" << d->pstate().line+1 << " DEBUG: " << result;
|
448
489
|
std::cerr << std::endl;
|
449
490
|
return 0;
|
450
491
|
}
|
451
492
|
|
452
|
-
|
493
|
+
Expression* Eval::operator()(List* l)
|
453
494
|
{
|
454
495
|
// special case for unevaluated map
|
455
496
|
if (l->separator() == SASS_HASH) {
|
@@ -490,7 +531,7 @@ namespace Sass {
|
|
490
531
|
return ll.detach();
|
491
532
|
}
|
492
533
|
|
493
|
-
|
534
|
+
Expression* Eval::operator()(Map* m)
|
494
535
|
{
|
495
536
|
if (m->is_expanded()) return m;
|
496
537
|
|
@@ -505,8 +546,8 @@ namespace Sass {
|
|
505
546
|
m->pstate(),
|
506
547
|
m->length());
|
507
548
|
for (auto key : m->keys()) {
|
508
|
-
|
509
|
-
|
549
|
+
Expression* ex_key = key->perform(this);
|
550
|
+
Expression* ex_val = m->at(key);
|
510
551
|
if (ex_val == NULL) continue;
|
511
552
|
ex_val = ex_val->perform(this);
|
512
553
|
*mm << std::make_pair(ex_key, ex_val);
|
@@ -522,7 +563,7 @@ namespace Sass {
|
|
522
563
|
return mm.detach();
|
523
564
|
}
|
524
565
|
|
525
|
-
|
566
|
+
Expression* Eval::operator()(Binary_Expression* b_in)
|
526
567
|
{
|
527
568
|
|
528
569
|
Expression_Obj lhs = b_in->left();
|
@@ -543,21 +584,21 @@ namespace Sass {
|
|
543
584
|
}
|
544
585
|
|
545
586
|
// Evaluate variables as early o
|
546
|
-
while (
|
587
|
+
while (Variable* l_v = Cast<Variable>(lhs)) {
|
547
588
|
lhs = operator()(l_v);
|
548
589
|
}
|
549
|
-
while (
|
590
|
+
while (Variable* r_v = Cast<Variable>(rhs)) {
|
550
591
|
rhs = operator()(r_v);
|
551
592
|
}
|
552
593
|
|
553
594
|
Binary_Expression_Obj b = b_in;
|
554
595
|
|
555
596
|
// Evaluate sub-expressions early on
|
556
|
-
while (
|
597
|
+
while (Binary_Expression* l_b = Cast<Binary_Expression>(lhs)) {
|
557
598
|
if (!force && l_b->is_delayed()) break;
|
558
599
|
lhs = operator()(l_b);
|
559
600
|
}
|
560
|
-
while (
|
601
|
+
while (Binary_Expression* r_b = Cast<Binary_Expression>(rhs)) {
|
561
602
|
if (!force && r_b->is_delayed()) break;
|
562
603
|
rhs = operator()(r_b);
|
563
604
|
}
|
@@ -571,9 +612,9 @@ namespace Sass {
|
|
571
612
|
|
572
613
|
// specific types we know are final
|
573
614
|
// handle them early to avoid overhead
|
574
|
-
if (
|
615
|
+
if (Number* l_n = Cast<Number>(lhs)) {
|
575
616
|
// lhs is number and rhs is number
|
576
|
-
if (
|
617
|
+
if (Number* r_n = Cast<Number>(rhs)) {
|
577
618
|
try {
|
578
619
|
switch (op_type) {
|
579
620
|
case Sass_OP::EQ: return *l_n == *r_n ? bool_true : bool_false;
|
@@ -583,7 +624,7 @@ namespace Sass {
|
|
583
624
|
case Sass_OP::LTE: return *l_n < *r_n || *l_n == *r_n ? bool_true : bool_false;
|
584
625
|
case Sass_OP::GT: return *l_n < *r_n || *l_n == *r_n ? bool_false : bool_true;
|
585
626
|
case Sass_OP::ADD: case Sass_OP::SUB: case Sass_OP::MUL: case Sass_OP::DIV: case Sass_OP::MOD:
|
586
|
-
return Operators::op_numbers(op_type, *l_n, *r_n,
|
627
|
+
return Operators::op_numbers(op_type, *l_n, *r_n, options(), b_in->pstate());
|
587
628
|
default: break;
|
588
629
|
}
|
589
630
|
}
|
@@ -594,17 +635,15 @@ namespace Sass {
|
|
594
635
|
}
|
595
636
|
}
|
596
637
|
// lhs is number and rhs is color
|
597
|
-
|
638
|
+
// Todo: allow to work with HSLA colors
|
639
|
+
else if (Color* r_col = Cast<Color>(rhs)) {
|
640
|
+
Color_RGBA_Obj r_c = r_col->toRGBA();
|
598
641
|
try {
|
599
642
|
switch (op_type) {
|
600
643
|
case Sass_OP::EQ: return *l_n == *r_c ? bool_true : bool_false;
|
601
644
|
case Sass_OP::NEQ: return *l_n == *r_c ? bool_false : bool_true;
|
602
|
-
case Sass_OP::LT: return *l_n < *r_c ? bool_true : bool_false;
|
603
|
-
case Sass_OP::GTE: return *l_n < *r_c ? bool_false : bool_true;
|
604
|
-
case Sass_OP::LTE: return *l_n < *r_c || *l_n == *r_c ? bool_true : bool_false;
|
605
|
-
case Sass_OP::GT: return *l_n < *r_c || *l_n == *r_c ? bool_false : bool_true;
|
606
645
|
case Sass_OP::ADD: case Sass_OP::SUB: case Sass_OP::MUL: case Sass_OP::DIV: case Sass_OP::MOD:
|
607
|
-
return Operators::op_number_color(op_type, *l_n, *r_c,
|
646
|
+
return Operators::op_number_color(op_type, *l_n, *r_c, options(), b_in->pstate());
|
608
647
|
default: break;
|
609
648
|
}
|
610
649
|
}
|
@@ -615,9 +654,11 @@ namespace Sass {
|
|
615
654
|
}
|
616
655
|
}
|
617
656
|
}
|
618
|
-
else if (
|
657
|
+
else if (Color* l_col = Cast<Color>(lhs)) {
|
658
|
+
Color_RGBA_Obj l_c = l_col->toRGBA();
|
619
659
|
// lhs is color and rhs is color
|
620
|
-
if (
|
660
|
+
if (Color* r_col = Cast<Color>(rhs)) {
|
661
|
+
Color_RGBA_Obj r_c = r_col->toRGBA();
|
621
662
|
try {
|
622
663
|
switch (op_type) {
|
623
664
|
case Sass_OP::EQ: return *l_c == *r_c ? bool_true : bool_false;
|
@@ -627,7 +668,7 @@ namespace Sass {
|
|
627
668
|
case Sass_OP::LTE: return *l_c < *r_c || *l_c == *r_c ? bool_true : bool_false;
|
628
669
|
case Sass_OP::GT: return *l_c < *r_c || *l_c == *r_c ? bool_false : bool_true;
|
629
670
|
case Sass_OP::ADD: case Sass_OP::SUB: case Sass_OP::MUL: case Sass_OP::DIV: case Sass_OP::MOD:
|
630
|
-
return Operators::op_colors(op_type, *l_c, *r_c,
|
671
|
+
return Operators::op_colors(op_type, *l_c, *r_c, options(), b_in->pstate());
|
631
672
|
default: break;
|
632
673
|
}
|
633
674
|
}
|
@@ -638,17 +679,13 @@ namespace Sass {
|
|
638
679
|
}
|
639
680
|
}
|
640
681
|
// lhs is color and rhs is number
|
641
|
-
else if (
|
682
|
+
else if (Number* r_n = Cast<Number>(rhs)) {
|
642
683
|
try {
|
643
684
|
switch (op_type) {
|
644
685
|
case Sass_OP::EQ: return *l_c == *r_n ? bool_true : bool_false;
|
645
686
|
case Sass_OP::NEQ: return *l_c == *r_n ? bool_false : bool_true;
|
646
|
-
case Sass_OP::LT: return *l_c < *r_n ? bool_true : bool_false;
|
647
|
-
case Sass_OP::GTE: return *l_c < *r_n ? bool_false : bool_true;
|
648
|
-
case Sass_OP::LTE: return *l_c < *r_n || *l_c == *r_n ? bool_true : bool_false;
|
649
|
-
case Sass_OP::GT: return *l_c < *r_n || *l_c == *r_n ? bool_false : bool_true;
|
650
687
|
case Sass_OP::ADD: case Sass_OP::SUB: case Sass_OP::MUL: case Sass_OP::DIV: case Sass_OP::MOD:
|
651
|
-
return Operators::op_color_number(op_type, *l_c, *r_n,
|
688
|
+
return Operators::op_color_number(op_type, *l_c, *r_n, options(), b_in->pstate());
|
652
689
|
default: break;
|
653
690
|
}
|
654
691
|
}
|
@@ -663,29 +700,29 @@ namespace Sass {
|
|
663
700
|
String_Schema_Obj ret_schema;
|
664
701
|
|
665
702
|
// only the last item will be used to eval the binary expression
|
666
|
-
if (
|
703
|
+
if (String_Schema* s_l = Cast<String_Schema>(b->left())) {
|
667
704
|
if (!s_l->has_interpolant() && (!s_l->is_right_interpolant())) {
|
668
705
|
ret_schema = SASS_MEMORY_NEW(String_Schema, b->pstate());
|
669
706
|
Binary_Expression_Obj bin_ex = SASS_MEMORY_NEW(Binary_Expression, b->pstate(),
|
670
707
|
b->op(), s_l->last(), b->right());
|
671
708
|
bin_ex->is_delayed(b->left()->is_delayed() || b->right()->is_delayed()); // unverified
|
672
709
|
for (size_t i = 0; i < s_l->length() - 1; ++i) {
|
673
|
-
ret_schema->append(s_l->at(i)->perform(this));
|
710
|
+
ret_schema->append(Cast<PreValue>(s_l->at(i)->perform(this)));
|
674
711
|
}
|
675
|
-
ret_schema->append(bin_ex->perform(this));
|
712
|
+
ret_schema->append(Cast<PreValue>(bin_ex->perform(this)));
|
676
713
|
return ret_schema->perform(this);
|
677
714
|
}
|
678
715
|
}
|
679
|
-
if (
|
716
|
+
if (String_Schema* s_r = Cast<String_Schema>(b->right())) {
|
680
717
|
|
681
718
|
if (!s_r->has_interpolant() && (!s_r->is_left_interpolant() || op_type == Sass_OP::DIV)) {
|
682
719
|
ret_schema = SASS_MEMORY_NEW(String_Schema, b->pstate());
|
683
720
|
Binary_Expression_Obj bin_ex = SASS_MEMORY_NEW(Binary_Expression, b->pstate(),
|
684
721
|
b->op(), b->left(), s_r->first());
|
685
722
|
bin_ex->is_delayed(b->left()->is_delayed() || b->right()->is_delayed()); // verified
|
686
|
-
ret_schema->append(bin_ex->perform(this));
|
723
|
+
ret_schema->append(Cast<PreValue>(bin_ex->perform(this)));
|
687
724
|
for (size_t i = 1; i < s_r->length(); ++i) {
|
688
|
-
ret_schema->append(s_r->at(i)->perform(this));
|
725
|
+
ret_schema->append(Cast<PreValue>(s_r->at(i)->perform(this)));
|
689
726
|
}
|
690
727
|
return ret_schema->perform(this);
|
691
728
|
}
|
@@ -716,8 +753,8 @@ namespace Sass {
|
|
716
753
|
AST_Node_Obj lu = lhs;
|
717
754
|
AST_Node_Obj ru = rhs;
|
718
755
|
|
719
|
-
Expression::
|
720
|
-
Expression::
|
756
|
+
Expression::Type l_type;
|
757
|
+
Expression::Type r_type;
|
721
758
|
|
722
759
|
// Is one of the operands an interpolant?
|
723
760
|
String_Schema_Obj s1 = Cast<String_Schema>(b->left());
|
@@ -737,7 +774,7 @@ namespace Sass {
|
|
737
774
|
if (op_type == Sass_OP::DIV || op_type == Sass_OP::MUL || op_type == Sass_OP::MOD || op_type == Sass_OP::ADD || op_type == Sass_OP::SUB ||
|
738
775
|
op_type == Sass_OP::EQ) {
|
739
776
|
// If possible upgrade LHS to a number (for number to string compare)
|
740
|
-
if (
|
777
|
+
if (String_Constant* str = Cast<String_Constant>(lhs)) {
|
741
778
|
std::string value(str->value());
|
742
779
|
const char* start = value.c_str();
|
743
780
|
if (Prelexer::sequence < Prelexer::dimension, Prelexer::end_of_file >(start) != 0) {
|
@@ -745,7 +782,7 @@ namespace Sass {
|
|
745
782
|
}
|
746
783
|
}
|
747
784
|
// If possible upgrade RHS to a number (for string to number compare)
|
748
|
-
if (
|
785
|
+
if (String_Constant* str = Cast<String_Constant>(rhs)) {
|
749
786
|
std::string value(str->value());
|
750
787
|
const char* start = value.c_str();
|
751
788
|
if (Prelexer::sequence < Prelexer::dimension, Prelexer::number >(start) != 0) {
|
@@ -760,12 +797,12 @@ namespace Sass {
|
|
760
797
|
|
761
798
|
if (force_delay) {
|
762
799
|
std::string str("");
|
763
|
-
str += v_l->to_string(
|
800
|
+
str += v_l->to_string(options());
|
764
801
|
if (b->op().ws_before) str += " ";
|
765
802
|
str += b->separator();
|
766
803
|
if (b->op().ws_after) str += " ";
|
767
|
-
str += v_r->to_string(
|
768
|
-
|
804
|
+
str += v_r->to_string(options());
|
805
|
+
String_Constant* val = SASS_MEMORY_NEW(String_Constant, b->pstate(), str);
|
769
806
|
val->is_interpolant(b->left()->has_interpolant());
|
770
807
|
return val;
|
771
808
|
}
|
@@ -785,7 +822,6 @@ namespace Sass {
|
|
785
822
|
}
|
786
823
|
catch (Exception::OperationError& err)
|
787
824
|
{
|
788
|
-
// throw Exception::Base(b->pstate(), err.what());
|
789
825
|
traces.push_back(Backtrace(b->pstate()));
|
790
826
|
throw Exception::SassValueError(traces, b->pstate(), err);
|
791
827
|
}
|
@@ -799,25 +835,25 @@ namespace Sass {
|
|
799
835
|
try {
|
800
836
|
ParserState pstate(b->pstate());
|
801
837
|
if (l_type == Expression::NUMBER && r_type == Expression::NUMBER) {
|
802
|
-
|
803
|
-
|
838
|
+
Number* l_n = Cast<Number>(lhs);
|
839
|
+
Number* r_n = Cast<Number>(rhs);
|
804
840
|
l_n->reduce(); r_n->reduce();
|
805
|
-
rv = Operators::op_numbers(op_type, *l_n, *r_n,
|
841
|
+
rv = Operators::op_numbers(op_type, *l_n, *r_n, options(), pstate);
|
806
842
|
}
|
807
843
|
else if (l_type == Expression::NUMBER && r_type == Expression::COLOR) {
|
808
|
-
|
809
|
-
|
810
|
-
rv = Operators::op_number_color(op_type, *l_n, *r_c,
|
844
|
+
Number* l_n = Cast<Number>(lhs);
|
845
|
+
Color_RGBA_Obj r_c = Cast<Color>(rhs)->toRGBA();
|
846
|
+
rv = Operators::op_number_color(op_type, *l_n, *r_c, options(), pstate);
|
811
847
|
}
|
812
848
|
else if (l_type == Expression::COLOR && r_type == Expression::NUMBER) {
|
813
|
-
|
814
|
-
|
815
|
-
rv = Operators::op_color_number(op_type, *l_c, *r_n,
|
849
|
+
Color_RGBA_Obj l_c = Cast<Color>(lhs)->toRGBA();
|
850
|
+
Number* r_n = Cast<Number>(rhs);
|
851
|
+
rv = Operators::op_color_number(op_type, *l_c, *r_n, options(), pstate);
|
816
852
|
}
|
817
853
|
else if (l_type == Expression::COLOR && r_type == Expression::COLOR) {
|
818
|
-
|
819
|
-
|
820
|
-
rv = Operators::op_colors(op_type, *l_c, *r_c,
|
854
|
+
Color_RGBA_Obj l_c = Cast<Color>(lhs)->toRGBA();
|
855
|
+
Color_RGBA_Obj r_c = Cast<Color>(rhs)->toRGBA();
|
856
|
+
rv = Operators::op_colors(op_type, *l_c, *r_c, options(), pstate);
|
821
857
|
}
|
822
858
|
else {
|
823
859
|
To_Value to_value(ctx);
|
@@ -838,15 +874,15 @@ namespace Sass {
|
|
838
874
|
traces.push_back(Backtrace(v_r->pstate()));
|
839
875
|
throw Exception::InvalidValue(traces, *v_r);
|
840
876
|
}
|
841
|
-
|
842
|
-
if (
|
877
|
+
Value* ex = Operators::op_strings(b->op(), *v_l, *v_r, options(), pstate, !interpolant); // pass true to compress
|
878
|
+
if (String_Constant* str = Cast<String_Constant>(ex))
|
843
879
|
{
|
844
880
|
if (str->concrete_type() == Expression::STRING)
|
845
881
|
{
|
846
|
-
|
847
|
-
|
882
|
+
String_Constant* lstr = Cast<String_Constant>(lhs);
|
883
|
+
String_Constant* rstr = Cast<String_Constant>(rhs);
|
848
884
|
if (op_type != Sass_OP::SUB) {
|
849
|
-
if (
|
885
|
+
if (String_Constant* org = lstr ? lstr : rstr)
|
850
886
|
{ str->quote_mark(org->quote_mark()); }
|
851
887
|
}
|
852
888
|
}
|
@@ -874,11 +910,11 @@ namespace Sass {
|
|
874
910
|
|
875
911
|
}
|
876
912
|
|
877
|
-
|
913
|
+
Expression* Eval::operator()(Unary_Expression* u)
|
878
914
|
{
|
879
915
|
Expression_Obj operand = u->operand()->perform(this);
|
880
916
|
if (u->optype() == Unary_Expression::NOT) {
|
881
|
-
|
917
|
+
Boolean* result = SASS_MEMORY_NEW(Boolean, u->pstate(), (bool)*operand);
|
882
918
|
result->value(!result->value());
|
883
919
|
return result;
|
884
920
|
}
|
@@ -890,7 +926,7 @@ namespace Sass {
|
|
890
926
|
return cpy.detach(); // return the copy
|
891
927
|
}
|
892
928
|
else if (u->optype() == Unary_Expression::SLASH) {
|
893
|
-
std::string str = '/' + nr->to_string(
|
929
|
+
std::string str = '/' + nr->to_string(options());
|
894
930
|
return SASS_MEMORY_NEW(String_Constant, u->pstate(), str);
|
895
931
|
}
|
896
932
|
// nothing for positive
|
@@ -903,7 +939,7 @@ namespace Sass {
|
|
903
939
|
u->operand(SASS_MEMORY_NEW(String_Quoted, u->pstate(), ""));
|
904
940
|
}
|
905
941
|
// Never apply unary opertions on colors @see #2140
|
906
|
-
else if (
|
942
|
+
else if (Color* color = Cast<Color>(operand)) {
|
907
943
|
// Use the color name if this was eval with one
|
908
944
|
if (color->disp().length() > 0) {
|
909
945
|
operand = SASS_MEMORY_NEW(String_Constant, operand->pstate(), color->disp());
|
@@ -922,7 +958,7 @@ namespace Sass {
|
|
922
958
|
return u;
|
923
959
|
}
|
924
960
|
|
925
|
-
|
961
|
+
Expression* Eval::operator()(Function_Call* c)
|
926
962
|
{
|
927
963
|
if (traces.size() > Constants::MaxCallStack) {
|
928
964
|
// XXX: this is never hit via spec tests
|
@@ -930,8 +966,18 @@ namespace Sass {
|
|
930
966
|
stm << "Stack depth exceeded max of " << Constants::MaxCallStack;
|
931
967
|
error(stm.str(), c->pstate(), traces);
|
932
968
|
}
|
969
|
+
|
970
|
+
if (Cast<String_Schema>(c->sname())) {
|
971
|
+
Expression_Obj evaluated_name = c->sname()->perform(this);
|
972
|
+
Expression_Obj evaluated_args = c->arguments()->perform(this);
|
973
|
+
std::string str(evaluated_name->to_string());
|
974
|
+
str += evaluated_args->to_string();
|
975
|
+
return SASS_MEMORY_NEW(String_Constant, c->pstate(), str);
|
976
|
+
}
|
977
|
+
|
933
978
|
std::string name(Util::normalize_underscores(c->name()));
|
934
979
|
std::string full_name(name + "[f]");
|
980
|
+
|
935
981
|
// we make a clone here, need to implement that further
|
936
982
|
Arguments_Obj args = c->arguments();
|
937
983
|
|
@@ -951,9 +997,9 @@ namespace Sass {
|
|
951
997
|
if (args->has_named_arguments()) {
|
952
998
|
error("Function " + c->name() + " doesn't support keyword arguments", c->pstate(), traces);
|
953
999
|
}
|
954
|
-
|
1000
|
+
String_Quoted* str = SASS_MEMORY_NEW(String_Quoted,
|
955
1001
|
c->pstate(),
|
956
|
-
lit->to_string(
|
1002
|
+
lit->to_string(options()));
|
957
1003
|
str->is_interpolant(c->is_interpolant());
|
958
1004
|
return str;
|
959
1005
|
} else {
|
@@ -969,7 +1015,7 @@ namespace Sass {
|
|
969
1015
|
if (full_name != "if[f]") {
|
970
1016
|
args = Cast<Arguments>(args->perform(this));
|
971
1017
|
}
|
972
|
-
|
1018
|
+
Definition* def = Cast<Definition>((*env)[full_name]);
|
973
1019
|
|
974
1020
|
if (c->func()) def = c->func()->definition();
|
975
1021
|
|
@@ -979,7 +1025,7 @@ namespace Sass {
|
|
979
1025
|
// account for rest arguments
|
980
1026
|
if (args->has_rest_argument() && args->length() > 0) {
|
981
1027
|
// get the rest arguments list
|
982
|
-
|
1028
|
+
List* rest = Cast<List>(args->last()->value());
|
983
1029
|
// arguments before rest argument plus rest
|
984
1030
|
if (rest) L += rest->length() - 1;
|
985
1031
|
}
|
@@ -999,13 +1045,13 @@ namespace Sass {
|
|
999
1045
|
|
1000
1046
|
Parameters_Obj params = def->parameters();
|
1001
1047
|
Env fn_env(def->environment());
|
1002
|
-
|
1048
|
+
env_stack().push_back(&fn_env);
|
1003
1049
|
|
1004
1050
|
if (func || body) {
|
1005
|
-
bind(std::string("Function"), c->name(), params, args, &
|
1051
|
+
bind(std::string("Function"), c->name(), params, args, &fn_env, this, traces);
|
1006
1052
|
std::string msg(", in function `" + c->name() + "`");
|
1007
1053
|
traces.push_back(Backtrace(c->pstate(), msg));
|
1008
|
-
|
1054
|
+
callee_stack().push_back({
|
1009
1055
|
c->name().c_str(),
|
1010
1056
|
c->pstate().path,
|
1011
1057
|
c->pstate().line + 1,
|
@@ -1024,7 +1070,7 @@ namespace Sass {
|
|
1024
1070
|
if (!result) {
|
1025
1071
|
error(std::string("Function ") + c->name() + " finished without @return", c->pstate(), traces);
|
1026
1072
|
}
|
1027
|
-
|
1073
|
+
callee_stack().pop_back();
|
1028
1074
|
traces.pop_back();
|
1029
1075
|
}
|
1030
1076
|
|
@@ -1042,10 +1088,10 @@ namespace Sass {
|
|
1042
1088
|
|
1043
1089
|
// populates env with default values for params
|
1044
1090
|
std::string ff(c->name());
|
1045
|
-
bind(std::string("Function"), c->name(), params, args, &
|
1091
|
+
bind(std::string("Function"), c->name(), params, args, &fn_env, this, traces);
|
1046
1092
|
std::string msg(", in function `" + c->name() + "`");
|
1047
1093
|
traces.push_back(Backtrace(c->pstate(), msg));
|
1048
|
-
|
1094
|
+
callee_stack().push_back({
|
1049
1095
|
c->name().c_str(),
|
1050
1096
|
c->pstate().path,
|
1051
1097
|
c->pstate().line + 1,
|
@@ -1054,24 +1100,30 @@ namespace Sass {
|
|
1054
1100
|
{ env }
|
1055
1101
|
});
|
1056
1102
|
|
1057
|
-
|
1103
|
+
AST2C ast2c;
|
1058
1104
|
union Sass_Value* c_args = sass_make_list(params->length(), SASS_COMMA, false);
|
1059
1105
|
for(size_t i = 0; i < params->length(); i++) {
|
1060
1106
|
Parameter_Obj param = params->at(i);
|
1061
1107
|
std::string key = param->name();
|
1062
1108
|
AST_Node_Obj node = fn_env.get_local(key);
|
1063
1109
|
Expression_Obj arg = Cast<Expression>(node);
|
1064
|
-
sass_list_set_value(c_args, i, arg->perform(&
|
1110
|
+
sass_list_set_value(c_args, i, arg->perform(&ast2c));
|
1065
1111
|
}
|
1066
|
-
union Sass_Value* c_val = c_func(c_args, c_function,
|
1112
|
+
union Sass_Value* c_val = c_func(c_args, c_function, compiler());
|
1067
1113
|
if (sass_value_get_tag(c_val) == SASS_ERROR) {
|
1068
|
-
|
1114
|
+
std::string message("error in C function " + c->name() + ": " + sass_error_get_message(c_val));
|
1115
|
+
sass_delete_value(c_val);
|
1116
|
+
sass_delete_value(c_args);
|
1117
|
+
error(message, c->pstate(), traces);
|
1069
1118
|
} else if (sass_value_get_tag(c_val) == SASS_WARNING) {
|
1070
|
-
|
1119
|
+
std::string message("warning in C function " + c->name() + ": " + sass_warning_get_message(c_val));
|
1120
|
+
sass_delete_value(c_val);
|
1121
|
+
sass_delete_value(c_args);
|
1122
|
+
error(message, c->pstate(), traces);
|
1071
1123
|
}
|
1072
|
-
result =
|
1124
|
+
result = c2ast(c_val, traces, c->pstate());
|
1073
1125
|
|
1074
|
-
|
1126
|
+
callee_stack().pop_back();
|
1075
1127
|
traces.pop_back();
|
1076
1128
|
sass_delete_value(c_args);
|
1077
1129
|
if (c_val != c_args)
|
@@ -1085,30 +1137,20 @@ namespace Sass {
|
|
1085
1137
|
|
1086
1138
|
result = result->perform(this);
|
1087
1139
|
result->is_interpolant(c->is_interpolant());
|
1088
|
-
|
1140
|
+
env_stack().pop_back();
|
1089
1141
|
return result.detach();
|
1090
1142
|
}
|
1091
1143
|
|
1092
|
-
|
1144
|
+
Expression* Eval::operator()(Variable* v)
|
1093
1145
|
{
|
1094
|
-
|
1095
|
-
Expression_Ptr evaluated_args = s->arguments()->perform(this);
|
1096
|
-
String_Schema_Obj ss = SASS_MEMORY_NEW(String_Schema, s->pstate(), 2);
|
1097
|
-
ss->append(evaluated_name);
|
1098
|
-
ss->append(evaluated_args);
|
1099
|
-
return ss->perform(this);
|
1100
|
-
}
|
1101
|
-
|
1102
|
-
Expression_Ptr Eval::operator()(Variable_Ptr v)
|
1103
|
-
{
|
1104
|
-
Expression_Obj value = 0;
|
1146
|
+
Expression_Obj value;
|
1105
1147
|
Env* env = environment();
|
1106
1148
|
const std::string& name(v->name());
|
1107
1149
|
EnvResult rv(env->find(name));
|
1108
1150
|
if (rv.found) value = static_cast<Expression*>(rv.it->second.ptr());
|
1109
1151
|
else error("Undefined variable: \"" + v->name() + "\".", v->pstate(), traces);
|
1110
|
-
if (
|
1111
|
-
if (
|
1152
|
+
if (Argument* arg = Cast<Argument>(value)) value = arg->value();
|
1153
|
+
if (Number* nr = Cast<Number>(value)) nr->zero(true); // force flag
|
1112
1154
|
value->is_interpolant(v->is_interpolant());
|
1113
1155
|
if (force) value->is_expanded(false);
|
1114
1156
|
value->set_delayed(false); // verified
|
@@ -1117,17 +1159,22 @@ namespace Sass {
|
|
1117
1159
|
return value.detach();
|
1118
1160
|
}
|
1119
1161
|
|
1120
|
-
|
1162
|
+
Expression* Eval::operator()(Color_RGBA* c)
|
1163
|
+
{
|
1164
|
+
return c;
|
1165
|
+
}
|
1166
|
+
|
1167
|
+
Expression* Eval::operator()(Color_HSLA* c)
|
1121
1168
|
{
|
1122
1169
|
return c;
|
1123
1170
|
}
|
1124
1171
|
|
1125
|
-
|
1172
|
+
Expression* Eval::operator()(Number* n)
|
1126
1173
|
{
|
1127
1174
|
return n;
|
1128
1175
|
}
|
1129
1176
|
|
1130
|
-
|
1177
|
+
Expression* Eval::operator()(Boolean* b)
|
1131
1178
|
{
|
1132
1179
|
return b;
|
1133
1180
|
}
|
@@ -1136,8 +1183,8 @@ namespace Sass {
|
|
1136
1183
|
|
1137
1184
|
bool needs_closing_brace = false;
|
1138
1185
|
|
1139
|
-
if (
|
1140
|
-
|
1186
|
+
if (Arguments* args = Cast<Arguments>(ex)) {
|
1187
|
+
List* ll = SASS_MEMORY_NEW(List, args->pstate(), 0, SASS_COMMA);
|
1141
1188
|
for(auto arg : args->elements()) {
|
1142
1189
|
ll->append(arg->value());
|
1143
1190
|
}
|
@@ -1146,7 +1193,7 @@ namespace Sass {
|
|
1146
1193
|
res += "(";
|
1147
1194
|
ex = ll;
|
1148
1195
|
}
|
1149
|
-
if (
|
1196
|
+
if (Number* nr = Cast<Number>(ex)) {
|
1150
1197
|
Number reduced(nr);
|
1151
1198
|
reduced.reduce();
|
1152
1199
|
if (!reduced.is_valid_css_unit()) {
|
@@ -1154,10 +1201,10 @@ namespace Sass {
|
|
1154
1201
|
throw Exception::InvalidValue(traces, *nr);
|
1155
1202
|
}
|
1156
1203
|
}
|
1157
|
-
if (
|
1204
|
+
if (Argument* arg = Cast<Argument>(ex)) {
|
1158
1205
|
ex = arg->value();
|
1159
1206
|
}
|
1160
|
-
if (
|
1207
|
+
if (String_Quoted* sq = Cast<String_Quoted>(ex)) {
|
1161
1208
|
if (was_itpl) {
|
1162
1209
|
bool was_interpolant = ex->is_interpolant();
|
1163
1210
|
ex = SASS_MEMORY_NEW(String_Constant, sq->pstate(), sq->value());
|
@@ -1172,8 +1219,13 @@ namespace Sass {
|
|
1172
1219
|
// XXX: this is never hit via spec tests
|
1173
1220
|
ex = ex->perform(this);
|
1174
1221
|
}
|
1222
|
+
// parent selector needs another go
|
1223
|
+
if (Cast<Parent_Reference>(ex)) {
|
1224
|
+
// XXX: this is never hit via spec tests
|
1225
|
+
ex = ex->perform(this);
|
1226
|
+
}
|
1175
1227
|
|
1176
|
-
if (
|
1228
|
+
if (List* l = Cast<List>(ex)) {
|
1177
1229
|
List_Obj ll = SASS_MEMORY_NEW(List, l->pstate(), 0, l->separator());
|
1178
1230
|
// this fixes an issue with bourbon sample, not really sure why
|
1179
1231
|
// if (l->size() && Cast<Null>((*l)[0])) { res += ""; }
|
@@ -1187,12 +1239,12 @@ namespace Sass {
|
|
1187
1239
|
// here. Normally single list items are already unwrapped.
|
1188
1240
|
if (l->size() > 1) {
|
1189
1241
|
// string_to_output would fail "#{'_\a' '_\a'}";
|
1190
|
-
std::string str(ll->to_string(
|
1242
|
+
std::string str(ll->to_string(options()));
|
1191
1243
|
str = read_hex_escapes(str); // read escapes
|
1192
1244
|
newline_to_space(str); // replace directly
|
1193
1245
|
res += str; // append to result string
|
1194
1246
|
} else {
|
1195
|
-
res += (ll->to_string(
|
1247
|
+
res += (ll->to_string(options()));
|
1196
1248
|
}
|
1197
1249
|
ll->is_interpolant(l->is_interpolant());
|
1198
1250
|
}
|
@@ -1207,9 +1259,9 @@ namespace Sass {
|
|
1207
1259
|
else {
|
1208
1260
|
// ex = ex->perform(this);
|
1209
1261
|
if (into_quotes && ex->is_interpolant()) {
|
1210
|
-
res += evacuate_escapes(ex ? ex->to_string(
|
1262
|
+
res += evacuate_escapes(ex ? ex->to_string(options()) : "");
|
1211
1263
|
} else {
|
1212
|
-
std::string str(ex ? ex->to_string(
|
1264
|
+
std::string str(ex ? ex->to_string(options()) : "");
|
1213
1265
|
if (into_quotes) str = read_hex_escapes(str);
|
1214
1266
|
res += str; // append to result string
|
1215
1267
|
}
|
@@ -1219,14 +1271,14 @@ namespace Sass {
|
|
1219
1271
|
|
1220
1272
|
}
|
1221
1273
|
|
1222
|
-
|
1274
|
+
Expression* Eval::operator()(String_Schema* s)
|
1223
1275
|
{
|
1224
1276
|
size_t L = s->length();
|
1225
1277
|
bool into_quotes = false;
|
1226
1278
|
if (L > 1) {
|
1227
1279
|
if (!Cast<String_Quoted>((*s)[0]) && !Cast<String_Quoted>((*s)[L - 1])) {
|
1228
|
-
if (
|
1229
|
-
if (
|
1280
|
+
if (String_Constant* l = Cast<String_Constant>((*s)[0])) {
|
1281
|
+
if (String_Constant* r = Cast<String_Constant>((*s)[L - 1])) {
|
1230
1282
|
if (r->value().size() > 0) {
|
1231
1283
|
if (l->value()[0] == '"' && r->value()[r->value().size() - 1] == '"') into_quotes = true;
|
1232
1284
|
if (l->value()[0] == '\'' && r->value()[r->value().size() - 1] == '\'') into_quotes = true;
|
@@ -1255,7 +1307,7 @@ namespace Sass {
|
|
1255
1307
|
// string schema seems to have a special unquoting behavior (also handles "nested" quotes)
|
1256
1308
|
String_Quoted_Obj str = SASS_MEMORY_NEW(String_Quoted, s->pstate(), res, 0, false, false, false, s->css());
|
1257
1309
|
// if (s->is_interpolant()) str->quote_mark(0);
|
1258
|
-
//
|
1310
|
+
// String_Constant* str = SASS_MEMORY_NEW(String_Constant, s->pstate(), res);
|
1259
1311
|
if (str->quote_mark()) str->quote_mark('*');
|
1260
1312
|
else if (!is_in_comment) str->value(string_to_output(str->value()));
|
1261
1313
|
str->is_interpolant(s->is_interpolant());
|
@@ -1263,32 +1315,25 @@ namespace Sass {
|
|
1263
1315
|
}
|
1264
1316
|
|
1265
1317
|
|
1266
|
-
|
1318
|
+
Expression* Eval::operator()(String_Constant* s)
|
1267
1319
|
{
|
1268
|
-
if (!s->is_delayed() && name_to_color(s->value())) {
|
1269
|
-
Color_Ptr c = SASS_MEMORY_COPY(name_to_color(s->value())); // copy
|
1270
|
-
c->pstate(s->pstate());
|
1271
|
-
c->disp(s->value());
|
1272
|
-
c->is_delayed(true);
|
1273
|
-
return c;
|
1274
|
-
}
|
1275
1320
|
return s;
|
1276
1321
|
}
|
1277
1322
|
|
1278
|
-
|
1323
|
+
Expression* Eval::operator()(String_Quoted* s)
|
1279
1324
|
{
|
1280
|
-
|
1325
|
+
String_Quoted* str = SASS_MEMORY_NEW(String_Quoted, s->pstate(), "");
|
1281
1326
|
str->value(s->value());
|
1282
1327
|
str->quote_mark(s->quote_mark());
|
1283
1328
|
str->is_interpolant(s->is_interpolant());
|
1284
1329
|
return str;
|
1285
1330
|
}
|
1286
1331
|
|
1287
|
-
|
1332
|
+
Expression* Eval::operator()(Supports_Operator* c)
|
1288
1333
|
{
|
1289
|
-
|
1290
|
-
|
1291
|
-
|
1334
|
+
Expression* left = c->left()->perform(this);
|
1335
|
+
Expression* right = c->right()->perform(this);
|
1336
|
+
Supports_Operator* cc = SASS_MEMORY_NEW(Supports_Operator,
|
1292
1337
|
c->pstate(),
|
1293
1338
|
Cast<Supports_Condition>(left),
|
1294
1339
|
Cast<Supports_Condition>(right),
|
@@ -1296,52 +1341,52 @@ namespace Sass {
|
|
1296
1341
|
return cc;
|
1297
1342
|
}
|
1298
1343
|
|
1299
|
-
|
1344
|
+
Expression* Eval::operator()(Supports_Negation* c)
|
1300
1345
|
{
|
1301
|
-
|
1302
|
-
|
1346
|
+
Expression* condition = c->condition()->perform(this);
|
1347
|
+
Supports_Negation* cc = SASS_MEMORY_NEW(Supports_Negation,
|
1303
1348
|
c->pstate(),
|
1304
1349
|
Cast<Supports_Condition>(condition));
|
1305
1350
|
return cc;
|
1306
1351
|
}
|
1307
1352
|
|
1308
|
-
|
1353
|
+
Expression* Eval::operator()(Supports_Declaration* c)
|
1309
1354
|
{
|
1310
|
-
|
1311
|
-
|
1312
|
-
|
1355
|
+
Expression* feature = c->feature()->perform(this);
|
1356
|
+
Expression* value = c->value()->perform(this);
|
1357
|
+
Supports_Declaration* cc = SASS_MEMORY_NEW(Supports_Declaration,
|
1313
1358
|
c->pstate(),
|
1314
1359
|
feature,
|
1315
1360
|
value);
|
1316
1361
|
return cc;
|
1317
1362
|
}
|
1318
1363
|
|
1319
|
-
|
1364
|
+
Expression* Eval::operator()(Supports_Interpolation* c)
|
1320
1365
|
{
|
1321
|
-
|
1322
|
-
|
1366
|
+
Expression* value = c->value()->perform(this);
|
1367
|
+
Supports_Interpolation* cc = SASS_MEMORY_NEW(Supports_Interpolation,
|
1323
1368
|
c->pstate(),
|
1324
1369
|
value);
|
1325
1370
|
return cc;
|
1326
1371
|
}
|
1327
1372
|
|
1328
|
-
|
1373
|
+
Expression* Eval::operator()(At_Root_Query* e)
|
1329
1374
|
{
|
1330
1375
|
Expression_Obj feature = e->feature();
|
1331
1376
|
feature = (feature ? feature->perform(this) : 0);
|
1332
1377
|
Expression_Obj value = e->value();
|
1333
1378
|
value = (value ? value->perform(this) : 0);
|
1334
|
-
|
1379
|
+
Expression* ee = SASS_MEMORY_NEW(At_Root_Query,
|
1335
1380
|
e->pstate(),
|
1336
1381
|
Cast<String>(feature),
|
1337
1382
|
value);
|
1338
1383
|
return ee;
|
1339
1384
|
}
|
1340
1385
|
|
1341
|
-
|
1386
|
+
Media_Query* Eval::operator()(Media_Query* q)
|
1342
1387
|
{
|
1343
1388
|
String_Obj t = q->media_type();
|
1344
|
-
t = static_cast<
|
1389
|
+
t = static_cast<String*>(t.isNull() ? 0 : t->perform(this));
|
1345
1390
|
Media_Query_Obj qq = SASS_MEMORY_NEW(Media_Query,
|
1346
1391
|
q->pstate(),
|
1347
1392
|
t,
|
@@ -1349,12 +1394,12 @@ namespace Sass {
|
|
1349
1394
|
q->is_negated(),
|
1350
1395
|
q->is_restricted());
|
1351
1396
|
for (size_t i = 0, L = q->length(); i < L; ++i) {
|
1352
|
-
qq->append(static_cast<
|
1397
|
+
qq->append(static_cast<Media_Query_Expression*>((*q)[i]->perform(this)));
|
1353
1398
|
}
|
1354
1399
|
return qq.detach();
|
1355
1400
|
}
|
1356
1401
|
|
1357
|
-
|
1402
|
+
Expression* Eval::operator()(Media_Query_Expression* e)
|
1358
1403
|
{
|
1359
1404
|
Expression_Obj feature = e->feature();
|
1360
1405
|
feature = (feature ? feature->perform(this) : 0);
|
@@ -1378,12 +1423,12 @@ namespace Sass {
|
|
1378
1423
|
e->is_interpolated());
|
1379
1424
|
}
|
1380
1425
|
|
1381
|
-
|
1426
|
+
Expression* Eval::operator()(Null* n)
|
1382
1427
|
{
|
1383
1428
|
return n;
|
1384
1429
|
}
|
1385
1430
|
|
1386
|
-
|
1431
|
+
Expression* Eval::operator()(Argument* a)
|
1387
1432
|
{
|
1388
1433
|
Expression_Obj val = a->value()->perform(this);
|
1389
1434
|
bool is_rest_argument = a->is_rest_argument();
|
@@ -1412,13 +1457,13 @@ namespace Sass {
|
|
1412
1457
|
is_keyword_argument);
|
1413
1458
|
}
|
1414
1459
|
|
1415
|
-
|
1460
|
+
Expression* Eval::operator()(Arguments* a)
|
1416
1461
|
{
|
1417
1462
|
Arguments_Obj aa = SASS_MEMORY_NEW(Arguments, a->pstate());
|
1418
1463
|
if (a->length() == 0) return aa.detach();
|
1419
1464
|
for (size_t i = 0, L = a->length(); i < L; ++i) {
|
1420
1465
|
Expression_Obj rv = (*a)[i]->perform(this);
|
1421
|
-
|
1466
|
+
Argument* arg = Cast<Argument>(rv);
|
1422
1467
|
if (!(arg->is_rest_argument() || arg->is_keyword_argument())) {
|
1423
1468
|
aa->append(arg);
|
1424
1469
|
}
|
@@ -1429,8 +1474,8 @@ namespace Sass {
|
|
1429
1474
|
Expression_Obj splat = Cast<Argument>(rest)->value()->perform(this);
|
1430
1475
|
|
1431
1476
|
Sass_Separator separator = SASS_COMMA;
|
1432
|
-
|
1433
|
-
|
1477
|
+
List* ls = Cast<List>(splat);
|
1478
|
+
Map* ms = Cast<Map>(splat);
|
1434
1479
|
|
1435
1480
|
List_Obj arglist = SASS_MEMORY_NEW(List,
|
1436
1481
|
splat->pstate(),
|
@@ -1454,7 +1499,7 @@ namespace Sass {
|
|
1454
1499
|
|
1455
1500
|
if (a->has_keyword_argument()) {
|
1456
1501
|
Expression_Obj rv = a->get_keyword_argument()->perform(this);
|
1457
|
-
|
1502
|
+
Argument* rvarg = Cast<Argument>(rv);
|
1458
1503
|
Expression_Obj kwarg = rvarg->value()->perform(this);
|
1459
1504
|
|
1460
1505
|
aa->append(SASS_MEMORY_NEW(Argument, kwarg->pstate(), kwarg, "", false, true));
|
@@ -1462,74 +1507,14 @@ namespace Sass {
|
|
1462
1507
|
return aa.detach();
|
1463
1508
|
}
|
1464
1509
|
|
1465
|
-
|
1510
|
+
Expression* Eval::operator()(Comment* c)
|
1466
1511
|
{
|
1467
1512
|
return 0;
|
1468
1513
|
}
|
1469
1514
|
|
1470
|
-
|
1515
|
+
Selector_List* Eval::operator()(Selector_List* s)
|
1471
1516
|
{
|
1472
|
-
|
1473
|
-
}
|
1474
|
-
|
1475
|
-
// All the binary helpers.
|
1476
|
-
|
1477
|
-
Expression_Ptr cval_to_astnode(union Sass_Value* v, Backtraces traces, ParserState pstate)
|
1478
|
-
{
|
1479
|
-
using std::strlen;
|
1480
|
-
using std::strcpy;
|
1481
|
-
Expression_Ptr e = NULL;
|
1482
|
-
switch (sass_value_get_tag(v)) {
|
1483
|
-
case SASS_BOOLEAN: {
|
1484
|
-
e = SASS_MEMORY_NEW(Boolean, pstate, !!sass_boolean_get_value(v));
|
1485
|
-
} break;
|
1486
|
-
case SASS_NUMBER: {
|
1487
|
-
e = SASS_MEMORY_NEW(Number, pstate, sass_number_get_value(v), sass_number_get_unit(v));
|
1488
|
-
} break;
|
1489
|
-
case SASS_COLOR: {
|
1490
|
-
e = SASS_MEMORY_NEW(Color, pstate, sass_color_get_r(v), sass_color_get_g(v), sass_color_get_b(v), sass_color_get_a(v));
|
1491
|
-
} break;
|
1492
|
-
case SASS_STRING: {
|
1493
|
-
if (sass_string_is_quoted(v))
|
1494
|
-
e = SASS_MEMORY_NEW(String_Quoted, pstate, sass_string_get_value(v));
|
1495
|
-
else {
|
1496
|
-
e = SASS_MEMORY_NEW(String_Constant, pstate, sass_string_get_value(v));
|
1497
|
-
}
|
1498
|
-
} break;
|
1499
|
-
case SASS_LIST: {
|
1500
|
-
List_Ptr l = SASS_MEMORY_NEW(List, pstate, sass_list_get_length(v), sass_list_get_separator(v));
|
1501
|
-
for (size_t i = 0, L = sass_list_get_length(v); i < L; ++i) {
|
1502
|
-
l->append(cval_to_astnode(sass_list_get_value(v, i), traces, pstate));
|
1503
|
-
}
|
1504
|
-
l->is_bracketed(sass_list_get_is_bracketed(v));
|
1505
|
-
e = l;
|
1506
|
-
} break;
|
1507
|
-
case SASS_MAP: {
|
1508
|
-
Map_Ptr m = SASS_MEMORY_NEW(Map, pstate);
|
1509
|
-
for (size_t i = 0, L = sass_map_get_length(v); i < L; ++i) {
|
1510
|
-
*m << std::make_pair(
|
1511
|
-
cval_to_astnode(sass_map_get_key(v, i), traces, pstate),
|
1512
|
-
cval_to_astnode(sass_map_get_value(v, i), traces, pstate));
|
1513
|
-
}
|
1514
|
-
e = m;
|
1515
|
-
} break;
|
1516
|
-
case SASS_NULL: {
|
1517
|
-
e = SASS_MEMORY_NEW(Null, pstate);
|
1518
|
-
} break;
|
1519
|
-
case SASS_ERROR: {
|
1520
|
-
error("Error in C function: " + std::string(sass_error_get_message(v)), pstate, traces);
|
1521
|
-
} break;
|
1522
|
-
case SASS_WARNING: {
|
1523
|
-
error("Warning in C function: " + std::string(sass_warning_get_message(v)), pstate, traces);
|
1524
|
-
} break;
|
1525
|
-
default: break;
|
1526
|
-
}
|
1527
|
-
return e;
|
1528
|
-
}
|
1529
|
-
|
1530
|
-
Selector_List_Ptr Eval::operator()(Selector_List_Ptr s)
|
1531
|
-
{
|
1532
|
-
std::vector<Selector_List_Obj> rv;
|
1517
|
+
SelectorStack rv;
|
1533
1518
|
Selector_List_Obj sl = SASS_MEMORY_NEW(Selector_List, s->pstate());
|
1534
1519
|
sl->is_optional(s->is_optional());
|
1535
1520
|
sl->media_block(s->media_block());
|
@@ -1560,14 +1545,14 @@ namespace Sass {
|
|
1560
1545
|
}
|
1561
1546
|
|
1562
1547
|
|
1563
|
-
|
1548
|
+
Selector_List* Eval::operator()(Complex_Selector* s)
|
1564
1549
|
{
|
1565
1550
|
bool implicit_parent = !exp.old_at_root_without_rule;
|
1566
|
-
if (is_in_selector_schema) exp.selector_stack.push_back(
|
1551
|
+
if (is_in_selector_schema) exp.selector_stack.push_back({});
|
1567
1552
|
Selector_List_Obj resolved = s->resolve_parent_refs(exp.selector_stack, traces, implicit_parent);
|
1568
1553
|
if (is_in_selector_schema) exp.selector_stack.pop_back();
|
1569
1554
|
for (size_t i = 0; i < resolved->length(); i++) {
|
1570
|
-
|
1555
|
+
Complex_Selector* is = resolved->at(i)->mutable_first();
|
1571
1556
|
while (is) {
|
1572
1557
|
if (is->head()) {
|
1573
1558
|
is->head(operator()(is->head()));
|
@@ -1578,10 +1563,10 @@ namespace Sass {
|
|
1578
1563
|
return resolved.detach();
|
1579
1564
|
}
|
1580
1565
|
|
1581
|
-
|
1566
|
+
Compound_Selector* Eval::operator()(Compound_Selector* s)
|
1582
1567
|
{
|
1583
1568
|
for (size_t i = 0; i < s->length(); i++) {
|
1584
|
-
|
1569
|
+
Simple_Selector* ss = s->at(i);
|
1585
1570
|
// skip parents here (called via resolve_parent_refs)
|
1586
1571
|
if (ss == NULL || Cast<Parent_Selector>(ss)) continue;
|
1587
1572
|
s->at(i) = Cast<Simple_Selector>(ss->perform(this));
|
@@ -1589,14 +1574,12 @@ namespace Sass {
|
|
1589
1574
|
return s;
|
1590
1575
|
}
|
1591
1576
|
|
1592
|
-
|
1577
|
+
Selector_List* Eval::operator()(Selector_Schema* s)
|
1593
1578
|
{
|
1594
1579
|
LOCAL_FLAG(is_in_selector_schema, true);
|
1595
1580
|
// the parser will look for a brace to end the selector
|
1596
|
-
ctx.c_options.in_selector = true; // do not compress colors
|
1597
1581
|
Expression_Obj sel = s->contents()->perform(this);
|
1598
|
-
std::string result_str(sel->to_string(
|
1599
|
-
ctx.c_options.in_selector = false; // flag temporary only
|
1582
|
+
std::string result_str(sel->to_string(options()));
|
1600
1583
|
result_str = unquote(Util::rtrim(result_str));
|
1601
1584
|
char* temp_cstr = sass_copy_c_string(result_str.c_str());
|
1602
1585
|
ctx.strings.push_back(temp_cstr); // attach to context
|
@@ -1605,26 +1588,23 @@ namespace Sass {
|
|
1605
1588
|
// a selector schema may or may not connect to parent?
|
1606
1589
|
bool chroot = s->connect_parent() == false;
|
1607
1590
|
Selector_List_Obj sl = p.parse_selector_list(chroot);
|
1608
|
-
auto vec_str_rend = ctx.strings.rend();
|
1609
|
-
auto vec_str_rbegin = ctx.strings.rbegin();
|
1610
|
-
// remove the first item searching from the back
|
1611
|
-
// we cannot assume our item is still the last one
|
1612
|
-
// order is not important, so we can optimize this
|
1613
|
-
auto it = std::find(vec_str_rbegin, vec_str_rend, temp_cstr);
|
1614
|
-
// undefined behavior if not found!
|
1615
|
-
if (it != vec_str_rend) {
|
1616
|
-
// overwrite with last item
|
1617
|
-
*it = ctx.strings.back();
|
1618
|
-
// remove last one from vector
|
1619
|
-
ctx.strings.pop_back();
|
1620
|
-
// free temporary copy
|
1621
|
-
free(temp_cstr);
|
1622
|
-
}
|
1623
1591
|
flag_is_in_selector_schema.reset();
|
1624
1592
|
return operator()(sl);
|
1625
1593
|
}
|
1626
1594
|
|
1627
|
-
|
1595
|
+
Expression* Eval::operator()(Parent_Selector* p)
|
1596
|
+
{
|
1597
|
+
if (Selector_List_Obj pr = selector()) {
|
1598
|
+
exp.selector_stack.pop_back();
|
1599
|
+
Selector_List_Obj rv = operator()(pr);
|
1600
|
+
exp.selector_stack.push_back(rv);
|
1601
|
+
return rv.detach();
|
1602
|
+
} else {
|
1603
|
+
return SASS_MEMORY_NEW(Null, p->pstate());
|
1604
|
+
}
|
1605
|
+
}
|
1606
|
+
|
1607
|
+
Expression* Eval::operator()(Parent_Reference* p)
|
1628
1608
|
{
|
1629
1609
|
if (Selector_List_Obj pr = selector()) {
|
1630
1610
|
exp.selector_stack.pop_back();
|
@@ -1636,7 +1616,7 @@ namespace Sass {
|
|
1636
1616
|
}
|
1637
1617
|
}
|
1638
1618
|
|
1639
|
-
|
1619
|
+
Simple_Selector* Eval::operator()(Simple_Selector* s)
|
1640
1620
|
{
|
1641
1621
|
return s;
|
1642
1622
|
}
|
@@ -1646,13 +1626,13 @@ namespace Sass {
|
|
1646
1626
|
// be fixed by implement superselector correctly for `:not`
|
1647
1627
|
// first use of "find" (ATM only implemented for selectors)
|
1648
1628
|
bool hasNotSelector(AST_Node_Obj obj) {
|
1649
|
-
if (
|
1629
|
+
if (Wrapped_Selector* w = Cast<Wrapped_Selector>(obj)) {
|
1650
1630
|
return w->name() == ":not";
|
1651
1631
|
}
|
1652
1632
|
return false;
|
1653
1633
|
}
|
1654
1634
|
|
1655
|
-
|
1635
|
+
Wrapped_Selector* Eval::operator()(Wrapped_Selector* s)
|
1656
1636
|
{
|
1657
1637
|
|
1658
1638
|
if (s->name() == ":not") {
|
@@ -1660,15 +1640,14 @@ namespace Sass {
|
|
1660
1640
|
if (s->selector()->find(hasNotSelector)) {
|
1661
1641
|
s->selector()->clear();
|
1662
1642
|
s->name(" ");
|
1663
|
-
} else
|
1664
|
-
|
1665
|
-
|
1666
|
-
|
1667
|
-
|
1643
|
+
} else {
|
1644
|
+
for (size_t i = 0; i < s->selector()->length(); ++i) {
|
1645
|
+
Complex_Selector* cs = s->selector()->at(i);
|
1646
|
+
if (cs->tail()) {
|
1647
|
+
s->selector()->clear();
|
1648
|
+
s->name(" ");
|
1649
|
+
}
|
1668
1650
|
}
|
1669
|
-
} else if (s->selector()->length() > 1) {
|
1670
|
-
s->selector()->clear();
|
1671
|
-
s->name(" ");
|
1672
1651
|
}
|
1673
1652
|
}
|
1674
1653
|
}
|