forked from GitHub/gf-core
when linearizing missing functions with brackets, the name of the function should still be reported
This commit is contained in:
@@ -13,7 +13,7 @@
|
|||||||
#include <pgf/literals.h>
|
#include <pgf/literals.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
|
||||||
//#define PGF_LINEARIZER_DEBUG
|
#define PGF_LINEARIZER_DEBUG
|
||||||
|
|
||||||
static void
|
static void
|
||||||
pgf_lzr_add_overl_entry(PgfCncOverloadMap* overl_table,
|
pgf_lzr_add_overl_entry(PgfCncOverloadMap* overl_table,
|
||||||
@@ -130,6 +130,13 @@ pgf_print_cnc_tree(PgfCncTree ctree, GuOut* out, GuExn* err)
|
|||||||
if (clit->n_vars > 0) gu_putc(')', out, err);
|
if (clit->n_vars > 0) gu_putc(')', out, err);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
case PGF_CNC_TREE_LINDEF: {
|
||||||
|
PgfCncTreeLinDef* clindef = ti.data;
|
||||||
|
gu_putc('(', out, err);
|
||||||
|
pgf_print_cnc_tree_vars(clindef->n_vars, clindef->context, out, err);
|
||||||
|
gu_printf(out, err, "F%d[%s] %s)", clindef->fun->funid, clindef->str);
|
||||||
|
break;
|
||||||
|
}
|
||||||
case GU_VARIANT_NULL:
|
case GU_VARIANT_NULL:
|
||||||
gu_puts("null", out, err);
|
gu_puts("null", out, err);
|
||||||
break;
|
break;
|
||||||
@@ -222,44 +229,32 @@ redo:;
|
|||||||
static PgfCncTree
|
static PgfCncTree
|
||||||
pgf_cnc_resolve_def(PgfCnc* cnc,
|
pgf_cnc_resolve_def(PgfCnc* cnc,
|
||||||
size_t n_vars, PgfPrintContext* context,
|
size_t n_vars, PgfPrintContext* context,
|
||||||
PgfCCat* ccat, GuString s, GuPool* pool)
|
PgfCId abs_id, PgfCCat* ccat, GuString s, GuPool* pool)
|
||||||
{
|
{
|
||||||
PgfCncTree lit = gu_null_variant;
|
|
||||||
PgfCncTree ret = gu_null_variant;
|
PgfCncTree ret = gu_null_variant;
|
||||||
|
PgfCncFun* fun = NULL;
|
||||||
|
|
||||||
PgfCncTreeLit* clit =
|
if (ccat->lindefs != NULL) {
|
||||||
gu_new_variant(PGF_CNC_TREE_LIT,
|
int index =
|
||||||
PgfCncTreeLit,
|
gu_choice_next(cnc->ch, gu_seq_length(ccat->lindefs));
|
||||||
&lit, pool);
|
if (index < 0) {
|
||||||
clit->n_vars = 0;
|
return ret;
|
||||||
clit->context = context;
|
}
|
||||||
clit->fid = cnc->fid++;
|
|
||||||
PgfLiteralStr* lit_str =
|
|
||||||
gu_new_flex_variant(PGF_LITERAL_STR,
|
|
||||||
PgfLiteralStr,
|
|
||||||
val, strlen(s)+1,
|
|
||||||
&clit->lit, pool);
|
|
||||||
strcpy((char*) lit_str->val, (char*) s);
|
|
||||||
|
|
||||||
if (ccat->lindefs == NULL)
|
fun = gu_seq_get(ccat->lindefs, PgfCncFun*, index);
|
||||||
return lit;
|
|
||||||
|
|
||||||
int index =
|
|
||||||
gu_choice_next(cnc->ch, gu_seq_length(ccat->lindefs));
|
|
||||||
if (index < 0) {
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
PgfCncTreeApp* capp =
|
|
||||||
gu_new_flex_variant(PGF_CNC_TREE_APP,
|
PgfCncTreeLinDef* clindef =
|
||||||
PgfCncTreeApp,
|
gu_new_variant(PGF_CNC_TREE_LINDEF,
|
||||||
args, 1, &ret, pool);
|
PgfCncTreeLinDef,
|
||||||
capp->ccat = ccat;
|
&ret, pool);
|
||||||
capp->fun = gu_seq_get(ccat->lindefs, PgfCncFun*, index);
|
clindef->abs_id = abs_id;
|
||||||
capp->fid = cnc->fid++;
|
clindef->ccat = ccat;
|
||||||
capp->n_vars = n_vars;
|
clindef->fun = fun;
|
||||||
capp->context = context;
|
clindef->fid = cnc->fid++;
|
||||||
capp->n_args = 1;
|
clindef->n_vars = n_vars;
|
||||||
capp->args[0] = lit;
|
clindef->context = context;
|
||||||
|
clindef->str = s;
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
@@ -433,10 +428,10 @@ pgf_cnc_resolve(PgfCnc* cnc,
|
|||||||
gu_putc('[', out, err);
|
gu_putc('[', out, err);
|
||||||
gu_string_write(efun->fun, out, err);
|
gu_string_write(efun->fun, out, err);
|
||||||
gu_putc(']', out, err);
|
gu_putc(']', out, err);
|
||||||
GuString s = gu_string_buf_freeze(sbuf, tmp_pool);
|
GuString s = gu_string_buf_freeze(sbuf, pool);
|
||||||
|
|
||||||
if (ccat != NULL) {
|
if (ccat != NULL) {
|
||||||
ret = pgf_cnc_resolve_def(cnc, n_vars, context, ccat, s, pool);
|
ret = pgf_cnc_resolve_def(cnc, n_vars, context, efun->fun, ccat, s, pool);
|
||||||
} else {
|
} else {
|
||||||
PgfCncTreeLit* clit =
|
PgfCncTreeLit* clit =
|
||||||
gu_new_variant(PGF_CNC_TREE_LIT,
|
gu_new_variant(PGF_CNC_TREE_LIT,
|
||||||
@@ -504,7 +499,7 @@ redo:;
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (ccat != NULL) {
|
if (ccat != NULL) {
|
||||||
ret = pgf_cnc_resolve_def(cnc, n_vars, context, ccat, ctxt->name, pool);
|
ret = pgf_cnc_resolve_def(cnc, n_vars, context, ctxt->name, ccat, ctxt->name, pool);
|
||||||
} else {
|
} else {
|
||||||
PgfCncTreeLit* clit =
|
PgfCncTreeLit* clit =
|
||||||
gu_new_variant(PGF_CNC_TREE_LIT,
|
gu_new_variant(PGF_CNC_TREE_LIT,
|
||||||
@@ -634,7 +629,7 @@ typedef struct {
|
|||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
PgfLinFuncs* funcs;
|
PgfLinFuncs* funcs;
|
||||||
PgfCncTreeApp* app;
|
PgfCncTree ctree;
|
||||||
PgfSymbolKP* kp;
|
PgfSymbolKP* kp;
|
||||||
GuBuf* events;
|
GuBuf* events;
|
||||||
PgfLzr* lzr;
|
PgfLzr* lzr;
|
||||||
@@ -642,7 +637,7 @@ typedef struct {
|
|||||||
} PgfLzrCache;
|
} PgfLzrCache;
|
||||||
|
|
||||||
static void
|
static void
|
||||||
pgf_lzr_linearize_symbols(PgfLzr* lzr, PgfCncTreeApp* fapp,
|
pgf_lzr_linearize_symbols(PgfLzr* lzr, PgfCncTree ctree,
|
||||||
PgfSymbols* syms, uint16_t sym_idx);
|
PgfSymbols* syms, uint16_t sym_idx);
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@@ -652,7 +647,7 @@ static void
|
|||||||
pgf_lzr_cache_flush(PgfLzrCache* cache, PgfSymbols* form)
|
pgf_lzr_cache_flush(PgfLzrCache* cache, PgfSymbols* form)
|
||||||
{
|
{
|
||||||
cache->lzr->funcs = cache->prev;
|
cache->lzr->funcs = cache->prev;
|
||||||
pgf_lzr_linearize_symbols(cache->lzr, cache->app, form, 0);
|
pgf_lzr_linearize_symbols(cache->lzr, cache->ctree, form, 0);
|
||||||
|
|
||||||
size_t n_cached = gu_buf_length(cache->events);
|
size_t n_cached = gu_buf_length(cache->events);
|
||||||
for (size_t i = 0; i < n_cached; i++) {
|
for (size_t i = 0; i < n_cached; i++) {
|
||||||
@@ -826,6 +821,12 @@ pgf_lzr_linearize_var(PgfLzr* lzr, PgfCncTree ctree, size_t var_idx)
|
|||||||
context = flit->context;
|
context = flit->context;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
case PGF_CNC_TREE_LINDEF: {
|
||||||
|
PgfCncTreeLinDef* flindef = cti.data;
|
||||||
|
n_vars = flindef->n_vars;
|
||||||
|
context = flindef->context;
|
||||||
|
break;
|
||||||
|
}
|
||||||
default:
|
default:
|
||||||
gu_impossible();
|
gu_impossible();
|
||||||
}
|
}
|
||||||
@@ -842,7 +843,7 @@ pgf_lzr_linearize_var(PgfLzr* lzr, PgfCncTree ctree, size_t var_idx)
|
|||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
pgf_lzr_linearize_symbols(PgfLzr* lzr, PgfCncTreeApp* fapp,
|
pgf_lzr_linearize_symbols(PgfLzr* lzr, PgfCncTree ctree,
|
||||||
PgfSymbols* syms, uint16_t sym_idx)
|
PgfSymbols* syms, uint16_t sym_idx)
|
||||||
{
|
{
|
||||||
size_t nsyms = gu_seq_length(syms);
|
size_t nsyms = gu_seq_length(syms);
|
||||||
@@ -851,26 +852,40 @@ pgf_lzr_linearize_symbols(PgfLzr* lzr, PgfCncTreeApp* fapp,
|
|||||||
GuVariantInfo sym_i = gu_variant_open(sym);
|
GuVariantInfo sym_i = gu_variant_open(sym);
|
||||||
switch (sym_i.tag) {
|
switch (sym_i.tag) {
|
||||||
case PGF_SYMBOL_CAT:
|
case PGF_SYMBOL_CAT:
|
||||||
case PGF_SYMBOL_LIT: {
|
case PGF_SYMBOL_LIT:
|
||||||
if (fapp == NULL)
|
|
||||||
return;
|
|
||||||
|
|
||||||
PgfSymbolIdx* sidx = sym_i.data;
|
|
||||||
gu_assert((unsigned) sidx->d < fapp->n_args);
|
|
||||||
|
|
||||||
PgfCncTree argf = fapp->args[sidx->d];
|
|
||||||
pgf_lzr_linearize_tree(lzr, argf, sidx->r);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
case PGF_SYMBOL_VAR: {
|
case PGF_SYMBOL_VAR: {
|
||||||
if (fapp == NULL)
|
if (gu_variant_is_null(ctree))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
PgfSymbolIdx* sidx = sym_i.data;
|
PgfSymbolIdx* sidx = sym_i.data;
|
||||||
gu_assert((unsigned) sidx->d < fapp->n_args);
|
|
||||||
|
|
||||||
PgfCncTree argf = fapp->args[sidx->d];
|
GuVariantInfo tree_i = gu_variant_open(ctree);
|
||||||
pgf_lzr_linearize_var(lzr, argf, sidx->r);
|
switch (tree_i.tag) {
|
||||||
|
case PGF_CNC_TREE_APP: {
|
||||||
|
PgfCncTreeApp* papp = tree_i.data;
|
||||||
|
|
||||||
|
gu_assert((unsigned) sidx->d < papp->n_args);
|
||||||
|
|
||||||
|
PgfCncTree argf = papp->args[sidx->d];
|
||||||
|
if (sym_i.tag == PGF_SYMBOL_VAR)
|
||||||
|
pgf_lzr_linearize_var(lzr, argf, sidx->r);
|
||||||
|
else
|
||||||
|
pgf_lzr_linearize_tree(lzr, argf, sidx->r);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case PGF_CNC_TREE_LINDEF: {
|
||||||
|
PgfCncTreeLinDef* plindef = tree_i.data;
|
||||||
|
|
||||||
|
gu_assert(sidx->d == 0);
|
||||||
|
|
||||||
|
if ((*lzr->funcs)->symbol_token) {
|
||||||
|
(*lzr->funcs)->symbol_token(lzr->funcs, plindef->str);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
gu_impossible();
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case PGF_SYMBOL_KS: {
|
case PGF_SYMBOL_KS: {
|
||||||
@@ -885,12 +900,12 @@ pgf_lzr_linearize_symbols(PgfLzr* lzr, PgfCncTreeApp* fapp,
|
|||||||
PgfSymbolKP* kp = sym_i.data;
|
PgfSymbolKP* kp = sym_i.data;
|
||||||
//gu_buf_push(pres, PgfSymbolKP*, kp);
|
//gu_buf_push(pres, PgfSymbolKP*, kp);
|
||||||
PgfLzrCache* cache = gu_new(PgfLzrCache, lzr->tmp_pool);
|
PgfLzrCache* cache = gu_new(PgfLzrCache, lzr->tmp_pool);
|
||||||
cache->funcs = &pgf_lzr_cache_funcs;
|
cache->funcs = &pgf_lzr_cache_funcs;
|
||||||
cache->app = fapp;
|
cache->ctree = ctree;
|
||||||
cache->kp = kp;
|
cache->kp = kp;
|
||||||
cache->events= gu_new_buf(PgfLzrCached, lzr->tmp_pool);
|
cache->events = gu_new_buf(PgfLzrCached, lzr->tmp_pool);
|
||||||
cache->lzr = lzr;
|
cache->lzr = lzr;
|
||||||
cache->prev = lzr->funcs;
|
cache->prev = lzr->funcs;
|
||||||
lzr->funcs = &cache->funcs;
|
lzr->funcs = &cache->funcs;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -945,8 +960,8 @@ pgf_lzr_linearize_tree(PgfLzr* lzr, PgfCncTree ctree, size_t lin_idx)
|
|||||||
}
|
}
|
||||||
|
|
||||||
gu_require(lin_idx < fun->n_lins);
|
gu_require(lin_idx < fun->n_lins);
|
||||||
pgf_lzr_linearize_symbols(lzr, fapp, fun->lins[lin_idx]->syms, 0);
|
pgf_lzr_linearize_symbols(lzr, ctree, fun->lins[lin_idx]->syms, 0);
|
||||||
|
|
||||||
if ((*lzr->funcs)->end_phrase && fapp->ccat != NULL) {
|
if ((*lzr->funcs)->end_phrase && fapp->ccat != NULL) {
|
||||||
(*lzr->funcs)->end_phrase(lzr->funcs,
|
(*lzr->funcs)->end_phrase(lzr->funcs,
|
||||||
fun->absfun->type->cid,
|
fun->absfun->type->cid,
|
||||||
@@ -1017,6 +1032,29 @@ pgf_lzr_linearize_tree(PgfLzr* lzr, PgfCncTree ctree, size_t lin_idx)
|
|||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
case PGF_CNC_TREE_LINDEF: {
|
||||||
|
PgfCncTreeLinDef* flindef = cti.data;
|
||||||
|
PgfCncFun* fun = flindef->fun;
|
||||||
|
|
||||||
|
if ((*lzr->funcs)->begin_phrase) {
|
||||||
|
(*lzr->funcs)->begin_phrase(lzr->funcs,
|
||||||
|
"",
|
||||||
|
flindef->fid, lin_idx,
|
||||||
|
flindef->abs_id);
|
||||||
|
}
|
||||||
|
|
||||||
|
gu_require(lin_idx < fun->n_lins);
|
||||||
|
pgf_lzr_linearize_symbols(lzr, ctree, fun->lins[lin_idx]->syms, 0);
|
||||||
|
|
||||||
|
if ((*lzr->funcs)->end_phrase) {
|
||||||
|
(*lzr->funcs)->end_phrase(lzr->funcs,
|
||||||
|
"",
|
||||||
|
flindef->fid, lin_idx,
|
||||||
|
flindef->abs_id);
|
||||||
|
}
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
default:
|
default:
|
||||||
gu_impossible();
|
gu_impossible();
|
||||||
}
|
}
|
||||||
@@ -1186,10 +1224,16 @@ pgf_lzr_get_table(PgfConcr* concr, PgfCncTree ctree,
|
|||||||
*labels = &s_label;
|
*labels = &s_label;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
case PGF_CNC_TREE_LINDEF: {
|
||||||
|
static GuString s = "s";
|
||||||
|
|
||||||
|
*n_lins = 1;
|
||||||
|
*labels = &s;
|
||||||
|
break;
|
||||||
|
}
|
||||||
default:
|
default:
|
||||||
gu_impossible();
|
gu_impossible();
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
PGF_API void
|
PGF_API void
|
||||||
@@ -1230,7 +1274,7 @@ pgf_get_tokens(PgfSymbols* syms, uint16_t sym_idx, GuPool* pool)
|
|||||||
};
|
};
|
||||||
|
|
||||||
PgfLzr* lzr = pgf_new_lzr(NULL, &flin.funcs, tmp_pool);
|
PgfLzr* lzr = pgf_new_lzr(NULL, &flin.funcs, tmp_pool);
|
||||||
pgf_lzr_linearize_symbols(lzr, NULL, syms, sym_idx);
|
pgf_lzr_linearize_symbols(lzr, gu_null_variant, syms, sym_idx);
|
||||||
|
|
||||||
while (lzr->funcs != &flin.funcs) {
|
while (lzr->funcs != &flin.funcs) {
|
||||||
PgfLzrCache* cache = gu_container(lzr->funcs, PgfLzrCache, funcs);
|
PgfLzrCache* cache = gu_container(lzr->funcs, PgfLzrCache, funcs);
|
||||||
|
|||||||
@@ -18,6 +18,7 @@ typedef enum {
|
|||||||
PGF_CNC_TREE_APP,
|
PGF_CNC_TREE_APP,
|
||||||
PGF_CNC_TREE_CHUNKS,
|
PGF_CNC_TREE_CHUNKS,
|
||||||
PGF_CNC_TREE_LIT,
|
PGF_CNC_TREE_LIT,
|
||||||
|
PGF_CNC_TREE_LINDEF
|
||||||
} PgfCncTreeTag;
|
} PgfCncTreeTag;
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
@@ -50,6 +51,19 @@ typedef struct {
|
|||||||
PgfLiteral lit;
|
PgfLiteral lit;
|
||||||
} PgfCncTreeLit;
|
} PgfCncTreeLit;
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
PgfCId abs_id;
|
||||||
|
|
||||||
|
PgfCCat* ccat;
|
||||||
|
PgfCncFun* fun;
|
||||||
|
int fid;
|
||||||
|
|
||||||
|
size_t n_vars;
|
||||||
|
PgfPrintContext* context;
|
||||||
|
|
||||||
|
GuString str;
|
||||||
|
} PgfCncTreeLinDef;
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/// An enumeration of #PgfCncTree trees.
|
/// An enumeration of #PgfCncTree trees.
|
||||||
|
|||||||
Reference in New Issue
Block a user