Clean up trailing whitespace
This commit is contained in:
1 parent
812703139c
commit
1628bbf95f
17 files changed
+343
-345
No files matched your search
@@ -69,7 +69,7 @@ static jv f_plus(jq_state *jq, jv input, jv a, jv b) {
|
|||||||
jv_free(b);
|
jv_free(b);
|
||||||
return a;
|
return a;
|
||||||
} else if (jv_get_kind(a) == JV_KIND_NUMBER && jv_get_kind(b) == JV_KIND_NUMBER) {
|
} else if (jv_get_kind(a) == JV_KIND_NUMBER && jv_get_kind(b) == JV_KIND_NUMBER) {
|
||||||
return jv_number(jv_number_value(a) +
|
return jv_number(jv_number_value(a) +
|
||||||
jv_number_value(b));
|
jv_number_value(b));
|
||||||
} else if (jv_get_kind(a) == JV_KIND_STRING && jv_get_kind(b) == JV_KIND_STRING) {
|
} else if (jv_get_kind(a) == JV_KIND_STRING && jv_get_kind(b) == JV_KIND_STRING) {
|
||||||
return jv_string_concat(a, b);
|
return jv_string_concat(a, b);
|
||||||
@@ -238,7 +238,7 @@ static jv f_multiply(jq_state *jq, jv input, jv a, jv b) {
|
|||||||
return jv_object_merge_recursive(a, b);
|
return jv_object_merge_recursive(a, b);
|
||||||
} else {
|
} else {
|
||||||
return type_error2(a, b, "cannot be multiplied");
|
return type_error2(a, b, "cannot be multiplied");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static jv f_divide(jq_state *jq, jv input, jv a, jv b) {
|
static jv f_divide(jq_state *jq, jv input, jv a, jv b) {
|
||||||
@@ -251,7 +251,7 @@ static jv f_divide(jq_state *jq, jv input, jv a, jv b) {
|
|||||||
return jv_string_split(a, b);
|
return jv_string_split(a, b);
|
||||||
} else {
|
} else {
|
||||||
return type_error2(a, b, "cannot be divided");
|
return type_error2(a, b, "cannot be divided");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static jv f_mod(jq_state *jq, jv input, jv a, jv b) {
|
static jv f_mod(jq_state *jq, jv input, jv a, jv b) {
|
||||||
@@ -262,7 +262,7 @@ static jv f_mod(jq_state *jq, jv input, jv a, jv b) {
|
|||||||
return jv_number((intmax_t)jv_number_value(a) % (intmax_t)jv_number_value(b));
|
return jv_number((intmax_t)jv_number_value(a) % (intmax_t)jv_number_value(b));
|
||||||
} else {
|
} else {
|
||||||
return type_error2(a, b, "cannot be divided (remainder)");
|
return type_error2(a, b, "cannot be divided (remainder)");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static jv f_equal(jq_state *jq, jv input, jv a, jv b) {
|
static jv f_equal(jq_state *jq, jv input, jv a, jv b) {
|
||||||
@@ -572,7 +572,7 @@ static jv f_sort(jq_state *jq, jv input){
|
|||||||
}
|
}
|
||||||
|
|
||||||
static jv f_sort_by_impl(jq_state *jq, jv input, jv keys) {
|
static jv f_sort_by_impl(jq_state *jq, jv input, jv keys) {
|
||||||
if (jv_get_kind(input) == JV_KIND_ARRAY &&
|
if (jv_get_kind(input) == JV_KIND_ARRAY &&
|
||||||
jv_get_kind(keys) == JV_KIND_ARRAY &&
|
jv_get_kind(keys) == JV_KIND_ARRAY &&
|
||||||
jv_array_length(jv_copy(input)) == jv_array_length(jv_copy(keys))) {
|
jv_array_length(jv_copy(input)) == jv_array_length(jv_copy(keys))) {
|
||||||
return jv_sort(input, keys);
|
return jv_sort(input, keys);
|
||||||
@@ -582,7 +582,7 @@ static jv f_sort_by_impl(jq_state *jq, jv input, jv keys) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
static jv f_group_by_impl(jq_state *jq, jv input, jv keys) {
|
static jv f_group_by_impl(jq_state *jq, jv input, jv keys) {
|
||||||
if (jv_get_kind(input) == JV_KIND_ARRAY &&
|
if (jv_get_kind(input) == JV_KIND_ARRAY &&
|
||||||
jv_get_kind(keys) == JV_KIND_ARRAY &&
|
jv_get_kind(keys) == JV_KIND_ARRAY &&
|
||||||
jv_array_length(jv_copy(input)) == jv_array_length(jv_copy(keys))) {
|
jv_array_length(jv_copy(input)) == jv_array_length(jv_copy(keys))) {
|
||||||
return jv_group(input, keys);
|
return jv_group(input, keys);
|
||||||
@@ -668,7 +668,7 @@ static jv f_match(jq_state *jq, jv input, jv regex, jv modifiers, jv testmode) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
jv_free(modarray);
|
jv_free(modarray);
|
||||||
} else if (jv_get_kind(modifiers) != JV_KIND_NULL) {
|
} else if (jv_get_kind(modifiers) != JV_KIND_NULL) {
|
||||||
// If it isn't a string or null, then it is the wrong type...
|
// If it isn't a string or null, then it is the wrong type...
|
||||||
jv_free(input);
|
jv_free(input);
|
||||||
jv_free(regex);
|
jv_free(regex);
|
||||||
@@ -695,7 +695,7 @@ static jv f_match(jq_state *jq, jv input, jv regex, jv modifiers, jv testmode) {
|
|||||||
const UChar* end = start + length;
|
const UChar* end = start + length;
|
||||||
region = onig_region_new();
|
region = onig_region_new();
|
||||||
do {
|
do {
|
||||||
onigret = onig_search(reg,
|
onigret = onig_search(reg,
|
||||||
(const UChar*)jv_string_value(input), end, /* string boundaries */
|
(const UChar*)jv_string_value(input), end, /* string boundaries */
|
||||||
start, end, /* search boundaries */
|
start, end, /* search boundaries */
|
||||||
region, ONIG_OPTION_NONE);
|
region, ONIG_OPTION_NONE);
|
||||||
@@ -1238,7 +1238,7 @@ static jv f_current_line(jq_state *jq) {
|
|||||||
#define LIBM_DDD(name) \
|
#define LIBM_DDD(name) \
|
||||||
{(cfunction_ptr)f_ ## name, "_" #name, 3},
|
{(cfunction_ptr)f_ ## name, "_" #name, 3},
|
||||||
#define LIBM_DDD_NO(name)
|
#define LIBM_DDD_NO(name)
|
||||||
|
|
||||||
static const struct cfunction function_list[] = {
|
static const struct cfunction function_list[] = {
|
||||||
#include "libm.h"
|
#include "libm.h"
|
||||||
{(cfunction_ptr)f_plus, "_plus", 3},
|
{(cfunction_ptr)f_plus, "_plus", 3},
|
||||||
@@ -1326,7 +1326,7 @@ static block bind_bytecoded_builtins(block b) {
|
|||||||
}
|
}
|
||||||
{
|
{
|
||||||
struct bytecoded_builtin builtin_def_1arg[] = {
|
struct bytecoded_builtin builtin_def_1arg[] = {
|
||||||
{"path", BLOCK(gen_op_simple(PATH_BEGIN),
|
{"path", BLOCK(gen_op_simple(PATH_BEGIN),
|
||||||
gen_call("arg", gen_noop()),
|
gen_call("arg", gen_noop()),
|
||||||
gen_op_simple(PATH_END))},
|
gen_op_simple(PATH_END))},
|
||||||
};
|
};
|
||||||
@@ -1340,14 +1340,14 @@ static block bind_bytecoded_builtins(block b) {
|
|||||||
// Note that we can now define `range` as a jq-coded function
|
// Note that we can now define `range` as a jq-coded function
|
||||||
block rangevar = gen_op_var_fresh(STOREV, "rangevar");
|
block rangevar = gen_op_var_fresh(STOREV, "rangevar");
|
||||||
block init = BLOCK(gen_op_simple(DUP), gen_call("start", gen_noop()), rangevar);
|
block init = BLOCK(gen_op_simple(DUP), gen_call("start", gen_noop()), rangevar);
|
||||||
block range = BLOCK(init,
|
block range = BLOCK(init,
|
||||||
gen_call("end", gen_noop()),
|
gen_call("end", gen_noop()),
|
||||||
gen_op_bound(RANGE, rangevar));
|
gen_op_bound(RANGE, rangevar));
|
||||||
builtins = BLOCK(builtins, gen_function("range",
|
builtins = BLOCK(builtins, gen_function("range",
|
||||||
BLOCK(gen_param("start"), gen_param("end")),
|
BLOCK(gen_param("start"), gen_param("end")),
|
||||||
range));
|
range));
|
||||||
}
|
}
|
||||||
|
|
||||||
return block_bind_referenced(builtins, b, OP_IS_CALL_PSEUDO);
|
return block_bind_referenced(builtins, b, OP_IS_CALL_PSEUDO);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+5
-5
@@ -106,10 +106,10 @@ void dump_operation(struct bytecode* bc, uint16_t* codeptr) {
|
|||||||
jv name;
|
jv name;
|
||||||
if (idx & ARG_NEWCLOSURE) {
|
if (idx & ARG_NEWCLOSURE) {
|
||||||
idx &= ~ARG_NEWCLOSURE;
|
idx &= ~ARG_NEWCLOSURE;
|
||||||
name = jv_object_get(jv_copy(getlevel(bc,level)->subfunctions[idx]->debuginfo),
|
name = jv_object_get(jv_copy(getlevel(bc,level)->subfunctions[idx]->debuginfo),
|
||||||
jv_string("name"));
|
jv_string("name"));
|
||||||
} else {
|
} else {
|
||||||
name = jv_array_get(jv_object_get(jv_copy(getlevel(bc,level)->debuginfo),
|
name = jv_array_get(jv_object_get(jv_copy(getlevel(bc,level)->debuginfo),
|
||||||
jv_string("params")), idx);
|
jv_string("params")), idx);
|
||||||
}
|
}
|
||||||
printf(" %s:%d",
|
printf(" %s:%d",
|
||||||
@@ -133,8 +133,8 @@ void dump_operation(struct bytecode* bc, uint16_t* codeptr) {
|
|||||||
} else if (op->flags & OP_HAS_VARIABLE) {
|
} else if (op->flags & OP_HAS_VARIABLE) {
|
||||||
uint16_t v = bc->code[pc++];
|
uint16_t v = bc->code[pc++];
|
||||||
jv name = jv_array_get(jv_object_get(jv_copy(getlevel(bc,imm)->debuginfo), jv_string("locals")), v);
|
jv name = jv_array_get(jv_object_get(jv_copy(getlevel(bc,imm)->debuginfo), jv_string("locals")), v);
|
||||||
printf(" $%s:%d",
|
printf(" $%s:%d",
|
||||||
jv_string_value(name),
|
jv_string_value(name),
|
||||||
v);
|
v);
|
||||||
jv_free(name);
|
jv_free(name);
|
||||||
if (imm) {
|
if (imm) {
|
||||||
@@ -143,7 +143,7 @@ void dump_operation(struct bytecode* bc, uint16_t* codeptr) {
|
|||||||
} else {
|
} else {
|
||||||
printf(" %d", imm);
|
printf(" %d", imm);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void bytecode_free(struct bytecode* bc) {
|
void bytecode_free(struct bytecode* bc) {
|
||||||
|
|||||||
+1
-1
@@ -11,7 +11,7 @@ typedef enum {
|
|||||||
} opcode;
|
} opcode;
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
NUM_OPCODES =
|
NUM_OPCODES =
|
||||||
#define OP(name, imm, in, out) +1
|
#define OP(name, imm, in, out) +1
|
||||||
#include "opcode_list.h"
|
#include "opcode_list.h"
|
||||||
#undef OP
|
#undef OP
|
||||||
|
|||||||
@@ -14,7 +14,7 @@
|
|||||||
/*
|
/*
|
||||||
The intermediate representation for jq filters is as a sequence of
|
The intermediate representation for jq filters is as a sequence of
|
||||||
struct inst, which form a doubly-linked list via the next and prev
|
struct inst, which form a doubly-linked list via the next and prev
|
||||||
pointers.
|
pointers.
|
||||||
|
|
||||||
A "block" represents a sequence of "struct inst", which may be
|
A "block" represents a sequence of "struct inst", which may be
|
||||||
empty.
|
empty.
|
||||||
@@ -28,7 +28,7 @@ struct inst {
|
|||||||
struct inst* prev;
|
struct inst* prev;
|
||||||
|
|
||||||
opcode op;
|
opcode op;
|
||||||
|
|
||||||
struct {
|
struct {
|
||||||
uint16_t intval;
|
uint16_t intval;
|
||||||
struct inst* target;
|
struct inst* target;
|
||||||
@@ -45,7 +45,7 @@ struct inst {
|
|||||||
// inst->bound_by = NULL - Unbound free variable
|
// inst->bound_by = NULL - Unbound free variable
|
||||||
// inst->bound_by = inst - This instruction binds a variable
|
// inst->bound_by = inst - This instruction binds a variable
|
||||||
// inst->bound_by = other - Uses variable bound by other instruction
|
// inst->bound_by = other - Uses variable bound by other instruction
|
||||||
// Unbound instructions (references to other things that may or may not
|
// Unbound instructions (references to other things that may or may not
|
||||||
// exist) are created by "gen_foo_unbound", and bindings are created by
|
// exist) are created by "gen_foo_unbound", and bindings are created by
|
||||||
// block_bind(definition, body), which binds all instructions in
|
// block_bind(definition, body), which binds all instructions in
|
||||||
// body which are unboudn and refer to "definition" by name.
|
// body which are unboudn and refer to "definition" by name.
|
||||||
@@ -288,7 +288,7 @@ static int block_count_actuals(block b) {
|
|||||||
for (inst* i = b.first; i; i = i->next) {
|
for (inst* i = b.first; i; i = i->next) {
|
||||||
switch (i->op) {
|
switch (i->op) {
|
||||||
default: assert(0 && "Unknown function type"); break;
|
default: assert(0 && "Unknown function type"); break;
|
||||||
case CLOSURE_CREATE:
|
case CLOSURE_CREATE:
|
||||||
case CLOSURE_PARAM:
|
case CLOSURE_PARAM:
|
||||||
case CLOSURE_CREATE_C:
|
case CLOSURE_CREATE_C:
|
||||||
args++;
|
args++;
|
||||||
@@ -462,7 +462,7 @@ block block_drop_unreferenced(block body) {
|
|||||||
|
|
||||||
jv block_take_imports(block* body) {
|
jv block_take_imports(block* body) {
|
||||||
jv imports = jv_array();
|
jv imports = jv_array();
|
||||||
|
|
||||||
inst* top = NULL;
|
inst* top = NULL;
|
||||||
if (body->first && body->first->op == TOP) {
|
if (body->first && body->first->op == TOP) {
|
||||||
top = block_take(body);
|
top = block_take(body);
|
||||||
@@ -808,7 +808,7 @@ block gen_condbranch(block iftrue, block iffalse) {
|
|||||||
|
|
||||||
block gen_and(block a, block b) {
|
block gen_and(block a, block b) {
|
||||||
// a and b = if a then (if b then true else false) else false
|
// a and b = if a then (if b then true else false) else false
|
||||||
return BLOCK(gen_op_simple(DUP), a,
|
return BLOCK(gen_op_simple(DUP), a,
|
||||||
gen_condbranch(BLOCK(gen_op_simple(POP),
|
gen_condbranch(BLOCK(gen_op_simple(POP),
|
||||||
b,
|
b,
|
||||||
gen_condbranch(gen_const(jv_true()),
|
gen_condbranch(gen_const(jv_true()),
|
||||||
@@ -870,7 +870,7 @@ static block gen_wildvar_binding(block var, const char* name, block body) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
block gen_cond(block cond, block iftrue, block iffalse) {
|
block gen_cond(block cond, block iftrue, block iffalse) {
|
||||||
return BLOCK(gen_op_simple(DUP), cond,
|
return BLOCK(gen_op_simple(DUP), cond,
|
||||||
gen_condbranch(BLOCK(gen_op_simple(POP), iftrue),
|
gen_condbranch(BLOCK(gen_op_simple(POP), iftrue),
|
||||||
BLOCK(gen_op_simple(POP), iffalse)));
|
BLOCK(gen_op_simple(POP), iffalse)));
|
||||||
}
|
}
|
||||||
@@ -988,7 +988,7 @@ static int expand_call_arglist(block* b) {
|
|||||||
// We expand the argument list as a series of instructions
|
// We expand the argument list as a series of instructions
|
||||||
switch (curr->bound_by->op) {
|
switch (curr->bound_by->op) {
|
||||||
default: assert(0 && "Unknown function type"); break;
|
default: assert(0 && "Unknown function type"); break;
|
||||||
case CLOSURE_CREATE:
|
case CLOSURE_CREATE:
|
||||||
case CLOSURE_PARAM: {
|
case CLOSURE_PARAM: {
|
||||||
block callargs = gen_noop();
|
block callargs = gen_noop();
|
||||||
for (inst* i; (i = block_take(&curr->arglist));) {
|
for (inst* i; (i = block_take(&curr->arglist));) {
|
||||||
@@ -1137,7 +1137,7 @@ static int compile(struct bytecode* bc, block b) {
|
|||||||
curr->bound_by->op == CLOSURE_PARAM);
|
curr->bound_by->op == CLOSURE_PARAM);
|
||||||
code[pos++] = (uint16_t)curr->imm.intval;
|
code[pos++] = (uint16_t)curr->imm.intval;
|
||||||
code[pos++] = nesting_level(bc, curr->bound_by);
|
code[pos++] = nesting_level(bc, curr->bound_by);
|
||||||
code[pos++] = curr->bound_by->imm.intval |
|
code[pos++] = curr->bound_by->imm.intval |
|
||||||
(curr->bound_by->op == CLOSURE_CREATE ? ARG_NEWCLOSURE : 0);
|
(curr->bound_by->op == CLOSURE_CREATE ? ARG_NEWCLOSURE : 0);
|
||||||
for (inst* arg = curr->arglist.first; arg; arg = arg->next) {
|
for (inst* arg = curr->arglist.first; arg; arg = arg->next) {
|
||||||
assert(arg->op == CLOSURE_REF && arg->bound_by->op == CLOSURE_CREATE);
|
assert(arg->op == CLOSURE_REF && arg->bound_by->op == CLOSURE_CREATE);
|
||||||
|
|||||||
+1
-1
@@ -81,7 +81,7 @@ static stack_ptr* stack_block_next(struct stack* s, stack_ptr p) {
|
|||||||
static void stack_reallocate(struct stack* s, size_t sz) {
|
static void stack_reallocate(struct stack* s, size_t sz) {
|
||||||
int old_mem_length = -(s->bound) + ALIGNMENT;
|
int old_mem_length = -(s->bound) + ALIGNMENT;
|
||||||
char* old_mem_start = s->mem_end - old_mem_length;
|
char* old_mem_start = s->mem_end - old_mem_length;
|
||||||
|
|
||||||
int new_mem_length = align_round_up((old_mem_length + sz + 256) * 2);
|
int new_mem_length = align_round_up((old_mem_length + sz + 256) * 2);
|
||||||
char* new_mem_start = jv_mem_realloc(old_mem_start, new_mem_length);
|
char* new_mem_start = jv_mem_realloc(old_mem_start, new_mem_length);
|
||||||
memmove(new_mem_start + (new_mem_length - old_mem_length),
|
memmove(new_mem_start + (new_mem_length - old_mem_length),
|
||||||
|
|||||||
@@ -123,7 +123,7 @@ static struct closure make_closure(struct jq_state* jq, uint16_t* pc) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static struct frame* frame_push(struct jq_state* jq, struct closure callee,
|
static struct frame* frame_push(struct jq_state* jq, struct closure callee,
|
||||||
uint16_t* argdef, int nargs) {
|
uint16_t* argdef, int nargs) {
|
||||||
stack_ptr new_frame_idx = stack_push_block(&jq->stk, jq->curr_frame, frame_size(callee.bc));
|
stack_ptr new_frame_idx = stack_push_block(&jq->stk, jq->curr_frame, frame_size(callee.bc));
|
||||||
struct frame* new_frame = stack_block(&jq->stk, new_frame_idx);
|
struct frame* new_frame = stack_block(&jq->stk, new_frame_idx);
|
||||||
@@ -208,7 +208,7 @@ void stack_save(jq_state *jq, uint16_t* retaddr, struct stack_pos sp){
|
|||||||
struct forkpoint* fork = stack_block(&jq->stk, jq->fork_top);
|
struct forkpoint* fork = stack_block(&jq->stk, jq->fork_top);
|
||||||
fork->saved_data_stack = jq->stk_top;
|
fork->saved_data_stack = jq->stk_top;
|
||||||
fork->saved_curr_frame = jq->curr_frame;
|
fork->saved_curr_frame = jq->curr_frame;
|
||||||
fork->path_len =
|
fork->path_len =
|
||||||
jv_get_kind(jq->path) == JV_KIND_ARRAY ? jv_array_length(jv_copy(jq->path)) : 0;
|
jv_get_kind(jq->path) == JV_KIND_ARRAY ? jv_array_length(jv_copy(jq->path)) : 0;
|
||||||
fork->subexp_nest = jq->subexp_nest;
|
fork->subexp_nest = jq->subexp_nest;
|
||||||
fork->return_address = retaddr;
|
fork->return_address = retaddr;
|
||||||
@@ -397,7 +397,7 @@ jv jq_next(jq_state *jq) {
|
|||||||
stack_push(jq, b);
|
stack_push(jq, b);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
case POP: {
|
case POP: {
|
||||||
jv_free(stack_pop(jq));
|
jv_free(stack_pop(jq));
|
||||||
break;
|
break;
|
||||||
@@ -604,8 +604,8 @@ jv jq_next(jq_state *jq) {
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
case EACH:
|
case EACH:
|
||||||
case EACH_OPT:
|
case EACH_OPT:
|
||||||
stack_push(jq, jv_number(-1));
|
stack_push(jq, jv_number(-1));
|
||||||
// fallthrough
|
// fallthrough
|
||||||
case ON_BACKTRACK(EACH):
|
case ON_BACKTRACK(EACH):
|
||||||
@@ -708,7 +708,7 @@ jv jq_next(jq_state *jq) {
|
|||||||
pc += offset;
|
pc += offset;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
case CALL_BUILTIN: {
|
case CALL_BUILTIN: {
|
||||||
int nargs = *pc++;
|
int nargs = *pc++;
|
||||||
jv top = stack_pop(jq);
|
jv top = stack_pop(jq);
|
||||||
@@ -733,7 +733,7 @@ jv jq_next(jq_state *jq) {
|
|||||||
// because the compiler should not generate this error.
|
// because the compiler should not generate this error.
|
||||||
default: return jv_invalid_with_msg(jv_string("Function takes too many arguments"));
|
default: return jv_invalid_with_msg(jv_string("Function takes too many arguments"));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (jv_is_valid(top)) {
|
if (jv_is_valid(top)) {
|
||||||
stack_push(jq, top);
|
stack_push(jq, top);
|
||||||
} else if (jv_invalid_has_msg(jv_copy(top))) {
|
} else if (jv_invalid_has_msg(jv_copy(top))) {
|
||||||
@@ -908,7 +908,7 @@ void jq_set_nomem_handler(jq_state *jq, void (*nomem_handler)(void *), void *dat
|
|||||||
void jq_start(jq_state *jq, jv input, int flags) {
|
void jq_start(jq_state *jq, jv input, int flags) {
|
||||||
jv_nomem_handler(jq->nomem_handler, jq->nomem_handler_data);
|
jv_nomem_handler(jq->nomem_handler, jq->nomem_handler_data);
|
||||||
jq_reset(jq);
|
jq_reset(jq);
|
||||||
|
|
||||||
struct closure top = {jq->bc, -1};
|
struct closure top = {jq->bc, -1};
|
||||||
struct frame* top_frame = frame_push(jq, top, 0, 0);
|
struct frame* top_frame = frame_push(jq, top, 0, 0);
|
||||||
top_frame->retdata = 0;
|
top_frame->retdata = 0;
|
||||||
|
|||||||
@@ -199,7 +199,7 @@ static void jv_test() {
|
|||||||
assert(jv_get_kind(a) == JV_KIND_ARRAY);
|
assert(jv_get_kind(a) == JV_KIND_ARRAY);
|
||||||
assert(jv_array_length(jv_copy(a)) == 0);
|
assert(jv_array_length(jv_copy(a)) == 0);
|
||||||
assert(jv_array_length(jv_copy(a)) == 0);
|
assert(jv_array_length(jv_copy(a)) == 0);
|
||||||
|
|
||||||
a = jv_array_append(a, jv_number(42));
|
a = jv_array_append(a, jv_number(42));
|
||||||
assert(jv_array_length(jv_copy(a)) == 1);
|
assert(jv_array_length(jv_copy(a)) == 1);
|
||||||
assert(jv_number_value(jv_array_get(jv_copy(a), 0)) == 42);
|
assert(jv_number_value(jv_array_get(jv_copy(a), 0)) == 42);
|
||||||
@@ -300,13 +300,13 @@ static void jv_test() {
|
|||||||
jv_free(shortstr);
|
jv_free(shortstr);
|
||||||
jv_free(longstr);
|
jv_free(longstr);
|
||||||
|
|
||||||
|
|
||||||
char a1s[] = "hello", a2s[] = "hello", bs[] = "goodbye";
|
char a1s[] = "hello", a2s[] = "hello", bs[] = "goodbye";
|
||||||
jv a1 = jv_string(a1s), a2 = jv_string(a2s), b = jv_string(bs);
|
jv a1 = jv_string(a1s), a2 = jv_string(a2s), b = jv_string(bs);
|
||||||
assert(jv_equal(jv_copy(a1), jv_copy(a2)));
|
assert(jv_equal(jv_copy(a1), jv_copy(a2)));
|
||||||
assert(jv_equal(jv_copy(a2), jv_copy(a1)));
|
assert(jv_equal(jv_copy(a2), jv_copy(a1)));
|
||||||
assert(!jv_equal(jv_copy(a1), jv_copy(b)));
|
assert(!jv_equal(jv_copy(a1), jv_copy(b)));
|
||||||
|
|
||||||
assert(jv_string_hash(jv_copy(a1)) == jv_string_hash(jv_copy(a1)));
|
assert(jv_string_hash(jv_copy(a1)) == jv_string_hash(jv_copy(a1)));
|
||||||
assert(jv_string_hash(jv_copy(a1)) == jv_string_hash(jv_copy(a2)));
|
assert(jv_string_hash(jv_copy(a1)) == jv_string_hash(jv_copy(a2)));
|
||||||
assert(jv_string_hash(jv_copy(b)) != jv_string_hash(jv_copy(a1)));
|
assert(jv_string_hash(jv_copy(b)) != jv_string_hash(jv_copy(a1)));
|
||||||
|
|||||||
@@ -84,7 +84,7 @@ jv jv_bool(int x) {
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
* Invalid objects, with optional error messages
|
* Invalid objects, with optional error messages
|
||||||
*/
|
*/
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
jv_refcnt refcnt;
|
jv_refcnt refcnt;
|
||||||
@@ -248,7 +248,7 @@ static jv* jvp_array_write(jv* a, int i) {
|
|||||||
jvp_array* new_array = jvp_array_alloc(ARRAY_SIZE_ROUND_UP(new_length));
|
jvp_array* new_array = jvp_array_alloc(ARRAY_SIZE_ROUND_UP(new_length));
|
||||||
int j;
|
int j;
|
||||||
for (j = 0; j < jvp_array_length(*a); j++) {
|
for (j = 0; j < jvp_array_length(*a); j++) {
|
||||||
new_array->elements[j] =
|
new_array->elements[j] =
|
||||||
jv_copy(array->elements[j + jvp_array_offset(*a)]);
|
jv_copy(array->elements[j + jvp_array_offset(*a)]);
|
||||||
}
|
}
|
||||||
for (; j < new_length; j++) {
|
for (; j < new_length; j++) {
|
||||||
@@ -263,13 +263,13 @@ static jv* jvp_array_write(jv* a, int i) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
static int jvp_array_equal(jv a, jv b) {
|
static int jvp_array_equal(jv a, jv b) {
|
||||||
if (jvp_array_length(a) != jvp_array_length(b))
|
if (jvp_array_length(a) != jvp_array_length(b))
|
||||||
return 0;
|
return 0;
|
||||||
if (jvp_array_ptr(a) == jvp_array_ptr(b) &&
|
if (jvp_array_ptr(a) == jvp_array_ptr(b) &&
|
||||||
jvp_array_offset(a) == jvp_array_offset(b))
|
jvp_array_offset(a) == jvp_array_offset(b))
|
||||||
return 1;
|
return 1;
|
||||||
for (int i=0; i<jvp_array_length(a); i++) {
|
for (int i=0; i<jvp_array_length(a); i++) {
|
||||||
if (!jv_equal(jv_copy(*jvp_array_read(a, i)),
|
if (!jv_equal(jv_copy(*jvp_array_read(a, i)),
|
||||||
jv_copy(*jvp_array_read(b, i))))
|
jv_copy(*jvp_array_read(b, i))))
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@@ -292,7 +292,7 @@ static jv jvp_array_slice(jv a, int start, int end) {
|
|||||||
int len = jvp_array_length(a);
|
int len = jvp_array_length(a);
|
||||||
jvp_clamp_slice_params(len, &start, &end);
|
jvp_clamp_slice_params(len, &start, &end);
|
||||||
assert(0 <= start && start <= end && end <= len);
|
assert(0 <= start && start <= end && end <= len);
|
||||||
|
|
||||||
// FIXME: maybe slice should reallocate if the slice is small enough
|
// FIXME: maybe slice should reallocate if the slice is small enough
|
||||||
if (start == end) {
|
if (start == end) {
|
||||||
jv_free(a);
|
jv_free(a);
|
||||||
@@ -427,7 +427,7 @@ jv jv_array_indexes(jv a, jv b) {
|
|||||||
typedef struct {
|
typedef struct {
|
||||||
jv_refcnt refcnt;
|
jv_refcnt refcnt;
|
||||||
uint32_t hash;
|
uint32_t hash;
|
||||||
// high 31 bits are length, low bit is a flag
|
// high 31 bits are length, low bit is a flag
|
||||||
// indicating whether hash has been computed.
|
// indicating whether hash has been computed.
|
||||||
uint32_t length_hashed;
|
uint32_t length_hashed;
|
||||||
uint32_t alloc_length;
|
uint32_t alloc_length;
|
||||||
@@ -511,7 +511,7 @@ static uint32_t jvp_string_remaining_space(jvp_string* s) {
|
|||||||
static jv jvp_string_append(jv string, const char* data, uint32_t len) {
|
static jv jvp_string_append(jv string, const char* data, uint32_t len) {
|
||||||
jvp_string* s = jvp_string_ptr(string);
|
jvp_string* s = jvp_string_ptr(string);
|
||||||
uint32_t currlen = jvp_string_length(s);
|
uint32_t currlen = jvp_string_length(s);
|
||||||
|
|
||||||
if (jvp_refcnt_unshared(string.u.ptr) &&
|
if (jvp_refcnt_unshared(string.u.ptr) &&
|
||||||
jvp_string_remaining_space(s) >= len) {
|
jvp_string_remaining_space(s) >= len) {
|
||||||
// the next string fits at the end of a
|
// the next string fits at the end of a
|
||||||
@@ -542,7 +542,7 @@ static uint32_t rotl32 (uint32_t x, int8_t r){
|
|||||||
|
|
||||||
static uint32_t jvp_string_hash(jv jstr) {
|
static uint32_t jvp_string_hash(jv jstr) {
|
||||||
jvp_string* str = jvp_string_ptr(jstr);
|
jvp_string* str = jvp_string_ptr(jstr);
|
||||||
if (str->length_hashed & 1)
|
if (str->length_hashed & 1)
|
||||||
return str->hash;
|
return str->hash;
|
||||||
|
|
||||||
/* The following is based on MurmurHash3.
|
/* The following is based on MurmurHash3.
|
||||||
@@ -561,13 +561,13 @@ static uint32_t jvp_string_hash(jv jstr) {
|
|||||||
|
|
||||||
for(int i = -nblocks; i; i++) {
|
for(int i = -nblocks; i; i++) {
|
||||||
uint32_t k1 = blocks[i]; //FIXME: endianness/alignment
|
uint32_t k1 = blocks[i]; //FIXME: endianness/alignment
|
||||||
|
|
||||||
k1 *= c1;
|
k1 *= c1;
|
||||||
k1 = rotl32(k1,15);
|
k1 = rotl32(k1,15);
|
||||||
k1 *= c2;
|
k1 *= c2;
|
||||||
|
|
||||||
h1 ^= k1;
|
h1 ^= k1;
|
||||||
h1 = rotl32(h1,13);
|
h1 = rotl32(h1,13);
|
||||||
h1 = h1*5+0xe6546b64;
|
h1 = h1*5+0xe6546b64;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -611,7 +611,7 @@ static int jvp_string_equal(jv a, jv b) {
|
|||||||
|
|
||||||
jv jv_string_sized(const char* str, int len) {
|
jv jv_string_sized(const char* str, int len) {
|
||||||
return
|
return
|
||||||
jvp_utf8_is_valid(str, str+len) ?
|
jvp_utf8_is_valid(str, str+len) ?
|
||||||
jvp_string_new(str, len) :
|
jvp_string_new(str, len) :
|
||||||
jvp_string_copy_replace_bad(str, len);
|
jvp_string_copy_replace_bad(str, len);
|
||||||
}
|
}
|
||||||
@@ -790,7 +790,7 @@ jv jv_string_slice(jv j, int start, int end) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
jv jv_string_concat(jv a, jv b) {
|
jv jv_string_concat(jv a, jv b) {
|
||||||
a = jvp_string_append(a, jv_string_value(b),
|
a = jvp_string_append(a, jv_string_value(b),
|
||||||
jvp_string_length(jvp_string_ptr(b)));
|
jvp_string_length(jvp_string_ptr(b)));
|
||||||
jv_free(b);
|
jv_free(b);
|
||||||
return a;
|
return a;
|
||||||
@@ -873,7 +873,7 @@ static jv jvp_object_new(int size) {
|
|||||||
// size must be a power of two
|
// size must be a power of two
|
||||||
assert(size > 0 && (size & (size - 1)) == 0);
|
assert(size > 0 && (size & (size - 1)) == 0);
|
||||||
|
|
||||||
jvp_object* obj = jv_mem_alloc(sizeof(jvp_object) +
|
jvp_object* obj = jv_mem_alloc(sizeof(jvp_object) +
|
||||||
sizeof(struct object_slot) * size +
|
sizeof(struct object_slot) * size +
|
||||||
sizeof(int) * (size * 2));
|
sizeof(int) * (size * 2));
|
||||||
obj->refcnt.count = 1;
|
obj->refcnt.count = 1;
|
||||||
@@ -927,8 +927,8 @@ static struct object_slot* jvp_object_next_slot(jv object, struct object_slot* s
|
|||||||
|
|
||||||
static struct object_slot* jvp_object_find_slot(jv object, jv keystr, int* bucket) {
|
static struct object_slot* jvp_object_find_slot(jv object, jv keystr, int* bucket) {
|
||||||
uint32_t hash = jvp_string_hash(keystr);
|
uint32_t hash = jvp_string_hash(keystr);
|
||||||
for (struct object_slot* curr = jvp_object_get_slot(object, *bucket);
|
for (struct object_slot* curr = jvp_object_get_slot(object, *bucket);
|
||||||
curr;
|
curr;
|
||||||
curr = jvp_object_next_slot(object, curr)) {
|
curr = jvp_object_next_slot(object, curr)) {
|
||||||
if (curr->hash == hash && jvp_string_equal(keystr, curr->string)) {
|
if (curr->hash == hash && jvp_string_equal(keystr, curr->string)) {
|
||||||
return curr;
|
return curr;
|
||||||
@@ -1046,8 +1046,8 @@ static int jvp_object_delete(jv* object, jv key) {
|
|||||||
int* bucket = jvp_object_find_bucket(*object, key);
|
int* bucket = jvp_object_find_bucket(*object, key);
|
||||||
int* prev_ptr = bucket;
|
int* prev_ptr = bucket;
|
||||||
uint32_t hash = jvp_string_hash(key);
|
uint32_t hash = jvp_string_hash(key);
|
||||||
for (struct object_slot* curr = jvp_object_get_slot(*object, *bucket);
|
for (struct object_slot* curr = jvp_object_get_slot(*object, *bucket);
|
||||||
curr;
|
curr;
|
||||||
curr = jvp_object_next_slot(*object, curr)) {
|
curr = jvp_object_next_slot(*object, curr)) {
|
||||||
if (hash == curr->hash && jvp_string_equal(key, curr->string)) {
|
if (hash == curr->hash && jvp_string_equal(key, curr->string)) {
|
||||||
*prev_ptr = curr->next;
|
*prev_ptr = curr->next;
|
||||||
@@ -1201,7 +1201,7 @@ int jv_object_iter_next(jv object, int iter) {
|
|||||||
struct object_slot* slot;
|
struct object_slot* slot;
|
||||||
do {
|
do {
|
||||||
iter++;
|
iter++;
|
||||||
if (iter >= jvp_object_size(object))
|
if (iter >= jvp_object_size(object))
|
||||||
return ITER_FINISHED;
|
return ITER_FINISHED;
|
||||||
slot = jvp_object_get_slot(object, iter);
|
slot = jvp_object_get_slot(object, iter);
|
||||||
} while (jv_get_kind(slot->string) == JV_KIND_NULL);
|
} while (jv_get_kind(slot->string) == JV_KIND_NULL);
|
||||||
@@ -1224,8 +1224,8 @@ jv jv_object_iter_value(jv object, int iter) {
|
|||||||
* Memory management
|
* Memory management
|
||||||
*/
|
*/
|
||||||
jv jv_copy(jv j) {
|
jv jv_copy(jv j) {
|
||||||
if (jv_get_kind(j) == JV_KIND_ARRAY ||
|
if (jv_get_kind(j) == JV_KIND_ARRAY ||
|
||||||
jv_get_kind(j) == JV_KIND_STRING ||
|
jv_get_kind(j) == JV_KIND_STRING ||
|
||||||
jv_get_kind(j) == JV_KIND_OBJECT ||
|
jv_get_kind(j) == JV_KIND_OBJECT ||
|
||||||
(jv_get_kind(j) == JV_KIND_INVALID && j.u.ptr != 0)) {
|
(jv_get_kind(j) == JV_KIND_INVALID && j.u.ptr != 0)) {
|
||||||
jvp_refcnt_inc(j.u.ptr);
|
jvp_refcnt_inc(j.u.ptr);
|
||||||
|
|||||||
@@ -154,7 +154,7 @@ jv jv_object_iter_value(jv, int);
|
|||||||
#define JV_OBJECT_IDX(_1,_2,_3,_4,_5,_6,_7,_8,NAME,...) NAME
|
#define JV_OBJECT_IDX(_1,_2,_3,_4,_5,_6,_7,_8,NAME,...) NAME
|
||||||
#define JV_OBJECT(...) \
|
#define JV_OBJECT(...) \
|
||||||
JV_OBJECT_IDX(__VA_ARGS__, JV_OBJECT_8, JV_OBJECT_7, JV_OBJECT_6, JV_OBJECT_5, JV_OBJECT_4, JV_OBJECT_3, JV_OBJECT_2, JV_OBJECT_1)(__VA_ARGS__)
|
JV_OBJECT_IDX(__VA_ARGS__, JV_OBJECT_8, JV_OBJECT_7, JV_OBJECT_6, JV_OBJECT_5, JV_OBJECT_4, JV_OBJECT_3, JV_OBJECT_2, JV_OBJECT_1)(__VA_ARGS__)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int jv_get_refcnt(jv);
|
int jv_get_refcnt(jv);
|
||||||
|
|||||||
@@ -88,9 +88,9 @@ jv jv_get(jv t, jv k) {
|
|||||||
}
|
}
|
||||||
} else if (jv_get_kind(t) == JV_KIND_ARRAY && jv_get_kind(k) == JV_KIND_ARRAY) {
|
} else if (jv_get_kind(t) == JV_KIND_ARRAY && jv_get_kind(k) == JV_KIND_ARRAY) {
|
||||||
v = jv_array_indexes(t, k);
|
v = jv_array_indexes(t, k);
|
||||||
} else if (jv_get_kind(t) == JV_KIND_NULL &&
|
} else if (jv_get_kind(t) == JV_KIND_NULL &&
|
||||||
(jv_get_kind(k) == JV_KIND_STRING ||
|
(jv_get_kind(k) == JV_KIND_STRING ||
|
||||||
jv_get_kind(k) == JV_KIND_NUMBER ||
|
jv_get_kind(k) == JV_KIND_NUMBER ||
|
||||||
jv_get_kind(k) == JV_KIND_OBJECT)) {
|
jv_get_kind(k) == JV_KIND_OBJECT)) {
|
||||||
jv_free(t);
|
jv_free(t);
|
||||||
jv_free(k);
|
jv_free(k);
|
||||||
@@ -123,7 +123,7 @@ jv jv_set(jv t, jv k, jv v) {
|
|||||||
return v;
|
return v;
|
||||||
}
|
}
|
||||||
int isnull = jv_get_kind(t) == JV_KIND_NULL;
|
int isnull = jv_get_kind(t) == JV_KIND_NULL;
|
||||||
if (jv_get_kind(k) == JV_KIND_STRING &&
|
if (jv_get_kind(k) == JV_KIND_STRING &&
|
||||||
(jv_get_kind(t) == JV_KIND_OBJECT || isnull)) {
|
(jv_get_kind(t) == JV_KIND_OBJECT || isnull)) {
|
||||||
if (isnull) t = jv_object();
|
if (isnull) t = jv_object();
|
||||||
t = jv_object_set(t, k, v);
|
t = jv_object_set(t, k, v);
|
||||||
@@ -214,7 +214,7 @@ jv jv_has(jv t, jv k) {
|
|||||||
jv jv_dels(jv t, jv keys) {
|
jv jv_dels(jv t, jv keys) {
|
||||||
assert(jv_get_kind(keys) == JV_KIND_ARRAY);
|
assert(jv_get_kind(keys) == JV_KIND_ARRAY);
|
||||||
assert(jv_is_valid(t));
|
assert(jv_is_valid(t));
|
||||||
|
|
||||||
if (jv_get_kind(t) == JV_KIND_NULL || jv_array_length(jv_copy(keys)) == 0) {
|
if (jv_get_kind(t) == JV_KIND_NULL || jv_array_length(jv_copy(keys)) == 0) {
|
||||||
// no change
|
// no change
|
||||||
} else if (jv_get_kind(t) == JV_KIND_ARRAY) {
|
} else if (jv_get_kind(t) == JV_KIND_ARRAY) {
|
||||||
@@ -285,7 +285,7 @@ jv jv_dels(jv t, jv keys) {
|
|||||||
jv_free(k);
|
jv_free(k);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
t = jv_object_delete(t, k);
|
t = jv_object_delete(t, k);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
jv err = jv_invalid_with_msg(jv_string_fmt("Cannot delete fields from %s",
|
jv err = jv_invalid_with_msg(jv_string_fmt("Cannot delete fields from %s",
|
||||||
@@ -316,7 +316,7 @@ jv jv_setpath(jv root, jv path, jv value) {
|
|||||||
}
|
}
|
||||||
jv pathcurr = jv_array_get(jv_copy(path), 0);
|
jv pathcurr = jv_array_get(jv_copy(path), 0);
|
||||||
jv pathrest = jv_array_slice(path, 1, jv_array_length(jv_copy(path)));
|
jv pathrest = jv_array_slice(path, 1, jv_array_length(jv_copy(path)));
|
||||||
return jv_set(root, pathcurr,
|
return jv_set(root, pathcurr,
|
||||||
jv_setpath(jv_get(jv_copy(root), jv_copy(pathcurr)), pathrest, value));
|
jv_setpath(jv_get(jv_copy(root), jv_copy(pathcurr)), pathrest, value));
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -382,7 +382,7 @@ static jv delpaths_sorted(jv object, jv paths, int start) {
|
|||||||
jv_free(paths);
|
jv_free(paths);
|
||||||
if (jv_is_valid(object))
|
if (jv_is_valid(object))
|
||||||
object = jv_dels(object, delkeys);
|
object = jv_dels(object, delkeys);
|
||||||
else
|
else
|
||||||
jv_free(delkeys);
|
jv_free(delkeys);
|
||||||
return object;
|
return object;
|
||||||
}
|
}
|
||||||
@@ -488,7 +488,7 @@ int jv_cmp(jv a, jv b) {
|
|||||||
|
|
||||||
case JV_KIND_NUMBER: {
|
case JV_KIND_NUMBER: {
|
||||||
double da = jv_number_value(a), db = jv_number_value(b);
|
double da = jv_number_value(a), db = jv_number_value(b);
|
||||||
|
|
||||||
// handle NaN as though it were null
|
// handle NaN as though it were null
|
||||||
if (da != da) r = jv_cmp(jv_null(), jv_number(db));
|
if (da != da) r = jv_cmp(jv_null(), jv_number(db));
|
||||||
else if (db != db) r = jv_cmp(jv_number(da), jv_null());
|
else if (db != db) r = jv_cmp(jv_number(da), jv_null());
|
||||||
|
|||||||
@@ -525,7 +525,7 @@ void jvp_dtoa_context_init(struct dtoa_context* C) {
|
|||||||
}
|
}
|
||||||
C->p5s = 0;
|
C->p5s = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static Bigint *
|
static Bigint *
|
||||||
Balloc(struct dtoa_context* C, int k)
|
Balloc(struct dtoa_context* C, int k)
|
||||||
{
|
{
|
||||||
|
|||||||
+8
-8
@@ -43,13 +43,13 @@ struct jv_parser {
|
|||||||
enum last_seen last_seen; // streamer
|
enum last_seen last_seen; // streamer
|
||||||
jv output; // streamer
|
jv output; // streamer
|
||||||
jv next; // both
|
jv next; // both
|
||||||
|
|
||||||
char* tokenbuf;
|
char* tokenbuf;
|
||||||
int tokenpos;
|
int tokenpos;
|
||||||
int tokenlen;
|
int tokenlen;
|
||||||
|
|
||||||
int line, column;
|
int line, column;
|
||||||
|
|
||||||
struct dtoa_context dtoa;
|
struct dtoa_context dtoa;
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
@@ -102,7 +102,7 @@ static void parser_reset(struct jv_parser* p) {
|
|||||||
p->output = jv_invalid();
|
p->output = jv_invalid();
|
||||||
jv_free(p->next);
|
jv_free(p->next);
|
||||||
p->next = jv_invalid();
|
p->next = jv_invalid();
|
||||||
for (int i=0; i<p->stackpos; i++)
|
for (int i=0; i<p->stackpos; i++)
|
||||||
jv_free(p->stack[i]);
|
jv_free(p->stack[i]);
|
||||||
p->stackpos = 0;
|
p->stackpos = 0;
|
||||||
p->tokenpos = 0;
|
p->tokenpos = 0;
|
||||||
@@ -157,7 +157,7 @@ static pfunc parse_token(struct jv_parser* p, char ch) {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case ':':
|
case ':':
|
||||||
if (!jv_is_valid(p->next))
|
if (!jv_is_valid(p->next))
|
||||||
return "Expected string key before ':'";
|
return "Expected string key before ':'";
|
||||||
if (p->stackpos == 0 || jv_get_kind(p->stack[p->stackpos-1]) != JV_KIND_OBJECT)
|
if (p->stackpos == 0 || jv_get_kind(p->stack[p->stackpos-1]) != JV_KIND_OBJECT)
|
||||||
return "':' not as part of an object";
|
return "':' not as part of an object";
|
||||||
@@ -177,7 +177,7 @@ static pfunc parse_token(struct jv_parser* p, char ch) {
|
|||||||
p->next = jv_invalid();
|
p->next = jv_invalid();
|
||||||
} else if (jv_get_kind(p->stack[p->stackpos-1]) == JV_KIND_STRING) {
|
} else if (jv_get_kind(p->stack[p->stackpos-1]) == JV_KIND_STRING) {
|
||||||
assert(p->stackpos > 1 && jv_get_kind(p->stack[p->stackpos-2]) == JV_KIND_OBJECT);
|
assert(p->stackpos > 1 && jv_get_kind(p->stack[p->stackpos-2]) == JV_KIND_OBJECT);
|
||||||
p->stack[p->stackpos-2] = jv_object_set(p->stack[p->stackpos-2],
|
p->stack[p->stackpos-2] = jv_object_set(p->stack[p->stackpos-2],
|
||||||
p->stack[p->stackpos-1], p->next);
|
p->stack[p->stackpos-1], p->next);
|
||||||
p->stackpos--;
|
p->stackpos--;
|
||||||
p->next = jv_invalid();
|
p->next = jv_invalid();
|
||||||
@@ -210,7 +210,7 @@ static pfunc parse_token(struct jv_parser* p, char ch) {
|
|||||||
if (jv_get_kind(p->stack[p->stackpos-1]) != JV_KIND_STRING)
|
if (jv_get_kind(p->stack[p->stackpos-1]) != JV_KIND_STRING)
|
||||||
return "Objects must consist of key:value pairs";
|
return "Objects must consist of key:value pairs";
|
||||||
assert(p->stackpos > 1 && jv_get_kind(p->stack[p->stackpos-2]) == JV_KIND_OBJECT);
|
assert(p->stackpos > 1 && jv_get_kind(p->stack[p->stackpos-2]) == JV_KIND_OBJECT);
|
||||||
p->stack[p->stackpos-2] = jv_object_set(p->stack[p->stackpos-2],
|
p->stack[p->stackpos-2] = jv_object_set(p->stack[p->stackpos-2],
|
||||||
p->stack[p->stackpos-1], p->next);
|
p->stack[p->stackpos-1], p->next);
|
||||||
p->stackpos--;
|
p->stackpos--;
|
||||||
p->next = jv_invalid();
|
p->next = jv_invalid();
|
||||||
@@ -410,7 +410,7 @@ static pfunc found_string(struct jv_parser* p) {
|
|||||||
char* in = p->tokenbuf;
|
char* in = p->tokenbuf;
|
||||||
char* out = p->tokenbuf;
|
char* out = p->tokenbuf;
|
||||||
char* end = p->tokenbuf + p->tokenpos;
|
char* end = p->tokenbuf + p->tokenpos;
|
||||||
|
|
||||||
while (in < end) {
|
while (in < end) {
|
||||||
char c = *in++;
|
char c = *in++;
|
||||||
if (c == '\\') {
|
if (c == '\\') {
|
||||||
@@ -479,7 +479,7 @@ static pfunc check_literal(struct jv_parser* p) {
|
|||||||
}
|
}
|
||||||
if (pattern) {
|
if (pattern) {
|
||||||
if (p->tokenpos != plen) return "Invalid literal";
|
if (p->tokenpos != plen) return "Invalid literal";
|
||||||
for (int i=0; i<plen; i++)
|
for (int i=0; i<plen; i++)
|
||||||
if (p->tokenbuf[i] != pattern[i])
|
if (p->tokenbuf[i] != pattern[i])
|
||||||
return "Invalid literal";
|
return "Invalid literal";
|
||||||
TRY(value(p, v));
|
TRY(value(p, v));
|
||||||
|
|||||||
+3
-3
@@ -19,7 +19,7 @@
|
|||||||
|
|
||||||
// Colour table. See http://en.wikipedia.org/wiki/ANSI_escape_code#Colors
|
// Colour table. See http://en.wikipedia.org/wiki/ANSI_escape_code#Colors
|
||||||
// for how to choose these.
|
// for how to choose these.
|
||||||
static const jv_kind colour_kinds[] =
|
static const jv_kind colour_kinds[] =
|
||||||
{JV_KIND_NULL, JV_KIND_FALSE, JV_KIND_TRUE, JV_KIND_NUMBER,
|
{JV_KIND_NULL, JV_KIND_FALSE, JV_KIND_TRUE, JV_KIND_NUMBER,
|
||||||
JV_KIND_STRING, JV_KIND_ARRAY, JV_KIND_OBJECT};
|
JV_KIND_STRING, JV_KIND_ARRAY, JV_KIND_OBJECT};
|
||||||
static const char* const colours[] =
|
static const char* const colours[] =
|
||||||
@@ -118,7 +118,7 @@ static void jvp_dump_string(jv str, int ascii_only, FILE* F, jv* S, int T) {
|
|||||||
sprintf(buf, "\\u%04x", c);
|
sprintf(buf, "\\u%04x", c);
|
||||||
} else {
|
} else {
|
||||||
c -= 0x10000;
|
c -= 0x10000;
|
||||||
sprintf(buf, "\\u%04x\\u%04x",
|
sprintf(buf, "\\u%04x\\u%04x",
|
||||||
0xD800 | ((c & 0xffc00) >> 10),
|
0xD800 | ((c & 0xffc00) >> 10),
|
||||||
0xDC00 | (c & 0x003ff));
|
0xDC00 | (c & 0x003ff));
|
||||||
}
|
}
|
||||||
@@ -283,7 +283,7 @@ static void jv_dump_term(struct dtoa_context* C, jv x, int flags, int indent, FI
|
|||||||
if (colour) put_str(colour, F, S, flags & JV_PRINT_ISATTY);
|
if (colour) put_str(colour, F, S, flags & JV_PRINT_ISATTY);
|
||||||
put_str((flags & JV_PRINT_PRETTY) ? ": " : ":", F, S, flags & JV_PRINT_ISATTY);
|
put_str((flags & JV_PRINT_PRETTY) ? ": " : ":", F, S, flags & JV_PRINT_ISATTY);
|
||||||
if (colour) put_str(COLRESET, F, S, flags & JV_PRINT_ISATTY);
|
if (colour) put_str(COLRESET, F, S, flags & JV_PRINT_ISATTY);
|
||||||
|
|
||||||
jv_dump_term(C, value, flags, indent + 1, F, S);
|
jv_dump_term(C, value, flags, indent + 1, F, S);
|
||||||
if (colour) put_str(colour, F, S, flags & JV_PRINT_ISATTY);
|
if (colour) put_str(colour, F, S, flags & JV_PRINT_ISATTY);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -56,9 +56,8 @@ struct lexer_param;
|
|||||||
(Loc).end = YYRHSLOC(Rhs, 0).end; \
|
(Loc).end = YYRHSLOC(Rhs, 0).end; \
|
||||||
} \
|
} \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
|
|
||||||
#line 62 "parser.h" /* yacc.c:1909 */
|
#line 61 "parser.h" /* yacc.c:1909 */
|
||||||
|
|
||||||
/* Token type. */
|
/* Token type. */
|
||||||
#ifndef YYTOKENTYPE
|
#ifndef YYTOKENTYPE
|
||||||
@@ -163,7 +162,7 @@ union YYSTYPE
|
|||||||
jv literal;
|
jv literal;
|
||||||
block blk;
|
block blk;
|
||||||
|
|
||||||
#line 167 "parser.h" /* yacc.c:1909 */
|
#line 166 "parser.h" /* yacc.c:1909 */
|
||||||
};
|
};
|
||||||
# define YYSTYPE_IS_TRIVIAL 1
|
# define YYSTYPE_IS_TRIVIAL 1
|
||||||
# define YYSTYPE_IS_DECLARED 1
|
# define YYSTYPE_IS_DECLARED 1
|
||||||
|
|||||||
@@ -23,7 +23,7 @@ struct lexer_param;
|
|||||||
(Loc).end = YYRHSLOC(Rhs, 0).end; \
|
(Loc).end = YYRHSLOC(Rhs, 0).end; \
|
||||||
} \
|
} \
|
||||||
} while (0)
|
} while (0)
|
||||||
}
|
}
|
||||||
|
|
||||||
%locations
|
%locations
|
||||||
%error-verbose
|
%error-verbose
|
||||||
@@ -123,7 +123,7 @@ struct lexer_param {
|
|||||||
/*YYERROR*/; \
|
/*YYERROR*/; \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
void yyerror(YYLTYPE* loc, block* answer, int* errors,
|
void yyerror(YYLTYPE* loc, block* answer, int* errors,
|
||||||
struct locfile* locations, struct lexer_param* lexer_param_ptr, const char *s){
|
struct locfile* locations, struct lexer_param* lexer_param_ptr, const char *s){
|
||||||
(*errors)++;
|
(*errors)++;
|
||||||
if (strstr(s, "unexpected")) {
|
if (strstr(s, "unexpected")) {
|
||||||
@@ -137,7 +137,7 @@ void yyerror(YYLTYPE* loc, block* answer, int* errors,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int yylex(YYSTYPE* yylval, YYLTYPE* yylloc, block* answer, int* errors,
|
int yylex(YYSTYPE* yylval, YYLTYPE* yylloc, block* answer, int* errors,
|
||||||
struct locfile* locations, struct lexer_param* lexer_param_ptr) {
|
struct locfile* locations, struct lexer_param* lexer_param_ptr) {
|
||||||
yyscan_t lexer = lexer_param_ptr->lexer;
|
yyscan_t lexer = lexer_param_ptr->lexer;
|
||||||
int tok = jq_yylex(yylval, yylloc, lexer);
|
int tok = jq_yylex(yylval, yylloc, lexer);
|
||||||
@@ -250,16 +250,16 @@ static block gen_definedor_assign(block object, block val) {
|
|||||||
return BLOCK(gen_op_simple(DUP),
|
return BLOCK(gen_op_simple(DUP),
|
||||||
val, tmp,
|
val, tmp,
|
||||||
gen_call("_modify", BLOCK(gen_lambda(object),
|
gen_call("_modify", BLOCK(gen_lambda(object),
|
||||||
gen_lambda(gen_definedor(gen_noop(),
|
gen_lambda(gen_definedor(gen_noop(),
|
||||||
gen_op_bound(LOADV, tmp))))));
|
gen_op_bound(LOADV, tmp))))));
|
||||||
}
|
}
|
||||||
|
|
||||||
static block gen_update(block object, block val, int optype) {
|
static block gen_update(block object, block val, int optype) {
|
||||||
block tmp = gen_op_var_fresh(STOREV, "tmp");
|
block tmp = gen_op_var_fresh(STOREV, "tmp");
|
||||||
return BLOCK(gen_op_simple(DUP),
|
return BLOCK(gen_op_simple(DUP),
|
||||||
val,
|
val,
|
||||||
tmp,
|
tmp,
|
||||||
gen_call("_modify", BLOCK(gen_lambda(object),
|
gen_call("_modify", BLOCK(gen_lambda(object),
|
||||||
gen_lambda(gen_binop(gen_noop(),
|
gen_lambda(gen_binop(gen_noop(),
|
||||||
gen_op_bound(LOADV, tmp),
|
gen_op_bound(LOADV, tmp),
|
||||||
optype)))));
|
optype)))));
|
||||||
@@ -274,7 +274,7 @@ Module Imports Exp {
|
|||||||
} |
|
} |
|
||||||
Module Imports FuncDefs {
|
Module Imports FuncDefs {
|
||||||
*answer = BLOCK($1, $2, $3);
|
*answer = BLOCK($1, $2, $3);
|
||||||
}
|
}
|
||||||
|
|
||||||
Module:
|
Module:
|
||||||
%empty {
|
%empty {
|
||||||
@@ -369,7 +369,7 @@ Exp '=' Exp {
|
|||||||
|
|
||||||
Exp "or" Exp {
|
Exp "or" Exp {
|
||||||
$$ = gen_or($1, $3);
|
$$ = gen_or($1, $3);
|
||||||
} |
|
} |
|
||||||
|
|
||||||
Exp "and" Exp {
|
Exp "and" Exp {
|
||||||
$$ = gen_and($1, $3);
|
$$ = gen_and($1, $3);
|
||||||
@@ -387,12 +387,12 @@ Exp "|=" Exp {
|
|||||||
$$ = gen_call("_modify", BLOCK(gen_lambda($1), gen_lambda($3)));
|
$$ = gen_call("_modify", BLOCK(gen_lambda($1), gen_lambda($3)));
|
||||||
} |
|
} |
|
||||||
|
|
||||||
Exp '|' Exp {
|
Exp '|' Exp {
|
||||||
$$ = block_join($1, $3);
|
$$ = block_join($1, $3);
|
||||||
} |
|
} |
|
||||||
|
|
||||||
Exp ',' Exp {
|
Exp ',' Exp {
|
||||||
$$ = gen_both($1, $3);
|
$$ = gen_both($1, $3);
|
||||||
} |
|
} |
|
||||||
|
|
||||||
Exp '+' Exp {
|
Exp '+' Exp {
|
||||||
@@ -467,8 +467,8 @@ Exp ">=" Exp {
|
|||||||
$$ = gen_binop($1, $3, GREATEREQ);
|
$$ = gen_binop($1, $3, GREATEREQ);
|
||||||
} |
|
} |
|
||||||
|
|
||||||
Term {
|
Term {
|
||||||
$$ = $1;
|
$$ = $1;
|
||||||
}
|
}
|
||||||
|
|
||||||
Import:
|
Import:
|
||||||
@@ -593,7 +593,7 @@ ElseBody:
|
|||||||
}
|
}
|
||||||
|
|
||||||
ExpD:
|
ExpD:
|
||||||
ExpD '|' ExpD {
|
ExpD '|' ExpD {
|
||||||
$$ = block_join($1, $3);
|
$$ = block_join($1, $3);
|
||||||
} |
|
} |
|
||||||
'-' ExpD {
|
'-' ExpD {
|
||||||
@@ -606,7 +606,7 @@ Term {
|
|||||||
|
|
||||||
Term:
|
Term:
|
||||||
'.' {
|
'.' {
|
||||||
$$ = gen_noop();
|
$$ = gen_noop();
|
||||||
} |
|
} |
|
||||||
REC {
|
REC {
|
||||||
$$ = gen_call("recurse", gen_noop());
|
$$ = gen_call("recurse", gen_noop());
|
||||||
@@ -626,8 +626,8 @@ BREAK error {
|
|||||||
Term FIELD '?' {
|
Term FIELD '?' {
|
||||||
$$ = gen_index_opt($1, gen_const($2));
|
$$ = gen_index_opt($1, gen_const($2));
|
||||||
} |
|
} |
|
||||||
FIELD '?' {
|
FIELD '?' {
|
||||||
$$ = gen_index_opt(gen_noop(), gen_const($1));
|
$$ = gen_index_opt(gen_noop(), gen_const($1));
|
||||||
} |
|
} |
|
||||||
Term '.' String '?' {
|
Term '.' String '?' {
|
||||||
$$ = gen_index_opt($1, $3);
|
$$ = gen_index_opt($1, $3);
|
||||||
@@ -638,8 +638,8 @@ Term '.' String '?' {
|
|||||||
Term FIELD {
|
Term FIELD {
|
||||||
$$ = gen_index($1, gen_const($2));
|
$$ = gen_index($1, gen_const($2));
|
||||||
} |
|
} |
|
||||||
FIELD {
|
FIELD {
|
||||||
$$ = gen_index(gen_noop(), gen_const($1));
|
$$ = gen_index(gen_noop(), gen_const($1));
|
||||||
} |
|
} |
|
||||||
Term '.' String {
|
Term '.' String {
|
||||||
$$ = gen_index($1, $3);
|
$$ = gen_index($1, $3);
|
||||||
@@ -655,19 +655,19 @@ Term '.' String {
|
|||||||
jv_free($2);
|
jv_free($2);
|
||||||
FAIL(@$, "try .[\"field\"] instead of .field for unusually named fields");
|
FAIL(@$, "try .[\"field\"] instead of .field for unusually named fields");
|
||||||
$$ = gen_noop();
|
$$ = gen_noop();
|
||||||
} |
|
} |
|
||||||
/* FIXME: string literals */
|
/* FIXME: string literals */
|
||||||
Term '[' Exp ']' '?' {
|
Term '[' Exp ']' '?' {
|
||||||
$$ = gen_index_opt($1, $3);
|
$$ = gen_index_opt($1, $3);
|
||||||
} |
|
} |
|
||||||
Term '[' Exp ']' {
|
Term '[' Exp ']' {
|
||||||
$$ = gen_index($1, $3);
|
$$ = gen_index($1, $3);
|
||||||
} |
|
} |
|
||||||
Term '[' ']' '?' {
|
Term '[' ']' '?' {
|
||||||
$$ = block_join($1, gen_op_simple(EACH_OPT));
|
$$ = block_join($1, gen_op_simple(EACH_OPT));
|
||||||
} |
|
} |
|
||||||
Term '[' ']' {
|
Term '[' ']' {
|
||||||
$$ = block_join($1, gen_op_simple(EACH));
|
$$ = block_join($1, gen_op_simple(EACH));
|
||||||
} |
|
} |
|
||||||
Term '[' Exp ':' Exp ']' '?' {
|
Term '[' Exp ':' Exp ']' '?' {
|
||||||
$$ = gen_slice_index($1, $3, $5, INDEX_OPT);
|
$$ = gen_slice_index($1, $3, $5, INDEX_OPT);
|
||||||
@@ -688,7 +688,7 @@ Term '[' ':' Exp ']' {
|
|||||||
$$ = gen_slice_index($1, gen_const(jv_null()), $4, INDEX);
|
$$ = gen_slice_index($1, gen_const(jv_null()), $4, INDEX);
|
||||||
} |
|
} |
|
||||||
LITERAL {
|
LITERAL {
|
||||||
$$ = gen_const($1);
|
$$ = gen_const($1);
|
||||||
} |
|
} |
|
||||||
String {
|
String {
|
||||||
$$ = $1;
|
$$ = $1;
|
||||||
@@ -696,16 +696,16 @@ String {
|
|||||||
FORMAT {
|
FORMAT {
|
||||||
$$ = gen_format(gen_noop(), $1);
|
$$ = gen_format(gen_noop(), $1);
|
||||||
} |
|
} |
|
||||||
'(' Exp ')' {
|
'(' Exp ')' {
|
||||||
$$ = $2;
|
$$ = $2;
|
||||||
} |
|
|
||||||
'[' Exp ']' {
|
|
||||||
$$ = gen_collect($2);
|
|
||||||
} |
|
} |
|
||||||
'[' ']' {
|
'[' Exp ']' {
|
||||||
$$ = gen_const(jv_array());
|
$$ = gen_collect($2);
|
||||||
} |
|
} |
|
||||||
'{' MkDict '}' {
|
'[' ']' {
|
||||||
|
$$ = gen_const(jv_array());
|
||||||
|
} |
|
||||||
|
'{' MkDict '}' {
|
||||||
block o = gen_const_object($2);
|
block o = gen_const_object($2);
|
||||||
if (o.first != NULL)
|
if (o.first != NULL)
|
||||||
$$ = o;
|
$$ = o;
|
||||||
@@ -719,7 +719,7 @@ FORMAT {
|
|||||||
'$' IDENT {
|
'$' IDENT {
|
||||||
$$ = gen_location(@$, locations, gen_op_unbound(LOADV, jv_string_value($2)));
|
$$ = gen_location(@$, locations, gen_op_unbound(LOADV, jv_string_value($2)));
|
||||||
jv_free($2);
|
jv_free($2);
|
||||||
} |
|
} |
|
||||||
IDENT {
|
IDENT {
|
||||||
const char *s = jv_string_value($1);
|
const char *s = jv_string_value($1);
|
||||||
if (strcmp(s, "false") == 0)
|
if (strcmp(s, "false") == 0)
|
||||||
@@ -860,15 +860,15 @@ Keyword:
|
|||||||
}
|
}
|
||||||
|
|
||||||
MkDict:
|
MkDict:
|
||||||
%empty {
|
%empty {
|
||||||
$$=gen_noop();
|
$$=gen_noop();
|
||||||
} |
|
} |
|
||||||
MkDictPair { $$ = $1; }
|
MkDictPair { $$ = $1; }
|
||||||
| MkDictPair ',' MkDict { $$=block_join($1, $3); }
|
| MkDictPair ',' MkDict { $$=block_join($1, $3); }
|
||||||
| error ',' MkDict { $$ = $3; }
|
| error ',' MkDict { $$ = $3; }
|
||||||
|
|
||||||
MkDictPair:
|
MkDictPair:
|
||||||
IDENT ':' ExpD {
|
IDENT ':' ExpD {
|
||||||
$$ = gen_dictpair(gen_const($1), $3);
|
$$ = gen_dictpair(gen_const($1), $3);
|
||||||
}
|
}
|
||||||
| Keyword ':' ExpD {
|
| Keyword ':' ExpD {
|
||||||
|
|||||||
@@ -104,7 +104,7 @@ jv get_home() {
|
|||||||
if (!home) {
|
if (!home) {
|
||||||
#ifndef WIN32
|
#ifndef WIN32
|
||||||
struct passwd* pwd = getpwuid(getuid());
|
struct passwd* pwd = getpwuid(getuid());
|
||||||
if (pwd)
|
if (pwd)
|
||||||
ret = jv_string(pwd->pw_dir);
|
ret = jv_string(pwd->pw_dir);
|
||||||
else
|
else
|
||||||
ret = jv_invalid_with_msg(jv_string("Could not find home directory."));
|
ret = jv_invalid_with_msg(jv_string("Could not find home directory."));
|
||||||
@@ -323,7 +323,7 @@ static int jq_util_input_read_more(jq_util_input_state *state) {
|
|||||||
|
|
||||||
if (p != NULL)
|
if (p != NULL)
|
||||||
state->current_line++;
|
state->current_line++;
|
||||||
|
|
||||||
if (p == NULL && state->parser != NULL) {
|
if (p == NULL && state->parser != NULL) {
|
||||||
/*
|
/*
|
||||||
* There should be no NULs in JSON texts (but JSON text
|
* There should be no NULs in JSON texts (but JSON text
|
||||||
|
|||||||
Reference in new issue
Block a user