From 7362879139faf87e909d8a7eacf6cf95a5bbd3b6 Mon Sep 17 00:00:00 2001 From: Kevin Day Date: Wed, 30 Sep 2026 21:01:49 -0500 Subject: [PATCH] Feature: Print operation content on error. Provide additional details on error by showing the exact line (without expanding any **IKI** syntax). This requires changes in some of the functions, which breaks **API** and **ABI**. This only happens in the level 3, so programs. The programs aren't as strictly required to be non-breaking changes. (Although, non-breaking changes is highly encouraged.) I decided the additional error information to be of more value than the breaking change aspect. --- level_3/fake/c/main/make/operate.c | 4 +- level_3/fake/c/main/make/operate_process.c | 6 +-- level_3/fake/c/main/make/operate_process.h | 4 +- .../fake/c/main/make/operate_process_type.c | 51 +++++++++++++++++-- level_3/fake/c/main/make/print/error.c | 6 ++- level_3/fake/c/main/make/print/error.h | 4 +- level_3/fake/c/main/print/context.c | 2 +- level_3/fake/c/main/print/error.c | 26 ++++++++-- level_3/fake/c/main/print/error.h | 4 +- 9 files changed, 87 insertions(+), 20 deletions(-) diff --git a/level_3/fake/c/main/make/operate.c b/level_3/fake/c/main/make/operate.c index d42fde66f..acbecfed7 100644 --- a/level_3/fake/c/main/make/operate.c +++ b/level_3/fake/c/main/make/operate.c @@ -1497,7 +1497,7 @@ extern "C" { data_make->error.set = &main->program.context.set; } - fake_print_error_operation_failed(&data_make->error, main->buffer, section->name, section->objects.array[i]); + fake_print_error_operation_failed(&data_make->error, main->buffer, section->name, section->objects.array[i], section->contents.array[i]); // F_signal_abort is used by the break section operation. if (F_status_set_fine(main->setting.state.status) == F_signal_abort) break; @@ -1546,7 +1546,7 @@ extern "C" { if (i == section->objects.used && F_status_is_error_not(main->setting.state.status) && (state_process.operation == fake_make_operation_type_and_e || state_process.operation == fake_make_operation_type_else_e || state_process.operation == fake_make_operation_type_if_e || state_process.operation == fake_make_operation_type_or_e)) { fake_make_print_error_operation_incomplete(&main->program.error, state_process.operation); - fake_print_error_operation_failed(&data_make->error, main->buffer, section->name, section->objects.array[section->objects.used - 1]); + fake_print_error_operation_failed(&data_make->error, main->buffer, section->name, section->objects.array[i - 1], section->contents.array[i - 1]); main->setting.state.status = F_status_set_error(F_failure); } diff --git a/level_3/fake/c/main/make/operate_process.c b/level_3/fake/c/main/make/operate_process.c index 1d95e95a7..b9158240b 100644 --- a/level_3/fake/c/main/make/operate_process.c +++ b/level_3/fake/c/main/make/operate_process.c @@ -346,14 +346,14 @@ extern "C" { } } - fake_make_operate_process_return(data_make, return_code, F_status_debug_source_d); + fake_make_operate_process_return(data_make, program, return_code, F_status_debug_source_d); return; } #endif // _di_fake_make_operate_process_execute_ #ifndef _di_fake_make_operate_process_return_ - void fake_make_operate_process_return(fake_make_data_t * const data_make, const int return_code, const f_string_t debug) { + void fake_make_operate_process_return(fake_make_data_t * const data_make, const f_string_static_t program, const int return_code, const f_string_t debug) { if (!data_make || !data_make->main) return; @@ -386,7 +386,7 @@ extern "C" { return; } - fake_make_print_error_program_failed(&main->program.error, return_code, debug); + fake_make_print_error_program_failed(&main->program.error, program, return_code, debug); main->setting.state.status = (data_make->setting_make.fail == fake_make_operation_fail_exit_e) ? F_status_set_error(F_failure) : F_failure; diff --git a/level_3/fake/c/main/make/operate_process.h b/level_3/fake/c/main/make/operate_process.h index bc9b61f34..297f8a033 100644 --- a/level_3/fake/c/main/make/operate_process.h +++ b/level_3/fake/c/main/make/operate_process.h @@ -207,6 +207,8 @@ extern "C" { * Errors (with error bit) from: f_conversion_number_signed_to_string(). * Errors (with error bit) from: f_string_append(). * Errors (with error bit) from: f_string_dynamic_append(). + * @param program + * The program that was executed. * @param return_code * The return code to process. * @param debug @@ -219,7 +221,7 @@ extern "C" { * @see f_string_dynamic_append() */ #ifndef _di_fake_make_operate_process_return_ - extern void fake_make_operate_process_return(fake_make_data_t * const data_make, const int return_code, const f_string_t debug); + extern void fake_make_operate_process_return(fake_make_data_t * const data_make, const f_string_static_t program, const int return_code, const f_string_t debug); #endif // _di_fake_make_operate_process_return_ /** diff --git a/level_3/fake/c/main/make/operate_process_type.c b/level_3/fake/c/main/make/operate_process_type.c index 650c97b77..0c14ecd68 100644 --- a/level_3/fake/c/main/make/operate_process_type.c +++ b/level_3/fake/c/main/make/operate_process_type.c @@ -39,7 +39,16 @@ extern "C" { fake_build_operate(data_make->data, main->cache_arguments.used ? &main->cache_arguments : 0, F_false, data_make->setting_make.stage); if (F_status_set_fine(main->setting.state.status) == F_interrupt) return; - fake_make_operate_process_return(data_make, F_status_is_error(main->setting.state.status) ? 1 : 0, F_status_debug_source_d); + fake_make_operate_process_return( + data_make, + data_make->main->cache_arguments.used + ? data_make->main->cache_arguments.array[0] + : f_string_empty_s, + F_status_is_error(main->setting.state.status) + ? 1 + : 0, + F_status_debug_source_d + ); } #endif // _di_fake_make_operate_process_type_build_ @@ -53,7 +62,16 @@ extern "C" { fake_clean_operate(data_make->data); if (F_status_set_fine(main->setting.state.status) == F_interrupt) return; - fake_make_operate_process_return(data_make, F_status_is_error(main->setting.state.status) ? 1 : 0, F_status_debug_source_d); + fake_make_operate_process_return( + data_make, + data_make->main->cache_arguments.used + ? data_make->main->cache_arguments.array[0] + : f_string_empty_s, + F_status_is_error(main->setting.state.status) + ? 1 + : 0, + F_status_debug_source_d + ); } #endif // _di_fake_make_operate_process_type_clean_ @@ -67,7 +85,14 @@ extern "C" { const int result = fake_execute(data_make->data, data_make->environment, data_make->setting_build.build_compiler); if (main->setting.state.status == F_child) return result; - fake_make_operate_process_return(data_make, result, F_status_debug_source_d); + fake_make_operate_process_return( + data_make, + data_make->main->cache_arguments.used + ? data_make->main->cache_arguments.array[0] + : f_string_empty_s, + result, + F_status_debug_source_d + ); return result; } @@ -1361,7 +1386,14 @@ extern "C" { const int result = fake_execute(data_make->data, data_make->environment, data_make->setting_build.build_indexer); if (main->setting.state.status == F_child) return result; - fake_make_operate_process_return(data_make, result, F_status_debug_source_d); + fake_make_operate_process_return( + data_make, + data_make->main->cache_arguments.used + ? data_make->main->cache_arguments.array[0] + : f_string_empty_s, + result, + F_status_debug_source_d + ); return result; } @@ -1893,7 +1925,16 @@ extern "C" { fake_skeleton_operate(data_make->data); if (F_status_set_fine(main->setting.state.status) == F_interrupt) return; - fake_make_operate_process_return(data_make, F_status_is_error(main->setting.state.status) ? 1 : 0, F_status_debug_source_d); + fake_make_operate_process_return( + data_make, + data_make->main->cache_arguments.used + ? data_make->main->cache_arguments.array[0] + : f_string_empty_s, + F_status_is_error(main->setting.state.status) + ? 1 + : 0, + F_status_debug_source_d + ); } #endif // _di_fake_make_operate_process_type_skeleton_ diff --git a/level_3/fake/c/main/make/print/error.c b/level_3/fake/c/main/make/print/error.c index e53b102df..3d8146220 100644 --- a/level_3/fake/c/main/make/print/error.c +++ b/level_3/fake/c/main/make/print/error.c @@ -282,7 +282,7 @@ extern "C" { #endif // _di_fake_make_print_error_pop_last_path_ #ifndef _di_fake_make_print_error_program_failed_ - f_status_t fake_make_print_error_program_failed(fl_print_t * const print, const int return_code, const f_string_t debug) { + f_status_t fake_make_print_error_program_failed(fl_print_t * const print, const f_string_static_t program, const int return_code, const f_string_t debug) { if (!print) return F_status_set_error(F_output_not); if (print->verbosity < f_console_verbosity_error_e) return F_output_not; @@ -298,6 +298,10 @@ extern "C" { fl_print_format(macro_fll_error_s(020_debug_close), print->to, print->context); } + if (program.used) { + fl_print_format("for program '%[%s%]%['", print->to, print->notable, program, print->notable, print->context, print->context); + } + fl_print_format(".%]%r", print->to, print->context, f_string_eol_s); f_file_stream_unlock(print->to); diff --git a/level_3/fake/c/main/make/print/error.h b/level_3/fake/c/main/make/print/error.h index 7bac7b802..d488daa02 100644 --- a/level_3/fake/c/main/make/print/error.h +++ b/level_3/fake/c/main/make/print/error.h @@ -423,6 +423,8 @@ extern "C" { * This requires print.custom to be fake_main_t. * * This does not alter print.custom.setting.state.status. + * @param program + * The program that was executed. * @param return_code * The return code from the program. * @param debug @@ -437,7 +439,7 @@ extern "C" { * F_output_not (with error bit) if setting is NULL. */ #ifndef _di_fake_make_print_error_program_failed_ - extern f_status_t fake_make_print_error_program_failed(fl_print_t * const print, const int return_code, const f_string_t debug); + extern f_status_t fake_make_print_error_program_failed(fl_print_t * const print, const f_string_static_t program, const int return_code, const f_string_t debug); #endif // _di_fake_make_print_error_program_failed_ /** diff --git a/level_3/fake/c/main/print/context.c b/level_3/fake/c/main/print/context.c index b8b0d1ea3..832817258 100644 --- a/level_3/fake/c/main/print/context.c +++ b/level_3/fake/c/main/print/context.c @@ -64,7 +64,7 @@ extern "C" { f_file_stream_lock(print->to); fl_print_format("%[%Q%S'%]", print->to, print->context, print->prefix, before, print->context); - fl_print_format("%[%un%]", print->to, print->notable, number, print->notable); + fl_print_format(f_string_format_un_single_s.string, print->to, print->notable, number, print->notable); fl_print_format("%['%S.%]%r", print->to, print->context, after, print->context, f_string_eol_s); f_file_stream_unlock(print->to); diff --git a/level_3/fake/c/main/print/error.c b/level_3/fake/c/main/print/error.c index fb5c4d057..4bdf09dc3 100644 --- a/level_3/fake/c/main/print/error.c +++ b/level_3/fake/c/main/print/error.c @@ -366,7 +366,7 @@ extern "C" { f_file_stream_lock(print->to); fl_print_format("%[%QOccurred on invalid UTF-8 character at %s (at '%]", print->to, print->context, print->prefix, main->setting.state.status == F_complete_not_utf_eos ? "end of string" : "stop point of string", print->context); - fl_print_format("%[%un%]", print->to, print->notable, range.start, print->notable); + fl_print_format(f_string_format_un_single_s.string, print->to, print->notable, range.start, print->notable); fl_print_format("%[ of the setting file '%]", print->to, print->context, print->context); fl_print_format(f_string_format_Q_single_s.string, print->to, print->notable, path_file, print->notable); fl_print_format("%[').%]%r", print->to, print->context, print->context, f_string_eol_s); @@ -408,7 +408,7 @@ extern "C" { f_file_stream_lock(print->to); fl_print_format("%[%S%Q%S(%]", print->to, print->context, prefix, print->prefix, before, print->context); - fl_print_format("%[%un%]", print->to, print->notable, number, print->notable); + fl_print_format(f_string_format_un_single_s.string, print->to, print->notable, number, print->notable); fl_print_format("%[)%S'%]", print->to, print->context, middle, print->context); fl_print_format(f_string_format_Q_single_s.string, print->to, print->notable, variable, print->notable); fl_print_format("%[%S", print->to, print->context, after); @@ -460,7 +460,7 @@ extern "C" { #endif // _di_fake_print_error_number_too_large_ #ifndef _di_fake_print_error_operation_failed_ - f_status_t fake_print_error_operation_failed(fl_print_t * const print, const f_string_static_t buffer, const f_range_t section_name, const f_range_t operation_name) { + f_status_t fake_print_error_operation_failed(fl_print_t * const print, const f_string_static_t buffer, const f_range_t section_name, const f_range_t operation_name, const f_ranges_t content) { if (!print || !print->custom) return F_status_set_error(F_output_not); if (print->verbosity < f_console_verbosity_error_e) return F_output_not; @@ -481,8 +481,24 @@ extern "C" { fl_print_format("%[' from section '%]", print->to, print->context, print->context); fl_print_format(f_string_format_Q_range_single_s.string, print->to, print->notable, buffer, section_name, print->notable); fl_print_format("%[' on line%] ", print->to, print->context, print->context); - fl_print_format("%[%un%]", print->to, print->notable, line, print->notable); - fl_print_format(" %[failed.%]%r", print->to, print->context, print->context, f_string_eol_s); + fl_print_format(f_string_format_un_single_s.string, print->to, print->notable, line, print->notable); + + if (content.used) { + fl_print_format(" %[for '%]%[", print->to, print->context, print->context, print->notable); + + for (f_number_unsigned_t i = 0; i < content.used; ++i) { + fl_print_format(f_string_format_Q_range_single_s.string, print->to, print->notable, buffer, content.array[i], print->notable); + + if (i + 1 < content.used) { + fl_print_format(f_string_ascii_space_s.string, print->to); + } + } // for + + fl_print_format("%]%[' failed.%]%r", print->to, print->notable, print->context, print->context, f_string_eol_s); + } + else { + fl_print_format(" %[failed.%]%r", print->to, print->context, print->context, f_string_eol_s); + } f_file_stream_unlock(print->to); diff --git a/level_3/fake/c/main/print/error.h b/level_3/fake/c/main/print/error.h index 2e46959c9..fc98d58c6 100644 --- a/level_3/fake/c/main/print/error.h +++ b/level_3/fake/c/main/print/error.h @@ -568,6 +568,8 @@ extern "C" { * The range within the buffer representing the section name. * @param operation_name * The range within the buffer representing the operation name within the section. + * @param content + * The range within the buffer representing the content for the operation within the section. * * @return * F_okay on success. @@ -580,7 +582,7 @@ extern "C" { * @see fl_print_format() */ #ifndef _di_fake_print_error_operation_failed_ - extern f_status_t fake_print_error_operation_failed(fl_print_t * const print, const f_string_static_t buffer, const f_range_t section_name, const f_range_t operation_name); + extern f_status_t fake_print_error_operation_failed(fl_print_t * const print, const f_string_static_t buffer, const f_range_t section_name, const f_range_t operation_name, const f_ranges_t content); #endif // _di_fake_print_error_operation_failed_ /** -- 2.52.0