From dae206f4eb3a0ccd5b995a5df9d4007b2967da60 Mon Sep 17 00:00:00 2001 From: Nick Gasson Date: Thu, 13 Jan 2022 12:28:25 +0800 Subject: [PATCH] Separate runtime calls for report and assertion failure --- src/cgen.c | 27 +++++++++++++++++---------- src/rt/rtkern.c | 43 +++++++++++++++++++++++++++++++++++++++---- src/symbols.txt | 1 + 3 files changed, 57 insertions(+), 14 deletions(-) diff --git a/src/cgen.c b/src/cgen.c index 31f7be62..7414009a 100644 --- a/src/cgen.c +++ b/src/cgen.c @@ -150,10 +150,12 @@ static LLVMValueRef llvm_int1(bool b) return LLVMConstInt(llvm_int1_type(), b, false); } +#if 0 static LLVMValueRef llvm_int8(int8_t i) { return LLVMConstInt(llvm_int8_type(), i, false); } +#endif static LLVMValueRef llvm_int32(int32_t i) { @@ -1125,14 +1127,8 @@ static void cgen_op_report(int op, cgen_ctx_t *ctx) LLVMValueRef length = cgen_get_arg(op, 2, ctx); LLVMValueRef locus = cgen_get_arg(op, 3, ctx); - LLVMValueRef args[] = { - message, - length, - severity, - llvm_int8(1), - locus, - }; - LLVMBuildCall(builder, llvm_fn("__nvc_assert_fail"), args, + LLVMValueRef args[] = { message, length, severity, locus }; + LLVMBuildCall(builder, llvm_fn("__nvc_report"), args, ARRAY_LEN(args), ""); } @@ -1166,7 +1162,6 @@ static void cgen_op_assert(int op, cgen_ctx_t *ctx) message, length, severity, - llvm_int8(0), locus }; LLVMBuildCall(builder, llvm_fn("__nvc_assert_fail"), args, @@ -3833,7 +3828,6 @@ static LLVMValueRef cgen_support_fn(const char *name) LLVMPointerType(llvm_int8_type(), 0), llvm_int32_type(), llvm_int8_type(), - llvm_int8_type(), llvm_debug_locus_type(), }; fn = LLVMAddFunction(module, "__nvc_assert_fail", @@ -3842,6 +3836,19 @@ static LLVMValueRef cgen_support_fn(const char *name) cgen_add_func_attr(fn, FUNC_ATTR_NOCAPTURE, 1); cgen_add_func_attr(fn, FUNC_ATTR_COLD, -1); } + + else if (strcmp(name, "__nvc_report") == 0) { + LLVMTypeRef args[] = { + LLVMPointerType(llvm_int8_type(), 0), + llvm_int32_type(), + llvm_int8_type(), + llvm_debug_locus_type(), + }; + fn = LLVMAddFunction(module, "__nvc_report", + LLVMFunctionType(llvm_void_type(), + args, ARRAY_LEN(args), false)); + cgen_add_func_attr(fn, FUNC_ATTR_NOCAPTURE, 1); + } else if (strcmp(name, "_debug_out") == 0) { LLVMTypeRef args[] = { llvm_int32_type(), diff --git a/src/rt/rtkern.c b/src/rt/rtkern.c index 881f6503..84bafbf9 100644 --- a/src/rt/rtkern.c +++ b/src/rt/rtkern.c @@ -878,7 +878,7 @@ void _convert_signal(sig_shared_t *ss, uint32_t offset, uint32_t count, DLLEXPORT void __nvc_assert_fail(const uint8_t *msg, int32_t msg_len, int8_t severity, - int8_t is_report, DEBUG_LOCUS(locus)) + DEBUG_LOCUS(locus)) { // LRM 93 section 8.2 // The error message consists of at least @@ -922,9 +922,44 @@ void __nvc_assert_fail(const uint8_t *msg, int32_t msg_len, int8_t severity, tree_t where = rt_locus_to_tree(locus_unit, locus_offset); - rt_msg(tree_loc(where), fn, "%s: %s %s: %.*s", - tmbuf, (is_report ? "Report" : "Assertion"), - levels[severity], msg_len, msg); + rt_msg(tree_loc(where), fn, "%s: Assertion %s: %.*s", + tmbuf, levels[severity], msg_len, msg); +} + +DLLEXPORT +void __nvc_report(const uint8_t *msg, int32_t msg_len, int8_t severity, + DEBUG_LOCUS(locus)) +{ + RT_ASSERT(severity <= SEVERITY_FAILURE); + + static const char *levels[] = { + "Note", "Warning", "Error", "Failure" + }; + + if (init_side_effect != SIDE_EFFECT_ALLOW) { + init_side_effect = SIDE_EFFECT_OCCURRED; + return; + } + + void (*fn)(const char *fmt, ...) = fatal; + + switch (severity) { + case SEVERITY_NOTE: fn = notef; break; + case SEVERITY_WARNING: fn = warnf; break; + case SEVERITY_ERROR: + case SEVERITY_FAILURE: fn = errorf; break; + } + + if (severity >= exit_severity) + fn = fatal; + + char tmbuf[64]; + rt_fmt_now(tmbuf, sizeof(tmbuf)); + + tree_t where = rt_locus_to_tree(locus_unit, locus_offset); + + rt_msg(tree_loc(where), fn, "%s: Report %s: %.*s", + tmbuf, levels[severity], msg_len, msg); } DLLEXPORT diff --git a/src/symbols.txt b/src/symbols.txt index 82c68d17..6feb6afe 100644 --- a/src/symbols.txt +++ b/src/symbols.txt @@ -10,6 +10,7 @@ __nvc_length_fail; __nvc_null_deref; __nvc_range_fail; + __nvc_report; _assert_fail; _canon_value; _convert_signal; -- 2.39.2