sassc 1.11.1 → 1.11.2
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/.travis.yml +2 -2
- data/README.md +3 -2
- data/ext/libsass/Makefile.conf +2 -1
- data/ext/libsass/appveyor.yml +10 -5
- data/ext/libsass/docs/dev-ast-memory.md +223 -0
- data/ext/libsass/include/sass/base.h +2 -0
- data/ext/libsass/script/bootstrap +7 -4
- data/ext/libsass/script/ci-build-libsass +3 -3
- data/ext/libsass/script/ci-install-compiler +2 -0
- data/ext/libsass/script/ci-report-coverage +2 -1
- data/ext/libsass/script/test-leaks.pl +103 -0
- data/ext/libsass/src/ast.cpp +621 -495
- data/ext/libsass/src/ast.hpp +801 -367
- data/ext/libsass/src/ast_def_macros.hpp +5 -5
- data/ext/libsass/src/ast_fwd_decl.hpp +312 -14
- data/ext/libsass/src/bind.cpp +54 -51
- data/ext/libsass/src/bind.hpp +3 -7
- data/ext/libsass/src/check_nesting.cpp +117 -120
- data/ext/libsass/src/check_nesting.hpp +38 -34
- data/ext/libsass/src/color_maps.cpp +3 -3
- data/ext/libsass/src/color_maps.hpp +3 -3
- data/ext/libsass/src/context.cpp +33 -34
- data/ext/libsass/src/context.hpp +12 -14
- data/ext/libsass/src/cssize.cpp +200 -228
- data/ext/libsass/src/cssize.hpp +49 -49
- data/ext/libsass/src/debugger.hpp +260 -241
- data/ext/libsass/src/emitter.cpp +6 -6
- data/ext/libsass/src/emitter.hpp +7 -7
- data/ext/libsass/src/environment.cpp +2 -2
- data/ext/libsass/src/environment.hpp +0 -2
- data/ext/libsass/src/error_handling.cpp +5 -5
- data/ext/libsass/src/error_handling.hpp +12 -12
- data/ext/libsass/src/eval.cpp +412 -401
- data/ext/libsass/src/eval.hpp +61 -62
- data/ext/libsass/src/expand.cpp +223 -204
- data/ext/libsass/src/expand.hpp +42 -42
- data/ext/libsass/src/extend.cpp +198 -201
- data/ext/libsass/src/extend.hpp +12 -14
- data/ext/libsass/src/file.hpp +4 -5
- data/ext/libsass/src/functions.cpp +413 -418
- data/ext/libsass/src/functions.hpp +7 -10
- data/ext/libsass/src/inspect.cpp +115 -109
- data/ext/libsass/src/inspect.hpp +69 -69
- data/ext/libsass/src/listize.cpp +31 -33
- data/ext/libsass/src/listize.hpp +8 -10
- data/ext/libsass/src/memory/SharedPtr.cpp +116 -0
- data/ext/libsass/src/memory/SharedPtr.hpp +202 -0
- data/ext/libsass/src/node.cpp +45 -43
- data/ext/libsass/src/node.hpp +15 -15
- data/ext/libsass/src/operation.hpp +136 -136
- data/ext/libsass/src/output.cpp +48 -49
- data/ext/libsass/src/output.hpp +14 -14
- data/ext/libsass/src/parser.cpp +530 -554
- data/ext/libsass/src/parser.hpp +91 -96
- data/ext/libsass/src/prelexer.cpp +13 -10
- data/ext/libsass/src/remove_placeholders.cpp +25 -21
- data/ext/libsass/src/remove_placeholders.hpp +7 -7
- data/ext/libsass/src/sass2scss.cpp +2 -1
- data/ext/libsass/src/sass_context.cpp +125 -107
- data/ext/libsass/src/sass_context.hpp +1 -1
- data/ext/libsass/src/sass_util.hpp +5 -5
- data/ext/libsass/src/sass_values.cpp +27 -27
- data/ext/libsass/src/source_map.cpp +2 -2
- data/ext/libsass/src/source_map.hpp +2 -2
- data/ext/libsass/src/subset_map.cpp +57 -0
- data/ext/libsass/src/subset_map.hpp +8 -76
- data/ext/libsass/src/to_c.cpp +13 -13
- data/ext/libsass/src/to_c.hpp +14 -14
- data/ext/libsass/src/to_value.cpp +20 -20
- data/ext/libsass/src/to_value.hpp +20 -21
- data/ext/libsass/src/util.cpp +55 -88
- data/ext/libsass/src/util.hpp +9 -13
- data/ext/libsass/src/values.cpp +27 -26
- data/ext/libsass/src/values.hpp +2 -2
- data/ext/libsass/test/test_subset_map.cpp +69 -69
- data/ext/libsass/win/libsass.targets +3 -2
- data/ext/libsass/win/libsass.vcxproj.filters +9 -6
- data/lib/sassc/version.rb +1 -1
- data/sassc.gemspec +0 -1
- data/test/native_test.rb +1 -1
- metadata +7 -5
- data/ext/libsass/src/ast_factory.hpp +0 -92
- data/ext/libsass/src/memory_manager.cpp +0 -77
- data/ext/libsass/src/memory_manager.hpp +0 -48
data/ext/libsass/src/eval.hpp
CHANGED
@@ -12,10 +12,10 @@ namespace Sass {
|
|
12
12
|
class Expand;
|
13
13
|
class Context;
|
14
14
|
|
15
|
-
class Eval : public Operation_CRTP<
|
15
|
+
class Eval : public Operation_CRTP<Expression_Ptr, Eval> {
|
16
16
|
|
17
17
|
private:
|
18
|
-
|
18
|
+
Expression_Ptr fallback_impl(AST_Node_Ptr n);
|
19
19
|
|
20
20
|
public:
|
21
21
|
Expand& exp;
|
@@ -27,83 +27,82 @@ namespace Sass {
|
|
27
27
|
bool is_in_comment;
|
28
28
|
|
29
29
|
Env* environment();
|
30
|
-
Context& context();
|
31
|
-
CommaSequence_Selector* selector();
|
32
30
|
Backtrace* backtrace();
|
31
|
+
Selector_List_Obj selector();
|
33
32
|
|
34
33
|
// for evaluating function bodies
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
//
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
34
|
+
Expression_Ptr operator()(Block_Ptr);
|
35
|
+
Expression_Ptr operator()(Assignment_Ptr);
|
36
|
+
Expression_Ptr operator()(If_Ptr);
|
37
|
+
Expression_Ptr operator()(For_Ptr);
|
38
|
+
Expression_Ptr operator()(Each_Ptr);
|
39
|
+
Expression_Ptr operator()(While_Ptr);
|
40
|
+
Expression_Ptr operator()(Return_Ptr);
|
41
|
+
Expression_Ptr operator()(Warning_Ptr);
|
42
|
+
Expression_Ptr operator()(Error_Ptr);
|
43
|
+
Expression_Ptr operator()(Debug_Ptr);
|
44
|
+
|
45
|
+
Expression_Ptr operator()(List_Ptr);
|
46
|
+
Expression_Ptr operator()(Map_Ptr);
|
47
|
+
Expression_Ptr operator()(Binary_Expression_Ptr);
|
48
|
+
Expression_Ptr operator()(Unary_Expression_Ptr);
|
49
|
+
Expression_Ptr operator()(Function_Call_Ptr);
|
50
|
+
Expression_Ptr operator()(Function_Call_Schema_Ptr);
|
51
|
+
Expression_Ptr operator()(Variable_Ptr);
|
52
|
+
Expression_Ptr operator()(Textual_Ptr);
|
53
|
+
Expression_Ptr operator()(Number_Ptr);
|
54
|
+
Expression_Ptr operator()(Color_Ptr);
|
55
|
+
Expression_Ptr operator()(Boolean_Ptr);
|
56
|
+
Expression_Ptr operator()(String_Schema_Ptr);
|
57
|
+
Expression_Ptr operator()(String_Quoted_Ptr);
|
58
|
+
Expression_Ptr operator()(String_Constant_Ptr);
|
59
|
+
// Expression_Ptr operator()(Selector_List_Ptr);
|
60
|
+
Expression_Ptr operator()(Media_Query_Ptr);
|
61
|
+
Expression_Ptr operator()(Media_Query_Expression_Ptr);
|
62
|
+
Expression_Ptr operator()(At_Root_Query_Ptr);
|
63
|
+
Expression_Ptr operator()(Supports_Operator_Ptr);
|
64
|
+
Expression_Ptr operator()(Supports_Negation_Ptr);
|
65
|
+
Expression_Ptr operator()(Supports_Declaration_Ptr);
|
66
|
+
Expression_Ptr operator()(Supports_Interpolation_Ptr);
|
67
|
+
Expression_Ptr operator()(Null_Ptr);
|
68
|
+
Expression_Ptr operator()(Argument_Ptr);
|
69
|
+
Expression_Ptr operator()(Arguments_Ptr);
|
70
|
+
Expression_Ptr operator()(Comment_Ptr);
|
72
71
|
|
73
72
|
// these will return selectors
|
74
|
-
|
75
|
-
|
76
|
-
|
73
|
+
Selector_List_Ptr operator()(Selector_List_Ptr);
|
74
|
+
Selector_List_Ptr operator()(Complex_Selector_Ptr);
|
75
|
+
Attribute_Selector_Ptr operator()(Attribute_Selector_Ptr);
|
77
76
|
// they don't have any specific implementatio (yet)
|
78
|
-
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
|
83
|
-
|
77
|
+
Element_Selector_Ptr operator()(Element_Selector_Ptr s) { return s; };
|
78
|
+
Pseudo_Selector_Ptr operator()(Pseudo_Selector_Ptr s) { return s; };
|
79
|
+
Wrapped_Selector_Ptr operator()(Wrapped_Selector_Ptr s) { return s; };
|
80
|
+
Class_Selector_Ptr operator()(Class_Selector_Ptr s) { return s; };
|
81
|
+
Id_Selector_Ptr operator()(Id_Selector_Ptr s) { return s; };
|
82
|
+
Placeholder_Selector_Ptr operator()(Placeholder_Selector_Ptr s) { return s; };
|
84
83
|
// actual evaluated selectors
|
85
|
-
|
86
|
-
|
84
|
+
Selector_List_Ptr operator()(Selector_Schema_Ptr);
|
85
|
+
Expression_Ptr operator()(Parent_Selector_Ptr);
|
87
86
|
|
88
87
|
template <typename U>
|
89
|
-
|
88
|
+
Expression_Ptr fallback(U x) { return fallback_impl(x); }
|
90
89
|
|
91
90
|
// -- only need to define two comparisons, and the rest can be implemented in terms of them
|
92
|
-
static bool eq(
|
93
|
-
static bool lt(
|
91
|
+
static bool eq(Expression_Obj, Expression_Obj);
|
92
|
+
static bool lt(Expression_Obj, Expression_Obj, std::string op);
|
94
93
|
// -- arithmetic on the combinations that matter
|
95
|
-
static
|
96
|
-
static
|
97
|
-
static
|
98
|
-
static
|
99
|
-
static
|
94
|
+
static Value_Ptr op_numbers(enum Sass_OP, const Number&, const Number&, struct Sass_Inspect_Options opt, ParserState* pstate = 0);
|
95
|
+
static Value_Ptr op_number_color(enum Sass_OP, const Number&, const Color&, struct Sass_Inspect_Options opt, ParserState* pstate = 0);
|
96
|
+
static Value_Ptr op_color_number(enum Sass_OP, const Color&, const Number&, struct Sass_Inspect_Options opt, ParserState* pstate = 0);
|
97
|
+
static Value_Ptr op_colors(enum Sass_OP, const Color&, const Color&, struct Sass_Inspect_Options opt, ParserState* pstate = 0);
|
98
|
+
static Value_Ptr op_strings(Sass::Operand, Value&, Value&, struct Sass_Inspect_Options opt, ParserState* pstate = 0, bool interpolant = false);
|
100
99
|
|
101
100
|
private:
|
102
|
-
void interpolation(Context& ctx, std::string& res,
|
101
|
+
void interpolation(Context& ctx, std::string& res, Expression_Obj ex, bool into_quotes, bool was_itpl = false);
|
103
102
|
|
104
103
|
};
|
105
104
|
|
106
|
-
|
105
|
+
Expression_Ptr cval_to_astnode(union Sass_Value* v, Backtrace* backtrace, ParserState pstate = ParserState("[AST]"));
|
107
106
|
|
108
107
|
}
|
109
108
|
|
data/ext/libsass/src/expand.cpp
CHANGED
@@ -2,6 +2,7 @@
|
|
2
2
|
#include <iostream>
|
3
3
|
#include <typeinfo>
|
4
4
|
|
5
|
+
#include "ast.hpp"
|
5
6
|
#include "expand.hpp"
|
6
7
|
#include "bind.hpp"
|
7
8
|
#include "eval.hpp"
|
@@ -12,29 +13,26 @@
|
|
12
13
|
namespace Sass {
|
13
14
|
|
14
15
|
// simple endless recursion protection
|
15
|
-
const
|
16
|
-
static unsigned int recursions = 0;
|
16
|
+
const size_t maxRecursion = 500;
|
17
17
|
|
18
|
-
Expand::Expand(Context& ctx, Env* env, Backtrace* bt, std::vector<
|
18
|
+
Expand::Expand(Context& ctx, Env* env, Backtrace* bt, std::vector<Selector_List_Obj>* stack)
|
19
19
|
: ctx(ctx),
|
20
20
|
eval(Eval(*this)),
|
21
|
-
|
22
|
-
block_stack(std::vector<Block*>()),
|
23
|
-
call_stack(std::vector<AST_Node*>()),
|
24
|
-
property_stack(std::vector<String*>()),
|
25
|
-
selector_stack(std::vector<CommaSequence_Selector*>()),
|
26
|
-
media_block_stack(std::vector<Media_Block*>()),
|
27
|
-
backtrace_stack(std::vector<Backtrace*>()),
|
21
|
+
recursions(0),
|
28
22
|
in_keyframes(false),
|
29
23
|
at_root_without_rule(false),
|
30
|
-
old_at_root_without_rule(false)
|
24
|
+
old_at_root_without_rule(false),
|
25
|
+
env_stack(std::vector<Env*>()),
|
26
|
+
block_stack(std::vector<Block_Ptr>()),
|
27
|
+
call_stack(std::vector<AST_Node_Obj>()),
|
28
|
+
selector_stack(std::vector<Selector_List_Obj>()),
|
29
|
+
media_block_stack(std::vector<Media_Block_Ptr>()),
|
30
|
+
backtrace_stack(std::vector<Backtrace*>())
|
31
31
|
{
|
32
32
|
env_stack.push_back(0);
|
33
33
|
env_stack.push_back(env);
|
34
34
|
block_stack.push_back(0);
|
35
35
|
call_stack.push_back(0);
|
36
|
-
// import_stack.push_back(0);
|
37
|
-
property_stack.push_back(0);
|
38
36
|
if (stack == NULL) { selector_stack.push_back(0); }
|
39
37
|
else { selector_stack.insert(selector_stack.end(), stack->begin(), stack->end()); }
|
40
38
|
media_block_stack.push_back(0);
|
@@ -54,7 +52,7 @@ namespace Sass {
|
|
54
52
|
return 0;
|
55
53
|
}
|
56
54
|
|
57
|
-
|
55
|
+
Selector_List_Obj Expand::selector()
|
58
56
|
{
|
59
57
|
if (selector_stack.size() > 0)
|
60
58
|
return selector_stack.back();
|
@@ -69,40 +67,42 @@ namespace Sass {
|
|
69
67
|
}
|
70
68
|
|
71
69
|
// blocks create new variable scopes
|
72
|
-
|
70
|
+
Block_Ptr Expand::operator()(Block_Ptr b)
|
73
71
|
{
|
74
72
|
// create new local environment
|
75
73
|
// set the current env as parent
|
76
74
|
Env env(environment());
|
77
75
|
// copy the block object (add items later)
|
78
|
-
|
76
|
+
Block_Obj bb = SASS_MEMORY_NEW(Block,
|
79
77
|
b->pstate(),
|
80
78
|
b->length(),
|
81
79
|
b->is_root());
|
82
80
|
// setup block and env stack
|
83
|
-
this->block_stack.push_back(bb);
|
81
|
+
this->block_stack.push_back(&bb);
|
84
82
|
this->env_stack.push_back(&env);
|
85
83
|
// operate on block
|
84
|
+
// this may throw up!
|
86
85
|
this->append_block(b);
|
87
86
|
// revert block and env stack
|
88
87
|
this->block_stack.pop_back();
|
89
88
|
this->env_stack.pop_back();
|
90
89
|
// return copy
|
91
|
-
return bb;
|
90
|
+
return bb.detach();
|
92
91
|
}
|
93
92
|
|
94
|
-
|
93
|
+
Statement_Ptr Expand::operator()(Ruleset_Ptr r)
|
95
94
|
{
|
96
95
|
LOCAL_FLAG(old_at_root_without_rule, at_root_without_rule);
|
97
96
|
|
98
97
|
if (in_keyframes) {
|
99
|
-
|
98
|
+
Block_Ptr bb = operator()(&r->block());
|
99
|
+
Keyframe_Rule_Obj k = SASS_MEMORY_NEW(Keyframe_Rule, r->pstate(), bb);
|
100
100
|
if (r->selector()) {
|
101
101
|
selector_stack.push_back(0);
|
102
|
-
k->
|
102
|
+
k->name(SASS_MEMORY_CAST_PTR(Selector_List, r->selector()->perform(&eval)));
|
103
103
|
selector_stack.pop_back();
|
104
104
|
}
|
105
|
-
return k;
|
105
|
+
return k.detach();
|
106
106
|
}
|
107
107
|
|
108
108
|
// reset when leaving scope
|
@@ -110,46 +110,48 @@ namespace Sass {
|
|
110
110
|
|
111
111
|
// do some special checks for the base level rules
|
112
112
|
if (r->is_root()) {
|
113
|
-
if (
|
114
|
-
for (
|
115
|
-
|
113
|
+
if (Selector_List_Ptr selector_list = SASS_MEMORY_CAST(Selector_List, r->selector())) {
|
114
|
+
for (Complex_Selector_Obj complex_selector : selector_list->elements()) {
|
115
|
+
Complex_Selector_Ptr tail = &complex_selector;
|
116
116
|
while (tail) {
|
117
|
-
if (tail->head()) for (
|
118
|
-
if (
|
117
|
+
if (tail->head()) for (Simple_Selector_Obj header : tail->head()->elements()) {
|
118
|
+
if (SASS_MEMORY_CAST(Parent_Selector, header) == NULL) continue; // skip all others
|
119
119
|
std::string sel_str(complex_selector->to_string(ctx.c_options));
|
120
120
|
error("Base-level rules cannot contain the parent-selector-referencing character '&'.", header->pstate(), backtrace());
|
121
121
|
}
|
122
|
-
tail = tail->tail();
|
122
|
+
tail = &tail->tail();
|
123
123
|
}
|
124
124
|
}
|
125
125
|
}
|
126
126
|
}
|
127
127
|
|
128
|
-
|
129
|
-
|
128
|
+
Expression_Obj ex = 0;
|
129
|
+
if (r->selector()) ex = r->selector()->perform(&eval);
|
130
|
+
Selector_List_Obj sel = SASS_MEMORY_CAST(Selector_List, ex);
|
130
131
|
if (sel == 0) throw std::runtime_error("Expanded null selector");
|
131
132
|
|
132
133
|
if (sel->length() == 0 || sel->has_parent_ref()) {
|
133
134
|
bool has_parent_selector = false;
|
134
135
|
for (size_t i = 0, L = selector_stack.size(); i < L && !has_parent_selector; i++) {
|
135
|
-
|
136
|
+
Selector_List_Obj ll = selector_stack.at(i);
|
136
137
|
has_parent_selector = ll != 0 && ll->length() > 0;
|
137
138
|
}
|
138
|
-
if (!has_parent_selector) {
|
139
|
+
if (sel->has_real_parent_ref() && !has_parent_selector) {
|
139
140
|
error("Base-level rules cannot contain the parent-selector-referencing character '&'.", sel->pstate(), backtrace());
|
140
141
|
}
|
141
142
|
}
|
142
143
|
|
143
|
-
selector_stack.push_back(sel);
|
144
|
+
selector_stack.push_back(&sel);
|
144
145
|
Env env(environment());
|
145
146
|
if (block_stack.back()->is_root()) {
|
146
147
|
env_stack.push_back(&env);
|
147
148
|
}
|
148
149
|
sel->set_media_block(media_block_stack.back());
|
149
|
-
|
150
|
-
|
150
|
+
Block_Obj blk = 0;
|
151
|
+
if (r->block()) blk = operator()(&r->block());
|
152
|
+
Ruleset_Ptr rr = SASS_MEMORY_NEW(Ruleset,
|
151
153
|
r->pstate(),
|
152
|
-
sel,
|
154
|
+
&sel,
|
153
155
|
blk);
|
154
156
|
selector_stack.pop_back();
|
155
157
|
if (block_stack.back()->is_root()) {
|
@@ -162,66 +164,70 @@ namespace Sass {
|
|
162
164
|
return rr;
|
163
165
|
}
|
164
166
|
|
165
|
-
|
167
|
+
Statement_Ptr Expand::operator()(Supports_Block_Ptr f)
|
166
168
|
{
|
167
|
-
|
168
|
-
|
169
|
+
Expression_Obj condition = f->condition()->perform(&eval);
|
170
|
+
Supports_Block_Obj ff = SASS_MEMORY_NEW(Supports_Block,
|
169
171
|
f->pstate(),
|
170
|
-
|
171
|
-
|
172
|
-
return ff;
|
172
|
+
SASS_MEMORY_CAST(Supports_Condition, condition),
|
173
|
+
operator()(&f->block()));
|
174
|
+
return ff.detach();
|
173
175
|
}
|
174
176
|
|
175
|
-
|
177
|
+
Statement_Ptr Expand::operator()(Media_Block_Ptr m)
|
176
178
|
{
|
177
179
|
media_block_stack.push_back(m);
|
178
|
-
|
180
|
+
Expression_Obj mq = m->media_queries()->perform(&eval);
|
179
181
|
std::string str_mq(mq->to_string(ctx.c_options));
|
180
182
|
char* str = sass_copy_c_string(str_mq.c_str());
|
181
183
|
ctx.strings.push_back(str);
|
182
184
|
Parser p(Parser::from_c_str(str, ctx, mq->pstate()));
|
183
|
-
mq = p.parse_media_queries();
|
184
|
-
|
185
|
+
mq = &p.parse_media_queries(); // re-assign now
|
186
|
+
List_Obj ls = SASS_MEMORY_CAST_PTR(List, mq->perform(&eval));
|
187
|
+
Block_Obj blk = operator()(&m->block());
|
188
|
+
Media_Block_Ptr mm = SASS_MEMORY_NEW(Media_Block,
|
185
189
|
m->pstate(),
|
186
|
-
|
187
|
-
|
190
|
+
ls,
|
191
|
+
blk,
|
188
192
|
0);
|
189
193
|
media_block_stack.pop_back();
|
190
194
|
mm->tabs(m->tabs());
|
191
195
|
return mm;
|
192
196
|
}
|
193
197
|
|
194
|
-
|
198
|
+
Statement_Ptr Expand::operator()(At_Root_Block_Ptr a)
|
195
199
|
{
|
196
|
-
|
197
|
-
|
200
|
+
Block_Obj ab = a->block();
|
201
|
+
Expression_Obj ae = &a->expression();
|
198
202
|
|
199
203
|
if (ae) ae = ae->perform(&eval);
|
200
|
-
else ae = SASS_MEMORY_NEW(
|
204
|
+
else ae = SASS_MEMORY_NEW(At_Root_Query, a->pstate());
|
201
205
|
|
202
206
|
LOCAL_FLAG(at_root_without_rule, true);
|
203
207
|
LOCAL_FLAG(in_keyframes, false);
|
204
208
|
|
205
|
-
|
206
|
-
|
209
|
+
;
|
210
|
+
|
211
|
+
Block_Obj bb = ab ? operator()(&ab) : NULL;
|
212
|
+
At_Root_Block_Obj aa = SASS_MEMORY_NEW(At_Root_Block,
|
207
213
|
a->pstate(),
|
208
214
|
bb,
|
209
|
-
|
210
|
-
return aa;
|
215
|
+
SASS_MEMORY_CAST(At_Root_Query, ae));
|
216
|
+
return aa.detach();
|
211
217
|
}
|
212
218
|
|
213
|
-
|
219
|
+
Statement_Ptr Expand::operator()(Directive_Ptr a)
|
214
220
|
{
|
215
221
|
LOCAL_FLAG(in_keyframes, a->is_keyframes());
|
216
|
-
|
217
|
-
|
218
|
-
|
222
|
+
Block_Ptr ab = &a->block();
|
223
|
+
Selector_Ptr as = &a->selector();
|
224
|
+
Expression_Ptr av = &a->value();
|
219
225
|
selector_stack.push_back(0);
|
220
226
|
if (av) av = av->perform(&eval);
|
221
|
-
if (as) as =
|
227
|
+
if (as) as = SASS_MEMORY_CAST_PTR(Selector, as->perform(&eval));
|
222
228
|
selector_stack.pop_back();
|
223
|
-
|
224
|
-
|
229
|
+
Block_Ptr bb = ab ? operator()(ab) : NULL;
|
230
|
+
Directive_Ptr aa = SASS_MEMORY_NEW(Directive,
|
225
231
|
a->pstate(),
|
226
232
|
a->keyword(),
|
227
233
|
as,
|
@@ -230,17 +236,23 @@ namespace Sass {
|
|
230
236
|
return aa;
|
231
237
|
}
|
232
238
|
|
233
|
-
|
239
|
+
Statement_Ptr Expand::operator()(Declaration_Ptr d)
|
234
240
|
{
|
235
|
-
|
236
|
-
|
237
|
-
|
238
|
-
|
239
|
-
|
241
|
+
Block_Obj ab = d->block();
|
242
|
+
String_Obj old_p = d->property();
|
243
|
+
Expression_Obj prop = old_p->perform(&eval);
|
244
|
+
String_Obj new_p = SASS_MEMORY_CAST(String, prop);
|
245
|
+
// we might get a color back
|
246
|
+
if (!new_p) {
|
247
|
+
std::string str(prop->to_string(ctx.c_options));
|
248
|
+
new_p = SASS_MEMORY_NEW(String_Constant, old_p->pstate(), str);
|
249
|
+
}
|
250
|
+
Expression_Obj value = d->value()->perform(&eval);
|
251
|
+
Block_Obj bb = ab ? operator()(&ab) : NULL;
|
240
252
|
if (!bb) {
|
241
253
|
if (!value || (value->is_invisible() && !d->is_important())) return 0;
|
242
254
|
}
|
243
|
-
|
255
|
+
Declaration_Ptr decl = SASS_MEMORY_NEW(Declaration,
|
244
256
|
d->pstate(),
|
245
257
|
new_p,
|
246
258
|
value,
|
@@ -250,14 +262,14 @@ namespace Sass {
|
|
250
262
|
return decl;
|
251
263
|
}
|
252
264
|
|
253
|
-
|
265
|
+
Statement_Ptr Expand::operator()(Assignment_Ptr a)
|
254
266
|
{
|
255
267
|
Env* env = environment();
|
256
268
|
std::string var(a->variable());
|
257
269
|
if (a->is_global()) {
|
258
270
|
if (a->is_default()) {
|
259
271
|
if (env->has_global(var)) {
|
260
|
-
|
272
|
+
Expression_Obj e = SASS_MEMORY_CAST(Expression, env->get_global(var));
|
261
273
|
if (!e || e->concrete_type() == Expression::NULL_VAL) {
|
262
274
|
env->set_global(var, a->value()->perform(&eval));
|
263
275
|
}
|
@@ -275,8 +287,8 @@ namespace Sass {
|
|
275
287
|
auto cur = env;
|
276
288
|
while (cur && cur->is_lexical()) {
|
277
289
|
if (cur->has_local(var)) {
|
278
|
-
if (
|
279
|
-
|
290
|
+
if (AST_Node_Obj node = cur->get_local(var)) {
|
291
|
+
Expression_Obj e = SASS_MEMORY_CAST(Expression, node);
|
280
292
|
if (!e || e->concrete_type() == Expression::NULL_VAL) {
|
281
293
|
cur->set_local(var, a->value()->perform(&eval));
|
282
294
|
}
|
@@ -291,8 +303,8 @@ namespace Sass {
|
|
291
303
|
throw std::runtime_error("Env not in sync");
|
292
304
|
}
|
293
305
|
else if (env->has_global(var)) {
|
294
|
-
if (
|
295
|
-
|
306
|
+
if (AST_Node_Obj node = env->get_global(var)) {
|
307
|
+
Expression_Obj e = SASS_MEMORY_CAST(Expression, node);
|
296
308
|
if (!e || e->concrete_type() == Expression::NULL_VAL) {
|
297
309
|
env->set_global(var, a->value()->perform(&eval));
|
298
310
|
}
|
@@ -311,26 +323,26 @@ namespace Sass {
|
|
311
323
|
return 0;
|
312
324
|
}
|
313
325
|
|
314
|
-
|
326
|
+
Statement_Ptr Expand::operator()(Import_Ptr imp)
|
315
327
|
{
|
316
|
-
|
317
|
-
if (imp->
|
318
|
-
|
319
|
-
result->
|
328
|
+
Import_Obj result = SASS_MEMORY_NEW(Import, imp->pstate());
|
329
|
+
if (imp->import_queries() && imp->import_queries()->size()) {
|
330
|
+
Expression_Obj ex = imp->import_queries()->perform(&eval);
|
331
|
+
result->import_queries(SASS_MEMORY_CAST(List, ex));
|
320
332
|
}
|
321
333
|
for ( size_t i = 0, S = imp->urls().size(); i < S; ++i) {
|
322
334
|
result->urls().push_back(imp->urls()[i]->perform(&eval));
|
323
335
|
}
|
324
336
|
// all resources have been dropped for Input_Stubs
|
325
337
|
// for ( size_t i = 0, S = imp->incs().size(); i < S; ++i) {}
|
326
|
-
return result;
|
338
|
+
return result.detach();
|
327
339
|
}
|
328
340
|
|
329
|
-
|
341
|
+
Statement_Ptr Expand::operator()(Import_Stub_Ptr i)
|
330
342
|
{
|
331
343
|
// get parent node from call stack
|
332
|
-
|
333
|
-
if (
|
344
|
+
AST_Node_Obj parent = call_stack.back();
|
345
|
+
if (SASS_MEMORY_CAST(Block, parent) == NULL) {
|
334
346
|
error("Import directives may not be used within control directives or mixins.", i->pstate());
|
335
347
|
}
|
336
348
|
// we don't seem to need that actually afterall
|
@@ -341,52 +353,53 @@ namespace Sass {
|
|
341
353
|
);
|
342
354
|
ctx.import_stack.push_back(import);
|
343
355
|
const std::string& abs_path(i->resource().abs_path);
|
344
|
-
append_block(ctx.sheets.at(abs_path).root);
|
356
|
+
append_block(&ctx.sheets.at(abs_path).root);
|
345
357
|
sass_delete_import(ctx.import_stack.back());
|
346
358
|
ctx.import_stack.pop_back();
|
347
359
|
return 0;
|
348
360
|
}
|
349
361
|
|
350
|
-
|
362
|
+
Statement_Ptr Expand::operator()(Warning_Ptr w)
|
351
363
|
{
|
352
364
|
// eval handles this too, because warnings may occur in functions
|
353
365
|
w->perform(&eval);
|
354
366
|
return 0;
|
355
367
|
}
|
356
368
|
|
357
|
-
|
369
|
+
Statement_Ptr Expand::operator()(Error_Ptr e)
|
358
370
|
{
|
359
371
|
// eval handles this too, because errors may occur in functions
|
360
372
|
e->perform(&eval);
|
361
373
|
return 0;
|
362
374
|
}
|
363
375
|
|
364
|
-
|
376
|
+
Statement_Ptr Expand::operator()(Debug_Ptr d)
|
365
377
|
{
|
366
378
|
// eval handles this too, because warnings may occur in functions
|
367
379
|
d->perform(&eval);
|
368
380
|
return 0;
|
369
381
|
}
|
370
382
|
|
371
|
-
|
383
|
+
Statement_Ptr Expand::operator()(Comment_Ptr c)
|
372
384
|
{
|
373
385
|
eval.is_in_comment = true;
|
374
|
-
|
386
|
+
Comment_Ptr rv = SASS_MEMORY_NEW(Comment, c->pstate(), SASS_MEMORY_CAST_PTR(String, c->text()->perform(&eval)), c->is_important());
|
375
387
|
eval.is_in_comment = false;
|
376
388
|
// TODO: eval the text, once we're parsing/storing it as a String_Schema
|
377
389
|
return rv;
|
378
390
|
}
|
379
391
|
|
380
|
-
|
392
|
+
Statement_Ptr Expand::operator()(If_Ptr i)
|
381
393
|
{
|
382
394
|
Env env(environment(), true);
|
383
395
|
env_stack.push_back(&env);
|
384
396
|
call_stack.push_back(i);
|
385
|
-
|
386
|
-
|
397
|
+
Expression_Obj rv = i->predicate()->perform(&eval);
|
398
|
+
if (*rv) {
|
399
|
+
append_block(&i->block());
|
387
400
|
}
|
388
401
|
else {
|
389
|
-
|
402
|
+
Block_Ptr alt = &i->alternative();
|
390
403
|
if (alt) append_block(alt);
|
391
404
|
}
|
392
405
|
call_stack.pop_back();
|
@@ -396,19 +409,19 @@ namespace Sass {
|
|
396
409
|
|
397
410
|
// For does not create a new env scope
|
398
411
|
// But iteration vars are reset afterwards
|
399
|
-
|
412
|
+
Statement_Ptr Expand::operator()(For_Ptr f)
|
400
413
|
{
|
401
414
|
std::string variable(f->variable());
|
402
|
-
|
415
|
+
Expression_Obj low = f->lower_bound()->perform(&eval);
|
403
416
|
if (low->concrete_type() != Expression::NUMBER) {
|
404
417
|
throw Exception::TypeMismatch(*low, "integer");
|
405
418
|
}
|
406
|
-
|
419
|
+
Expression_Obj high = f->upper_bound()->perform(&eval);
|
407
420
|
if (high->concrete_type() != Expression::NUMBER) {
|
408
421
|
throw Exception::TypeMismatch(*high, "integer");
|
409
422
|
}
|
410
|
-
|
411
|
-
|
423
|
+
Number_Obj sass_start = SASS_MEMORY_CAST(Number, low);
|
424
|
+
Number_Obj sass_end = SASS_MEMORY_CAST(Number, high);
|
412
425
|
// check if units are valid for sequence
|
413
426
|
if (sass_start->unit() != sass_end->unit()) {
|
414
427
|
std::stringstream msg; msg << "Incompatible units: '"
|
@@ -422,16 +435,17 @@ namespace Sass {
|
|
422
435
|
Env env(environment(), true);
|
423
436
|
env_stack.push_back(&env);
|
424
437
|
call_stack.push_back(f);
|
425
|
-
|
426
|
-
env.set_local(variable, it);
|
427
|
-
|
438
|
+
Number_Obj it = SASS_MEMORY_NEW(Number, low->pstate(), start, sass_end->unit());
|
439
|
+
env.set_local(variable, &it);
|
440
|
+
Block_Ptr body = &f->block();
|
428
441
|
if (start < end) {
|
429
442
|
if (f->is_inclusive()) ++end;
|
430
443
|
for (double i = start;
|
431
444
|
i < end;
|
432
445
|
++i) {
|
446
|
+
it = SASS_MEMORY_COPY(it);
|
433
447
|
it->value(i);
|
434
|
-
env.set_local(variable, it);
|
448
|
+
env.set_local(variable, &it);
|
435
449
|
append_block(body);
|
436
450
|
}
|
437
451
|
} else {
|
@@ -439,8 +453,9 @@ namespace Sass {
|
|
439
453
|
for (double i = start;
|
440
454
|
i > end;
|
441
455
|
--i) {
|
456
|
+
it = SASS_MEMORY_COPY(it);
|
442
457
|
it->value(i);
|
443
|
-
env.set_local(variable, it);
|
458
|
+
env.set_local(variable, &it);
|
444
459
|
append_block(body);
|
445
460
|
}
|
446
461
|
}
|
@@ -451,78 +466,79 @@ namespace Sass {
|
|
451
466
|
|
452
467
|
// Eval does not create a new env scope
|
453
468
|
// But iteration vars are reset afterwards
|
454
|
-
|
469
|
+
Statement_Ptr Expand::operator()(Each_Ptr e)
|
455
470
|
{
|
456
471
|
std::vector<std::string> variables(e->variables());
|
457
|
-
|
458
|
-
|
459
|
-
|
472
|
+
Expression_Obj expr = e->list()->perform(&eval);
|
473
|
+
List_Obj list = 0;
|
474
|
+
Map_Obj map;
|
460
475
|
if (expr->concrete_type() == Expression::MAP) {
|
461
|
-
map =
|
476
|
+
map = SASS_MEMORY_CAST(Map, expr);
|
462
477
|
}
|
463
|
-
else if (
|
464
|
-
Listize listize
|
465
|
-
|
478
|
+
else if (Selector_List_Ptr ls = SASS_MEMORY_CAST(Selector_List, expr)) {
|
479
|
+
Listize listize;
|
480
|
+
Expression_Obj rv = ls->perform(&listize);
|
481
|
+
list = SASS_MEMORY_CAST(List, rv);
|
466
482
|
}
|
467
483
|
else if (expr->concrete_type() != Expression::LIST) {
|
468
|
-
list = SASS_MEMORY_NEW(
|
469
|
-
|
484
|
+
list = SASS_MEMORY_NEW(List, expr->pstate(), 1, SASS_COMMA);
|
485
|
+
list->append(expr);
|
470
486
|
}
|
471
487
|
else {
|
472
|
-
list =
|
488
|
+
list = SASS_MEMORY_CAST(List, expr);
|
473
489
|
}
|
474
490
|
// remember variables and then reset them
|
475
491
|
Env env(environment(), true);
|
476
492
|
env_stack.push_back(&env);
|
477
493
|
call_stack.push_back(e);
|
478
|
-
|
494
|
+
Block_Ptr body = &e->block();
|
479
495
|
|
480
496
|
if (map) {
|
481
497
|
for (auto key : map->keys()) {
|
482
|
-
|
483
|
-
|
498
|
+
Expression_Obj k = key->perform(&eval);
|
499
|
+
Expression_Obj v = map->at(key)->perform(&eval);
|
484
500
|
|
485
501
|
if (variables.size() == 1) {
|
486
|
-
|
487
|
-
|
488
|
-
|
489
|
-
env.set_local(variables[0], variable);
|
502
|
+
List_Obj variable = SASS_MEMORY_NEW(List, map->pstate(), 2, SASS_SPACE);
|
503
|
+
variable->append(k);
|
504
|
+
variable->append(v);
|
505
|
+
env.set_local(variables[0], &variable);
|
490
506
|
} else {
|
491
|
-
env.set_local(variables[0], k);
|
492
|
-
env.set_local(variables[1], v);
|
507
|
+
env.set_local(variables[0], &k);
|
508
|
+
env.set_local(variables[1], &v);
|
493
509
|
}
|
494
510
|
append_block(body);
|
495
511
|
}
|
496
512
|
}
|
497
513
|
else {
|
498
514
|
// bool arglist = list->is_arglist();
|
499
|
-
if (list->length() == 1 &&
|
500
|
-
list =
|
515
|
+
if (list->length() == 1 && SASS_MEMORY_CAST(Selector_List, list)) {
|
516
|
+
list = SASS_MEMORY_CAST(List, list);
|
501
517
|
}
|
502
518
|
for (size_t i = 0, L = list->length(); i < L; ++i) {
|
503
|
-
|
519
|
+
Expression_Obj e = list->at(i);
|
504
520
|
// unwrap value if the expression is an argument
|
505
|
-
if (
|
521
|
+
if (Argument_Obj arg = SASS_MEMORY_CAST(Argument, e)) e = arg->value();
|
506
522
|
// check if we got passed a list of args (investigate)
|
507
|
-
if (
|
523
|
+
if (List_Obj scalars = SASS_MEMORY_CAST(List, e)) {
|
508
524
|
if (variables.size() == 1) {
|
509
|
-
|
525
|
+
List_Obj var = scalars;
|
510
526
|
// if (arglist) var = (*scalars)[0];
|
511
|
-
env.set_local(variables[0], var);
|
527
|
+
env.set_local(variables[0], &var);
|
512
528
|
} else {
|
513
529
|
for (size_t j = 0, K = variables.size(); j < K; ++j) {
|
514
|
-
|
515
|
-
? SASS_MEMORY_NEW(
|
530
|
+
Expression_Obj res = j >= scalars->length()
|
531
|
+
? SASS_MEMORY_NEW(Null, expr->pstate())
|
516
532
|
: (*scalars)[j]->perform(&eval);
|
517
|
-
env.set_local(variables[j], res);
|
533
|
+
env.set_local(variables[j], &res);
|
518
534
|
}
|
519
535
|
}
|
520
536
|
} else {
|
521
537
|
if (variables.size() > 0) {
|
522
|
-
env.set_local(variables
|
538
|
+
env.set_local(variables.at(0), &e);
|
523
539
|
for (size_t j = 1, K = variables.size(); j < K; ++j) {
|
524
|
-
|
525
|
-
env.set_local(variables[j], res);
|
540
|
+
Expression_Obj res = SASS_MEMORY_NEW(Null, expr->pstate());
|
541
|
+
env.set_local(variables[j], &res);
|
526
542
|
}
|
527
543
|
}
|
528
544
|
}
|
@@ -534,36 +550,38 @@ namespace Sass {
|
|
534
550
|
return 0;
|
535
551
|
}
|
536
552
|
|
537
|
-
|
553
|
+
Statement_Ptr Expand::operator()(While_Ptr w)
|
538
554
|
{
|
539
|
-
|
540
|
-
|
555
|
+
Expression_Obj pred = w->predicate();
|
556
|
+
Block_Ptr body = &w->block();
|
541
557
|
Env env(environment(), true);
|
542
558
|
env_stack.push_back(&env);
|
543
559
|
call_stack.push_back(w);
|
544
|
-
|
560
|
+
Expression_Obj cond = pred->perform(&eval);
|
561
|
+
while (*&cond) {
|
545
562
|
append_block(body);
|
563
|
+
cond = pred->perform(&eval);
|
546
564
|
}
|
547
565
|
call_stack.pop_back();
|
548
566
|
env_stack.pop_back();
|
549
567
|
return 0;
|
550
568
|
}
|
551
569
|
|
552
|
-
|
570
|
+
Statement_Ptr Expand::operator()(Return_Ptr r)
|
553
571
|
{
|
554
572
|
error("@return may only be used within a function", r->pstate(), backtrace());
|
555
573
|
return 0;
|
556
574
|
}
|
557
575
|
|
558
576
|
|
559
|
-
void Expand::expand_selector_list(
|
577
|
+
void Expand::expand_selector_list(Selector_Obj s, Selector_List_Obj extender) {
|
560
578
|
|
561
|
-
if (
|
562
|
-
for (
|
563
|
-
|
579
|
+
if (Selector_List_Obj sl = SASS_MEMORY_CAST(Selector_List, s)) {
|
580
|
+
for (Complex_Selector_Obj complex_selector : sl->elements()) {
|
581
|
+
Complex_Selector_Obj tail = complex_selector;
|
564
582
|
while (tail) {
|
565
|
-
if (tail->head()) for (
|
566
|
-
if (
|
583
|
+
if (tail->head()) for (Simple_Selector_Obj header : tail->head()->elements()) {
|
584
|
+
if (SASS_MEMORY_CAST(Parent_Selector, header) == NULL) continue; // skip all others
|
567
585
|
std::string sel_str(complex_selector->to_string(ctx.c_options));
|
568
586
|
error("Can't extend " + sel_str + ": can't extend parent selectors", header->pstate(), backtrace());
|
569
587
|
}
|
@@ -573,78 +591,78 @@ namespace Sass {
|
|
573
591
|
}
|
574
592
|
|
575
593
|
|
576
|
-
|
577
|
-
if (contextualized ==
|
594
|
+
Selector_List_Obj contextualized = SASS_MEMORY_CAST_PTR(Selector_List, s->perform(&eval));
|
595
|
+
if (contextualized == false) return;
|
578
596
|
for (auto complex_sel : contextualized->elements()) {
|
579
|
-
|
597
|
+
Complex_Selector_Obj c = complex_sel;
|
580
598
|
if (!c->head() || c->tail()) {
|
581
599
|
std::string sel_str(contextualized->to_string(ctx.c_options));
|
582
600
|
error("Can't extend " + sel_str + ": can't extend nested selectors", c->pstate(), backtrace());
|
583
601
|
}
|
584
|
-
|
602
|
+
Compound_Selector_Obj placeholder = c->head();
|
585
603
|
if (contextualized->is_optional()) placeholder->is_optional(true);
|
586
604
|
for (size_t i = 0, L = extender->length(); i < L; ++i) {
|
587
|
-
|
605
|
+
Complex_Selector_Obj sel = (*extender)[i];
|
588
606
|
if (!(sel->head() && sel->head()->length() > 0 &&
|
589
|
-
|
607
|
+
SASS_MEMORY_CAST(Parent_Selector, (*sel->head())[0])))
|
590
608
|
{
|
591
|
-
|
609
|
+
Compound_Selector_Obj hh = SASS_MEMORY_NEW(Compound_Selector, (*extender)[i]->pstate());
|
592
610
|
hh->media_block((*extender)[i]->media_block());
|
593
|
-
|
611
|
+
Complex_Selector_Obj ssel = SASS_MEMORY_NEW(Complex_Selector, (*extender)[i]->pstate());
|
594
612
|
ssel->media_block((*extender)[i]->media_block());
|
595
613
|
if (sel->has_line_feed()) ssel->has_line_feed(true);
|
596
|
-
|
614
|
+
Parent_Selector_Obj ps = SASS_MEMORY_NEW(Parent_Selector, (*extender)[i]->pstate());
|
597
615
|
ps->media_block((*extender)[i]->media_block());
|
598
|
-
|
616
|
+
hh->append(&ps);
|
599
617
|
ssel->tail(sel);
|
600
618
|
ssel->head(hh);
|
601
619
|
sel = ssel;
|
602
620
|
}
|
603
621
|
// if (c->has_line_feed()) sel->has_line_feed(true);
|
604
|
-
ctx.subset_map.put(placeholder
|
622
|
+
ctx.subset_map.put(placeholder, std::make_pair(sel, placeholder));
|
605
623
|
}
|
606
624
|
}
|
607
625
|
|
608
626
|
}
|
609
627
|
|
610
|
-
Statement* Expand::operator()(
|
628
|
+
Statement* Expand::operator()(Extension_Ptr e)
|
611
629
|
{
|
612
|
-
if (
|
613
|
-
|
614
|
-
|
630
|
+
if (Selector_List_Obj extender = SASS_MEMORY_CAST(Selector_List, selector())) {
|
631
|
+
Selector_Obj s = e->selector();
|
632
|
+
Selector_List_Obj sl = NULL;
|
615
633
|
// check if we already have a valid selector list
|
616
|
-
if ((sl =
|
634
|
+
if ((sl = SASS_MEMORY_CAST(Selector_List, s))) {}
|
617
635
|
// convert selector schema to a selector list
|
618
|
-
else if (
|
636
|
+
else if (Selector_Schema_Obj schema = SASS_MEMORY_CAST(Selector_Schema, s)) {
|
619
637
|
if (schema->has_real_parent_ref()) {
|
620
|
-
sl = eval(schema);
|
638
|
+
sl = eval(&schema);
|
621
639
|
} else {
|
622
640
|
selector_stack.push_back(0);
|
623
|
-
sl = eval(schema);
|
641
|
+
sl = eval(&schema);
|
624
642
|
sl->remove_parent_selectors();
|
625
643
|
selector_stack.pop_back();
|
626
644
|
}
|
627
645
|
}
|
628
646
|
// abort on invalid selector
|
629
|
-
if (sl
|
630
|
-
for (
|
631
|
-
if (cs
|
647
|
+
if (sl.isNull()) return NULL;
|
648
|
+
for (Complex_Selector_Obj cs : sl->elements()) {
|
649
|
+
if (!cs.isNull() && !cs->head().isNull()) {
|
632
650
|
cs->head()->media_block(media_block_stack.back());
|
633
651
|
}
|
634
652
|
}
|
635
653
|
selector_stack.push_back(0);
|
636
|
-
expand_selector_list(sl, extender);
|
654
|
+
expand_selector_list(&sl, extender);
|
637
655
|
selector_stack.pop_back();
|
638
656
|
}
|
639
657
|
return 0;
|
640
658
|
}
|
641
659
|
|
642
|
-
|
660
|
+
Statement_Ptr Expand::operator()(Definition_Ptr d)
|
643
661
|
{
|
644
662
|
Env* env = environment();
|
645
|
-
|
663
|
+
Definition_Obj dd = SASS_MEMORY_COPY(d);
|
646
664
|
env->local_frame()[d->name() +
|
647
|
-
(d->type() == Definition::MIXIN ? "[m]" : "[f]")] = dd;
|
665
|
+
(d->type() == Definition::MIXIN ? "[m]" : "[f]")] = ⅆ
|
648
666
|
|
649
667
|
if (d->type() == Definition::FUNCTION && (
|
650
668
|
Prelexer::calc_fn_call(d->name().c_str()) ||
|
@@ -659,60 +677,60 @@ namespace Sass {
|
|
659
677
|
);
|
660
678
|
}
|
661
679
|
|
662
|
-
|
663
680
|
// set the static link so we can have lexical scoping
|
664
681
|
dd->environment(env);
|
665
682
|
return 0;
|
666
683
|
}
|
667
684
|
|
668
|
-
|
685
|
+
Statement_Ptr Expand::operator()(Mixin_Call_Ptr c)
|
669
686
|
{
|
670
|
-
recursions ++;
|
671
687
|
|
672
688
|
if (recursions > maxRecursion) {
|
673
689
|
throw Exception::StackError(*c);
|
674
690
|
}
|
675
691
|
|
692
|
+
recursions ++;
|
693
|
+
|
676
694
|
Env* env = environment();
|
677
695
|
std::string full_name(c->name() + "[m]");
|
678
696
|
if (!env->has(full_name)) {
|
679
697
|
error("no mixin named " + c->name(), c->pstate(), backtrace());
|
680
698
|
}
|
681
|
-
|
682
|
-
|
683
|
-
|
699
|
+
Definition_Obj def = SASS_MEMORY_CAST(Definition, (*env)[full_name]);
|
700
|
+
Block_Obj body = def->block();
|
701
|
+
Parameters_Obj params = def->parameters();
|
684
702
|
|
685
703
|
if (c->block() && c->name() != "@content" && !body->has_content()) {
|
686
704
|
error("Mixin \"" + c->name() + "\" does not accept a content block.", c->pstate(), backtrace());
|
687
705
|
}
|
688
|
-
|
689
|
-
|
706
|
+
Expression_Obj rv = c->arguments()->perform(&eval);
|
707
|
+
Arguments_Obj args = SASS_MEMORY_CAST(Arguments, rv);
|
690
708
|
Backtrace new_bt(backtrace(), c->pstate(), ", in mixin `" + c->name() + "`");
|
691
709
|
backtrace_stack.push_back(&new_bt);
|
692
710
|
Env new_env(def->environment());
|
693
711
|
env_stack.push_back(&new_env);
|
694
712
|
if (c->block()) {
|
695
713
|
// represent mixin content blocks as thunks/closures
|
696
|
-
|
714
|
+
Definition_Obj thunk = SASS_MEMORY_NEW(Definition,
|
697
715
|
c->pstate(),
|
698
716
|
"@content",
|
699
|
-
SASS_MEMORY_NEW(
|
717
|
+
SASS_MEMORY_NEW(Parameters, c->pstate()),
|
700
718
|
c->block(),
|
701
719
|
Definition::MIXIN);
|
702
720
|
thunk->environment(env);
|
703
|
-
new_env.local_frame()["@content[m]"] = thunk;
|
721
|
+
new_env.local_frame()["@content[m]"] = &thunk;
|
704
722
|
}
|
705
723
|
|
706
724
|
bind(std::string("Mixin"), c->name(), params, args, &ctx, &new_env, &eval);
|
707
725
|
|
708
|
-
|
709
|
-
|
726
|
+
Block_Obj trace_block = SASS_MEMORY_NEW(Block, c->pstate());
|
727
|
+
Trace_Obj trace = SASS_MEMORY_NEW(Trace, c->pstate(), c->name(), trace_block);
|
710
728
|
|
711
729
|
|
712
|
-
block_stack.push_back(trace_block);
|
713
|
-
for (auto bb :
|
714
|
-
|
715
|
-
if (ith)
|
730
|
+
block_stack.push_back(&trace_block);
|
731
|
+
for (auto bb : body->elements()) {
|
732
|
+
Statement_Obj ith = bb->perform(this);
|
733
|
+
if (ith) trace->block()->append(ith);
|
716
734
|
}
|
717
735
|
block_stack.pop_back();
|
718
736
|
|
@@ -720,10 +738,10 @@ namespace Sass {
|
|
720
738
|
backtrace_stack.pop_back();
|
721
739
|
|
722
740
|
recursions --;
|
723
|
-
return trace;
|
741
|
+
return trace.detach();
|
724
742
|
}
|
725
743
|
|
726
|
-
|
744
|
+
Statement_Ptr Expand::operator()(Content_Ptr c)
|
727
745
|
{
|
728
746
|
Env* env = environment();
|
729
747
|
// convert @content directives into mixin calls to the underlying thunk
|
@@ -733,36 +751,37 @@ namespace Sass {
|
|
733
751
|
selector_stack.push_back(0);
|
734
752
|
}
|
735
753
|
|
736
|
-
|
754
|
+
Mixin_Call_Obj call = SASS_MEMORY_NEW(Mixin_Call,
|
737
755
|
c->pstate(),
|
738
756
|
"@content",
|
739
|
-
SASS_MEMORY_NEW(
|
757
|
+
SASS_MEMORY_NEW(Arguments, c->pstate()));
|
740
758
|
|
741
|
-
|
759
|
+
Trace_Obj trace = SASS_MEMORY_CAST_PTR(Trace, call->perform(this));
|
742
760
|
|
743
761
|
if (block_stack.back()->is_root()) {
|
744
762
|
selector_stack.pop_back();
|
745
763
|
}
|
746
764
|
|
747
|
-
return trace;
|
765
|
+
return trace.detach();
|
748
766
|
}
|
749
767
|
|
750
768
|
// produce an error if something is not implemented
|
751
|
-
inline
|
769
|
+
inline Statement_Ptr Expand::fallback_impl(AST_Node_Ptr n)
|
752
770
|
{
|
753
771
|
std::string err =std:: string("`Expand` doesn't handle ") + typeid(*n).name();
|
754
|
-
|
772
|
+
String_Quoted_Obj msg = SASS_MEMORY_NEW(String_Quoted, ParserState("[WARN]"), err);
|
755
773
|
error("unknown internal error; please contact the LibSass maintainers", n->pstate(), backtrace());
|
756
|
-
return SASS_MEMORY_NEW(
|
774
|
+
return SASS_MEMORY_NEW(Warning, ParserState("[WARN]"), &msg);
|
757
775
|
}
|
758
776
|
|
759
777
|
// process and add to last block on stack
|
760
|
-
inline void Expand::append_block(
|
778
|
+
inline void Expand::append_block(Block_Ptr b)
|
761
779
|
{
|
762
780
|
if (b->is_root()) call_stack.push_back(b);
|
763
781
|
for (size_t i = 0, L = b->length(); i < L; ++i) {
|
764
|
-
|
765
|
-
|
782
|
+
Statement_Ptr stm = &b->at(i);
|
783
|
+
Statement_Obj ith = stm->perform(this);
|
784
|
+
if (ith) block_stack.back()->append(ith);
|
766
785
|
}
|
767
786
|
if (b->is_root()) call_stack.pop_back();
|
768
787
|
}
|