Skip to content
This repository was archived by the owner on Feb 15, 2023. It is now read-only.

Commit 5da65e7

Browse files
Fix segmentations failure in error.c gumbo_caret_diagnostic_to_string
Without this patch method find_last_newline returns value bigger than find_next_newline and in line `original_line.length = line_end - line_start;` overflow happens. Before changes newly added test failed with segmentation failure: ``` ./test-driver: line 107: 12171 Segmentation fault (core dumped) "$@" > $log_file 2>&1 ``` This slightly changed copy of code used in nokogumbo gem. [Link](https://github.com/rubys/nokogumbo/blob/8b4446847dea5c614759684ebcae4c580c47f4ad/ext/nokogumboc/nokogumbo.c#L230)
1 parent aa91b27 commit 5da65e7

File tree

3 files changed

+45
-2
lines changed

3 files changed

+45
-2
lines changed

Makefile.am

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -93,7 +93,8 @@ gumbo_test_SOURCES = \
9393
tests/tokenizer.cc \
9494
tests/test_utils.cc \
9595
tests/utf8.cc \
96-
tests/vector.cc
96+
tests/vector.cc \
97+
tests/error.cc
9798
gumbo_test_DEPENDENCIES = libgumbo.la
9899
gumbo_test_LDADD = libgumbo.la
99100

src/error.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -140,7 +140,7 @@ static const char* find_last_newline(
140140
// There may be an error at EOF, which would be a nul byte.
141141
assert(*c || c == error_location);
142142
}
143-
return c == original_text ? c : c + 1;
143+
return c == original_text || c == error_location ? c : c + 2;
144144
}
145145

146146
// Finds the next newline in the original source buffer from a given byte

tests/error.cc

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
#include "gumbo.h"
2+
#include "parser.h"
3+
#include "error.h"
4+
5+
#include <string>
6+
7+
#include "gtest/gtest.h"
8+
#include "test_utils.h"
9+
10+
namespace {
11+
12+
class GumboErrorTest : public ::testing::Test {
13+
protected:
14+
GumboErrorTest() {}
15+
16+
virtual ~GumboErrorTest() {
17+
18+
}
19+
};
20+
21+
TEST_F(GumboErrorTest, NewlineAfterLessThanSymbol) {
22+
const GumboOptions *options = &kGumboDefaultOptions;
23+
// const char *input = "<html><body><\n</html></body>";
24+
const char *input = "<\n";
25+
size_t input_len = strlen(input);
26+
GumboOutput *output = gumbo_parse_with_options(options, input, input_len);
27+
GumboVector *errors = &output->errors;
28+
GumboParser parser = { ._options = options };
29+
GumboStringBuffer msg;
30+
31+
gumbo_string_buffer_init(&parser, &msg);
32+
for (size_t i=0; i < errors->length; i++) {
33+
GumboError *err = (GumboError *)errors->data[i];
34+
gumbo_string_buffer_clear(&parser, &msg);
35+
gumbo_caret_diagnostic_to_string(&parser, err, input, &msg);
36+
}
37+
gumbo_string_buffer_destroy(&parser, &msg);
38+
39+
gumbo_destroy_output(options, output);
40+
}
41+
42+
}

0 commit comments

Comments
 (0)