sassc 1.8.4 → 1.8.5

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 8fe1d16ee2088d1a7579e272a1a7e06ec45fcfc4
4
- data.tar.gz: fdf4b18309732cf9657becf31f4cf42170cce51c
3
+ metadata.gz: ab6f4c497bb370c122244297018added959a8af8
4
+ data.tar.gz: ad910a4be141fd033b143c1723f7a8dfef523243
5
5
  SHA512:
6
- metadata.gz: 9182f4bbf92967e5dae1c870427d372d1bb672f7fab914a4b412d032ab2391456a2989dc5313e71f9e50d476e905d16ee72de22038136ead8674c58a074a38cb
7
- data.tar.gz: 80fe5528ca2af133a4075ee84b9b3aafd0f1c8eb11aa73ac827eaf96cdedbd349ad933f5f0a990fffeb43ce96b866de0b2bed50f3b5c809dfe5f22f9dde6096f
6
+ metadata.gz: 1cd8b55db12f25fca765171af3e7ae3f11702e39a0df778009088dc254777ee90bd138467ef4efcbc865e507c096ce165f3dcd8abae3bfe925eec9e084eaa83d
7
+ data.tar.gz: 45205737303fbaca70c190457d30d234eec1c814bd279810bac275a7360c09a59f8f1a0552c6321b658023d986f5e6d4fb7887d8682bcbc45fbdbf1ea685e310
data/README.md CHANGED
@@ -25,6 +25,8 @@ and [awesome contributors](https://github.com/bolandrm/sassc-ruby/graphs/contrib
25
25
 
26
26
  ## Changelog
27
27
 
28
+ - **1.8.5**
29
+ - Update to Libsass 3.3.4
28
30
  - **1.8.4**
29
31
  - Update to Libsass 3.3.3
30
32
  - **1.8.3**
@@ -1,5 +1,5 @@
1
1
 
2
- Copyright (C) 2012-2016 by Hampton Catlin
2
+ Copyright (C) 2012-2016 by the Sass Open Source Foundation
3
3
 
4
4
  Permission is hereby granted, free of charge, to any person obtaining a copy of
5
5
  this software and associated documentation files (the "Software"), to deal in
@@ -3,7 +3,7 @@ LibSass
3
3
 
4
4
  by Aaron Leung ([@akhleung]), Hampton Catlin ([@hcatlin]), Marcel Greter ([@mgreter]) and Michael Mifsud ([@xzyfer])
5
5
 
6
- [![Linux CI](https://travis-ci.org/sass/libsass.png?branch=master)](https://travis-ci.org/sass/libsass)
6
+ [![Linux CI](https://travis-ci.org/sass/libsass.svg?branch=master)](https://travis-ci.org/sass/libsass)
7
7
  [![Windows CI](https://ci.appveyor.com/api/projects/status/github/sass/libsass?svg=true)](https://ci.appveyor.com/project/sass/libsass/branch/master)
8
8
  [![Bountysource](https://www.bountysource.com/badge/tracker?tracker_id=283068)](https://www.bountysource.com/trackers/283068-libsass?utm_source=283068&utm_medium=shield&utm_campaign=TRACKER_BADGE)
9
9
  [![Coverage Status](https://img.shields.io/coveralls/sass/libsass.svg)](https://coveralls.io/r/sass/libsass?branch=feature%2Ftest-travis-ci-3)
@@ -13,7 +13,7 @@ https://github.com/sass/libsass
13
13
 
14
14
  LibSass is just a library, but if you want to RUN LibSass,
15
15
  then go to https://github.com/sass/sassc or
16
- https://github.com/sass/ruby-libsass or
16
+ https://github.com/sass/sassc-ruby or
17
17
  [find your local implementer](docs/implementations.md).
18
18
 
19
19
  LibSass requires GCC 4.6+ or Clang/LLVM. If your OS is older, this version may not compile.
@@ -68,20 +68,16 @@ Sass is a CSS pre-processor language to add on exciting, new,
68
68
  awesome features to CSS. Sass was the first language of its kind
69
69
  and by far the most mature and up to date codebase.
70
70
 
71
- Sass was originally created by the co-creator of this library,
72
- Hampton Catlin ([@hcatlin]). The extension and continuing evolution
73
- of the language has all been the result of years of work by Natalie
74
- Weizenbaum ([@nex3]) and Chris Eppstein ([@chriseppstein]).
71
+ Sass was originally concieved of by the co-creator of this library,
72
+ Hampton Catlin ([@hcatlin]). Most of the language has been the result of years
73
+ of work by Natalie Weizenbaum ([@nex3]) and Chris Eppstein ([@chriseppstein]).
75
74
 
76
75
  For more information about Sass itself, please visit http://sass-lang.com
77
76
 
78
- Contribution Agreement
79
- ----------------------
77
+ Initial development of libsass by Aaron Leung and Hampton Catlin was supported by [Moovweb](http://www.moovweb.com).
80
78
 
81
- Any contribution to the project are seen as copyright assigned to Hampton Catlin, a
82
- human on the planet earth. Your contribution warrants that you have the right to
83
- assign copyright on your work. The intention here is to ensure that the project
84
- remains totally free (liberal, like).
79
+ Licensing
80
+ ---------
85
81
 
86
82
  Our MIT license is designed to be as simple, and liberal as possible.
87
83
 
@@ -94,4 +90,3 @@ Our MIT license is designed to be as simple, and liberal as possible.
94
90
 
95
91
  sass2scss was originally written by [Marcel Greter](@mgreter)
96
92
  and he happily agreed to have it merged into the project.
97
-
@@ -1,4 +1,4 @@
1
- os: Visual Studio 2015
1
+ os: Visual Studio 2013
2
2
 
3
3
  environment:
4
4
  CTEST_OUTPUT_ON_FAILURE: 1
@@ -949,6 +949,7 @@ namespace Sass {
949
949
 
950
950
  Selector_List* Selector_List::parentize(Selector_List* ps, Context& ctx)
951
951
  {
952
+ if (!this->has_parent_ref()) return this;
952
953
  Selector_List* ss = SASS_MEMORY_NEW(ctx.mem, Selector_List, pstate());
953
954
  for (size_t pi = 0, pL = ps->length(); pi < pL; ++pi) {
954
955
  Selector_List* list = SASS_MEMORY_NEW(ctx.mem, Selector_List, pstate());
@@ -1085,18 +1086,16 @@ namespace Sass {
1085
1086
  Complex_Selector* Complex_Selector::first()
1086
1087
  {
1087
1088
  // declare variables used in loop
1088
- Complex_Selector* cur = this->tail_;
1089
- const Compound_Selector* head = head_;
1089
+ Complex_Selector* cur = this;
1090
+ const Compound_Selector* head;
1090
1091
  // processing loop
1091
1092
  while (cur)
1092
1093
  {
1093
1094
  // get the head
1094
1095
  head = cur->head_;
1095
- // check for single parent ref
1096
- if (head && head->length() == 1)
1097
- {
1098
- // abort (and return) if it is not a parent selector
1099
- if (!dynamic_cast<Parent_Selector*>((*head)[0])) break;
1096
+ // abort (and return) if it is not a parent selector
1097
+ if (!head || head->length() != 1 || !dynamic_cast<Parent_Selector*>((*head)[0])) {
1098
+ break;
1100
1099
  }
1101
1100
  // advance to next
1102
1101
  cur = cur->tail_;
@@ -1897,6 +1896,10 @@ namespace Sass {
1897
1896
  return false;
1898
1897
  }
1899
1898
 
1899
+ bool String_Constant::is_invisible() const {
1900
+ return value_.empty() && quote_mark_ == 0;
1901
+ }
1902
+
1900
1903
  bool String_Constant::operator== (const Expression& rhs) const
1901
1904
  {
1902
1905
  if (const String_Quoted* qstr = dynamic_cast<const String_Quoted*>(&rhs)) {
@@ -2030,14 +2033,6 @@ namespace Sass {
2030
2033
  return to_string({ NESTED, 5 });
2031
2034
  }
2032
2035
 
2033
- // helper function for serializing colors
2034
- template <size_t range>
2035
- static double cap_channel(double c) {
2036
- if (c > range) return range;
2037
- else if (c < 0) return 0;
2038
- else return c;
2039
- }
2040
-
2041
2036
  std::string String_Quoted::inspect() const
2042
2037
  {
2043
2038
  return quote(value_, '*');
@@ -2064,4 +2059,3 @@ namespace Sass {
2064
2059
  }
2065
2060
 
2066
2061
  }
2067
-
@@ -1514,6 +1514,7 @@ namespace Sass {
1514
1514
  { }
1515
1515
  std::string type() { return "string"; }
1516
1516
  static std::string type_name() { return "string"; }
1517
+ virtual bool is_invisible() const;
1517
1518
 
1518
1519
  virtual size_t hash()
1519
1520
  {
@@ -351,8 +351,9 @@ namespace Sass {
351
351
 
352
352
  // process the resolved entry
353
353
  else if (resolved.size() == 1) {
354
+ bool use_cache = c_importers.size() == 0;
354
355
  // use cache for the resource loading
355
- if (sheets.count(resolved[0].abs_path)) return resolved[0];
356
+ if (use_cache && sheets.count(resolved[0].abs_path)) return resolved[0];
356
357
  // try to read the content of the resolved file entry
357
358
  // the memory buffer returned must be freed by us!
358
359
  if (char* contents = read_file(resolved[0].abs_path)) {
@@ -436,7 +437,7 @@ namespace Sass {
436
437
  // query data from the current include
437
438
  Sass_Import_Entry include = *it_includes;
438
439
  char* source = sass_import_take_source(include);
439
- char* srcmap = sass_import_take_source(include);
440
+ char* srcmap = sass_import_take_srcmap(include);
440
441
  size_t line = sass_import_get_error_line(include);
441
442
  size_t column = sass_import_get_error_column(include);
442
443
  const char *abs_path = sass_import_get_abs_path(include);
@@ -357,6 +357,7 @@ inline void debug_ast(AST_Node* node, std::string ind, Env* env)
357
357
  Import_Stub* block = dynamic_cast<Import_Stub*>(node);
358
358
  std::cerr << ind << "Import_Stub " << block;
359
359
  std::cerr << " (" << pstate_source_position(node) << ")";
360
+ std::cerr << " [" << block->imp_path() << "] ";
360
361
  std::cerr << " " << block->tabs() << std::endl;
361
362
  } else if (dynamic_cast<Import*>(node)) {
362
363
  Import* block = dynamic_cast<Import*>(node);
@@ -504,22 +504,22 @@ namespace Sass {
504
504
  }
505
505
 
506
506
  // only the last item will be used to eval the binary expression
507
- if (String_Schema* s_1 = dynamic_cast<String_Schema*>(b->left())) {
508
- if (!s_1->is_right_interpolant()) {
509
- ret_schema = SASS_MEMORY_NEW(ctx.mem, String_Schema, s_1->pstate());
507
+ if (String_Schema* s_l = dynamic_cast<String_Schema*>(b->left())) {
508
+ if (!s_l->has_interpolant() && (!s_l->is_right_interpolant())) {
509
+ ret_schema = SASS_MEMORY_NEW(ctx.mem, String_Schema, s_l->pstate());
510
510
  Binary_Expression* bin_ex = SASS_MEMORY_NEW(ctx.mem, Binary_Expression, b->pstate(),
511
- b->op(), s_1->last(), b->right());
511
+ b->op(), s_l->last(), b->right());
512
512
  bin_ex->is_delayed(b->left()->is_delayed() || b->right()->is_delayed());
513
513
  // bin_ex->is_interpolant(b->left()->is_interpolant());
514
- for (size_t i = 0; i < s_1->length() - 1; ++i) {
515
- *ret_schema << s_1->at(i)->perform(this);
514
+ for (size_t i = 0; i < s_l->length() - 1; ++i) {
515
+ *ret_schema << s_l->at(i)->perform(this);
516
516
  }
517
517
  *ret_schema << bin_ex->perform(this);
518
518
  return ret_schema->perform(this);
519
519
  }
520
520
  }
521
521
  if (String_Schema* s_r = dynamic_cast<String_Schema*>(b->right())) {
522
- if (!s_r->is_left_interpolant() || op_type == Sass_OP::DIV) {
522
+ if (!s_r->has_interpolant() && (!s_r->is_left_interpolant() || op_type == Sass_OP::DIV)) {
523
523
  ret_schema = SASS_MEMORY_NEW(ctx.mem, String_Schema, s_r->pstate());
524
524
  Binary_Expression* bin_ex = SASS_MEMORY_NEW(ctx.mem, Binary_Expression, b->pstate(),
525
525
  b->op(), b->left(), s_r->first());
@@ -691,7 +691,7 @@ namespace Sass {
691
691
  }
692
692
  }
693
693
 
694
- if (force_delay) {
694
+ if (force_delay) {
695
695
  std::string str("");
696
696
  str += v_l->to_string(ctx.c_options);
697
697
  if (b->op().ws_before) str += " ";
@@ -1125,11 +1125,12 @@ namespace Sass {
1125
1125
  if (List* l = dynamic_cast<List*>(ex)) {
1126
1126
  List* ll = SASS_MEMORY_NEW(ctx.mem, List, l->pstate(), 0, l->separator());
1127
1127
  // this fixes an issue with bourbon sample, not really sure why
1128
- if (l->size() && dynamic_cast<Null*>((*l)[0])) { res += " "; }
1128
+ // if (l->size() && dynamic_cast<Null*>((*l)[0])) { res += ""; }
1129
1129
  for(auto item : *l) {
1130
1130
  item->is_interpolant(l->is_interpolant());
1131
1131
  std::string rl(""); interpolation(ctx, rl, item, into_quotes, l->is_interpolant());
1132
- if (rl != "") *ll << SASS_MEMORY_NEW(ctx.mem, String_Quoted, item->pstate(), rl);
1132
+ bool is_null = dynamic_cast<Null*>(item) != 0; // rl != ""
1133
+ if (!is_null) *ll << SASS_MEMORY_NEW(ctx.mem, String_Quoted, item->pstate(), rl);
1133
1134
  }
1134
1135
  res += (ll->to_string(ctx.c_options));
1135
1136
  ll->is_interpolant(l->is_interpolant());
@@ -1170,15 +1171,22 @@ namespace Sass {
1170
1171
  }
1171
1172
  }
1172
1173
  }
1174
+ bool was_quoted = false;
1175
+ bool was_interpolant = false;
1173
1176
  std::string res("");
1174
1177
  for (size_t i = 0; i < L; ++i) {
1178
+ bool is_quoted = dynamic_cast<String_Quoted*>((*s)[i]) != NULL;
1175
1179
  (*s)[i]->perform(this);
1180
+ if (was_quoted && !(*s)[i]->is_interpolant() && !was_interpolant) { res += " "; }
1181
+ else if (i > 0 && is_quoted && !(*s)[i]->is_interpolant() && !was_interpolant) { res += " "; }
1176
1182
  Expression* ex = (*s)[i]->is_delayed() ? (*s)[i] : (*s)[i]->perform(this);
1177
1183
  interpolation(ctx, res, ex, into_quotes, ex->is_interpolant());
1184
+ was_quoted = dynamic_cast<String_Quoted*>((*s)[i]) != NULL;
1185
+ was_interpolant = (*s)[i]->is_interpolant();
1178
1186
 
1179
1187
  }
1180
1188
  if (!s->is_interpolant()) {
1181
- if (res == "") return SASS_MEMORY_NEW(ctx.mem, Null, s->pstate());
1189
+ if (s->length() > 1 && res == "") return SASS_MEMORY_NEW(ctx.mem, Null, s->pstate());
1182
1190
  return SASS_MEMORY_NEW(ctx.mem, String_Constant, s->pstate(), res);
1183
1191
  }
1184
1192
  String_Quoted* str = SASS_MEMORY_NEW(ctx.mem, String_Quoted, s->pstate(), res);
@@ -117,6 +117,17 @@ namespace Sass {
117
117
  Selector_List* sel = dynamic_cast<Selector_List*>(ex);
118
118
  if (sel == 0) throw std::runtime_error("Expanded null selector");
119
119
 
120
+ if (sel->length() == 0 || sel->has_parent_ref()) {
121
+ bool has_parent_selector = false;
122
+ for (size_t i = 0, L = selector_stack.size(); i < L && !has_parent_selector; i++) {
123
+ Selector_List* ll = selector_stack.at(i);
124
+ has_parent_selector = ll != 0 && ll->length() > 0;
125
+ }
126
+ if (!has_parent_selector) {
127
+ error("Base-level rules cannot contain the parent-selector-referencing character '&'.", sel->pstate(), backtrace());
128
+ }
129
+ }
130
+
120
131
  selector_stack.push_back(sel);
121
132
  Env* env = 0;
122
133
  if (block_stack.back()->is_root()) {
@@ -1690,7 +1690,6 @@ namespace Sass {
1690
1690
  Sass_Output_Style old_style;
1691
1691
  old_style = ctx.c_options.output_style;
1692
1692
  ctx.c_options.output_style = TO_SASS;
1693
- Sass_Output_Options out(ctx.c_options);
1694
1693
  Emitter emitter(ctx.c_options);
1695
1694
  Inspect i(emitter);
1696
1695
  i.in_declaration = false;
@@ -406,7 +406,10 @@ namespace Sass {
406
406
  Expression* list_item = (*list)[i];
407
407
  if (output_style() != TO_SASS) {
408
408
  if (list_item->is_invisible()) {
409
- continue;
409
+ // this fixes an issue with "" in a list
410
+ if (!dynamic_cast<String_Constant*>(list_item)) {
411
+ continue;
412
+ }
410
413
  }
411
414
  }
412
415
  if (items_output) {
@@ -544,42 +544,50 @@ JsonNode *json_mkobject(void)
544
544
 
545
545
  static void append_node(JsonNode *parent, JsonNode *child)
546
546
  {
547
- child->parent = parent;
548
- child->prev = parent->children.tail;
549
- child->next = NULL;
550
-
551
- if (parent->children.tail != NULL)
552
- parent->children.tail->next = child;
553
- else
554
- parent->children.head = child;
555
- parent->children.tail = child;
547
+ if (child != NULL && parent != NULL) {
548
+ child->parent = parent;
549
+ child->prev = parent->children.tail;
550
+ child->next = NULL;
551
+
552
+ if (parent->children.tail != NULL)
553
+ parent->children.tail->next = child;
554
+ else
555
+ parent->children.head = child;
556
+ parent->children.tail = child;
557
+ }
556
558
  }
557
559
 
558
560
  static void prepend_node(JsonNode *parent, JsonNode *child)
559
561
  {
560
- child->parent = parent;
561
- child->prev = NULL;
562
- child->next = parent->children.head;
563
-
564
- if (parent->children.head != NULL)
565
- parent->children.head->prev = child;
566
- else
567
- parent->children.tail = child;
568
- parent->children.head = child;
562
+ if (child != NULL && parent != NULL) {
563
+ child->parent = parent;
564
+ child->prev = NULL;
565
+ child->next = parent->children.head;
566
+
567
+ if (parent->children.head != NULL)
568
+ parent->children.head->prev = child;
569
+ else
570
+ parent->children.tail = child;
571
+ parent->children.head = child;
572
+ }
569
573
  }
570
574
 
571
575
  static void append_member(JsonNode *object, char *key, JsonNode *value)
572
576
  {
573
- value->key = key;
574
- append_node(object, value);
577
+ if (value != NULL && object != NULL) {
578
+ value->key = key;
579
+ append_node(object, value);
580
+ }
575
581
  }
576
582
 
577
583
  void json_append_element(JsonNode *array, JsonNode *element)
578
584
  {
579
- assert(array->tag == JSON_ARRAY);
580
- assert(element->parent == NULL);
581
-
582
- append_node(array, element);
585
+ if (array != NULL && element !=NULL) {
586
+ assert(array->tag == JSON_ARRAY);
587
+ assert(element->parent == NULL);
588
+
589
+ append_node(array, element);
590
+ }
583
591
  }
584
592
 
585
593
  void json_prepend_element(JsonNode *array, JsonNode *element)
@@ -592,40 +600,47 @@ void json_prepend_element(JsonNode *array, JsonNode *element)
592
600
 
593
601
  void json_append_member(JsonNode *object, const char *key, JsonNode *value)
594
602
  {
595
- assert(object->tag == JSON_OBJECT);
596
- assert(value->parent == NULL);
597
-
598
- append_member(object, json_strdup(key), value);
603
+ if (object != NULL && key != NULL && value != NULL) {
604
+ assert(object->tag == JSON_OBJECT);
605
+ assert(value->parent == NULL);
606
+
607
+ append_member(object, json_strdup(key), value);
608
+ }
599
609
  }
600
610
 
601
611
  void json_prepend_member(JsonNode *object, const char *key, JsonNode *value)
602
612
  {
603
- assert(object->tag == JSON_OBJECT);
604
- assert(value->parent == NULL);
605
-
606
- value->key = json_strdup(key);
607
- prepend_node(object, value);
613
+ if (object != NULL && key != NULL && value != NULL) {
614
+ assert(object->tag == JSON_OBJECT);
615
+ assert(value->parent == NULL);
616
+
617
+ value->key = json_strdup(key);
618
+ prepend_node(object, value);
619
+ }
608
620
  }
609
621
 
610
622
  void json_remove_from_parent(JsonNode *node)
611
623
  {
612
- JsonNode *parent = node->parent;
613
-
614
- if (parent != NULL) {
615
- if (node->prev != NULL)
616
- node->prev->next = node->next;
617
- else
618
- parent->children.head = node->next;
619
- if (node->next != NULL)
620
- node->next->prev = node->prev;
621
- else
622
- parent->children.tail = node->prev;
623
-
624
- free(node->key);
625
-
626
- node->parent = NULL;
627
- node->prev = node->next = NULL;
628
- node->key = NULL;
624
+ if (node != NULL) {
625
+ JsonNode *parent = node->parent;
626
+
627
+ if (parent != NULL) {
628
+ if (node->prev != NULL)
629
+ node->prev->next = node->next;
630
+ else
631
+ parent->children.head = node->next;
632
+
633
+ if (node->next != NULL)
634
+ node->next->prev = node->prev;
635
+ else
636
+ parent->children.tail = node->prev;
637
+
638
+ free(node->key);
639
+
640
+ node->parent = NULL;
641
+ node->prev = node->next = NULL;
642
+ node->key = NULL;
643
+ }
629
644
  }
630
645
  }
631
646
 
@@ -137,7 +137,7 @@ namespace Sass {
137
137
  const char* any_char(const char* src) { return *src ? src + 1 : src; }
138
138
 
139
139
  // Match word boundary (zero-width lookahead).
140
- const char* word_boundary(const char* src) { return is_character(*src) ? 0 : src; }
140
+ const char* word_boundary(const char* src) { return is_character(*src) || *src == '#' ? 0 : src; }
141
141
 
142
142
  // Match linefeed /(?:\n|\r\n?)/
143
143
  const char* re_linebreak(const char* src)
@@ -67,7 +67,8 @@ namespace Sass {
67
67
  // search for unicode char
68
68
  for(const char& chr : wbuf.buffer) {
69
69
  // skip all ascii chars
70
- if (chr >= 0) continue;
70
+ // static cast to unsigned to handle `char` being signed / unsigned
71
+ if (static_cast<unsigned>(chr) < 128) continue;
71
72
  // declare the charset
72
73
  if (output_style() != COMPRESSED)
73
74
  charset = "@charset \"UTF-8\";"
@@ -200,7 +200,7 @@ namespace Sass {
200
200
 
201
201
  // abort if we are in function context and have nothing parsed yet
202
202
  else if (stack.back() == Scope::Function) {
203
- error("Functions can only contain variable declarations and control directives", pstate);
203
+ error("Functions can only contain variable declarations and control directives.", pstate);
204
204
  }
205
205
 
206
206
  // parse imports to process later
@@ -221,8 +221,7 @@ namespace Sass {
221
221
  }
222
222
 
223
223
  else if (lex < kwd_extend >(true)) {
224
- Scope parent = stack.empty() ? Scope::Rules : stack.back();
225
- if (parent == Scope::Root) {
224
+ if (block->is_root()) {
226
225
  error("Extend directives may only be used within rules.", pstate);
227
226
  }
228
227
 
@@ -290,12 +289,7 @@ namespace Sass {
290
289
  do {
291
290
  while (lex< block_comment >());
292
291
  if (lex< quoted_string >()) {
293
- if (!ctx.call_importers(unquote(std::string(lexed)), path, pstate, imp))
294
- {
295
- // push single file import
296
- // import_single_file(imp, lexed);
297
- to_import.push_back(std::pair<std::string,Function_Call*>(std::string(lexed), 0));
298
- }
292
+ to_import.push_back(std::pair<std::string,Function_Call*>(std::string(lexed), 0));
299
293
  }
300
294
  else if (lex< uri_prefix >()) {
301
295
  Arguments* args = SASS_MEMORY_NEW(ctx.mem, Arguments, pstate);
@@ -333,7 +327,7 @@ namespace Sass {
333
327
  for(auto location : to_import) {
334
328
  if (location.second) {
335
329
  imp->urls().push_back(location.second);
336
- } else {
330
+ } else if (!ctx.call_importers(unquote(location.first), path, pstate, imp)) {
337
331
  ctx.import_url(imp, location.first, path);
338
332
  }
339
333
  }
@@ -345,7 +339,12 @@ namespace Sass {
345
339
  {
346
340
  Scope parent = stack.empty() ? Scope::Rules : stack.back();
347
341
  if (parent != Scope::Root && parent != Scope::Rules && parent != Scope::Function) {
348
- error("Functions may not be defined within control directives or other mixins.", pstate);
342
+ if (which_type == Definition::FUNCTION) {
343
+ error("Functions may not be defined within control directives or other mixins.", pstate);
344
+ } else {
345
+ error("Mixins may not be defined within control directives or other mixins.", pstate);
346
+ }
347
+
349
348
  }
350
349
  std::string which_str(lexed);
351
350
  if (!lex< identifier >()) error("invalid name in " + which_str + " definition", pstate);
@@ -615,7 +614,7 @@ namespace Sass {
615
614
  while (peek_css< exactly<','> >())
616
615
  {
617
616
  lex< css_comments >(false);
618
- // consume everything up and including the comma speparator
617
+ // consume everything up and including the comma separator
619
618
  reloop = lex< exactly<','> >() != 0;
620
619
  // remember line break (also between some commas)
621
620
  had_linefeed = had_linefeed || peek_newline();
@@ -719,7 +718,7 @@ namespace Sass {
719
718
  // EO parse_complex_selector
720
719
 
721
720
  // parse one compound selector, which is basically
722
- // a list of simple selectors (directly adjancent)
721
+ // a list of simple selectors (directly adjacent)
723
722
  // lex them exactly (without skipping white-space)
724
723
  Compound_Selector* Parser::parse_compound_selector()
725
724
  {
@@ -747,7 +746,7 @@ namespace Sass {
747
746
  seq->has_parent_reference(true);
748
747
  (*seq) << SASS_MEMORY_NEW(ctx.mem, Parent_Selector, pstate);
749
748
  // parent selector only allowed at start
750
- // upcoming sass may allow also trailing
749
+ // upcoming Sass may allow also trailing
751
750
  if (seq->length() > 1) {
752
751
  ParserState state(pstate);
753
752
  Simple_Selector* cur = (*seq)[seq->length()-1];
@@ -834,7 +833,7 @@ namespace Sass {
834
833
  }
835
834
 
836
835
  // a pseudo selector often starts with one or two colons
837
- // it can contain more selectors inside parantheses
836
+ // it can contain more selectors inside parentheses
838
837
  Simple_Selector* Parser::parse_pseudo_selector() {
839
838
  if (lex< sequence<
840
839
  optional < pseudo_prefix >,
@@ -1213,9 +1212,9 @@ namespace Sass {
1213
1212
  : lex<kwd_lte>() ? Sass_OP::LTE
1214
1213
  : lex<kwd_gt>() ? Sass_OP::GT
1215
1214
  : lex<kwd_lt>() ? Sass_OP::LT
1216
- // we checked the possibilites on top of fn
1215
+ // we checked the possibilities on top of fn
1217
1216
  : Sass_OP::EQ;
1218
- // is directly adjancent to expression?
1217
+ // is directly adjacent to expression?
1219
1218
  bool right_ws = peek < css_comments >() != NULL;
1220
1219
  operators.push_back({ op, left_ws, right_ws });
1221
1220
  operands.push_back(parse_expression());
@@ -1238,7 +1237,6 @@ namespace Sass {
1238
1237
  // NOTE: dashes do NOT count as subtract operation
1239
1238
  Expression* lhs = parse_operators();
1240
1239
  // if it's a singleton, return it (don't wrap it)
1241
- // if it's a singleton, return it (don't wrap it)
1242
1240
  if (!(peek_css< exactly<'+'> >(position) ||
1243
1241
  // condition is a bit misterious, but some combinations should not be counted as operations
1244
1242
  (peek< no_spaces >(position) && peek< sequence< negate< unsigned_number >, exactly<'-'>, negate< space > > >(position)) ||
@@ -1308,7 +1306,6 @@ namespace Sass {
1308
1306
  if (!lex_css< exactly<')'> >()) error("unclosed parenthesis", pstate);
1309
1307
  // expression can be evaluated
1310
1308
  // make sure wrapped lists and division expressions are non-delayed within parentheses
1311
- // make sure wrapped lists and division expressions are non-delayed within parentheses
1312
1309
  if (value->concrete_type() == Expression::LIST) {
1313
1310
  // List* l = static_cast<List*>(value);
1314
1311
  // if (!l->empty()) (*l)[0]->is_delayed(false);
@@ -1416,7 +1413,7 @@ namespace Sass {
1416
1413
  if (lex< percentage >())
1417
1414
  { return SASS_MEMORY_NEW(ctx.mem, Textual, pstate, Textual::PERCENTAGE, lexed); }
1418
1415
 
1419
- // match hex number first because 0x000 looks like a number followed by an indentifier
1416
+ // match hex number first because 0x000 looks like a number followed by an identifier
1420
1417
  if (lex< sequence < alternatives< hex, hex0 >, negate < exactly<'-'> > > >())
1421
1418
  { return SASS_MEMORY_NEW(ctx.mem, Textual, pstate, Textual::HEX, lexed); }
1422
1419
 
@@ -1598,6 +1595,8 @@ namespace Sass {
1598
1595
  }
1599
1596
 
1600
1597
  const char* e = 0;
1598
+ const char* ee = end;
1599
+ end = stop;
1601
1600
  size_t num_items = 0;
1602
1601
  bool need_space = false;
1603
1602
  while (position < stop) {
@@ -1607,7 +1606,7 @@ namespace Sass {
1607
1606
  }
1608
1607
  if (need_space) {
1609
1608
  need_space = false;
1610
- (*schema) << SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, " ");
1609
+ // (*schema) << SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, " ");
1611
1610
  }
1612
1611
  if ((e = peek< re_functional >()) && e < stop) {
1613
1612
  (*schema) << parse_function_call();
@@ -1630,23 +1629,26 @@ namespace Sass {
1630
1629
  lex < exactly < rbrace > >();
1631
1630
  }
1632
1631
  // lex some string constants or other valid token
1633
- // Note: [-+] chars are left over from ie. `#{3}+3`
1632
+ // Note: [-+] chars are left over from i.e. `#{3}+3`
1634
1633
  else if (lex< alternatives < exactly<'%'>, exactly < '-' >, exactly < '+' > > >()) {
1635
1634
  (*schema) << SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, lexed);
1636
1635
  }
1637
- else if (lex< sequence < identifier > >()) {
1638
- (*schema) << SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, lexed);
1636
+ // lex a quoted string
1637
+ else if (lex< quoted_string >()) {
1638
+ // need_space = true;
1639
+ // if (schema->length()) (*schema) << SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, " ");
1640
+ // else need_space = true;
1641
+ (*schema) << parse_string();
1639
1642
  if ((*position == '"' || *position == '\'') || peek < alternatives < alpha > >()) {
1640
- need_space = true;
1643
+ // need_space = true;
1641
1644
  }
1645
+ if (peek < exactly < '-' > >()) break;
1642
1646
  }
1643
- // lex a quoted string
1644
- else if (lex< quoted_string >()) {
1645
- (*schema) << SASS_MEMORY_NEW(ctx.mem, String_Quoted, pstate, lexed, '"');
1647
+ else if (lex< sequence < identifier > >()) {
1648
+ (*schema) << SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, lexed);
1646
1649
  if ((*position == '"' || *position == '\'') || peek < alternatives < alpha > >()) {
1647
- need_space = true;
1650
+ // need_space = true;
1648
1651
  }
1649
- if (peek < exactly < '-' > >()) return schema;
1650
1652
  }
1651
1653
  // lex (normalized) variable
1652
1654
  else if (lex< variable >()) {
@@ -1677,10 +1679,15 @@ namespace Sass {
1677
1679
  (*schema) << parse_factor();
1678
1680
  }
1679
1681
  else {
1680
- return schema;
1682
+ break;
1681
1683
  }
1682
1684
  ++num_items;
1683
1685
  }
1686
+ if (position != stop) {
1687
+ (*schema) << SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, std::string(position, stop));
1688
+ position = stop;
1689
+ }
1690
+ end = ee;
1684
1691
  return schema;
1685
1692
  }
1686
1693
 
@@ -1773,6 +1780,11 @@ namespace Sass {
1773
1780
  suffix = std::string(lexed);
1774
1781
  }
1775
1782
 
1783
+ std::string uri("");
1784
+ if (url_string) {
1785
+ uri = url_string->to_string({ NESTED, 5 });
1786
+ }
1787
+
1776
1788
  if (String_Schema* schema = dynamic_cast<String_Schema*>(url_string)) {
1777
1789
  String_Schema* res = SASS_MEMORY_NEW(ctx.mem, String_Schema, pstate);
1778
1790
  (*res) << SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, prefix);
@@ -1780,7 +1792,7 @@ namespace Sass {
1780
1792
  (*res) << SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, suffix);
1781
1793
  return res;
1782
1794
  } else {
1783
- std::string res = prefix + url_string->to_string({ NESTED, 5 }) + suffix;
1795
+ std::string res = prefix + uri + suffix;
1784
1796
  return SASS_MEMORY_NEW(ctx.mem, String_Constant, pstate, res);
1785
1797
  }
1786
1798
  }
@@ -1894,7 +1906,7 @@ namespace Sass {
1894
1906
  if (!peek< exactly <'$'> >()) {
1895
1907
  css_error("Invalid CSS", " after ", ": expected \"$\", was ");
1896
1908
  }
1897
- // we expect a simple identfier as the call name
1909
+ // we expect a simple identifier as the call name
1898
1910
  if (!lex< sequence < exactly <'$'>, identifier > >()) {
1899
1911
  lex< exactly <'$'> >(); // move pstate and position up
1900
1912
  css_error("Invalid CSS", " after ", ": expected identifier, was ");
@@ -1905,7 +1917,7 @@ namespace Sass {
1905
1917
  // helper to parse identifier
1906
1918
  Token Parser::lex_identifier()
1907
1919
  {
1908
- // we expect a simple identfier as the call name
1920
+ // we expect a simple identifier as the call name
1909
1921
  if (!lex< identifier >()) { // ToDo: pstate wrong?
1910
1922
  css_error("Invalid CSS", " after ", ": expected identifier, was ");
1911
1923
  }
@@ -2092,7 +2104,7 @@ namespace Sass {
2092
2104
  }
2093
2105
 
2094
2106
  // TODO: This needs some major work. Although feature conditions
2095
- // look like declarations their semantics differ siginificantly
2107
+ // look like declarations their semantics differ significantly
2096
2108
  Supports_Condition* Parser::parse_supports_declaration()
2097
2109
  {
2098
2110
  Supports_Condition* cond = 0;
@@ -2132,7 +2144,6 @@ namespace Sass {
2132
2144
  Block* body = 0;
2133
2145
  At_Root_Expression* expr = 0;
2134
2146
  Lookahead lookahead_result;
2135
- // stack.push_back(Scope::Root);
2136
2147
  LOCAL_FLAG(in_at_root, true);
2137
2148
  if (lex< exactly<'('> >()) {
2138
2149
  expr = parse_at_root_expression();
@@ -2147,7 +2158,6 @@ namespace Sass {
2147
2158
  }
2148
2159
  At_Root_Block* at_root = SASS_MEMORY_NEW(ctx.mem, At_Root_Block, at_source_position, body);
2149
2160
  if (expr) at_root->expression(expr);
2150
- // stack.pop_back();
2151
2161
  return at_root;
2152
2162
  }
2153
2163
 
@@ -2259,7 +2269,7 @@ namespace Sass {
2259
2269
  if (const char* q =
2260
2270
  peek <
2261
2271
  alternatives <
2262
- // partial bem selector
2272
+ // partial BEM selector
2263
2273
  sequence <
2264
2274
  ampersand,
2265
2275
  one_plus <
@@ -2300,7 +2310,7 @@ namespace Sass {
2300
2310
  // single or double colon
2301
2311
  optional < pseudo_prefix >
2302
2312
  >,
2303
- // accept hypens in token
2313
+ // accept hyphens in token
2304
2314
  one_plus < sequence <
2305
2315
  // can start with hyphens
2306
2316
  zero_plus < exactly<'-'> >,
@@ -2389,19 +2399,27 @@ namespace Sass {
2389
2399
  non_greedy <
2390
2400
  alternatives <
2391
2401
  // consume whitespace
2392
- block_comment, spaces,
2402
+ block_comment, // spaces,
2393
2403
  // main tokens
2394
- interpolant,
2404
+ sequence <
2405
+ interpolant,
2406
+ optional <
2407
+ quoted_string
2408
+ >
2409
+ >,
2395
2410
  identifier,
2396
2411
  variable,
2397
2412
  // issue #442
2398
2413
  sequence <
2399
2414
  parenthese_scope,
2400
- interpolant
2415
+ interpolant,
2416
+ optional <
2417
+ quoted_string
2418
+ >
2401
2419
  >
2402
2420
  >,
2403
2421
  sequence <
2404
- optional_spaces,
2422
+ // optional_spaces,
2405
2423
  alternatives <
2406
2424
  exactly<'{'>,
2407
2425
  exactly<'}'>,
@@ -2424,7 +2442,7 @@ namespace Sass {
2424
2442
  // ToDo: remove
2425
2443
  rv.position = q;
2426
2444
  // check expected opening bracket
2427
- // only after successfull matching
2445
+ // only after successful matching
2428
2446
  if (peek < exactly<'{'> >(q)) rv.found = q;
2429
2447
  else if (peek < exactly<';'> >(q)) rv.found = q;
2430
2448
  else if (peek < exactly<'}'> >(q)) rv.found = q;
@@ -116,7 +116,10 @@ namespace Sass {
116
116
  const char* it_before_token = sneak < mx >(start);
117
117
 
118
118
  // match the given prelexer
119
- return mx(it_before_token);
119
+ const char* match = mx(it_before_token);
120
+
121
+ // check if match is in valid range
122
+ return match <= end ? match : 0;
120
123
 
121
124
  }
122
125
 
@@ -142,6 +145,9 @@ namespace Sass {
142
145
  // now call matcher to get position after token
143
146
  const char* it_after_token = mx(it_before_token);
144
147
 
148
+ // check if match is in valid range
149
+ if (it_after_token > end) return 0;
150
+
145
151
  // maybe we want to update the parser state anyway?
146
152
  if (force == false) {
147
153
  // assertion that we got a valid match
@@ -220,7 +220,10 @@ extern "C" {
220
220
  size_t imp_size = 0; while (imp) { imp_size ++; imp = imp->next; }
221
221
  // create char* array to hold all paths plus null terminator
222
222
  const char** plugin_paths = (const char**) calloc(imp_size + 1, sizeof(char*));
223
- if (plugin_paths == 0) throw(std::bad_alloc());
223
+ if (plugin_paths == 0) {
224
+ free(include_paths); //free include_paths before throw
225
+ throw(std::bad_alloc());
226
+ }
224
227
  // reset iterator
225
228
  imp = c_ctx->plugin_paths;
226
229
  // copy over the paths
@@ -1,3 +1,3 @@
1
1
  module SassC
2
- VERSION = "1.8.4"
2
+ VERSION = "1.8.5"
3
3
  end
@@ -17,6 +17,15 @@ namespace :libsass do
17
17
  end
18
18
 
19
19
  file "lib/libsass.so" => "Makefile" do
20
- sh 'make lib/libsass.so'
20
+ make_program = ENV['MAKE']
21
+ make_program ||= case RUBY_PLATFORM
22
+ when /mswin/
23
+ 'nmake'
24
+ when /(bsd|solaris)/
25
+ 'gmake'
26
+ else
27
+ 'make'
28
+ end
29
+ sh "#{make_program} lib/libsass.so"
21
30
  end
22
31
  end
@@ -9,7 +9,7 @@ module SassC
9
9
 
10
10
  class General < MiniTest::Test
11
11
  def test_it_reports_the_libsass_version
12
- assert_equal "3.3.3", Native.version
12
+ assert_equal "3.3.4", Native.version
13
13
  end
14
14
  end
15
15
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sassc
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.8.4
4
+ version: 1.8.5
5
5
  platform: ruby
6
6
  authors:
7
7
  - Ryan Boland
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-01-20 00:00:00.000000000 Z
11
+ date: 2016-03-21 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rake