author | Olivier Brunel
<jjk@jjacky.com> 2023-01-06 17:13:43 UTC |
committer | Olivier Brunel
<jjk@jjacky.com> 2023-01-06 17:13:43 UTC |
parent | ddc195d80340a6c9ddd7a9b951018ff908faef35 |
main.c | +38 | -6 |
diff --git a/main.c b/main.c index 0af5a2c..eb3126b 100644 --- a/main.c +++ b/main.c @@ -67,6 +67,7 @@ enum { DOC_BUFFERING = (1 << 1), DOC_FULL_TOC = (1 << 2), DOC_IS_INDEX = (1 << 3), /* i.e. enable the <TOC> tag */ + DOC_BUFFERED_A = (1 << 4), }; struct ctx { @@ -858,7 +859,10 @@ enter_span(MD_SPANTYPE type, void *details, void *ctx_) { MD_SPAN_A_DETAIL *d = details; - if (!get_section(&d->href)) { + if (get_section(&d->href)) { + BUFFERING_ON(); + ctx->doc.flags |= DOC_BUFFERED_A; + } else { if (!raw_str(ctx, "<a href=\"") || !attribute(ctx, &d->href)) return ERR_PARSER_ENTER_SPAN; @@ -923,17 +927,45 @@ leave_span(MD_SPANTYPE type, void *details, void *ctx_) case MD_SPAN_A: { - MD_SPAN_A_DETAIL *d = details; - int section = get_section(&d->href); + if (ctx->doc.flags & DOC_BUFFERED_A) { + MD_SPAN_A_DETAIL *d = details; + int section = get_section(&d->href); + + BUFFERING_OFF(s, l); + ctx->doc.flags &= ~DOC_BUFFERED_A; + + if (!section) + return ERR_PARSER_LEAVE_SPAN; - if (section) { char buf[UINT32_FMT + 2]; buf[0] = '('; section = uint32_fmt(buf + 1, (uint32) section); buf[1 + section] = ')'; buf[2 + section] = '\0'; - if (!raw_str(ctx, buf)) - return ERR_PARSER_LEAVE_SPAN; + + const char *file; + for (int i = 0; i < ctx->nb_pages; ++i) { + file = ctx->sa.s + ctx->pages[i].fileoff; + if (!memcmp(file, s, l) + && file[l] == '.' + && file[l + 1] == section + '0' + && !memcmp(file + l + 2, ".html", 6)) + break; + file = NULL; + } + + if (file) { + if (!raw_str(ctx, "<a href=\"") + || !escape_text(ctx, file, strlen(file)) + || !raw_str(ctx, "\">") + || !raw_text(ctx, s, l) + || !raw_str(ctx, buf) + || !raw_str(ctx, "</a>")) + return ERR_PARSER_ENTER_SPAN; + } else { + if (!raw_text(ctx, s, l) || !raw_str(ctx, buf)) + return ERR_PARSER_LEAVE_SPAN; + } } else { if (!raw_str(ctx, "</a>")) return ERR_PARSER_LEAVE_SPAN;