The resulting design made --expand redundant, so it is removed.
Substitution is implemented and works independent of the --name parameter.
Added a new macro to the FLL project called f_macro_memory_structure_macro_increment().
Too often do I have to create those structures, so here is a macro to perform the increment.
I started to update the rest of the project and then decided not to spend time on that right now.
This, therefore, primarily focuses on getting the macro working in IKI.
IKI Read is now considered usable, except for the UTF-8 support.
The UTF-8 support is dependent on updating a ton of UTF-8 codes.
This will be done at a later time.
The IKI Read program will eventually need to be reviewed for mistakes and cleanups.
if (!found) {
// populate list of remaining parameters.parameter not associated with anything.
if (remaining->used >= remaining->size) {
- f_macro_string_lengths_resize(status, (*remaining), remaining->size + f_console_default_allocation_step);
-
+ f_macro_memory_structure_macro_increment(status, (*remaining), 1, f_console_default_allocation_step, f_macro_string_lengths_resize, F_buffer_too_large);
if (F_status_is_error(status)) {
f_macro_string_lengths_delete_simple(needs_additional);
return status;
* @return
* F_none on success.
* F_data_not if "additional" parameters were expected but not found.
+ * F_buffer_too_large (with error bit) if a buffer would exceed max length.
* F_failure (with error bit) if width is not long enough to convert when processing arguments as UTF-8.
* F_parameter (with error bit) if a parameter is invalid.
* F_utf (with error bit) if character is an invalid UTF-8 character, when processing arguments.
}
if (names->used >= names->size) {
- f_macro_string_dynamics_resize(status, (*names), names->size + f_directory_default_allocation_step);
+ f_macro_memory_structure_macro_increment(status, (*names), 1, f_directory_default_allocation_step, f_macro_string_dynamics_resize, F_buffer_too_large);
if (F_status_is_error(status)) break;
}
* @return
* F_none on success.
* F_data_not if directory is empty.
+ * F_buffer_too_large (with error bit) if the directory buffer max length would be exceeded.
* F_failure (with error bit) if failed to read directory information.
* F_memory_reallocation (with error bit) on memory reallocation error.
* F_parameter (with error bit) if a parameter is invalid.
}
#endif // _di_f_macro_memory_structures_adjust_
+/**
+ * Provide a macro for calling other macros for incrementing a buffer.
+ *
+ * If the used + step is greater than size, then increase by step_default.
+ * If step_default exceeds f_array_length_size, then attempt to increment by step.
+ * If step exceeds f_array_length_size, set status to error_too_large.
+ *
+ * Be sure to check size for error after calling this.
+ *
+ * status: the status to return.
+ * structures: the structures to operate on.
+ * step: the step to increase by, must be less than or equal to step_default.
+ * step_default: the default step to increase by if memory allows.
+ * macro_resize: the resize structure macro to call that excepts the exact arguments: (status, structure, new_length).
+ * error_too_large: the error status to return when f_array_length_size would be exceeded.
+ */
+#ifndef _di_f_macro_memory_structure_macro_increment_
+ #define f_macro_memory_structure_macro_increment(status, structure, step, step_default, macro_resize, error_too_large) \
+ if (structure.used + step > structure.size) { \
+ if (structure.used + step_default > f_array_length_size) { \
+ if (structure.used + step > structure.size > f_array_length_size) { \
+ status = F_status_set_error(error_too_large); \
+ } \
+ else { \
+ macro_resize(status, structure, structure.size + step); \
+ } \
+ } \
+ else { \
+ macro_resize(status, structure, structure.size + step_default); \
+ } \
+ }
+#endif // _di_f_macro_memory_structure_macro_increment_
+
#ifdef __cplusplus
} // extern "C"
#endif
if (length == 0) {
// When PATH is "", this is actually a valid search path for PWD.
// Therefore append an equivalent representation of PWD (string used length is 0).
- if (paths->used + 1 > paths->size) {
- if (paths->size + f_memory_default_allocation_step > f_array_length_size) {
- if (paths->size + 1 > f_array_length_size) {
- return F_status_set_error(F_buffer_too_large);
- }
-
- f_macro_string_dynamics_resize(status, (*paths), paths->used + 1);
- if (F_status_is_error(status)) return status;
- }
- else {
- f_macro_string_dynamics_resize(status, (*paths), paths->used + f_memory_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
- }
+ f_macro_memory_structure_macro_increment(status, (*paths), 1, f_memory_default_allocation_step, f_macro_string_dynamics_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
f_macro_string_dynamic_clear(paths->array[paths->used]);
paths->used++;
for (i = 0; i <= length; i++) {
if (i == length || path[i] == f_path_separator_variable[0]) {
- if (paths->used + 1 > paths->size) {
- if (paths->size + f_memory_default_allocation_step > f_array_length_size) {
- if (paths->size + 1 > f_array_length_size) {
- return F_status_set_error(F_buffer_too_large);
- }
-
- f_macro_string_dynamics_resize(status, (*paths), paths->used + 1);
- if (F_status_is_error(status)) return status;
- }
- else {
- f_macro_string_dynamics_resize(status, (*paths), paths->used + f_memory_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
- }
+ f_macro_memory_structure_macro_increment(status, (*paths), 1, f_memory_default_allocation_step, f_macro_string_dynamics_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
if (i == 0) {
f_macro_string_dynamic_clear(paths->array[paths->used]);
if (path.used == 0) {
// When PATH is "", this is actually a valid search path for PWD.
// Therefore append an equivalent representation of PWD (string used length is 0).
- if (paths->used + 1 > paths->size) {
- if (paths->size + f_memory_default_allocation_step > f_array_length_size) {
- if (paths->size + 1 > f_array_length_size) {
- return F_status_set_error(F_buffer_too_large);
- }
-
- f_macro_string_dynamics_resize(status, (*paths), paths->used + 1);
- if (F_status_is_error(status)) return status;
- }
- else {
- f_macro_string_dynamics_resize(status, (*paths), paths->used + f_memory_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
- }
+ f_macro_memory_structure_macro_increment(status, (*paths), 1, f_memory_default_allocation_step, f_macro_string_dynamics_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
f_macro_string_dynamic_clear(paths->array[paths->used]);
paths->used++;
for (i = 0; i <= path.used; i++) {
if (i == path.used || path.string[i] == f_path_separator_variable[0]) {
- if (paths->used + 1 > paths->size) {
- if (paths->size + f_memory_default_allocation_step > f_array_length_size) {
- if (paths->size + 1 > f_array_length_size) {
- return F_status_set_error(F_buffer_too_large);
- }
-
- f_macro_string_dynamics_resize(status, (*paths), paths->used + 1);
- if (F_status_is_error(status)) return status;
- }
- else {
- f_macro_string_dynamics_resize(status, (*paths), paths->used + f_memory_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
- }
+ f_macro_memory_structure_macro_increment(status, (*paths), 1, f_memory_default_allocation_step, f_macro_string_dynamics_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
if (i == 0) {
f_macro_string_dynamic_clear(paths->array[paths->used]);
if (length == 0) {
// When PATH is "", this is actually a valid search path for PWD.
// Therefore append an equivalent representation of PWD (string used length is 0).
- if (paths->used + 1 > paths->size) {
- if (paths->size + f_memory_default_allocation_step > f_array_length_size) {
- if (paths->size + 1 > f_array_length_size) {
- return F_status_set_error(F_buffer_too_large);
- }
-
- f_macro_string_dynamics_resize(status, (*paths), paths->used + 1);
- if (F_status_is_error(status)) return status;
- }
- else {
- f_macro_string_dynamics_resize(status, (*paths), paths->used + f_memory_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
- }
+ f_macro_memory_structure_macro_increment(status, (*paths), 1, f_memory_default_allocation_step, f_macro_string_dynamics_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
paths->array[paths->used].string = 0;
paths->array[paths->used].used = 0;
j--;
if (j == 0 || path[j] == f_path_separator_variable[0]) {
- if (paths->used + 1 > paths->size) {
- if (paths->size + f_memory_default_allocation_step > f_array_length_size) {
- if (paths->size + 1 > f_array_length_size) {
- return F_status_set_error(F_buffer_too_large);
- }
-
- f_macro_string_dynamics_resize(status, (*paths), paths->used + 1);
- if (F_status_is_error(status)) return status;
- }
- else {
- f_macro_string_dynamics_resize(status, (*paths), paths->used + f_memory_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
- }
+ f_macro_memory_structure_macro_increment(status, (*paths), 1, f_memory_default_allocation_step, f_macro_string_dynamics_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
if (path[j] == f_path_separator_variable[0]) {
total = last - i;
if (path.used == 0) {
// When PATH is "", this is actually a valid search path for PWD.
// Therefore append an equivalent representation of PWD (string used length is 0).
- if (paths->used + 1 > paths->size) {
- if (paths->size + f_memory_default_allocation_step > f_array_length_size) {
- if (paths->size + 1 > f_array_length_size) {
- return F_status_set_error(F_buffer_too_large);
- }
-
- f_macro_string_dynamics_resize(status, (*paths), paths->used + 1);
- if (F_status_is_error(status)) return status;
- }
- else {
- f_macro_string_dynamics_resize(status, (*paths), paths->used + f_memory_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
- }
+ f_macro_memory_structure_macro_increment(status, (*paths), 1, f_memory_default_allocation_step, f_macro_string_dynamics_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
f_macro_string_dynamic_clear(paths->array[paths->used]);
paths->used++;
j--;
if (j == 0 || path.string[j] == f_path_separator_variable[0]) {
- if (paths->used + 1 > paths->size) {
- if (paths->size + f_memory_default_allocation_step > f_array_length_size) {
- if (paths->size + 1 > f_array_length_size) {
- return F_status_set_error(F_buffer_too_large);
- }
-
- f_macro_string_dynamics_resize(status, (*paths), paths->used + 1);
- if (F_status_is_error(status)) return status;
- }
- else {
- f_macro_string_dynamics_resize(status, (*paths), paths->used + f_memory_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
- }
+ f_macro_memory_structure_macro_increment(status, (*paths), 1, f_memory_default_allocation_step, f_macro_string_dynamics_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
if (path.string[j] == f_path_separator_variable[0]) {
total = last - i;
width = f_macro_utf_byte_width(serialize.string[i]);
if (serialize.string[i] == f_serialize_simple_splitter || i + 1 >= serialize.used) {
- if (strings->used >= strings->size) {
- f_macro_string_dynamics_resize(status, (*strings), strings->size + f_serialize_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
+ f_macro_memory_structure_macro_increment(status, (*strings), 1, f_serialize_default_allocation_step, f_macro_string_dynamics_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
if (start == i) {
strings->array[strings->used].used = 0;
width = f_macro_utf_byte_width(serialize.string[i]);
if (serialize.string[i] == f_serialize_simple_splitter || i + 1 >= serialize.used) {
- if (locations->used >= locations->size) {
- f_macro_string_ranges_resize(status, (*locations), locations->size + f_serialize_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
+ f_macro_memory_structure_macro_increment(status, (*locations), 1, f_serialize_default_allocation_step, f_macro_string_ranges_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
if (start == i) {
// provide an invalid start to stop range to communicate that there is no data.
* @return
* F_none on success.
* F_incomplete_utf_eos if end of sting is reached before a complete UTF-8 character can be processed.
+ * F_buffer_too_large (with error bit) if a buffer would exceed maximum length.
* F_memory_reallocation (with error bit) on memory reallocation error.
* F_parameter (with error bit) if a parameter is invalid.
*/
* @return
* F_none on success.
* F_incomplete_utf_eos if end of sting is reached before a complete UTF-8 character can be processed.
+ * F_buffer_too_large (with error bit) if a buffer would exceed memory max length.
* F_memory_reallocation (with error bit) on memory reallocation error.
* F_parameter (with error bit) if a parameter is invalid.
*/
const f_status status_failure = status;
- if (failures->used + 1 > failures->size) {
- if (failures->size + f_memory_default_allocation_step > f_array_length_size) {
- if (failures->size + 1 > f_array_length_size) {
- return F_status_set_error(F_buffer_too_large);
- }
-
- f_macro_directory_statuss_resize(status, (*failures), failures->used + 1);
- if (F_status_is_error(status)) return status;
- }
- else {
- f_macro_directory_statuss_resize(status, (*failures), failures->used + f_memory_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
- }
+ f_macro_memory_structure_macro_increment(status, (*failures), 1, f_memory_default_allocation_step, f_macro_directory_statuss_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
f_directory_status failure = f_directory_status_initialize;
f_string_length size = 0;
const f_status status_failure = status;
- if (failures->used + 1 > failures->size) {
- if (failures->size + f_memory_default_allocation_step > f_array_length_size) {
- if (failures->size + 1 > f_array_length_size) {
- return F_status_set_error(F_buffer_too_large);
- }
-
- f_macro_directory_statuss_resize(status, (*failures), failures->used + 1);
- if (F_status_is_error(status)) return status;
- }
- else {
- f_macro_directory_statuss_resize(status, (*failures), failures->used + f_memory_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
- }
+ f_macro_memory_structure_macro_increment(status, (*failures), 1, f_memory_default_allocation_step, f_macro_directory_statuss_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
f_directory_status failure = f_directory_status_initialize;
f_string_length size = 0;
* @return
* F_none on success.
* F_data_not if directory is empty.
+ * F_buffer_too_large (with error bit) if a buffer would exceed max length.
* F_directory_descriptor (with error bit) on directory file descriptor error.
* F_directory_open (with error bit) on directory open error.
* F_directory_stream (with error bit) on directory stream error.
status = F_none;
}
else {
- if (destination->used >= destination->size) {
- f_macro_string_dynamics_resize(status, (*destination), destination->size + f_console_default_allocation_step);
- if (F_status_is_error(status)) return status;
- }
+ f_macro_memory_structure_macro_increment(status, (*destination), 1, f_console_default_allocation_step, f_macro_string_dynamics_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) break;
destination->array[destination->used] = ripped;
destination->used++;
* @return
* F_none on success.
* F_data_not if nothing to rip, no allocations or reallocations are performed.
+ * F_buffer_too_large (with error bit) if a buffer would exceed max length.
* F_memory_allocation (with error bit) on memory allocation error.
* F_memory_reallocation (with error bit) on memory reallocation error.
* F_parameter (with error bit) if a parameter is invalid.
printf("%c", f_string_eol[0]);
fll_program_print_help_option(context, iki_read_short_substitute, iki_read_long_substitute, f_console_symbol_short_enable, f_console_symbol_long_enable,"Substitute the entire variable for the given name and content value with the given string.");
- fll_program_print_help_option(context, iki_read_short_expand, iki_read_long_expand, f_console_symbol_short_enable, f_console_symbol_long_enable, " Expand variables into their respective content.");
fll_program_print_help_usage(context, iki_read_name, "filename(s)");
printf(" option, requires 3 additional parameters: ");
fl_color_print(f_type_output, context.notable, context.reset, "<");
- printf("%s", iki_read_replacement_vocabulary);
+ printf("%s", iki_read_substitution_vocabulary);
fl_color_print(f_type_output, context.notable, context.reset, ">");
printf(" ");
fl_color_print(f_type_output, context.notable, context.reset, "<");
- printf("%s", iki_read_replacement_replace);
+ printf("%s", iki_read_substitution_replace);
fl_color_print(f_type_output, context.notable, context.reset, ">");
printf(" ");
fl_color_print(f_type_output, context.notable, context.reset, "<");
- printf("%s", iki_read_replacement_with);
+ printf("%s", iki_read_substitution_with);
fl_color_print(f_type_output, context.notable, context.reset, ">");
printf(".%c", f_string_eol[0]);
- fl_color_print(f_type_output, context.notable, context.reset, " %s", iki_read_replacement_vocabulary);
+ fl_color_print(f_type_output, context.notable, context.reset, " %s", iki_read_substitution_vocabulary);
printf(": The name of the vocabulary whose content is to be substituted.%c", f_string_eol[0]);
- fl_color_print(f_type_output, context.notable, context.reset, " %s", iki_read_replacement_replace);
+ fl_color_print(f_type_output, context.notable, context.reset, " %s", iki_read_substitution_replace);
printf(": The content matching this exact string will be substituted.%c", f_string_eol[0]);
- fl_color_print(f_type_output, context.notable, context.reset, " %s", iki_read_replacement_with);
+ fl_color_print(f_type_output, context.notable, context.reset, " %s", iki_read_substitution_with);
printf(": The new string to use as the substitute.%c", f_string_eol[0]);
printf("%c", f_string_eol[0]);
printf("%c", f_string_eol[0]);
- printf(" All substitution is applied before any expansion when both the ", f_string_eol[0]);
- fl_color_print(f_type_output, context.notable, context.reset, "%s%s", f_console_symbol_long_enable, iki_read_long_substitute);
- printf(" option and the ");
- fl_color_print(f_type_output, context.notable, context.reset, "%s%s", f_console_symbol_long_enable, iki_read_long_expand);
- printf(" option are specified.%c", f_string_eol[0]);
-
- printf("%c", f_string_eol[0]);
-
printf(" The default behavior is to only display content portion of the IKI variable.%c", f_string_eol[0]);
printf("%c", f_string_eol[0]);
}
}
- if (data->parameters[iki_read_parameter_expand].result == f_console_result_found) {
- if (data->parameters[iki_read_parameter_total].result == f_console_result_found) {
- if (data->verbosity != iki_read_verbosity_quiet) {
- fprintf(f_type_error, "%c", f_string_eol[0]);
- fl_color_print(f_type_error, data->context.error, data->context.reset, "ERROR: Cannot specify the '");
- fl_color_print(f_type_error, data->context.notable, data->context.reset, "%s%s", f_console_symbol_long_enable, iki_read_long_expand);
- fl_color_print(f_type_error, data->context.error, data->context.reset, "' parameter with the '");
- fl_color_print(f_type_error, data->context.notable, data->context.reset, "%s%s", f_console_symbol_long_enable, iki_read_long_total);
- fl_color_print_line(f_type_error, data->context.error, data->context.reset, "' parameter.");
- }
-
- status = F_status_set_error(F_parameter);
- }
- }
-
if (data->parameters[iki_read_parameter_literal].result == f_console_result_found) {
if (data->parameters[iki_read_parameter_object].result == f_console_result_found) {
if (data->verbosity != iki_read_verbosity_quiet) {
};
#define iki_read_short_at "a"
- #define iki_read_short_expand "e"
#define iki_read_short_line "l"
#define iki_read_short_literal "L"
#define iki_read_short_name "n"
#define iki_read_short_whole "w"
#define iki_read_long_at "at"
- #define iki_read_long_expand "expand"
#define iki_read_long_line "line"
#define iki_read_long_literal "literal"
#define iki_read_long_name "name"
iki_read_parameter_version,
iki_read_parameter_at,
- iki_read_parameter_expand,
iki_read_parameter_line,
iki_read_parameter_literal,
iki_read_parameter_name,
f_console_parameter_initialize(f_console_standard_short_verbose, f_console_standard_long_verbose, 0, 0, f_console_type_inverse), \
f_console_parameter_initialize(f_console_standard_short_version, f_console_standard_long_version, 0, 0, f_console_type_inverse), \
f_console_parameter_initialize(iki_read_short_at, iki_read_long_at, 0, 1, f_console_type_normal), \
- f_console_parameter_initialize(iki_read_short_expand, iki_read_long_expand, 0, 0, f_console_type_normal), \
f_console_parameter_initialize(iki_read_short_line, iki_read_long_line, 0, 1, f_console_type_normal), \
f_console_parameter_initialize(iki_read_short_literal, iki_read_long_literal, 0, 0, f_console_type_normal), \
f_console_parameter_initialize(iki_read_short_name, iki_read_long_name, 0, 1, f_console_type_normal), \
f_console_parameter_initialize(iki_read_short_total, iki_read_long_total, 0, 0, f_console_type_normal), \
}
- #define iki_read_total_parameters 16
+ #define iki_read_total_parameters 15
#endif // _di_iki_read_defines_
-#ifndef _di_iki_read_replacement_
- #define iki_read_replacement_vocabulary "vocabulary"
- #define iki_read_replacement_replace "replace"
- #define iki_read_replacement_with "with"
+#ifndef _di_iki_read_substitution_
+ #define iki_read_substitution_vocabulary "vocabulary"
+ #define iki_read_substitution_replace "replace"
+ #define iki_read_substitution_with "with"
typedef struct {
- f_string_static vocabulary;
f_string_static replace;
f_string_static with;
- } iki_read_replacement;
+ } iki_read_substitution;
- #define iki_read_replacement_initialize \
+ #define iki_read_substitution_initialize \
{ \
f_string_static_initialize, \
f_string_static_initialize, \
- f_string_static_initialize, \
}
- #define macro_iki_read_replacement_initialize(vocabulary, replace, with) \
+ #define macro_iki_read_substitution_initialize(replace, with) \
{ \
- f_macro_string_static_initialize(vocabulary), \
f_macro_string_static_initialize(replace), \
f_macro_string_static_initialize(with), \
}
-#endif // _di_iki_read_replacement_
+#endif // _di_iki_read_substitution_
-#ifndef _di_iki_read_replacements_
+#ifndef _di_iki_read_substitutions_
typedef struct {
- iki_read_replacement *array;
+ iki_read_substitution *array;
f_array_length size;
f_array_length used;
- } iki_read_replacements;
+ } iki_read_substitutions;
- #define iki_read_replacements_initialize {0, 0, 0}
+ #define iki_read_substitutions_initialize {0, 0, 0}
- #define macro_iki_read_replacements_clear(replacements) f_macro_memory_structure_clear(replacements)
+ #define macro_iki_read_substitutions_clear(replacements) f_macro_memory_structure_clear(replacements)
- #define macro_iki_read_replacements_new(status, replacements, length) f_macro_memory_structure_new(status, replacements, iki_read_replacement, length)
+ #define macro_iki_read_substitutions_new(status, replacements, length) f_macro_memory_structure_new(status, replacements, iki_read_substitution, length)
- #define macro_iki_read_replacements_delete_simple(replacements) \
+ #define macro_iki_read_substitutions_delete_simple(replacements) \
replacements.used = replacements.size; \
while (replacements.used > 0) { \
replacements.used--; \
} \
- if (replacements.used == 0) f_macro_memory_structure_delete_simple(replacements, iki_read_replacement)
+ if (replacements.used == 0) f_macro_memory_structure_delete_simple(replacements, iki_read_substitution)
- #define macro_iki_read_replacements_destroy_simple(replacements) \
+ #define macro_iki_read_substitutions_destroy_simple(replacements) \
replacements.used = replacements.size; \
while (replacements.used > 0) { \
replacements.used--; \
} \
- if (replacements.used == 0) f_macro_memory_structure_destroy_simple(replacements, iki_read_replacement)
+ if (replacements.used == 0) f_macro_memory_structure_destroy_simple(replacements, iki_read_substitution)
- #define macro_iki_read_replacements_resize(status, replacements, new_length) \
+ #define macro_iki_read_substitutions_resize(status, replacements, new_length) \
status = F_none; \
if (new_length < replacements.size) { \
f_array_length i = replacements.size - new_length; \
if (status != F_none) break; \
} \
} \
- if (status == F_none) status = f_memory_resize((void **) & replacements.array, sizeof(iki_read_replacement), replacements.size, new_length); \
+ if (status == F_none) status = f_memory_resize((void **) & replacements.array, sizeof(iki_read_substitution), replacements.size, new_length); \
if (status == F_none) { \
if (new_length > replacements.size) { \
f_array_length i = replacements.size; \
for (; i < new_length; i++) { \
- memset(&replacements.array[i], 0, sizeof(iki_read_replacement)); \
+ memset(&replacements.array[i], 0, sizeof(iki_read_substitution)); \
} \
} \
replacements.size = new_length; \
if (replacements.used > replacements.size) replacements.used = new_length; \
}
- #define macro_iki_read_replacements_adjust(status, replacements, new_length) \
+ #define macro_iki_read_substitutions_adjust(status, replacements, new_length) \
status = F_none; \
if (new_length < replacements.size) { \
f_array_length i = replacements.size - new_length; \
if (status != F_none) break; \
} \
} \
- if (status == F_none) status = f_memory_adjust((void **) & replacements.array, sizeof(iki_read_replacement), replacements.size, new_length); \
+ if (status == F_none) status = f_memory_adjust((void **) & replacements.array, sizeof(iki_read_substitution), replacements.size, new_length); \
if (status == F_none) { \
if (new_length > replacements.size) { \
f_array_length i = replacements.size; \
for (; i < new_length; i++) { \
- memset(&replacements.array[i], 0, sizeof(iki_read_replacement)); \
+ memset(&replacements.array[i], 0, sizeof(iki_read_substitution)); \
} \
} \
replacements.size = new_length; \
if (replacements.used > replacements.size) replacements.used = new_length; \
}
-#endif // _di_iki_read_replacements_
+#endif // _di_iki_read_substitutions_
#ifndef _di_iki_read_data_
typedef struct {
f_string_dynamic buffer;
- iki_read_replacements replacements;
+ iki_read_substitutions replacements;
fl_color_context context;
} iki_read_data;
0, \
0, \
f_string_dynamic_initialize, \
- iki_read_replacements_initialize, \
+ iki_read_substitutions_initialize, \
fl_color_context_initialize, \
}
#endif // _di_iki_read_data_
return status;
}
+ bool content_only = data->mode == iki_read_mode_content;
+
+ iki_read_substitutions substitutionss[variable->used];
+
+ memset(substitutionss, 0, sizeof(iki_read_substitutions) * variable->used);
+
+ if (data->mode == iki_read_mode_literal || data->mode == iki_read_mode_content) {
+ status = iki_read_substitutions_identify(arguments, file_name, data, vocabulary, substitutionss);
+ if (F_status_is_error(status)) {
+ iki_read_print_error(data->context, data->verbosity, F_status_set_fine(status), "iki_read_substitutions_identify", F_true);
+
+ for (f_array_length i = 0; i < variable->used; i++) {
+ macro_iki_read_substitutions_delete_simple(substitutionss[i]);
+ } // for
+
+ return status;
+ }
+ }
+
if (data->parameters[iki_read_parameter_name].result == f_console_result_additional) {
f_string_dynamic name = f_string_dynamic_initialize;
f_array_length index = 0;
f_array_length i = 0;
f_array_length j = 0;
-
buffer_range->start = 0;
for (; i < data->parameters[iki_read_parameter_name].additional.used; i++) {
if (F_status_is_error(status)) {
iki_read_print_error(data->context, data->verbosity, F_status_set_fine(status), "fl_string_append_nulless", F_true);
+ for (f_array_length i = 0; i < variable->used; i++) {
+ macro_iki_read_substitutions_delete_simple(substitutionss[i]);
+ } // for
+
f_macro_string_dynamic_delete_simple(name);
return status;
}
if (status == F_equal_to) {
unmatched = F_false;
- f_print_string_dynamic_partial(f_type_output, data->buffer, ranges->array[j]);
+ if (substitutionss[j].used) {
+ iki_read_substitutions_print(*data, *variable, *content, *ranges, substitutionss[j], j, content_only);
+ }
+ else {
+ f_print_string_dynamic_partial(f_type_output, data->buffer, ranges->array[j]);
+ }
+
printf("%c", f_string_eol[0]);
}
} // for
f_macro_string_dynamic_delete_simple(name);
- if (unmatched) return F_data_not;
+ if (unmatched) status = F_data_not;
+ else status = F_none;
}
else if (ranges->used) {
- for (f_array_length i = 0; i < ranges->used; i++) {
- f_print_string_dynamic_partial(f_type_output, data->buffer, ranges->array[i]);
+ f_array_length i = 0;
+ f_string_length j = 0;
+
+ for (; i < ranges->used; i++) {
+
+ if (substitutionss[i].used) {
+ iki_read_substitutions_print(*data, *variable, *content, *ranges, substitutionss[i], i, content_only);
+ }
+ else {
+ f_print_string_dynamic_partial(f_type_output, data->buffer, ranges->array[i]);
+ }
+
printf("%c", f_string_eol[0]);
} // for
+
+ status = F_none;
}
else {
- return F_data_not;
+ status = F_data_not;
}
- return F_none;
+ for (f_array_length i = 0; i < variable->used; i++) {
+ macro_iki_read_substitutions_delete_simple(substitutionss[i]);
+ } // for
+
+ return status;
}
#endif // _di_iki_read_process_buffer_ranges_
return F_none;
}
+ iki_read_substitutions substitutionss[variable->used];
+
+ memset(substitutionss, 0, sizeof(iki_read_substitutions) * variable->used);
+
+ if (data->mode == iki_read_mode_literal || data->mode == iki_read_mode_content) {
+ status = iki_read_substitutions_identify(arguments, file_name, data, vocabulary, substitutionss);
+ if (F_status_is_error(status)) {
+ iki_read_print_error(data->context, data->verbosity, F_status_set_fine(status), "iki_read_substitutions_identify", F_true);
+
+ for (f_array_length i = 0; i < variable->used; i++) {
+ macro_iki_read_substitutions_delete_simple(substitutionss[i]);
+ } // for
+
+ return status;
+ }
+ }
+
f_string_dynamics names = f_string_dynamics_initialize;
f_string_range name_range = f_string_range_initialize;
+ f_string_range substitution_range = f_string_range_initialize;
+
bool name_missed = F_true;
+ substitution_range.start = 0;
+
if (data->parameters[iki_read_parameter_name].result == f_console_result_additional) {
f_array_length i = 0;
f_array_length j = 0;
} // for
if (name_missed) {
- if (names.used + 1 > names.size) {
- if (names.used + f_iki_default_allocation_step > f_array_length_size) {
- if (names.used + 1 > names.size > f_array_length_size) {
- iki_read_print_error(data->context, data->verbosity, F_buffer_too_large, "iki_read_process_buffer_ranges_whole", F_true);
-
- f_macro_string_dynamics_delete_simple(names);
- return F_status_set_error(F_buffer_too_large);
- }
- else {
- f_macro_string_dynamics_resize(status, names, names.used + 1);
- }
- }
- else {
- f_macro_string_dynamics_resize(status, names, names.used + f_iki_default_allocation_step);
- }
-
- if (F_status_is_error(status)) {
- iki_read_print_error(data->context, data->verbosity, F_status_set_fine(status), "iki_read_process_buffer_ranges_whole", F_true);
-
- f_macro_string_dynamics_delete_simple(names);
- return status;
- }
+ f_macro_memory_structure_macro_increment(status, names, 1, f_iki_default_allocation_step, f_macro_string_dynamics_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) {
+ iki_read_print_error(data->context, data->verbosity, F_status_set_fine(status), "iki_read_process_buffer_ranges_whole", F_true);
+ break;
}
status = fl_string_append_nulless(arguments.argv[index], length_argument, &names.array[names.used]);
if (F_status_is_error(status)) {
iki_read_print_error(data->context, data->verbosity, F_status_set_fine(status), "fl_string_append_nulless", F_true);
-
- f_macro_string_dynamics_delete_simple(names);
- return status;
+ break;
}
names.used++;
}
} // for
+
+ if (F_status_is_error(status)) {
+ for (i = 0; i < variable->used; i++) {
+ macro_iki_read_substitutions_delete_simple(substitutionss[i]);
+ } // for
+
+ f_macro_string_dynamics_delete_simple(names);
+ return status;
+ }
}
- f_string_length i = buffer_range.start;
- f_array_length j = 0;
- f_array_length k = 0;
+ {
+ f_string_length i = buffer_range.start;
+ f_array_length j = 0;
+ f_array_length k = 0;
- range = buffer_range;
- name_range.start = 0;
+ range = buffer_range;
+ name_range.start = 0;
- while (i <= range.stop && j < variable->used) {
- if (i < variable->array[j].start) {
- range.stop = variable->array[j].start - 1;
+ while (i <= range.stop && j < variable->used) {
+ if (i < variable->array[j].start) {
+ range.stop = variable->array[j].start - 1;
- f_print_string_dynamic_partial(f_type_output, data->buffer, range);
+ f_print_string_dynamic_partial(f_type_output, data->buffer, range);
- range.start = variable->array[j].stop + 1;
- range.stop = buffer_range.stop;
+ range.start = variable->array[j].stop + 1;
+ range.stop = buffer_range.stop;
- i = variable->array[j].start;
- }
+ i = variable->array[j].start;
+ }
- // @todo handle expansion and substitution.
- if (names.used) {
- name_missed = F_true;
+ if (names.used) {
+ name_missed = F_true;
- for (k = 0; k < names.used; k++) {
- name_range.stop = names.array[k].used - 1;
+ for (k = 0; k < names.used; k++) {
+ name_range.stop = names.array[k].used - 1;
- status = fl_string_dynamic_partial_compare(data->buffer, names.array[k], vocabulary->array[j], name_range);
+ status = fl_string_dynamic_partial_compare(data->buffer, names.array[k], vocabulary->array[j], name_range);
- if (status == F_equal_to) {
- name_missed = F_false;
- break;
- }
- } // for
+ if (status == F_equal_to) {
+ name_missed = F_false;
+ break;
+ }
+ } // for
- if (name_missed) {
- f_print_string_dynamic_partial(f_type_output, data->buffer, variable->array[j]);
+ if (name_missed) {
+ if (substitutionss[j].used) {
+ iki_read_substitutions_print(*data, *variable, *content, *variable, substitutionss[j], j, F_false);
+ }
+ else {
+ f_print_string_dynamic_partial(f_type_output, data->buffer, variable->array[j]);
+ }
+ }
+ else {
+ if (substitutionss[j].used) {
+ iki_read_substitutions_print(*data, *variable, *content, *ranges, substitutionss[j], j, F_true);
+ }
+ else {
+ f_print_string_dynamic_partial(f_type_output, data->buffer, ranges->array[j]);
+ }
+ }
}
else {
- f_print_string_dynamic_partial(f_type_output, data->buffer, ranges->array[j]);
+ if (substitutionss[j].used) {
+ iki_read_substitutions_print(*data, *variable, *content, *ranges, substitutionss[j], j, F_true);
+ }
+ else {
+ f_print_string_dynamic_partial(f_type_output, data->buffer, ranges->array[j]);
+ }
}
- }
- else {
- f_print_string_dynamic_partial(f_type_output, data->buffer, ranges->array[j]);
- }
- i = variable->array[j].stop + 1;
- j++;
- } // while
+ i = variable->array[j].stop + 1;
+ j++;
+ } // while
- if (i <= buffer_range.stop) {
- range.start = i;
- f_print_string_dynamic_partial(f_type_output, data->buffer, range);
+ if (i <= buffer_range.stop) {
+ range.start = i;
+ f_print_string_dynamic_partial(f_type_output, data->buffer, range);
+ }
}
+ for (f_array_length i = 0; i < variable->used; i++) {
+ macro_iki_read_substitutions_delete_simple(substitutionss[i]);
+ } // for
+
f_macro_string_dynamics_delete_simple(names);
return F_none;
}
}
#endif // _di_iki_read_process_buffer_total_
+#ifndef _di_iki_read_substitutions_identify_
+ f_return_status iki_read_substitutions_identify(const f_console_arguments arguments, const f_string file_name, iki_read_data *data, f_iki_vocabulary *vocabulary, iki_read_substitutions *substitutionss) {
+ if (data->parameters[iki_read_parameter_substitute].result != f_console_result_additional) return F_none;
+
+ f_status status = F_none;
+
+ f_array_length i = 0;
+ f_array_length j = 0;
+
+ f_array_length index = 0;
+ f_array_length index_2 = 0;
+
+ f_string_length length = 0;
+
+ f_console_parameter *parameter = &data->parameters[iki_read_parameter_substitute];
+
+ for (; i < parameter->additional.used; i += 3) {
+ index = parameter->additional.array[i];
+ length = strnlen(arguments.argv[index], f_console_length_size);
+
+ for (j = 0; j < vocabulary->used; j++) {
+ status = fl_string_compare(arguments.argv[index], data->buffer.string + vocabulary->array[j].start, length, (vocabulary->array[j].stop - vocabulary->array[j].start) + 1);
+
+ if (status == F_equal_to) {
+ f_macro_memory_structure_macro_increment(status, substitutionss[j], 1, f_iki_default_allocation_step, macro_iki_read_substitutions_resize, F_buffer_too_large);
+ if (F_status_is_error(status)) return status;
+
+ index = parameter->additional.array[i + 1];
+ index_2 = substitutionss[j].used;
+ substitutionss[j].array[index_2].replace.string = arguments.argv[index];
+ substitutionss[j].array[index_2].replace.used = strnlen(arguments.argv[index], f_console_length_size);
+ substitutionss[j].array[index_2].replace.size = substitutionss[j].array[index_2].replace.used;
+
+ index = parameter->additional.array[i + 2];
+ substitutionss[j].array[index_2].with.string = arguments.argv[index];
+ substitutionss[j].array[index_2].with.used = strnlen(arguments.argv[index], f_console_length_size);
+ substitutionss[j].array[index_2].with.size = substitutionss[j].array[index_2].with.used;
+
+ substitutionss[j].used++;
+ }
+ } // for
+ } // for
+
+ return F_none;
+ }
+#endif // _di_iki_read_substitutions_identify_
+
+#ifndef _di_iki_read_substitutions_print_
+ void iki_read_substitutions_print(const iki_read_data data, const f_iki_variable variable, const f_iki_content content, const f_string_ranges ranges, const iki_read_substitutions substitutions, const f_string_length index, const bool content_only) {
+ f_status status = F_none;
+
+ f_string_length i = 0;
+ f_string_range range = f_string_range_initialize;
+
+ range.start = 0;
+
+ for (; i < substitutions.used; i++) {
+ range.stop = substitutions.array[i].replace.used - 1;
+
+ status = fl_string_dynamic_partial_compare(substitutions.array[i].replace, data.buffer, range, content.array[index]);
+ if (status == F_equal_to) break;
+ } // for
+
+ if (status == F_equal_to) {
+ if (content_only) {
+ f_print_string_dynamic(f_type_output, substitutions.array[i].with);
+ }
+ else {
+ range.start = variable.array[index].start;
+ range.stop = content.array[index].start - 1;
+
+ f_print_string_dynamic_partial(f_type_output, data.buffer, range);
+
+ f_print_string_dynamic(f_type_output, substitutions.array[i].with);
+
+ range.start = content.array[index].stop + 1;
+ range.stop = variable.array[index].stop;
+
+ f_print_string_dynamic_partial(f_type_output, data.buffer, range);
+ }
+ }
+ else {
+ f_print_string_dynamic_partial(f_type_output, data.buffer, ranges.array[index]);
+ }
+ }
+#endif // _di_iki_read_substitutions_print_
+
#ifdef __cplusplus
} // extern "C"
#endif
extern f_return_status iki_read_process_buffer_total(const f_console_arguments arguments, const f_string file_name, iki_read_data *data, f_iki_variable *variable, f_iki_vocabulary *vocabulary, f_iki_content *content) f_gcc_attribute_visibility_internal;
#endif // _di_iki_read_process_buffer_total_
+/**
+ * Process the arguments, associating substitions with a given vocabulary.
+ *
+ * @param arguments
+ * The console arguments passed to the program.
+ * @param file_name
+ * The name of the file being processed.
+ * @param data
+ * The program specific data.
+ * @param vocabulary
+ * The ranges representing a vocabulary.
+ * @param substitutionss
+ * An array of substitutionss with each index representing an index for in the respective vocabulary array.
+ *
+ * @return
+ * F_none on success.
+ *
+ * Status codes (with error bit) are returned on any problem.
+ */
+#ifndef _di_iki_read_substitutions_identify_
+ extern f_return_status iki_read_substitutions_identify(const f_console_arguments arguments, const f_string file_name, iki_read_data *data, f_iki_vocabulary *vocabulary, iki_read_substitutions *substitutionss) f_gcc_attribute_visibility_internal;
+#endif // _di_iki_read_substitutions_identify_
+
+/**
+ * Print any applicable substition and if there is non then print the given range at the given index.
+ *
+ * @param data
+ * The program specific data.
+ * @param variable
+ * The ranges representing a variable.
+ * @param content
+ * The ranges representing a content.
+ * @param ranges
+ * The ranges containing the desired range to print as specified by index.
+ * @param substitutions
+ * The substitions associated with the variable for the given range at the given index to use for potential printing.
+ * @param index
+ * The index used to identify the desired range in variable, content, and ranges.
+ * @param content_only
+ * Set to TRUE to only print the content when printing substituted text.
+ * Set to FALSE to print the entire variable when printing substituted text.
+ */
+#ifndef _di_iki_read_substitutions_print_
+ extern void iki_read_substitutions_print(const iki_read_data data, const f_iki_variable variable, const f_iki_content content, const f_string_ranges ranges, const iki_read_substitutions substitutions, const f_string_length index, const bool content_only) f_gcc_attribute_visibility_internal;
+#endif // _di_iki_read_substitutions_print_
+
#ifdef __cplusplus
} // extern "C"
#endif