Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add lineno #7

Open
wants to merge 3 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
62 changes: 32 additions & 30 deletions bootstrap/peg_cbyte.c
Original file line number Diff line number Diff line change
Expand Up @@ -101,12 +101,12 @@ void Node_print(Node *self, Parser *parser, const unsigned char *input, int dept
{
int flags = self->flags;
unsigned char *data = esc_string(&input[self->offset], self->length, 40);
const char *def_name = Parser_def_name(parser, self->def);
const char *def_name = Parser_def_name(parser, self->def);

if (depth == 0) {
printf("---------------------------------------------------------------------------------\n");
printf("---------------------------------------------------------------------------------\n");
printf(" Begin Len DefID Flags Def. Name / Data\n");
printf("---------------------------------------------------------------------------------\n");
printf("---------------------------------------------------------------------------------\n");
}
printf("%6d %6d %6d | %s%s%s | %*s%s \"%s\"\n",
self->offset,
Expand All @@ -123,7 +123,7 @@ void Node_print(Node *self, Parser *parser, const unsigned char *input, int dept
for (Node *p = self->head; p; p = p->next) {
Node_print(p, parser, input, depth + 1);
}
}
}

Node *Node_new(int def, int offset, int length, int flags)
{
Expand Down Expand Up @@ -173,7 +173,7 @@ Node *Node_unwrap(Node *self)
if (!(self->flags & (STOP|LEAF)) && self->num_children == 1) {
Node *tmp = Node_unwrap(self->head);
self->head = NULL;
Node_free(self);
Node_free(self);
return tmp;
}
Node *p = self->head; self->head = NULL;
Expand Down Expand Up @@ -208,6 +208,8 @@ Parser *Parser_new(const ByteCode *byte_code)
self->tree_root = NULL;
self->max_tree_depth = 256;
self->max_stack_size = 256 * 8;
self->lineno = 1;
self->lineno_offset = 0;
self->error_offset = -1;
self->error_parent_def = -1;
self->error_def = -1;
Expand Down Expand Up @@ -245,8 +247,8 @@ void Parser_expected(Parser *self, int parent_def, int def, int inst, int offset
void Parser_print_error(Parser *self, const unsigned char *input)
{
#if ERRORS
const char *parent_def_name = Parser_def_name(self, self->error_parent_def);
const char *def_name = Parser_def_name(self, self->error_def);
const char *parent_def_name = Parser_def_name(self, self->error_parent_def);
const char *def_name = Parser_def_name(self, self->error_def);

if (self->error_offset >= 0) {
if (self->error_inst >= 0) {
Expand All @@ -266,29 +268,29 @@ void Parser_print_error(Parser *self, const unsigned char *input)
esc = esc_string((unsigned char *)&self->error_inst, sizeof(int), 20);
break;
}
printf("%s \"%s\" in %s at offset %d\n",
printf("%s \"%s\" in %s at offset %d in line %d:%d\n",
self->error_expected ? "Expected" : "Unexpected",
str ? (unsigned char *)str : esc,
def_name ? def_name : "<N/A>",
self->error_offset);
self->error_offset, self->lineno, self->error_offset-self->lineno_offset);
if (esc) {
free(esc);
esc = NULL;
}
}
else {
if (parent_def_name) {
printf("%s %s in %s at offset %d\n",
printf("%s %s in %s at offset %d in line %d:%d\n",
self->error_expected ? "Expected" : "Unexpected",
def_name ? def_name : "<N/A>",
parent_def_name ? parent_def_name : "<N/A>",
self->error_offset);
self->error_offset, self->lineno, self->error_offset-self->lineno_offset);
}
else {
printf("%s %s at offset %d\n",
printf("%s %s at offset %d in line %d:%d\n",
self->error_expected ? "Expected" : "Unexpected",
def_name ? def_name : "<N/A>",
self->error_offset);
self->error_offset, self->lineno, self->error_offset-self->lineno_offset);
}
}
}
Expand Down Expand Up @@ -322,7 +324,7 @@ int Parser_parse(Parser *self, const unsigned char *input, int size)

const int *instructions = self->instructions;

int op = 0, arg = 0, pc = 0;
int op = 0, arg = 0, pc = 0;

if (size < 0) { return INVALID_SIZE; }

Expand All @@ -340,7 +342,7 @@ int Parser_parse(Parser *self, const unsigned char *input, int size)
#endif
op = instructions[pc] & 0xff;
arg = instructions[pc] >> 8;

/*
printf("pc=%d op=%d arg=%d top=%d tt=%d stack: ", pc, op, arg, top, tree_top);
for (int i = 0; i <= top; i++) {
Expand All @@ -355,7 +357,7 @@ int Parser_parse(Parser *self, const unsigned char *input, int size)

// Identifier
case IDENT: // arg = def; Identifier "call"; on success, next instruction skipped (See ISUCC, IFAIL)
if (top >= self->max_stack_size - 4) return STACK_OVERFLOW;
if (top >= self->max_stack_size - 4) return STACK_OVERFLOW;
if (!locked) {
if (tree_top >= self->max_tree_depth - 2) return TREE_STACK_OVERFLOW;
if (self->def_flags[arg] & (LEAF | IGNORE)) {
Expand Down Expand Up @@ -385,7 +387,7 @@ int Parser_parse(Parser *self, const unsigned char *input, int size)
if (!locked) {
tree_stack[tree_top]->length = offset - tree_stack[tree_top]->offset;
--tree_top;
if (self->def_flags[arg] & IGNORE) {
if (self->def_flags[arg] & IGNORE) {
#if SANITY_CHECKS
if (tree_top < 0) return TREE_STACK_UNDERFLOW;
#endif
Expand Down Expand Up @@ -447,9 +449,9 @@ int Parser_parse(Parser *self, const unsigned char *input, int size)

// Repeat +
case RPBEG:
if (top >= self->max_stack_size - 4) return STACK_OVERFLOW;
if (top >= self->max_stack_size - 4) return STACK_OVERFLOW;
#if ERRORS && ERROR_REPEAT_INHIBIT
stack[++top] = 0; // used to inhibit error tracking after 1st rep
stack[++top] = 0; // used to inhibit error tracking after 1st rep
#endif
stack[++top] = tree_stack[tree_top]->num_children; // num_children - backtrack point
stack[++top] = offset; // offset - backtrack point
Expand All @@ -464,7 +466,7 @@ int Parser_parse(Parser *self, const unsigned char *input, int size)
pc = arg; // continue looping
#if ERRORS && ERROR_REPEAT_INHIBIT
if (!err_locked) { // inhibit error tracking after 1st rep
stack[top-3] = 1; err_locked = 1;
stack[top-3] = 1; err_locked = 1;
}
#endif
}
Expand Down Expand Up @@ -495,10 +497,10 @@ int Parser_parse(Parser *self, const unsigned char *input, int size)
if (top >= self->max_stack_size - 4) return STACK_OVERFLOW;
#if ERRORS && ERROR_REPEAT_INHIBIT
if (!err_locked) { // inhibit error tracking
stack[++top] = 1; err_locked = 1;
stack[++top] = 1; err_locked = 1;
}
else {
stack[++top] = 0;
stack[++top] = 0;
}
#endif
stack[++top] = tree_stack[tree_top]->num_children; // num_children - backtrack point
Expand Down Expand Up @@ -528,7 +530,7 @@ int Parser_parse(Parser *self, const unsigned char *input, int size)
break;

// Repeat ?
case RQMAT: // no looping for ?
case RQMAT: // no looping for ?
stack[top-1] = tree_stack[tree_top]->num_children; // update backtrack point
stack[top] = offset; // update backtrack point
break;
Expand All @@ -542,17 +544,17 @@ int Parser_parse(Parser *self, const unsigned char *input, int size)
stack[++top] = offset; // save offset for backtrack
#if ERRORS
#if ERRORS_PRED
stack[++top] = pc + 1; // 1st child inst address for error
stack[++top] = pc + 1; // 1st child inst address for error
#endif
if (!err_locked) {
stack[++top] = 1; err_locked = 1;
stack[++top] = 1; err_locked = 1;
}
else {
stack[++top] = 0;
stack[++top] = 0;
}
#endif
break;

case PMATCHF: // Predicate matched, match is considered failure, arg = failure address
case PNOMATF: // Predicate not matched, not match is considered failure, arg = failure address
#if ERRORS && ERRORS_PRED
Expand Down Expand Up @@ -597,13 +599,13 @@ int Parser_parse(Parser *self, const unsigned char *input, int size)
const unsigned char *mstr = self->strings[arg];
for (i = 0; i < mlen; ++i) {
if (mstr[i] == input[offset]) {
++offset;
if(input[offset++] == '\n') {++self->lineno; self->lineno_offset=offset;}
++pc;
break;
}
if ((i < mlen - 2) && (mstr[i+1] == '-')) {
if ((input[offset] >= mstr[i]) && (input[offset] <= mstr[i+2])) {
++offset;
if(input[offset++] == '\n') {++self->lineno; self->lineno_offset=offset;}
++pc;
break;
}
Expand Down Expand Up @@ -649,7 +651,7 @@ int Parser_parse(Parser *self, const unsigned char *input, int size)

// Dot
case DOT: // arg = fail addr; match any char; goto addr on failure
if (offset < size) { offset++; break; }
if (offset < size) { if(input[offset++] == '\n') {++self->lineno; self->lineno_offset=offset;} break; }
#if ERRORS && ERRORS_TERMINALS
if (!err_locked) {
Parser_expected(self,
Expand Down
2 changes: 2 additions & 0 deletions bootstrap/peg_cbyte.h
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,8 @@ typedef struct _Parser
Node *tree_root;
int max_tree_depth;
int max_stack_size;
int lineno;
int lineno_offset;
int error_offset;
int error_def;
int error_parent_def;
Expand Down
4 changes: 2 additions & 2 deletions bootstrap/peg_cbyte.rb
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ class Output
attr_reader :c, :h, :basename
def initialize(basename)
@basename = basename
@c = OutStream.new("#{basename}.c")
@c = OutStream.new("#{basename}.c")
@h = OutStream.new("#{basename}.h")
end
def close
Expand Down Expand Up @@ -232,7 +232,7 @@ def output(pg)
out.c.puts "#{pre}_str_len,"
out.c.indent -= 1
out.c.puts "};"
out.h.puts "ByteCode #{pre}_byte_code;"
out.h.puts "extern ByteCode #{pre}_byte_code;"
end
end

Expand Down
56 changes: 32 additions & 24 deletions examples/peg_parse_file.c
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@ char *read_file(char *filename, int *length_return)
input = NULL;
}

if (fd >= 0) {
if (fd >= 0) {
close(fd);
fd = -1;
}
Expand All @@ -93,51 +93,59 @@ char *read_file(char *filename, int *length_return)

int main(int argc, char *argv[])
{
unsigned char *input = NULL;
unsigned char *input = NULL;
int length = -1;
ByteCode *byte_code = NULL;
ByteCode *byte_code = NULL;
Parser *parser = NULL;
int parse_result = 0;
int ret = 0;
int arg_idx_input = 2;

#ifdef DEBUG_MEM
mtrace();
#endif

if (argc != 3) {
fprintf(stderr, "usage: %s <grammar> <file>\n", argv[0]);
if (argc < 2) {
fprintf(stderr, "usage: %s <grammar> [<file>]\n", argv[0]);
ret = 1;
goto done;
}

// Read the grammar file into input
input = (unsigned char *)read_file(argv[1], &length);
if (!input) {
fprintf(stderr, "Could not read grammar file: %s\n", argv[1]);
ret = 2;
goto done;
}
if(argc == 3) { // Grammar and input file
// Read the grammar file into input
input = (unsigned char *)read_file(argv[1], &length);
if (!input) {
fprintf(stderr, "Could not read grammar file: %s\n", argv[1]);
ret = 2;
goto done;
}

// Compile the grammar file into byte_code
// Compile the grammar file into byte_code

byte_code = Compiler_compile(input, length, &parse_result, 1);
if (!byte_code) {
fprintf(stderr, "Grammar file failed to compile. Parser returned: %d\n", parse_result);
ret = 3;
goto done;
byte_code = Compiler_compile(input, length, &parse_result, 1);
if (!byte_code) {
fprintf(stderr, "Grammar file failed to compile. Parser returned: %d\n", parse_result);
ret = 3;
goto done;
}
else {
fprintf(stderr, "Grammar file compiled successfully. Parser returned: %d\n", parse_result);
}

free(input);
}
else {
fprintf(stderr, "Grammar file compiled successfully. Parser returned: %d\n", parse_result);
arg_idx_input = 1;
byte_code = &peg_byte_code;
}

free(input);
input = NULL;
length = -1;

// Read the file to parse into input
input = (unsigned char *)read_file(argv[2], &length);
input = (unsigned char *)read_file(argv[arg_idx_input], &length);
if (!input) {
fprintf(stderr, "Could not read file: %s\n", argv[2]);
fprintf(stderr, "Could not read file: %s\n", argv[arg_idx_input]);
ret = 4;
goto done;
}
Expand All @@ -158,13 +166,13 @@ int main(int argc, char *argv[])
printf("parse failed with result: %d\n", parse_result);
Parser_print_error(parser, input);
ret = 5;
goto done;
goto done;
}

ret = 0;
done:

if (byte_code) {
if (byte_code && (argc == 3)) {
ByteCode_free(byte_code);
byte_code = NULL;
}
Expand Down
Loading