Skip to content

Commit 11a9862

Browse files
authored
Merge pull request #2484 from mgreter/bugfix/memory-corruption
Fix memory corruption on error in parse_selector_schema
2 parents 0e12964 + a12c47c commit 11a9862

File tree

3 files changed

+20
-3
lines changed

3 files changed

+20
-3
lines changed

src/ast_def_macros.hpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ class LocalOption {
3333

3434
#define NESTING_GUARD(name) \
3535
LocalOption<size_t> cnt_##name(name, name + 1); \
36-
if (nestings > MAX_NESTING) throw Exception::NestingLimitError(pstate); \
36+
if (name > MAX_NESTING) throw Exception::NestingLimitError(pstate); \
3737

3838
#define ATTACH_OPERATIONS()\
3939
virtual void perform(Operation<void>* op) { (*op)(this); }\

src/eval.cpp

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1789,11 +1789,28 @@ namespace Sass {
17891789
Expression_Obj sel = s->contents()->perform(this);
17901790
std::string result_str(sel->to_string(ctx.c_options));
17911791
result_str = unquote(Util::rtrim(result_str));
1792-
Parser p = Parser::from_c_str(result_str.c_str(), ctx, s->pstate());
1792+
char* temp_cstr = sass_copy_c_string(result_str.c_str());
1793+
ctx.strings.push_back(temp_cstr); // attach to context
1794+
Parser p = Parser::from_c_str(temp_cstr, ctx, s->pstate());
17931795
p.last_media_block = s->media_block();
17941796
// a selector schema may or may not connect to parent?
17951797
bool chroot = s->connect_parent() == false;
17961798
Selector_List_Obj sl = p.parse_selector_list(chroot);
1799+
auto vec_str_rend = ctx.strings.rend();
1800+
auto vec_str_rbegin = ctx.strings.rbegin();
1801+
// remove the first item searching from the back
1802+
// we cannot assume our item is still the last one
1803+
// order is not important, so we can optimize this
1804+
auto it = std::find(vec_str_rbegin, vec_str_rend, temp_cstr);
1805+
// undefined behavior if not found!
1806+
if (it != vec_str_rend) {
1807+
// overwrite with last item
1808+
*it = ctx.strings.back();
1809+
// remove last one from vector
1810+
ctx.strings.pop_back();
1811+
// free temporary copy
1812+
free(temp_cstr);
1813+
}
17971814
flag_is_in_selector_schema.reset();
17981815
return operator()(sl);
17991816
}

src/file.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -415,7 +415,7 @@ namespace Sass {
415415
file.seekg(0, std::ios::beg);
416416
file.read(contents, size);
417417
contents[size+0] = '\0';
418-
contents[size+0] = '\0';
418+
contents[size+1] = '\0';
419419
file.close();
420420
}
421421
#endif

0 commit comments

Comments
 (0)