Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
N
node-sass
Overview
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
楚学文
node-sass
Commits
9e8b930e
Commit
9e8b930e
authored
Apr 02, 2012
by
Aaron Leung
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Finished the node refactor. Required more debugging than I expected.
parent
42a50269
Hide whitespace changes
Inline
Side-by-side
Showing
13 changed files
with
125 additions
and
193 deletions
+125
-193
Makefile
Makefile
+1
-1
context.hpp
context.hpp
+1
-2
document.cpp
document.cpp
+10
-10
document.hpp
document.hpp
+2
-2
document_parser.cpp
document_parser.cpp
+6
-6
eval_apply.cpp
eval_apply.cpp
+55
-55
node.cpp
node.cpp
+15
-22
node.hpp
node.hpp
+4
-84
sassc.cpp
sassc.cpp
+3
-2
input.scss
spec/basic/15_arithmetic_and_lists/input.scss
+2
-2
output.css
spec/basic/15_arithmetic_and_lists/output.css
+2
-2
values.cpp
values.cpp
+4
-4
values.hpp
values.hpp
+20
-1
No files found.
Makefile
View file @
9e8b930e
build
:
sassc.cpp document.cpp node.cpp
token
.cpp prelexer.cpp
build
:
sassc.cpp document.cpp node.cpp
values
.cpp prelexer.cpp
g++
-o
bin/sassc sassc.cpp document.cpp document_parser.cpp eval_apply.cpp node.cpp values.cpp prelexer.cpp
g++
-o
bin/sassc sassc.cpp document.cpp document_parser.cpp eval_apply.cpp node.cpp values.cpp prelexer.cpp
test
:
build
test
:
build
...
...
context.hpp
View file @
9e8b930e
...
@@ -39,8 +39,7 @@ namespace Sass {
...
@@ -39,8 +39,7 @@ namespace Sass {
size_t
ref_count
;
size_t
ref_count
;
Context
()
Context
()
:
pending
(
vector
<
Node
>
()),
:
source_refs
(
vector
<
char
*>
()),
source_refs
(
vector
<
char
*>
()),
ref_count
(
0
)
ref_count
(
0
)
{
}
{
}
...
...
document.cpp
View file @
9e8b930e
...
@@ -9,8 +9,8 @@ namespace Sass {
...
@@ -9,8 +9,8 @@ namespace Sass {
:
path
(
path
),
source
(
source
),
:
path
(
path
),
source
(
source
),
line_number
(
1
),
own_source
(
false
),
line_number
(
1
),
own_source
(
false
),
context
(
*
(
new
Context
())),
context
(
*
(
new
Context
())),
root
(
Node
(
1
,
Node
::
root
)),
root
(
Node
(
Node
::
root
,
1
)),
lexed
(
Token
())
lexed
(
Token
::
make
())
{
{
if
(
!
source
)
{
if
(
!
source
)
{
std
::
FILE
*
f
;
std
::
FILE
*
f
;
...
@@ -35,8 +35,8 @@ namespace Sass {
...
@@ -35,8 +35,8 @@ namespace Sass {
:
path
(
path
),
source
(
0
),
:
path
(
path
),
source
(
0
),
line_number
(
1
),
own_source
(
false
),
line_number
(
1
),
own_source
(
false
),
context
(
context
),
context
(
context
),
root
(
Node
(
1
,
Node
::
root
)),
root
(
Node
(
Node
::
root
,
1
)),
lexed
(
Token
())
lexed
(
Token
::
make
())
{
{
std
::
FILE
*
f
;
std
::
FILE
*
f
;
// TO DO: CHECK f AGAINST NULL/0
// TO DO: CHECK f AGAINST NULL/0
...
@@ -59,12 +59,12 @@ namespace Sass {
...
@@ -59,12 +59,12 @@ namespace Sass {
if
(
context
.
ref_count
==
0
)
delete
&
context
;
if
(
context
.
ref_count
==
0
)
delete
&
context
;
}
}
void
Document
::
eval_pending
()
//
void Document::eval_pending()
{
//
{
for
(
int
i
=
0
;
i
<
context
.
pending
.
size
();
++
i
)
{
//
for (int i = 0; i < context.pending.size(); ++i) {
eval
(
context
.
pending
[
i
],
context
.
global_env
);
//
eval(context.pending[i], context.global_env);
}
//
}
}
//
}
using
std
::
string
;
using
std
::
string
;
using
std
::
stringstream
;
using
std
::
stringstream
;
...
...
document.hpp
View file @
9e8b930e
...
@@ -85,7 +85,7 @@ namespace Sass {
...
@@ -85,7 +85,7 @@ namespace Sass {
after_whitespace
=
spaces
(
position
);
after_whitespace
=
spaces
(
position
);
if
(
after_whitespace
)
{
if
(
after_whitespace
)
{
line_number
+=
count_interval
<
'\n'
>
(
position
,
after_whitespace
);
line_number
+=
count_interval
<
'\n'
>
(
position
,
after_whitespace
);
lexed
=
Token
(
position
,
after_whitespace
);
lexed
=
Token
::
make
(
position
,
after_whitespace
);
return
position
=
after_whitespace
;
return
position
=
after_whitespace
;
}
}
else
{
else
{
...
@@ -101,7 +101,7 @@ namespace Sass {
...
@@ -101,7 +101,7 @@ namespace Sass {
const
char
*
after_token
=
mx
(
after_whitespace
);
const
char
*
after_token
=
mx
(
after_whitespace
);
if
(
after_token
)
{
if
(
after_token
)
{
line_number
+=
count_interval
<
'\n'
>
(
position
,
after_token
);
line_number
+=
count_interval
<
'\n'
>
(
position
,
after_token
);
lexed
=
Token
(
after_whitespace
,
after_token
);
lexed
=
Token
::
make
(
after_whitespace
,
after_token
);
return
position
=
after_token
;
return
position
=
after_token
;
}
}
else
{
else
{
...
...
document_parser.cpp
View file @
9e8b930e
...
@@ -26,8 +26,8 @@ namespace Sass {
...
@@ -26,8 +26,8 @@ namespace Sass {
lex
<
exactly
<
';'
>
>
();
lex
<
exactly
<
';'
>
>
();
}
}
else
if
(
peek
<
variable
>
(
position
))
{
else
if
(
peek
<
variable
>
(
position
))
{
lex
<
exactly
<
';'
>
>
();
root
<<
parse_assignment
();
root
<<
parse_assignment
();
lex
<
exactly
<
';'
>
>
();
}
}
else
{
else
{
root
<<
parse_ruleset
();
root
<<
parse_ruleset
();
...
@@ -152,7 +152,7 @@ namespace Sass {
...
@@ -152,7 +152,7 @@ namespace Sass {
Node
Document
::
parse_selector_group
()
Node
Document
::
parse_selector_group
()
{
{
Node
group
(
line_number
,
Node
::
selector_group
,
1
);
Node
group
(
Node
::
selector_group
,
line_number
,
1
);
group
<<
parse_selector
();
group
<<
parse_selector
();
while
(
lex
<
exactly
<
','
>
>
())
group
<<
parse_selector
();
while
(
lex
<
exactly
<
','
>
>
())
group
<<
parse_selector
();
return
group
;
return
group
;
...
@@ -266,7 +266,7 @@ namespace Sass {
...
@@ -266,7 +266,7 @@ namespace Sass {
Node
Document
::
parse_attribute_selector
()
Node
Document
::
parse_attribute_selector
()
{
{
Node
attr_sel
(
line_number
,
Node
::
attribute_selecto
r
,
3
);
Node
attr_sel
(
Node
::
attribute_selector
,
line_numbe
r
,
3
);
lex
<
exactly
<
'['
>
>
();
lex
<
exactly
<
'['
>
>
();
lex
<
type_selector
>
();
lex
<
type_selector
>
();
attr_sel
<<
Node
(
Node
::
value
,
line_number
,
lexed
);
attr_sel
<<
Node
(
Node
::
value
,
line_number
,
lexed
);
...
@@ -316,8 +316,8 @@ namespace Sass {
...
@@ -316,8 +316,8 @@ namespace Sass {
block
[
0
].
has_expansions
=
true
;
block
[
0
].
has_expansions
=
true
;
}
}
else
if
(
lex
<
variable
>
())
{
else
if
(
lex
<
variable
>
())
{
semicolon
=
true
;
block
<<
parse_assignment
();
block
<<
parse_assignment
();
semicolon
=
true
;
}
}
// else if (look_for_rule(position)) {
// else if (look_for_rule(position)) {
// block << parse_rule();
// block << parse_rule();
...
@@ -498,7 +498,7 @@ namespace Sass {
...
@@ -498,7 +498,7 @@ namespace Sass {
if
(
lex
<
rgb_prefix
>
())
if
(
lex
<
rgb_prefix
>
())
{
{
Node
result
(
Node
::
color
,
line_number
,
3
);
Node
result
(
Node
::
numeric_
color
,
line_number
,
3
);
lex
<
number
>
();
lex
<
number
>
();
result
<<
Node
(
line_number
,
std
::
atof
(
lexed
.
begin
));
result
<<
Node
(
line_number
,
std
::
atof
(
lexed
.
begin
));
lex
<
exactly
<
','
>
>
();
lex
<
exactly
<
','
>
>
();
...
@@ -644,7 +644,7 @@ namespace Sass {
...
@@ -644,7 +644,7 @@ namespace Sass {
(
q
=
peek
<
id_name
>
(
p
))
||
(
q
=
peek
<
class_name
>
(
p
))
||
(
q
=
peek
<
id_name
>
(
p
))
||
(
q
=
peek
<
class_name
>
(
p
))
||
(
q
=
look_for_pseudo
(
p
))
||
(
q
=
look_for_attrib
(
p
));
(
q
=
look_for_pseudo
(
p
))
||
(
q
=
look_for_attrib
(
p
));
// cerr << "looking for simple selector; found:" << endl;
// cerr << "looking for simple selector; found:" << endl;
// cerr << (q ? string(Token(q,q+8)) : "nothing") << endl;
// cerr << (q ? string(Token
::make
(q,q+8)) : "nothing") << endl;
return
q
;
return
q
;
}
}
...
...
eval_apply.cpp
View file @
9e8b930e
...
@@ -10,19 +10,18 @@ namespace Sass {
...
@@ -10,19 +10,18 @@ namespace Sass {
switch
(
expr
.
type
)
switch
(
expr
.
type
)
{
{
case
Node
:
:
mixin
:
{
case
Node
:
:
mixin
:
{
env
[
expr
[
0
].
token
]
=
expr
;
env
[
expr
[
0
].
content
.
token
]
=
expr
;
// cerr << "DEFINED MIXIN: " << string(expr[0].token) << endl << endl;
return
expr
;
return
expr
;
}
break
;
}
break
;
case
Node
:
:
expansion
:
{
case
Node
:
:
expansion
:
{
Token
name
(
expr
[
0
].
token
);
Token
name
(
expr
[
0
].
content
.
token
);
// cerr << "EVALUATING EXPANSION: " << string(name) << endl;
// cerr << "EVALUATING EXPANSION: " << string(name) << endl;
Node
args
(
expr
[
1
]);
Node
args
(
expr
[
1
]);
Node
mixin
(
env
[
name
]);
Node
mixin
(
env
[
name
]);
Node
expansion
(
apply
(
mixin
,
args
,
env
));
Node
expansion
(
apply
(
mixin
,
args
,
env
));
expr
.
children
->
pop_back
();
expr
.
c
ontent
.
c
hildren
->
pop_back
();
expr
.
children
->
pop_back
();
expr
.
c
ontent
.
c
hildren
->
pop_back
();
expr
+=
expansion
;
expr
+=
expansion
;
// expr[0].has_rules_or_comments |= expansion[0].has_rules_or_comments;
// expr[0].has_rules_or_comments |= expansion[0].has_rules_or_comments;
// expr[0].has_rulesets |= expansion[0].has_rulesets;
// expr[0].has_rulesets |= expansion[0].has_rulesets;
...
@@ -63,11 +62,11 @@ namespace Sass {
...
@@ -63,11 +62,11 @@ namespace Sass {
val
=
eval
(
val
,
env
);
val
=
eval
(
val
,
env
);
}
}
Node
var
(
expr
[
0
]);
Node
var
(
expr
[
0
]);
if
(
env
.
query
(
var
.
token
))
{
if
(
env
.
query
(
var
.
content
.
token
))
{
env
[
var
.
token
]
=
val
;
env
[
var
.
content
.
token
]
=
val
;
}
}
else
{
else
{
env
.
current_frame
[
var
.
token
]
=
val
;
env
.
current_frame
[
var
.
content
.
token
]
=
val
;
}
}
return
expr
;
return
expr
;
}
break
;
}
break
;
...
@@ -95,7 +94,8 @@ namespace Sass {
...
@@ -95,7 +94,8 @@ namespace Sass {
}
break
;
}
break
;
case
Node
:
:
expression
:
{
case
Node
:
:
expression
:
{
Node
acc
(
expr
.
line_number
,
Node
::
expression
,
eval
(
expr
[
0
],
env
));
Node
acc
(
Node
::
expression
,
expr
.
line_number
,
1
);
acc
<<
eval
(
expr
[
0
],
env
);
Node
rhs
(
eval
(
expr
[
2
],
env
));
Node
rhs
(
eval
(
expr
[
2
],
env
));
accumulate
(
expr
[
1
].
type
,
acc
,
rhs
);
accumulate
(
expr
[
1
].
type
,
acc
,
rhs
);
for
(
int
i
=
3
;
i
<
expr
.
size
();
i
+=
2
)
{
for
(
int
i
=
3
;
i
<
expr
.
size
();
i
+=
2
)
{
...
@@ -107,7 +107,8 @@ namespace Sass {
...
@@ -107,7 +107,8 @@ namespace Sass {
case
Node
:
:
term
:
{
case
Node
:
:
term
:
{
if
(
expr
.
eval_me
)
{
if
(
expr
.
eval_me
)
{
Node
acc
(
expr
.
line_number
,
Node
::
expression
,
eval
(
expr
[
0
],
env
));
Node
acc
(
Node
::
expression
,
expr
.
line_number
,
1
);
acc
<<
eval
(
expr
[
0
],
env
);
Node
rhs
(
eval
(
expr
[
2
],
env
));
Node
rhs
(
eval
(
expr
[
2
],
env
));
accumulate
(
expr
[
1
].
type
,
acc
,
rhs
);
accumulate
(
expr
[
1
].
type
,
acc
,
rhs
);
for
(
int
i
=
3
;
i
<
expr
.
size
();
i
+=
2
)
{
for
(
int
i
=
3
;
i
<
expr
.
size
();
i
+=
2
)
{
...
@@ -123,22 +124,22 @@ namespace Sass {
...
@@ -123,22 +124,22 @@ namespace Sass {
case
Node
:
:
textual_percentage
:
case
Node
:
:
textual_percentage
:
case
Node
:
:
textual_dimension
:
{
case
Node
:
:
textual_dimension
:
{
double
numval
=
std
::
atof
(
expr
.
token
.
begin
);
return
Node
(
expr
.
line_number
,
Token
unit
(
Prelexer
::
number
(
expr
.
token
.
begin
),
expr
.
token
.
end
);
std
::
atof
(
expr
.
content
.
token
.
begin
),
return
Node
(
expr
.
line_number
,
numval
,
unit
);
Token
::
make
(
Prelexer
::
number
(
expr
.
content
.
token
.
begin
),
expr
.
content
.
token
.
end
));
}
break
;
}
break
;
case
Node
:
:
textual_number
:
{
case
Node
:
:
textual_number
:
{
double
numval
=
std
::
atof
(
expr
.
token
.
begin
);
return
Node
(
expr
.
line_number
,
std
::
atof
(
expr
.
content
.
token
.
begin
));
return
Node
(
expr
.
line_number
,
numval
);
}
break
;
}
break
;
case
Node
:
:
textual_hex
:
{
case
Node
:
:
textual_hex
:
{
Node
triple
(
expr
.
line_number
,
Node
::
hex_triple
,
3
);
Node
triple
(
Node
::
numeric_color
,
expr
.
line_number
,
3
);
Token
hext
(
expr
.
token
.
begin
+
1
,
expr
.
token
.
end
);
Token
hext
(
Token
::
make
(
expr
.
content
.
token
.
begin
+
1
,
expr
.
content
.
token
.
end
)
);
if
(
hext
.
length
()
==
6
)
{
if
(
hext
.
length
()
==
6
)
{
for
(
int
i
=
0
;
i
<
6
;
i
+=
2
)
{
for
(
int
i
=
0
;
i
<
6
;
i
+=
2
)
{
Node
thing
(
expr
.
line_number
,
static_cast
<
double
>
(
std
::
strtol
(
string
(
hext
.
begin
+
i
,
2
).
c_str
(),
NULL
,
16
)));
//
Node thing(expr.line_number, static_cast<double>(std::strtol(string(hext.begin+i, 2).c_str(), NULL, 16)));
triple
<<
Node
(
expr
.
line_number
,
static_cast
<
double
>
(
std
::
strtol
(
string
(
hext
.
begin
+
i
,
2
).
c_str
(),
NULL
,
16
)));
triple
<<
Node
(
expr
.
line_number
,
static_cast
<
double
>
(
std
::
strtol
(
string
(
hext
.
begin
+
i
,
2
).
c_str
(),
NULL
,
16
)));
}
}
}
}
...
@@ -151,7 +152,7 @@ namespace Sass {
...
@@ -151,7 +152,7 @@ namespace Sass {
}
break
;
}
break
;
case
Node
:
:
variable
:
{
case
Node
:
:
variable
:
{
return
env
[
expr
.
token
];
return
env
[
expr
.
content
.
token
];
}
break
;
}
break
;
default:
{
default:
{
...
@@ -162,26 +163,26 @@ namespace Sass {
...
@@ -162,26 +163,26 @@ namespace Sass {
Node
accumulate
(
Node
::
Type
op
,
Node
&
acc
,
Node
&
rhs
)
Node
accumulate
(
Node
::
Type
op
,
Node
&
acc
,
Node
&
rhs
)
{
{
Node
lhs
(
acc
.
children
->
back
());
Node
lhs
(
acc
.
c
ontent
.
c
hildren
->
back
());
double
lnum
=
lhs
.
numeric_value
;
double
lnum
=
lhs
.
content
.
numeric_value
;
double
rnum
=
rhs
.
numeric_value
;
double
rnum
=
rhs
.
content
.
numeric_value
;
if
(
lhs
.
type
==
Node
::
number
&&
rhs
.
type
==
Node
::
number
)
{
if
(
lhs
.
type
==
Node
::
number
&&
rhs
.
type
==
Node
::
number
)
{
Node
result
(
acc
.
line_number
,
operate
(
op
,
lnum
,
rnum
));
Node
result
(
acc
.
line_number
,
operate
(
op
,
lnum
,
rnum
));
acc
.
children
->
pop_back
();
acc
.
c
ontent
.
c
hildren
->
pop_back
();
acc
.
children
->
push_back
(
result
);
acc
.
c
ontent
.
c
hildren
->
push_back
(
result
);
}
}
// TO DO: find a way to merge the following two clauses
// TO DO: find a way to merge the following two clauses
else
if
(
lhs
.
type
==
Node
::
number
&&
rhs
.
type
==
Node
::
numeric_dimension
)
{
else
if
(
lhs
.
type
==
Node
::
number
&&
rhs
.
type
==
Node
::
numeric_dimension
)
{
// TO DO: disallow division
// TO DO: disallow division
Node
result
(
acc
.
line_number
,
operate
(
op
,
lnum
,
rnum
),
rhs
.
token
);
Node
result
(
acc
.
line_number
,
operate
(
op
,
lnum
,
rnum
),
Token
::
make
(
rhs
.
content
.
dimension
.
unit
,
Prelexer
::
identifier
(
rhs
.
content
.
dimension
.
unit
))
);
acc
.
children
->
pop_back
();
acc
.
c
ontent
.
c
hildren
->
pop_back
();
acc
.
children
->
push_back
(
result
);
acc
.
c
ontent
.
c
hildren
->
push_back
(
result
);
}
}
else
if
(
lhs
.
type
==
Node
::
numeric_dimension
&&
rhs
.
type
==
Node
::
number
)
{
else
if
(
lhs
.
type
==
Node
::
numeric_dimension
&&
rhs
.
type
==
Node
::
number
)
{
Node
result
(
acc
.
line_number
,
operate
(
op
,
lnum
,
rnum
),
lhs
.
token
);
Node
result
(
acc
.
line_number
,
operate
(
op
,
lnum
,
rnum
),
Token
::
make
(
lhs
.
content
.
dimension
.
unit
,
Prelexer
::
identifier
(
rhs
.
content
.
dimension
.
unit
))
);
acc
.
children
->
pop_back
();
acc
.
c
ontent
.
c
hildren
->
pop_back
();
acc
.
children
->
push_back
(
result
);
acc
.
c
ontent
.
c
hildren
->
push_back
(
result
);
}
}
else
if
(
lhs
.
type
==
Node
::
numeric_dimension
&&
rhs
.
type
==
Node
::
numeric_dimension
)
{
else
if
(
lhs
.
type
==
Node
::
numeric_dimension
&&
rhs
.
type
==
Node
::
numeric_dimension
)
{
// TO DO: CHECK FOR MISMATCHED UNITS HERE
// TO DO: CHECK FOR MISMATCHED UNITS HERE
...
@@ -189,49 +190,49 @@ namespace Sass {
...
@@ -189,49 +190,49 @@ namespace Sass {
if
(
op
==
Node
::
div
)
if
(
op
==
Node
::
div
)
{
result
=
Node
(
acc
.
line_number
,
operate
(
op
,
lnum
,
rnum
));
}
{
result
=
Node
(
acc
.
line_number
,
operate
(
op
,
lnum
,
rnum
));
}
else
else
{
result
=
Node
(
acc
.
line_number
,
operate
(
op
,
lnum
,
rnum
),
lhs
.
token
);
}
{
result
=
Node
(
acc
.
line_number
,
operate
(
op
,
lnum
,
rnum
),
Token
::
make
(
lhs
.
content
.
dimension
.
unit
,
Prelexer
::
identifier
(
rhs
.
content
.
dimension
.
unit
))
);
}
acc
.
children
->
pop_back
();
acc
.
c
ontent
.
c
hildren
->
pop_back
();
acc
.
children
->
push_back
(
result
);
acc
.
c
ontent
.
c
hildren
->
push_back
(
result
);
}
}
// TO DO: find a way to merge the following two clauses
// TO DO: find a way to merge the following two clauses
else
if
(
lhs
.
type
==
Node
::
number
&&
rhs
.
type
==
Node
::
hex_triple
)
{
else
if
(
lhs
.
type
==
Node
::
number
&&
rhs
.
type
==
Node
::
numeric_color
)
{
if
(
op
!=
Node
::
sub
&&
op
!=
Node
::
div
)
{
if
(
op
!=
Node
::
sub
&&
op
!=
Node
::
div
)
{
double
h1
=
operate
(
op
,
lhs
.
numeric_value
,
rhs
[
0
]
.
numeric_value
);
double
h1
=
operate
(
op
,
lhs
.
content
.
numeric_value
,
rhs
[
0
].
content
.
numeric_value
);
double
h2
=
operate
(
op
,
lhs
.
numeric_value
,
rhs
[
1
]
.
numeric_value
);
double
h2
=
operate
(
op
,
lhs
.
content
.
numeric_value
,
rhs
[
1
].
content
.
numeric_value
);
double
h3
=
operate
(
op
,
lhs
.
numeric_value
,
rhs
[
2
]
.
numeric_value
);
double
h3
=
operate
(
op
,
lhs
.
content
.
numeric_value
,
rhs
[
2
].
content
.
numeric_value
);
acc
.
children
->
pop_back
();
acc
.
c
ontent
.
c
hildren
->
pop_back
();
acc
<<
Node
(
acc
.
line_number
,
h1
,
h2
,
h3
);
acc
<<
Node
(
acc
.
line_number
,
h1
,
h2
,
h3
);
}
}
// trying to handle weird edge cases ... not sure if it's worth it
// trying to handle weird edge cases ... not sure if it's worth it
else
if
(
op
==
Node
::
div
)
{
else
if
(
op
==
Node
::
div
)
{
acc
<<
Node
(
acc
.
line_number
,
Node
::
div
);
acc
<<
Node
(
Node
::
div
);
acc
<<
rhs
;
acc
<<
rhs
;
}
}
else
if
(
op
==
Node
::
sub
)
{
else
if
(
op
==
Node
::
sub
)
{
acc
<<
Node
(
acc
.
line_number
,
Node
::
sub
);
acc
<<
Node
(
Node
::
sub
);
acc
<<
rhs
;
acc
<<
rhs
;
}
}
else
{
else
{
acc
<<
rhs
;
acc
<<
rhs
;
}
}
}
}
else
if
(
lhs
.
type
==
Node
::
hex_triple
&&
rhs
.
type
==
Node
::
number
)
{
else
if
(
lhs
.
type
==
Node
::
numeric_color
&&
rhs
.
type
==
Node
::
number
)
{
double
h1
=
operate
(
op
,
lhs
[
0
].
numeric_value
,
rhs
.
numeric_value
);
double
h1
=
operate
(
op
,
lhs
[
0
].
content
.
numeric_value
,
rhs
.
content
.
numeric_value
);
double
h2
=
operate
(
op
,
lhs
[
1
].
numeric_value
,
rhs
.
numeric_value
);
double
h2
=
operate
(
op
,
lhs
[
1
].
content
.
numeric_value
,
rhs
.
content
.
numeric_value
);
double
h3
=
operate
(
op
,
lhs
[
2
].
numeric_value
,
rhs
.
numeric_value
);
double
h3
=
operate
(
op
,
lhs
[
2
].
content
.
numeric_value
,
rhs
.
content
.
numeric_value
);
acc
.
children
->
pop_back
();
acc
.
c
ontent
.
c
hildren
->
pop_back
();
acc
<<
Node
(
acc
.
line_number
,
h1
,
h2
,
h3
);
acc
<<
Node
(
acc
.
line_number
,
h1
,
h2
,
h3
);
}
}
else
if
(
lhs
.
type
==
Node
::
hex_triple
&&
rhs
.
type
==
Node
::
hex_triple
)
{
else
if
(
lhs
.
type
==
Node
::
numeric_color
&&
rhs
.
type
==
Node
::
numeric_color
)
{
double
h1
=
operate
(
op
,
lhs
[
0
].
numeric_value
,
rhs
[
0
]
.
numeric_value
);
double
h1
=
operate
(
op
,
lhs
[
0
].
content
.
numeric_value
,
rhs
[
0
].
content
.
numeric_value
);
double
h2
=
operate
(
op
,
lhs
[
1
].
numeric_value
,
rhs
[
1
]
.
numeric_value
);
double
h2
=
operate
(
op
,
lhs
[
1
].
content
.
numeric_value
,
rhs
[
1
].
content
.
numeric_value
);
double
h3
=
operate
(
op
,
lhs
[
2
].
numeric_value
,
rhs
[
2
]
.
numeric_value
);
double
h3
=
operate
(
op
,
lhs
[
2
].
content
.
numeric_value
,
rhs
[
2
].
content
.
numeric_value
);
acc
.
children
->
pop_back
();
acc
.
c
ontent
.
c
hildren
->
pop_back
();
acc
<<
Node
(
acc
.
line_number
,
h1
,
h2
,
h3
);
acc
<<
Node
(
acc
.
line_number
,
h1
,
h2
,
h3
);
}
}
else
{
else
{
// TO DO: disallow division and multiplication on lists
// TO DO: disallow division and multiplication on lists
acc
.
children
->
push_back
(
rhs
);
acc
.
c
ontent
.
c
hildren
->
push_back
(
rhs
);
}
}
return
acc
;
return
acc
;
...
@@ -256,12 +257,11 @@ namespace Sass {
...
@@ -256,12 +257,11 @@ namespace Sass {
Node
params
(
mixin
[
1
]);
Node
params
(
mixin
[
1
]);
Node
body
(
mixin
[
2
].
clone
());
Node
body
(
mixin
[
2
].
clone
());
Environment
m_env
;
Environment
m_env
;
// cerr << "CLONED BODY" << endl;
// bind arguments
// bind arguments
for
(
int
i
=
0
,
j
=
0
;
i
<
args
.
size
();
++
i
)
{
for
(
int
i
=
0
,
j
=
0
;
i
<
args
.
size
();
++
i
)
{
if
(
args
[
i
].
type
==
Node
::
assignment
)
{
if
(
args
[
i
].
type
==
Node
::
assignment
)
{
Node
arg
(
args
[
i
]);
Node
arg
(
args
[
i
]);
Token
name
(
arg
[
0
].
token
);
Token
name
(
arg
[
0
].
content
.
token
);
if
(
!
m_env
.
query
(
name
))
{
if
(
!
m_env
.
query
(
name
))
{
m_env
[
name
]
=
eval
(
arg
[
1
],
env
);
m_env
[
name
]
=
eval
(
arg
[
1
],
env
);
}
}
...
@@ -269,7 +269,7 @@ namespace Sass {
...
@@ -269,7 +269,7 @@ namespace Sass {
else
{
else
{
// TO DO: ensure (j < params.size())
// TO DO: ensure (j < params.size())
Node
param
(
params
[
j
]);
Node
param
(
params
[
j
]);
Token
name
(
param
.
type
==
Node
::
variable
?
param
.
token
:
param
[
0
]
.
token
);
Token
name
(
param
.
type
==
Node
::
variable
?
param
.
content
.
token
:
param
[
0
].
content
.
token
);
m_env
[
name
]
=
eval
(
args
[
i
],
env
);
m_env
[
name
]
=
eval
(
args
[
i
],
env
);
++
j
;
++
j
;
}
}
...
@@ -279,7 +279,7 @@ namespace Sass {
...
@@ -279,7 +279,7 @@ namespace Sass {
for
(
int
i
=
0
;
i
<
params
.
size
();
++
i
)
{
for
(
int
i
=
0
;
i
<
params
.
size
();
++
i
)
{
if
(
params
[
i
].
type
==
Node
::
assignment
)
{
if
(
params
[
i
].
type
==
Node
::
assignment
)
{
Node
param
(
params
[
i
]);
Node
param
(
params
[
i
]);
Token
name
(
param
[
0
].
token
);
Token
name
(
param
[
0
].
content
.
token
);
if
(
!
m_env
.
query
(
name
))
{
if
(
!
m_env
.
query
(
name
))
{
m_env
[
name
]
=
eval
(
param
[
1
],
env
);
m_env
[
name
]
=
eval
(
param
[
1
],
env
);
}
}
...
...
node.cpp
View file @
9e8b930e
...
@@ -40,7 +40,7 @@ namespace Sass {
...
@@ -40,7 +40,7 @@ namespace Sass {
}
}
return
result
;
return
result
;
}
break
;
}
break
;
case
selector
:
{
case
selector
:
{
string
result
;
string
result
;
if
(
!
has_backref
&&
!
prefix
.
empty
())
{
if
(
!
has_backref
&&
!
prefix
.
empty
())
{
...
@@ -48,7 +48,7 @@ namespace Sass {
...
@@ -48,7 +48,7 @@ namespace Sass {
result
+=
' '
;
result
+=
' '
;
}
}
if
(
at
(
0
).
type
==
selector_combinator
)
{
if
(
at
(
0
).
type
==
selector_combinator
)
{
result
+=
string
(
at
(
0
).
content
.
token
);
result
+=
at
(
0
).
content
.
token
.
to_string
(
);
result
+=
' '
;
result
+=
' '
;
}
}
else
{
else
{
...
@@ -59,12 +59,12 @@ namespace Sass {
...
@@ -59,12 +59,12 @@ namespace Sass {
}
}
return
result
;
return
result
;
}
break
;
}
break
;
case
selector_combinator
:
{
case
selector_combinator
:
{
if
(
std
::
isspace
(
content
.
token
.
begin
[
0
]))
return
string
(
" "
);
if
(
std
::
isspace
(
content
.
token
.
begin
[
0
]))
return
string
(
" "
);
else
return
string
(
" "
)
+=
string
(
content
.
token
)
+=
string
(
" "
);
else
return
string
(
" "
)
+=
string
(
content
.
token
)
+=
string
(
" "
);
}
break
;
}
break
;
case
simple_selector_sequence
:
{
case
simple_selector_sequence
:
{
string
result
;
string
result
;
for
(
int
i
=
0
;
i
<
size
();
++
i
)
{
for
(
int
i
=
0
;
i
<
size
();
++
i
)
{
...
@@ -72,14 +72,14 @@ namespace Sass {
...
@@ -72,14 +72,14 @@ namespace Sass {
}
}
return
result
;
return
result
;
}
break
;
}
break
;
case
pseudo_negation
:
{
case
pseudo_negation
:
{
string
result
(
at
(
0
).
to_string
(
prefix
));
string
result
(
at
(
0
).
to_string
(
prefix
));
result
+=
at
(
1
).
to_string
(
prefix
);
result
+=
at
(
1
).
to_string
(
prefix
);
result
+=
')'
;
result
+=
')'
;
return
result
;
return
result
;
}
break
;
}
break
;
case
functional_pseudo
:
{
case
functional_pseudo
:
{
string
result
(
at
(
0
).
to_string
(
prefix
));
string
result
(
at
(
0
).
to_string
(
prefix
));
for
(
int
i
=
1
;
i
<
size
();
++
i
)
{
for
(
int
i
=
1
;
i
<
size
();
++
i
)
{
...
@@ -88,7 +88,7 @@ namespace Sass {
...
@@ -88,7 +88,7 @@ namespace Sass {
result
+=
')'
;
result
+=
')'
;
return
result
;
return
result
;
}
break
;
}
break
;
case
attribute_selector
:
{
case
attribute_selector
:
{
string
result
(
"["
);
string
result
(
"["
);
for
(
int
i
=
0
;
i
<
3
;
++
i
)
for
(
int
i
=
0
;
i
<
3
;
++
i
)
...
@@ -96,7 +96,7 @@ namespace Sass {
...
@@ -96,7 +96,7 @@ namespace Sass {
result
+=
']'
;
result
+=
']'
;
return
result
;
return
result
;
}
break
;
}
break
;
case
backref
:
{
case
backref
:
{
return
prefix
;
return
prefix
;
}
break
;
}
break
;
...
@@ -122,10 +122,6 @@ namespace Sass {
...
@@ -122,10 +122,6 @@ namespace Sass {
case
expression
:
case
expression
:
case
term
:
{
case
term
:
{
string
result
(
at
(
0
).
to_string
(
prefix
));
string
result
(
at
(
0
).
to_string
(
prefix
));
// for (int i = 2; i < size(); i += 2) {
// // result += " ";
// result += at(i).to_string(prefix);
// }
for
(
int
i
=
1
;
i
<
size
();
++
i
)
{
for
(
int
i
=
1
;
i
<
size
();
++
i
)
{
if
(
!
(
at
(
i
).
type
==
add
||
if
(
!
(
at
(
i
).
type
==
add
||
// at(i).type == sub || // another edge case -- consider uncommenting
// at(i).type == sub || // another edge case -- consider uncommenting
...
@@ -147,21 +143,16 @@ namespace Sass {
...
@@ -147,21 +143,16 @@ namespace Sass {
case
numeric_dimension
:
{
case
numeric_dimension
:
{
stringstream
ss
;
stringstream
ss
;
// ss.setf(std::ios::fixed, std::ios::floatfield);
// ss.precision(3);
ss
<<
content
.
dimension
.
numeric_value
;
ss
<<
content
.
dimension
.
numeric_value
;
Token
unit
;
ss
<<
string
(
content
.
dimension
.
unit
,
2
);
unit
.
begin
=
content
.
dimension
.
unit
;
// << string(content.dimension.unit, Prelexer::identifier(content.dimension.unit) - content.dimension.unit);
unit
.
end
=
Prelexer
::
identifier
(
content
.
dimension
.
unit
);
// cerr << Token::make(content.dimension.unit, content.dimension.unit + 2).to_string();
ss
<<
string
(
unit
);
// << Token::make(content.dimension.unit, Prelexer::identifier(content.dimension.unit)).to_string();
// << string(Token(content.dimension.unit, Prelexer::identifier(content.dimension.unit)));
return
ss
.
str
();
return
ss
.
str
();
}
break
;
}
break
;
case
number
:
{
case
number
:
{
stringstream
ss
;
stringstream
ss
;
// ss.setf(std::ios::fixed, std::ios::floatfield);
// ss.precision(3);
ss
<<
content
.
numeric_value
;
ss
<<
content
.
numeric_value
;
return
ss
.
str
();
return
ss
.
str
();
}
break
;
}
break
;
...
@@ -213,7 +204,9 @@ namespace Sass {
...
@@ -213,7 +204,9 @@ namespace Sass {
// } break;
// } break;
default
:
{
default
:
{
return
string
(
content
.
token
);
// return content.token.to_string();
if
(
!
has_children
&&
type
!=
flags
)
return
content
.
token
.
to_string
();
else
return
""
;
}
break
;
}
break
;
}
}
}
}
...
...
node.hpp
View file @
9e8b930e
...
@@ -3,11 +3,13 @@
...
@@ -3,11 +3,13 @@
#include <vector>
#include <vector>
#include <sstream>
#include <sstream>
#include "values.hpp"
#include "values.hpp"
#include <iostream>
namespace
Sass
{
namespace
Sass
{
using
std
::
string
;
using
std
::
string
;
using
std
::
vector
;
using
std
::
vector
;
using
std
::
stringstream
;
using
std
::
stringstream
;
using
std
::
cerr
;
using
std
::
endl
;
struct
Node
{
struct
Node
{
enum
Type
{
enum
Type
{
...
@@ -96,7 +98,7 @@ namespace Sass {
...
@@ -96,7 +98,7 @@ namespace Sass {
void
clear
()
void
clear
()
{
{
type
=
none
;
line_number
=
0
;
type
=
none
;
line_number
=
0
;
has_children
=
false
;
has_statements
=
false
;
has_blocks
=
false
;
has_expansions
=
false
;
has_statements
=
false
;
has_blocks
=
false
;
has_expansions
=
false
;
has_backref
=
false
;
from_variable
=
false
;
eval_me
=
false
;
has_backref
=
false
;
from_variable
=
false
;
eval_me
=
false
;
}
}
...
@@ -174,6 +176,7 @@ namespace Sass {
...
@@ -174,6 +176,7 @@ namespace Sass {
clear
();
clear
();
type
=
numeric_dimension
;
type
=
numeric_dimension
;
line_number
=
ln
;
line_number
=
ln
;
content
.
dimension
=
Dimension
();
content
.
dimension
.
numeric_value
=
val
;
content
.
dimension
.
numeric_value
=
val
;
content
.
dimension
.
unit
=
tok
.
begin
;
content
.
dimension
.
unit
=
tok
.
begin
;
}
}
...
@@ -192,86 +195,4 @@ namespace Sass {
...
@@ -192,86 +195,4 @@ namespace Sass {
++
allocations
;
++
allocations
;
}
}
};
};
struct
Orig_Node
{
enum
Type
{
root
,
ruleset
,
propset
,
selector_group
,
selector
,
selector_combinator
,
simple_selector_sequence
,
backref
,
simple_selector
,
type_selector
,
class_selector
,
id_selector
,
pseudo
,
pseudo_negation
,
functional_pseudo
,
attribute_selector
,
block
,
rule
,
property
,
nil
,
comma_list
,
space_list
,
expression
,
add
,
sub
,
term
,
mul
,
div
,
factor
,
values
,
value
,
identifier
,
uri
,
textual_percentage
,
textual_dimension
,
textual_number
,
textual_hex
,
string_constant
,
numeric_percentage
,
numeric_dimension
,
number
,
hex_triple
,
mixin
,
parameters
,
expansion
,
arguments
,
variable
,
assignment
,
comment
,
none
,
flags
};
string
to_string
(
const
string
&
prefix
)
const
;
Node
clone
()
const
;
void
echo
(
stringstream
&
buf
,
size_t
depth
=
0
);
void
emit_nested_css
(
stringstream
&
buf
,
size_t
depth
,
const
vector
<
string
>&
prefixes
);
void
emit_nested_css
(
stringstream
&
buf
,
size_t
depth
);
void
emit_expanded_css
(
stringstream
&
buf
,
const
string
&
prefix
);
void
flatten
();
};
}
}
\ No newline at end of file
sassc.cpp
View file @
9e8b930e
...
@@ -29,6 +29,7 @@ int main(int argc, char* argv[]) {
...
@@ -29,6 +29,7 @@ int main(int argc, char* argv[]) {
}
}
Document
doc
(
path
,
0
);
Document
doc
(
path
,
0
);
cerr
<<
"PREPARING TO PARSE DOCUMENT"
<<
endl
;
doc
.
parse_scss
();
doc
.
parse_scss
();
cerr
<<
"SUCCESSFULLY PARSED DOCUMENT"
<<
endl
;
cerr
<<
"SUCCESSFULLY PARSED DOCUMENT"
<<
endl
;
// doc.eval_pending();
// doc.eval_pending();
...
@@ -36,8 +37,8 @@ int main(int argc, char* argv[]) {
...
@@ -36,8 +37,8 @@ int main(int argc, char* argv[]) {
cerr
<<
"SUCCESSFULLY EVALED DOCUMENT"
<<
endl
;
cerr
<<
"SUCCESSFULLY EVALED DOCUMENT"
<<
endl
;
string
output
=
doc
.
emit_css
(
style
);
string
output
=
doc
.
emit_css
(
style
);
cerr
<<
"Fresh nodes:
\t
"
<<
Node
::
fresh
<<
endl
;
//
cerr << "Fresh nodes:\t" << Node::fresh << endl;
cerr
<<
"Copied nodes:
\t
"
<<
Node
::
copied
<<
endl
;
//
cerr << "Copied nodes:\t" << Node::copied << endl;
cerr
<<
"Allocations:
\t
"
<<
Node
::
allocations
<<
endl
;
cerr
<<
"Allocations:
\t
"
<<
Node
::
allocations
<<
endl
;
cout
<<
output
;
cout
<<
output
;
...
...
spec/basic/15_arithmetic_and_lists/input.scss
View file @
9e8b930e
...
@@ -23,8 +23,8 @@ div {
...
@@ -23,8 +23,8 @@ div {
l
:
15
/
5
/
$three
;
l
:
15
/
5
/
$three
;
m
:
1
/
2
,
$stuff
url("www.foo.com/blah.png")
blah
blah
;
m
:
1
/
2
,
$stuff
url("www.foo.com/blah.png")
blah
blah
;
n
:
1
2
3
,
$stuff
4
5
(
6
,
7
8
9
);
n
:
1
2
3
,
$stuff
4
5
(
6
,
7
8
9
);
o
:
3px
+
3px
;
o
:
3px
+
3px
+
3px
;
p
:
4
+
1
em
;
p
:
4
+
1
px
;
q
:
(
20pt
/
10pt
);
q
:
(
20pt
/
10pt
);
r
:
16em
*
4
;
r
:
16em
*
4
;
s
:
(
5em
/
2
);
s
:
(
5em
/
2
);
...
...
spec/basic/15_arithmetic_and_lists/output.css
View file @
9e8b930e
...
@@ -19,8 +19,8 @@ div {
...
@@ -19,8 +19,8 @@ div {
l
:
1
;
l
:
1
;
m
:
1
/
2
,
1
2
3
url("www.foo.com/blah.png")
blah
blah
;
m
:
1
/
2
,
1
2
3
url("www.foo.com/blah.png")
blah
blah
;
n
:
1
2
3
,
1
2
3
4
5
6
,
7
8
9
;
n
:
1
2
3
,
1
2
3
4
5
6
,
7
8
9
;
o
:
6
px
;
o
:
9
px
;
p
:
5
em
;
p
:
5
px
;
q
:
2
;
q
:
2
;
r
:
64em
;
r
:
64em
;
s
:
2.5em
;
s
:
2.5em
;
...
...
values.cpp
View file @
9e8b930e
#include "
token
.hpp"
#include "
values
.hpp"
namespace
Sass
{
namespace
Sass
{
Token
::
Token
()
:
begin
(
0
),
end
(
0
)
{
}
//
Token::Token() : begin(0), end(0) { }
Token
::
Token
(
const
char
*
begin
,
const
char
*
end
)
//
Token::Token(const char* begin, const char* end)
:
begin
(
begin
),
end
(
end
)
{
}
//
: begin(begin), end(end) { }
string
Token
::
unquote
()
const
{
string
Token
::
unquote
()
const
{
string
result
;
string
result
;
...
...
values.hpp
View file @
9e8b930e
...
@@ -17,6 +17,9 @@ namespace Sass {
...
@@ -17,6 +17,9 @@ namespace Sass {
inline
operator
string
()
const
inline
operator
string
()
const
{
return
string
(
begin
,
end
-
begin
);
}
{
return
string
(
begin
,
end
-
begin
);
}
string
to_string
()
const
{
return
string
(
begin
,
end
-
begin
);
}
string
unquote
()
const
;
string
unquote
()
const
;
void
unquote_to_stream
(
std
::
stringstream
&
buf
)
const
;
void
unquote_to_stream
(
std
::
stringstream
&
buf
)
const
;
...
@@ -25,7 +28,23 @@ namespace Sass {
...
@@ -25,7 +28,23 @@ namespace Sass {
bool
operator
==
(
const
Token
&
rhs
)
const
;
bool
operator
==
(
const
Token
&
rhs
)
const
;
operator
bool
()
operator
bool
()
{
return
begin
&&
end
&&
begin
>=
end
;
}
{
return
begin
&&
end
&&
begin
>=
end
;
}
// static Token make()
// {
// Token t;
// t.begin = 0;
// t.end = 0;
// return t;
// }
//
static
Token
make
(
const
char
*
b
=
0
,
const
char
*
e
=
0
)
{
Token
t
;
t
.
begin
=
b
;
t
.
end
=
e
;
return
t
;
}
};
};
struct
Dimension
{
struct
Dimension
{
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment