diff --git a/clib/markdown.go b/clib/markdown.go index 78115a28a1aec0bb470343cd176e846246075b32..0e143bebfe0275762e08a6a09d2aa3dc0dffddf0 100644 --- a/clib/markdown.go +++ b/clib/markdown.go @@ -56,7 +56,10 @@ static char* md4c_to_html(const char* input, size_t input_len, size_t* out_len) } */ import "C" -import "unsafe" +import ( + "log" + "unsafe" +) // MarkdownToHTML converts Markdown bytes to HTML using md4c (C). // This is significantly faster than goldmark for large documents. @@ -71,7 +74,8 @@ func MarkdownToHTML(md []byte) []byte { var outLen C.size_t result := C.md4c_to_html((*C.char)(cInput), C.size_t(len(md)), &outLen) if result == nil { - return md // fallback to original on failure + log.Printf("markdown: md4c_to_html failed, falling back to escaped plain-text HTML") + return markdownPlainTextHTML(md) } defer C.free(unsafe.Pointer(result)) diff --git a/clib/markdown_fallback.go b/clib/markdown_fallback.go new file mode 100644 index 0000000000000000000000000000000000000000..1ebabdcc920a95ecfea1f1b8b0a6cfea9cc6af26 --- /dev/null +++ b/clib/markdown_fallback.go @@ -0,0 +1,7 @@ +package clib + +import "html" + +func markdownPlainTextHTML(md []byte) []byte { + return []byte("
" + html.EscapeString(string(md)) + "
") +} diff --git a/clib/markdown_fallback_test.go b/clib/markdown_fallback_test.go new file mode 100644 index 0000000000000000000000000000000000000000..e7b6430af68e26b8e92ebfc0df126b91b9315460 --- /dev/null +++ b/clib/markdown_fallback_test.go @@ -0,0 +1,25 @@ +package clib + +import ( + "strings" + "testing" +) + +func TestMarkdownPlainTextHTMLFallbackEscapesInput(t *testing.T) { + input := []byte("# Heading\n\n\nliteral") + + got := string(markdownPlainTextHTML(input)) + + if !strings.HasPrefix(got, "
") || !strings.HasSuffix(got, "
") { + t.Fatalf("fallback should wrap content in pre tag, got %q", got) + } + if strings.Contains(got, "