Finish updating the fss write programs.
I will sleep on this and then review them later to look for mistakes, oversights, bugs, inconsistencies, and possible cleanups.
Improve the console parameter handling functionality.
The sub-locations need to also have their locations stored.
Cleanup the struct stat file_stat name, renaming it to stat_file for more consistency.
Remove some memsets(), these might be better left to higher level operations.
Assuming I do not change my mind on this later.
Use the word "amount" instead of "length" when the increase/decrease is not the whole length but a fraction.
Reorganize some string functions parameters to be more consistent with the current design practices.
* - location: The last location in argv[] where this parameter is found.
* - location_sub: The last sub-location at location in argv (only used by short parameters, such as -h or +l).
* - locations: All locations within argv where this parameter is found (order is preserved).
+ * - locations_sub: All sub-locations within argv where this parameter is found (order is preserved).
* - additional: An array of locations representing where in the argv[] the additional arguments are found.
*/
#ifndef _di_f_console_parameter_t_
f_array_length_t location;
f_string_length_t location_sub;
f_array_lengths_t locations;
+ f_array_lengths_t locations_sub;
f_array_lengths_t additional;
} f_console_parameter_t;
- #define f_console_parameter_t_initialize(symbol_short, symbol_long, symbol_other, has_additional, type_value) { symbol_short, symbol_long, symbol_other, has_additional, type_value, f_console_result_none, 0, 0, 0, f_array_lengths_t_initialize, f_array_lengths_t_initialize }
+ #define f_console_parameter_t_initialize(symbol_short, symbol_long, symbol_other, has_additional, type_value) { symbol_short, symbol_long, symbol_other, has_additional, type_value, f_console_result_none, 0, 0, 0, f_array_lengths_t_initialize, f_array_lengths_t_initialize, f_array_lengths_t_initialize }
- #define f_macro_console_parameter_t_initialize(symbol_short, symbol_long, symbol_other, has_additional, type_value, result, total, location, location_sub, locations, additional) { symbol_short, symbol_long, symbol_other, has_additional, type_value, result, total, location, location_sub, locations, additional }
+ #define f_macro_console_parameter_t_initialize(symbol_short, symbol_long, symbol_other, has_additional, type_value, result, total, location, location_sub, locations, locations_sub, additional) { symbol_short, symbol_long, symbol_other, has_additional, type_value, result, total, location, location_sub, locations, locations_sub, additional }
#endif // _di_f_console_parameter_t_
/**
}
}
+ if (parameters.parameter[i].locations_sub.used == parameters.parameter[i].locations_sub.size) {
+ f_macro_string_lengths_t_resize(status, parameters.parameter[i].locations_sub, parameters.parameter[i].locations_sub.size + f_console_default_allocation_step);
+
+ if (F_status_is_error(status)) {
+ f_macro_string_lengths_t_delete_simple(needs_additional);
+ return status;
+ }
+ }
+
parameters.parameter[i].locations.array[parameters.parameter[i].locations.used++] = location;
parameters.parameter[i].result = f_console_result_found;
if (result == console_short) {
parameters.parameter[i].location_sub = sub_location;
+ parameters.parameter[i].locations_sub.array[parameters.parameter[i].locations_sub.used++] = sub_location;
+ }
+ else {
+ parameters.parameter[i].locations_sub.array[parameters.parameter[i].locations_sub.used++] = 0;
}
if (parameters.parameter[i].has_additional) {
}
}
+ if (parameters.parameter[i].locations_sub.used == parameters.parameter[i].locations_sub.size) {
+ f_macro_string_lengths_t_resize(status, parameters.parameter[i].locations_sub, parameters.parameter[i].locations_sub.size + f_console_default_allocation_step);
+
+ if (F_status_is_error(status)) {
+ f_macro_string_lengths_t_delete_simple(needs_additional);
+ return status;
+ }
+ }
+
parameters.parameter[i].locations.array[parameters.parameter[i].locations.used++] = location;
+ parameters.parameter[i].locations_sub.array[parameters.parameter[i].locations_sub.used++] = 0;
parameters.parameter[i].result = f_console_result_found;
parameters.parameter[i].location = location;
#endif // _di_level_0_parameter_checking_
f_status_t status = F_none;
- struct stat file_stat;
+ struct stat stat_file;
- memset(&file_stat, 0, sizeof(struct stat));
+ memset(&stat_file, 0, sizeof(struct stat));
- status = private_f_file_stat(path, F_false, &file_stat);
+ status = private_f_file_stat(path, F_false, &stat_file);
if (F_status_is_error(status)) {
if (F_status_set_fine(status) == F_file_found_not) return F_false;
#endif // _di_level_0_parameter_checking_
f_status_t status = F_none;
- struct stat file_stat;
+ struct stat stat_file;
- memset(&file_stat, 0, sizeof(struct stat));
+ memset(&stat_file, 0, sizeof(struct stat));
- status = private_f_file_stat_at(at_id, path, flag, &file_stat);
+ status = private_f_file_stat_at(at_id, path, flag, &stat_file);
if (F_status_is_error(status)) {
if (F_status_set_fine(status) == F_file_found_not) return F_false;
if (!path) return F_status_set_error(F_parameter);
#endif // _di_level_0_parameter_checking_
- struct stat file_stat;
+ struct stat stat_file;
- memset(&file_stat, 0, sizeof(struct stat));
+ memset(&stat_file, 0, sizeof(struct stat));
- f_status_t status = private_f_file_stat(path, dereference, &file_stat);
+ f_status_t status = private_f_file_stat(path, dereference, &stat_file);
if (F_status_is_error(status)) return status;
- if (f_macro_file_type_get(file_stat.st_mode) == type) return F_true;
+ if (f_macro_file_type_get(stat_file.st_mode) == type) return F_true;
return F_false;
}
if (!path) return F_status_set_error(F_parameter);
#endif // _di_level_0_parameter_checking_
- struct stat file_stat;
+ struct stat stat_file;
- memset(&file_stat, 0, sizeof(struct stat));
+ memset(&stat_file, 0, sizeof(struct stat));
- if (fstatat(at_id, path, &file_stat, flag) < 0) {
+ if (fstatat(at_id, path, &stat_file, flag) < 0) {
if (errno == ENAMETOOLONG) return F_status_set_error(F_name);
if (errno == EFAULT) return F_status_set_error(F_buffer);
if (errno == ENOMEM) return F_status_set_error(F_memory_out);
return F_status_set_error(F_file_stat);
}
- if (file_stat.st_mode == (S_IFMT & S_IFDIR)) return F_true;
+ if (stat_file.st_mode == (S_IFMT & S_IFDIR)) return F_true;
return F_false;
}
f_macro_string_dynamic_t_resize(status, (*buffer), buffer->size + file.size_read);
if (F_status_is_error(status)) return status;
-
- memset(buffer->string + buffer->used, 0, sizeof(file.size_read));
}
buffer_read = buffer->string + buffer->used;
f_string_t buffer_read = 0;
- if (buffer->used + size_read > buffer->size) {
- if (buffer->size + size_read > f_string_length_t_size) {
+ if (buffer->used + file.size_read > buffer->size) {
+ if (buffer->size + file.size_read > f_string_length_t_size) {
return F_status_set_error(F_string_too_large);
}
- f_macro_string_dynamic_t_resize(status, (*buffer), buffer->size + size_read);
+ f_macro_string_dynamic_t_resize(status, (*buffer), buffer->size + file.size_read);
if (F_status_is_error(status)) return status;
-
- memset(buffer->string + buffer->used, 0, sizeof(file.size_read));
}
buffer_read = buffer->string + buffer->used;
f_macro_string_dynamic_t_resize(status, (*buffer), buffer->size + buffer_size);
if (F_status_is_error(status)) return status;
-
- memset(buffer->string + buffer->used, 0, sizeof(buffer_size));
}
buffer_read = buffer->string + buffer->used;
if (!size) return F_status_set_error(F_parameter);
#endif // _di_level_0_parameter_checking_
- struct stat file_stat;
+ struct stat stat_file;
- memset(&file_stat, 0, sizeof(struct stat));
+ memset(&stat_file, 0, sizeof(struct stat));
- f_status_t status = private_f_file_stat(path, dereference, &file_stat);
+ f_status_t status = private_f_file_stat(path, dereference, &stat_file);
if (F_status_is_error(status)) return status;
- *size = file_stat.st_size;
+ *size = stat_file.st_size;
return F_none;
}
if (!size) return F_status_set_error(F_parameter);
#endif // _di_level_0_parameter_checking_
- struct stat file_stat;
+ struct stat stat_file;
- memset(&file_stat, 0, sizeof(struct stat));
+ memset(&stat_file, 0, sizeof(struct stat));
- f_status_t status = private_f_file_stat_at(at_id, path, dereference, &file_stat);
+ f_status_t status = private_f_file_stat_at(at_id, path, dereference, &stat_file);
if (F_status_is_error(status)) return status;
- *size = file_stat.st_size;
+ *size = stat_file.st_size;
return F_none;
}
if (!size) return F_status_set_error(F_parameter);
#endif // _di_level_0_parameter_checking_
- struct stat file_stat;
+ struct stat stat_file;
- memset(&file_stat, 0, sizeof(struct stat));
+ memset(&stat_file, 0, sizeof(struct stat));
- f_status_t status = private_f_file_stat_by_id(id, &file_stat);
+ f_status_t status = private_f_file_stat_by_id(id, &stat_file);
if (F_status_is_error(status)) return status;
- *size = file_stat.st_size;
+ *size = stat_file.st_size;
return F_none;
}
#endif // _di_f_file_size_by_id_
#ifndef _di_f_file_stat_
- f_return_status f_file_stat(const f_string_t path, const bool dereference, struct stat *file_stat) {
+ f_return_status f_file_stat(const f_string_t path, const bool dereference, struct stat *stat_file) {
#ifndef _di_level_0_parameter_checking_
if (!path) return F_status_set_error(F_parameter);
- if (!file_stat) return F_status_set_error(F_parameter);
+ if (!stat_file) return F_status_set_error(F_parameter);
#endif // _di_level_0_parameter_checking_
- return private_f_file_stat(path, dereference, file_stat);
+ return private_f_file_stat(path, dereference, stat_file);
}
#endif // _di_f_file_stat_
#ifndef _di_f_file_stat_at_
- f_return_status f_file_stat_at(const int at_id, const f_string_t path, const int flag, struct stat *file_stat) {
+ f_return_status f_file_stat_at(const int at_id, const f_string_t path, const int flag, struct stat *stat_file) {
#ifndef _di_level_0_parameter_checking_
if (!path) return F_status_set_error(F_parameter);
if (at_id <= 0) return F_status_set_error(F_parameter);
- if (!file_stat) return F_status_set_error(F_parameter);
+ if (!stat_file) return F_status_set_error(F_parameter);
#endif // _di_level_0_parameter_checking_
- return private_f_file_stat_at(at_id, path, flag, file_stat);
+ return private_f_file_stat_at(at_id, path, flag, stat_file);
}
#endif // _di_f_file_stat_at_
#ifndef _di_f_file_stat_by_id_
- f_return_status f_file_stat_by_id(const int id, struct stat *file_stat) {
+ f_return_status f_file_stat_by_id(const int id, struct stat *stat_file) {
#ifndef _di_level_0_parameter_checking_
if (id <= 0) return F_status_set_error(F_parameter);
- if (!file_stat) return F_status_set_error(F_parameter);
+ if (!stat_file) return F_status_set_error(F_parameter);
#endif // _di_level_0_parameter_checking_
- return private_f_file_stat_by_id(id, file_stat);
+ return private_f_file_stat_by_id(id, stat_file);
}
#endif // _di_f_file_stat_by_id_
if (F_status_is_error(status)) return status;
}
- memset(buffer->string + buffer->used, 0, sizeof(buffer_size));
-
size_read = fread(buffer->string + buffer->used, amount, file.size_read, file.stream);
if (ferror(file.stream)) {
f_macro_string_dynamic_t_resize(status, (*buffer), buffer->size + buffer_size);
if (F_status_is_error(status)) return status;
-
- memset(buffer->string + buffer->used, 0, sizeof(buffer_size));
}
size_read = fread(buffer->string + buffer->used, amount, file.size_read, file.stream);
#endif // _di_level_0_parameter_checking_
f_status_t status = F_none;
- struct stat file_stat;
+ struct stat stat_file;
- memset(&file_stat, 0, sizeof(struct stat));
+ memset(&stat_file, 0, sizeof(struct stat));
- status = private_f_file_stat(path, F_false, &file_stat);
+ status = private_f_file_stat(path, F_false, &stat_file);
if (F_status_set_fine(status) == F_file_found_not) {
return private_f_file_create(path, mode, dereference);
#endif // _di_level_0_parameter_checking_
f_status_t status = F_none;
- struct stat file_stat;
+ struct stat stat_file;
- memset(&file_stat, 0, sizeof(struct stat));
+ memset(&stat_file, 0, sizeof(struct stat));
- status = private_f_file_stat_at(at_id, path, flag, &file_stat);
+ status = private_f_file_stat_at(at_id, path, flag, &stat_file);
if (F_status_set_fine(status) == F_file_found_not) {
return private_f_file_create_at(at_id, path, mode, F_false);
if (!type) return F_status_set_error(F_parameter);
#endif // _di_level_0_parameter_checking_
- struct stat file_stat;
+ struct stat stat_file;
- memset(&file_stat, 0, sizeof(struct stat));
+ memset(&stat_file, 0, sizeof(struct stat));
- if (stat(path, &file_stat) < 0) {
+ if (stat(path, &stat_file) < 0) {
if (errno == ENAMETOOLONG) return F_status_set_error(F_name);
if (errno == EFAULT) return F_status_set_error(F_buffer);
if (errno == ENOMEM) return F_status_set_error(F_memory_out);
return F_status_set_error(F_file_stat);
}
- *type = f_macro_file_type_get(file_stat.st_mode);
+ *type = f_macro_file_type_get(stat_file.st_mode);
return F_none;
}
if (!type) return F_status_set_error(F_parameter);
#endif // _di_level_0_parameter_checking_
- struct stat file_stat;
+ struct stat stat_file;
- memset(&file_stat, 0, sizeof(struct stat));
+ memset(&stat_file, 0, sizeof(struct stat));
- if (fstatat(at_id, path, &file_stat, flag) < 0) {
+ if (fstatat(at_id, path, &stat_file, flag) < 0) {
if (errno == ENAMETOOLONG) return F_status_set_error(F_name);
if (errno == EFAULT) return F_status_set_error(F_buffer);
if (errno == ENOMEM) return F_status_set_error(F_memory_out);
return F_status_set_error(F_file_stat);
}
- *type = f_macro_file_type_get(file_stat.st_mode);
+ *type = f_macro_file_type_get(stat_file.st_mode);
return F_none;
}
* @param dereference
* Set to TRUE to dereferenc symlinks (often is what is desired).
* Set to FALSE to operate on the symlink itself.
- * @param file_stat
+ * @param stat_file
* The statistics read.
*
* @return
* @see stat()
*/
#ifndef _di_f_file_stat_
- extern f_return_status f_file_stat(const f_string_t path, const bool dereference, struct stat *file_stat);
+ extern f_return_status f_file_stat(const f_string_t path, const bool dereference, struct stat *stat_file);
#endif // _di_f_file_stat_
/**
* The path to the file.
* @param flag
* Any valid flag, such as f_file_at_path_empty, f_file_at_automount_no, or f_file_at_symlink_follow_no.
- * @param file_stat
+ * @param stat_file
* The statistics read.
*
* @return
* @see fstatat()
*/
#ifndef _di_f_file_stat_at_
- extern f_return_status f_file_stat_at(const int at_id, const f_string_t path, const int flag, struct stat *file_stat);
+ extern f_return_status f_file_stat_at(const int at_id, const f_string_t path, const int flag, struct stat *stat_file);
#endif // _di_f_file_stat_at_
/**
*
* @param id
* The file descriptor.
- * @param file_stat
+ * @param stat_file
* The statistics read.
*
* @return
* @see fstat()
*/
#ifndef _di_f_file_stat_by_id_
- extern f_return_status f_file_stat_by_id(const int id, struct stat *file_stat);
+ extern f_return_status f_file_stat_by_id(const int id, struct stat *stat_file);
#endif // _di_f_file_stat_by_id_
/**
if (!length) return F_data_not;
for (register f_string_length_t i = 0; i < length; ++i) {
- if (!string[i]) continue;
-
- if (!fputc(string[i], output)) {
- return F_status_set_error(F_output);
+ if (string[i]) {
+ if (!fputc(string[i], output)) {
+ return F_status_set_error(F_output);
+ }
}
} // for
return F_status_set_error(F_string_too_large);
}
- f_macro_string_dynamic_t_resize(status, (*destination), 1);
+ f_macro_string_dynamic_t_resize(status, (*destination), destination->used + 1);
if (F_status_is_error(status)) return status;
}
else {
- f_macro_string_dynamic_t_resize(status, (*destination), f_fss_default_allocation_step);
+ f_macro_string_dynamic_t_resize(status, (*destination), destination->used + f_fss_default_allocation_step);
if (F_status_is_error(status)) return status;
}
#endif // !defined(_di_fl_string_compare_trim_) || !defined(_di_fl_string_dynamic_compare_trim_) || !defined(_di_fl_string_dynamic_partial_compare_trim_)
#if !defined(_di_fl_string_dynamic_size_increase_) || !defined(_di_fl_string_append_) || !defined(_di_fl_string_dynamic_append_) || !defined(_di_fl_string_append_mash_) || !defined(_di_fl_string_dynamic_mash_) || !defined(_di_fl_string_append_nulless_) || !defined(_di_fl_string_dynamic_append_nulless_) || !defined(_di_fl_string_mash_nulless_) || !defined(_di_fl_string_dynamic_mash_nulless_) || !defined(_di_fl_string_prepend_) || !defined(_di_fl_string_dynamic_prepend_) || !defined(_di_fl_string_prepend_nulless_) || !defined(_di_fl_string_dynamic_prepend_nulless_)
- f_return_status private_fl_string_dynamic_size_increase(const f_string_length_t length, f_string_dynamic_t *string) {
+ f_return_status private_fl_string_dynamic_size_increase(const f_string_length_t amount, f_string_dynamic_t *string) {
f_status_t status = F_none;
- if (string->size + length > f_string_length_t_size) {
+ if (string->size + amount > f_string_length_t_size) {
if (string->size == f_string_length_t_size) {
return F_status_set_error(F_string_too_large);
}
return F_string_too_large;
}
- f_macro_string_dynamic_t_resize(status, (*string), string->size + length);
+ f_macro_string_dynamic_t_resize(status, (*string), string->size + amount);
return status;
}
#endif // !defined(_di_fl_string_dynamic_size_increase_) || !defined(_di_fl_string_append_) || !defined(_di_fl_string_dynamic_append_) || !defined(_di_fl_string_append_mash_) || !defined(_di_fl_string_dynamic_mash_) || !defined(_di_fl_string_append_nulless_) || !defined(_di_fl_string_dynamic_append_nulless_) || !defined(_di_fl_string_mash_nulless_) || !defined(_di_fl_string_dynamic_mash_nulless_) || !defined(_di_fl_string_prepend_) || !defined(_di_fl_string_dynamic_prepend_) || !defined(_di_fl_string_prepend_nulless_) || !defined(_di_fl_string_dynamic_prepend_nulless_)
*
* Intended to be shared to each of the different implementation variations.
*
- * @param length
+ * @param amount
* A positive number greater than 0 representing how much to increase the size by.
* @param string
* The string to resize.
* F_string_too_large (with error bit) if the combined string is too large.
*/
#if !defined(_di_fl_string_dynamic_size_increase_) || !defined(_di_fl_string_append_) || !defined(_di_fl_string_dynamic_append_) || !defined(_di_fl_string_append_mash_) || !defined(_di_fl_string_dynamic_mash_) || !defined(_di_fl_string_append_nulless_) || !defined(_di_fl_string_dynamic_append_nulless_) || !defined(_di_fl_string_mash_nulless_) || !defined(_di_fl_string_dynamic_mash_nulless_) || !defined(_di_fl_string_prepend_) || !defined(_di_fl_string_dynamic_prepend_) || !defined(_di_fl_string_prepend_nulless_) || !defined(_di_fl_string_dynamic_prepend_nulless_)
- extern f_return_status private_fl_string_dynamic_size_increase(const f_string_length_t length, f_string_dynamic_t *string) f_gcc_attribute_visibility_internal;
+ extern f_return_status private_fl_string_dynamic_size_increase(const f_string_length_t amount, f_string_dynamic_t *string) f_gcc_attribute_visibility_internal;
#endif // !defined(_di_fl_string_dynamic_size_increase_) || !defined(_di_fl_string_append_) || !defined(_di_fl_string_dynamic_append_) || !defined(_di_fl_string_append_mash_) || !defined(_di_fl_string_dynamic_mash_) || !defined(_di_fl_string_append_nulless_) || !defined(_di_fl_string_dynamic_append_nulless_) || !defined(_di_fl_string_mash_nulless_) || !defined(_di_fl_string_dynamic_mash_nulless_) || !defined(_di_fl_string_prepend_) || !defined(_di_fl_string_dynamic_prepend_) || !defined(_di_fl_string_prepend_nulless_) || !defined(_di_fl_string_dynamic_prepend_nulless_)
/**
#endif // _di_fl_string_dynamic_rip_nulless_
#ifndef _di_fl_string_dynamic_size_decrease_
- f_return_status fl_string_dynamic_size_decrease(const f_string_length_t length, f_string_dynamic_t *string) {
+ f_return_status fl_string_dynamic_size_decrease(const f_string_length_t amount, f_string_dynamic_t *string) {
#ifndef _di_level_1_parameter_checking_
- if (!length) return F_status_set_error(F_parameter);
+ if (!amount) return F_status_set_error(F_parameter);
if (!string) return F_status_set_error(F_parameter);
#endif // _di_level_1_parameter_checking_
f_status_t status = F_none;
- if (string->size - length > 0) {
- f_macro_string_dynamic_t_resize(status, (*string), string->size - length);
+ if (string->size - amount > 0) {
+ f_macro_string_dynamic_t_resize(status, (*string), string->size - amount);
}
- else if (string->size - length <= 0) {
+ else if (string->size - amount <= 0) {
f_macro_string_dynamic_t_delete(status, (*string));
}
#endif // _di_fl_string_dynamic_size_decrease_
#ifndef _di_fl_string_dynamic_size_increase_
- f_return_status fl_string_dynamic_size_increase(const f_string_length_t length, f_string_dynamic_t *string) {
+ f_return_status fl_string_dynamic_size_increase(const f_string_length_t amount, f_string_dynamic_t *string) {
#ifndef _di_level_1_parameter_checking_
- if (!length) return F_status_set_error(F_parameter);
+ if (!amount) return F_status_set_error(F_parameter);
if (!string) return F_status_set_error(F_parameter);
#endif // _di_level_1_parameter_checking_
- return private_fl_string_dynamic_size_increase(length, string);
+ return private_fl_string_dynamic_size_increase(amount, string);
}
#endif // _di_fl_string_dynamic_size_increase_
#endif // _di_fl_string_dynamic_seek_line_
#ifndef _di_fl_string_dynamic_seek_line_to_
- f_return_status fl_string_dynamic_seek_line_to(const f_string_t string, f_string_range_t *range, const int8_t seek_to_this) {
+ f_return_status fl_string_dynamic_seek_line_to(const f_string_t string, const int8_t seek_to_this, f_string_range_t *range) {
#ifndef _di_level_1_parameter_checking_
if (!range) return F_status_set_error(F_parameter);
#endif // _di_level_1_parameter_checking_
#endif // _di_fl_string_dynamic_seek_line_to_
#ifndef _di_fl_string_dynamic_seek_line_to_utf_character_
- f_return_status fl_string_dynamic_seek_line_to_utf_character(const f_string_t string, f_string_range_t *range, const f_utf_character_t seek_to_this) {
+ f_return_status fl_string_dynamic_seek_line_to_utf_character(const f_string_t string, const f_utf_character_t seek_to_this, f_string_range_t *range) {
#ifndef _di_level_1_parameter_checking_
if (!range) return F_status_set_error(F_parameter);
#endif // _di_level_1_parameter_checking_
#endif // _di_fl_string_dynamic_seek_line_to_utf_character_
#ifndef _di_fl_string_dynamic_seek_line_until_graph_
- f_return_status fl_string_dynamic_seek_line_until_graph(const f_string_t string, f_string_range_t *range, const int8_t placeholder) {
+ f_return_status fl_string_dynamic_seek_line_until_graph(const f_string_t string, const int8_t placeholder, f_string_range_t *range) {
#ifndef _di_level_1_parameter_checking_
if (!range) return F_status_set_error(F_parameter);
#endif // _di_level_1_parameter_checking_
#endif // _di_fl_string_dynamic_seek_line_until_graph_
#ifndef _di_fl_string_dynamic_seek_line_until_non_graph_
- f_return_status fl_string_dynamic_seek_line_until_non_graph(const f_string_t string, f_string_range_t *range, const int8_t placeholder) {
+ f_return_status fl_string_dynamic_seek_line_until_non_graph(const f_string_t string, const int8_t placeholder, f_string_range_t *range) {
#ifndef _di_level_1_parameter_checking_
if (!range) return F_status_set_error(F_parameter);
#endif // _di_level_1_parameter_checking_
#endif // _di_fl_string_dynamic_seek_line_until_non_graph_
#ifndef _di_fl_string_dynamic_seek_to_
- f_return_status fl_string_dynamic_seek_to(const f_string_t string, f_string_range_t *range, const int8_t seek_to_this) {
+ f_return_status fl_string_dynamic_seek_to(const f_string_t string, const int8_t seek_to_this, f_string_range_t *range) {
#ifndef _di_level_1_parameter_checking_
if (!range) return F_status_set_error(F_parameter);
#endif // _di_level_1_parameter_checking_
#endif // _di_fl_string_dynamic_seek_to_
#ifndef _di_fl_string_dynamic_seek_to_utf_character_
- f_return_status fl_string_dynamic_seek_to_utf_character(const f_string_t string, f_string_range_t *range, const f_utf_character_t seek_to_this) {
+ f_return_status fl_string_dynamic_seek_to_utf_character(const f_string_t string, const f_utf_character_t seek_to_this, f_string_range_t *range) {
#ifndef _di_level_1_parameter_checking_
if (!range) return F_status_set_error(F_parameter);
#endif // _di_level_1_parameter_checking_
* If the given length is too small, then the resize will fail.
* This will not shrink the size to less than 0.
*
- * @param length
+ * @param amount
* A positive number greater than 0 representing how much to decrease the size by.
* @param string
* The string to resize.
* F_string_too_large (with error bit) if the combined string is too large.
*/
#ifndef _di_fl_string_dynamic_size_decrease_
- extern f_return_status fl_string_dynamic_size_decrease(const f_string_length_t length, f_string_dynamic_t *string);
+ extern f_return_status fl_string_dynamic_size_decrease(const f_string_length_t amount, f_string_dynamic_t *string);
#endif // _di_fl_string_dynamic_size_decrease_
/**
* If the given length is too large for the buffer, then attempt to set max buffer size (f_string_length_t_size).
* If already set to the maximum buffer size, then the resize will fail.
*
- * @param length
+ * @param amount
* A positive number greater than 0 representing how much to increase the size by.
* @param string
* The string to resize.
* F_string_too_large (with error bit) if the combined string is too large.
*/
#ifndef _di_fl_string_dynamic_size_increase_
- extern f_return_status fl_string_dynamic_size_increase(const f_string_length_t length, f_string_dynamic_t *string);
+ extern f_return_status fl_string_dynamic_size_increase(const f_string_length_t amount, f_string_dynamic_t *string);
#endif // _di_fl_string_dynamic_size_increase_
/**
*
* @param string
* The string to traverse.
+ * @param seek_to_this
+ * A single-width character representing a character to seek to.
* @param range
* A range within the buffer representing the start and stop locations.
* The start location will be incremented by seek.
- * @param seek_to_this
- * A single-width character representing a character to seek to.
*
* @return
* F_none on success.
* F_parameter (with error bit) if a parameter is invalid.
*/
#ifndef _di_fl_string_dynamic_seek_line_to_
- extern f_return_status fl_string_dynamic_seek_line_to(const f_string_t string, f_string_range_t *range, const int8_t seek_to_this);
+ extern f_return_status fl_string_dynamic_seek_line_to(const f_string_t string, const int8_t seek_to_this, f_string_range_t *range);
#endif // _di_fl_string_dynamic_seek_line_to_
/**
*
* @param string
* The string to traverse.
+ * @param seek_to_this
+ * A 1-width, 2-width, 3-width, or 4-width character representing a character to seek to.
* @param range
* A range within the buffer representing the start and stop locations.
* The start location will be incremented by seek.
- * @param seek_to_this
- * A 1-width, 2-width, 3-width, or 4-width character representing a character to seek to.
*
* @return
* F_none on success.
* @see f_utf_char_to_character()
*/
#ifndef _di_fl_string_dynamic_seek_line_to_utf_character_
- extern f_return_status fl_string_dynamic_seek_line_to_utf_character(const f_string_t string, f_string_range_t *range, const f_utf_character_t seek_to_this);
+ extern f_return_status fl_string_dynamic_seek_line_to_utf_character(const f_string_t string, const f_utf_character_t seek_to_this, f_string_range_t *range);
#endif // _di_fl_string_dynamic_seek_line_to_utf_character_
/**
*
* @param string
* The string to traverse.
- * @param range
- * A range within the buffer representing the start and stop locations.
* @param placeholder
* A single-width character representing a placeholder to ignore (may be NULL).
+ * @param range
+ * A range within the buffer representing the start and stop locations.
*
* @return
* F_none on success.
* @see f_utf_is_graph()
*/
#ifndef _di_fl_string_dynamic_seek_line_until_graph_
- extern f_return_status fl_string_dynamic_seek_line_until_graph(const f_string_t string, f_string_range_t *range, const int8_t placeholder);
+ extern f_return_status fl_string_dynamic_seek_line_until_graph(const f_string_t string, const int8_t placeholder, f_string_range_t *range);
#endif // _di_fl_string_dynamic_seek_line_until_graph_
/**
*
* @param string
* The string to traverse.
- * @param range
- * A range within the buffer representing the start and stop locations.
* @param placeholder
* A single-width character representing a placeholder to ignore (may be NULL).
+ * @param range
+ * A range within the buffer representing the start and stop locations.
*
* @return
* F_none on success.
* @see f_utf_is_graph()
*/
#ifndef _di_fl_string_dynamic_seek_line_until_non_graph_
- extern f_return_status fl_string_dynamic_seek_line_until_non_graph(const f_string_t string, f_string_range_t *range, const int8_t placeholder);
+ extern f_return_status fl_string_dynamic_seek_line_until_non_graph(const f_string_t string, const int8_t placeholder, f_string_range_t *range);
#endif // _di_fl_string_dynamic_seek_line_until_non_graph_
/**
*
* @param string
* The string to traverse.
+ * @param seek_to_this
+ * A single-width character representing a character to seek to.
* @param range
* A range within the buffer representing the start and stop locations.
* The start location will be incremented by seek.
- * @param seek_to_this
- * A single-width character representing a character to seek to.
*
* @return
* F_none on success.
* F_parameter (with error bit) if a parameter is invalid.
*/
#ifndef _di_fl_string_dynamic_seek_to_
- extern f_return_status fl_string_dynamic_seek_to(const f_string_t string, f_string_range_t *range, const int8_t seek_to_this);
+ extern f_return_status fl_string_dynamic_seek_to(const f_string_t string, const int8_t seek_to_this, f_string_range_t *range);
#endif // _di_fl_string_dynamic_seek_to_
/**
*
* @param string
* The string to traverse.
+ * @param seek_to_this
+ * A 1-width, 2-width, 3-width, or 4-width character representing a character to seek to.
* @param range
* A range within the buffer representing the start and stop locations.
* The start location will be incremented by seek.
- * @param seek_to_this
- * A 1-width, 2-width, 3-width, or 4-width character representing a character to seek to.
*
* @return
* F_none on success.
* @see f_utf_char_to_character()
*/
#ifndef _di_fl_string_dynamic_seek_to_utf_character_
- extern f_return_status fl_string_dynamic_seek_to_utf_character(const f_string_t string, f_string_range_t *range, const f_utf_character_t seek_to_this);
+ extern f_return_status fl_string_dynamic_seek_to_utf_character(const f_string_t string, const f_utf_character_t seek_to_this, f_string_range_t *range);
#endif // _di_fl_string_dynamic_seek_to_utf_character_
/**
for (f_string_length_t i = 0; i < byte_dump_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
} // for
f_macro_string_lengths_t_delete_simple(data->remaining);
+
f_macro_color_context_t_delete_simple(data->context);
return F_none;
for (f_string_length_t i = 0; i < fake_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
} // for
#ifndef _di_firewall_delete_data_
f_return_status firewall_delete_data(firewall_data_t *data) {
- f_string_length_t i = 0;
- while (i < firewall_total_parameters) {
+ for (f_string_length_t i = 0; i < firewall_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
- i++;
- } // while
+ } // for
f_macro_string_dynamics_t_delete_simple(data->chains);
f_macro_string_lengths_t_delete_simple(data->remaining);
#ifndef _di_fss_basic_list_read_delete_data_
f_return_status fss_basic_list_read_delete_data(fss_basic_list_read_data_t *data) {
- f_status_t status = F_none;
- f_string_length_t i = 0;
- while (i < fss_basic_list_read_total_parameters) {
+ for (f_string_length_t i = 0; i < fss_basic_list_read_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
- i++;
- } // while
+ } // for
f_macro_fss_contents_t_delete_simple(data->contents);
f_macro_fss_objects_t_delete_simple(data->objects);
fss_basic_list_write_error_parameter_value_missing_print(*data, f_console_symbol_long_enable, fss_basic_list_write_long_content);
status = F_status_set_error(F_parameter);
}
- else if (data->parameters[fss_basic_list_write_parameter_object].locations.used != data->parameters[fss_basic_list_write_parameter_content].locations.used) {
+ else if (data->parameters[fss_basic_list_write_parameter_object].locations.used != data->parameters[fss_basic_list_write_parameter_content].locations.used && data->parameters[fss_basic_list_write_parameter_partial].result == f_console_result_none) {
fss_basic_list_write_error_parameter_same_times_print(*data);
status = F_status_set_error(F_parameter);
}
status = F_status_set_error(F_parameter);
}
}
+
+ if (F_status_is_error_not(status)) {
+ if (data->parameters[fss_basic_list_write_parameter_content].result == f_console_result_additional) {
+ f_array_length_t location_object = 0;
+ f_array_length_t location_content = 0;
+ f_array_length_t location_sub_object = 0;
+ f_array_length_t location_sub_content = 0;
+
+ for (f_array_length_t i = 0; i < data->parameters[fss_basic_list_write_parameter_object].locations.used; i++) {
+ location_object = data->parameters[fss_basic_list_write_parameter_object].locations.array[i];
+ location_content = data->parameters[fss_basic_list_write_parameter_content].locations.array[i];
+ location_sub_object = data->parameters[fss_basic_list_write_parameter_object].locations_sub.array[i];
+ location_sub_content = data->parameters[fss_basic_list_write_parameter_content].locations_sub.array[i];
+
+ if (location_object > location_content || location_object == location_content && location_sub_object > location_sub_content) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sEach ", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "%s%s", f_console_symbol_long_enable, fss_basic_list_write_long_object);
+ fl_color_print(data->error.to.stream, data->context.set.error, "' parameter must be specified before a '");
+ fl_color_print(data->error.to.stream, data->context.set.notable, "%s%s", f_console_symbol_long_enable, fss_basic_list_write_long_content);
+ fl_color_print(data->error.to.stream, data->context.set.error, "' parameter.%c", f_string_eol[0]);
+
+ status = F_status_set_error(F_parameter);
+ break;
+ }
+ } // for
+ }
+ }
}
else if (data->parameters[fss_basic_list_write_parameter_content].locations.used) {
if (data->parameters[fss_basic_list_write_parameter_content].locations.used != data->parameters[fss_basic_list_write_parameter_content].additional.used) {
status = F_status_set_error(F_parameter);
}
+
+ if (F_status_is_error_not(status) && data->process_pipe) {
+ if (data->parameters[fss_basic_list_write_parameter_partial].result == f_console_result_found) {
+ if (data->error.verbosity != f_console_verbosity_quiet) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sThe '", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "%s%s", f_console_symbol_long_enable, fss_basic_list_write_long_partial);
+ fl_color_print(data->error.to.stream, data->context.set.error, "' parameter cannot be used when processing a pipe.%c", f_string_eol[0]);
+ }
+
+ status = F_status_set_error(F_parameter);
+ }
+ }
}
- f_fss_quote_t quoted = f_fss_delimit_quote_double;
+ f_fss_quote_t quote = f_fss_delimit_quote_double;
if (F_status_is_error_not(status)) {
if (data->parameters[fss_basic_list_write_parameter_double].result == f_console_result_found) {
if (data->parameters[fss_basic_list_write_parameter_single].result == f_console_result_found) {
if (data->parameters[fss_basic_list_write_parameter_double].location < data->parameters[fss_basic_list_write_parameter_single].location) {
- quoted = f_fss_delimit_quote_single;
+ quote = f_fss_delimit_quote_single;
}
}
}
else if (data->parameters[fss_basic_list_write_parameter_single].result == f_console_result_found) {
- quoted = f_fss_delimit_quote_single;
+ quote = f_fss_delimit_quote_single;
}
}
f_string_dynamic_t escaped = f_string_dynamic_t_initialize;
if (data->process_pipe) {
- f_file_t input = f_file_t_initialize;
-
- input.id = f_type_descriptor_input;
- input.size_read = 1;
-
- bool object_ended = F_false;
-
- f_string_length_t previous = 0;
- f_string_range_t range = f_string_range_t_initialize;
-
- range.start = 0;
-
- if (data->parameters[fss_basic_list_write_parameter_partial].result == f_console_result_found) {
- for (f_status_t status_pipe = F_none; ; ) {
-
- if (status_pipe != F_none_eof) {
- status_pipe = f_file_read(input, &buffer);
-
- if (F_status_is_error(status_pipe)) {
- fll_error_file_print(data->error, F_status_set_fine(status), "f_file_read_to", F_true, "-", "read", fll_error_file_type_pipe);
-
- status = F_status_set_error(F_pipe);
- break;
- }
-
- if (!buffer.used) {
- if (data->error.verbosity != f_console_verbosity_quiet) {
- fl_color_print(data->error.to.stream, data->context.set.error, "%sThe pipe has no data.%c", fll_error_print_error, f_string_eol[0]);
- }
-
- status = F_status_set_error(F_parameter);
- break;
- }
-
- range.stop = buffer.used - 1;
- }
-
- previous = range.start;
- status = fl_string_dynamic_seek_line(buffer.string, &range);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_seek_line", F_true);
- break;
- }
-
- if (status == F_data_not_stop) {
- status = F_status_set_error(F_parameter);
-
- fll_error_print(data->error, F_parameter, "fl_string_dynamic_seek_line", F_true);
- break;
- }
-
- range.stop = range.start - 1;
- range.start = previous;
-
- if (data->parameters[fss_basic_list_write_parameter_object].result == f_console_result_found) {
- object.used = 0;
-
- if (buffer.used) {
- status = fl_string_dynamic_partial_append_nulless(buffer, range, &object);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_partial_append_nulless", F_true);
- break;
- }
- }
- }
- else {
- content.used = 0;
-
- if (buffer.used) {
- status = fl_string_dynamic_partial_append_nulless(buffer, range, &object);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_partial_append_nulless", F_true);
- break;
- }
- }
- }
-
- status = fss_basic_list_write_process(*data, output, object, content, quoted, &buffer);
- if (F_status_is_error(status)) break;
-
- // restore the range, positioned after the newline.
- range.start = range.stop + 2;
- range.stop = buffer.used - 1;
-
- // only clear the buffer and reset the start when the entire buffer has been processed.
- if (range.start > range.stop) {
- range.start = 0;
- buffer.used = 0;
- }
-
- if (status_pipe == F_none_eof && !buffer.used && !object_ended) break;
- } // for
- }
- else {
- for (f_status_t status_pipe = F_none; ; ) {
-
- if (status_pipe != F_none_eof) {
- status_pipe = f_file_read(input, &buffer);
-
- if (F_status_is_error(status_pipe)) {
- fll_error_file_print(data->error, F_status_set_fine(status), "f_file_read_to", F_true, "-", "read", fll_error_file_type_pipe);
-
- status = F_status_set_error(F_pipe);
- break;
- }
-
- if (!buffer.used) {
- if (data->error.verbosity != f_console_verbosity_quiet) {
- fl_color_print(data->error.to.stream, data->context.set.error, "%sThe pipe has no data.%c", fll_error_print_error, f_string_eol[0]);
- }
-
- status = F_status_set_error(F_parameter);
- break;
- }
-
- range.stop = buffer.used - 1;
- }
-
- previous = range.start;
- status = fl_string_dynamic_seek_line(buffer.string, &range);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_seek_line", F_true);
- break;
- }
-
- if (status == F_data_not_stop) {
- status = F_status_set_error(F_parameter);
-
- fll_error_print(data->error, F_parameter, "fl_string_dynamic_seek_line", F_true);
- break;
- }
-
- if (object_ended && previous == range.start) {
- if (data->error.verbosity != f_console_verbosity_quiet) {
- fl_color_print(data->error.to.stream, data->context.set.error, "%sThe pipe has incorrectly placed newlines.%c", fll_error_print_error, f_string_eol[0]);
- }
-
- status = F_status_set_error(F_parameter);
- break;
- }
-
- range.stop = range.start - 1;
- range.start = previous;
-
- if (object_ended) {
- content.used = 0;
-
- if (buffer.used) {
- status = fl_string_dynamic_partial_append_nulless(buffer, range, &content);
+ status = fss_basic_list_write_process_pipe(*data, output, quote, &buffer);
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_partial_append_nulless", F_true);
- break;
- }
- }
-
- status = fss_basic_list_write_process(*data, output, object, content, quoted, &buffer);
- if (F_status_is_error(status)) break;
-
- object_ended = F_false;
- }
- else {
- object.used = 0;
-
- status = fl_string_dynamic_partial_append_nulless(buffer, range, &object);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_partial_append_nulless", F_true);
- break;
- }
-
- object_ended = F_true;
- }
-
- // restore the range, positioned after the newline.
- range.start = range.stop + 2;
- range.stop = buffer.used - 1;
-
- // only clear the buffer and reset the start when the entire buffer has been processed.
- if (range.start > range.stop) {
- range.start = 0;
- buffer.used = 0;
- }
-
- if (status_pipe == F_none_eof && !buffer.used && !object_ended) break;
- } // for
-
- if (F_status_is_error_not(status) && object_ended) {
- if (data->error.verbosity != f_console_verbosity_quiet) {
- fl_color_print(data->error.to.stream, data->context.set.error, "%sThe pipe has an object without content.%c", fll_error_print_error, f_string_eol[0]);
- }
-
- status = F_status_set_error(F_parameter);
- }
+ if (F_status_is_error(status)) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sWhile processing the ", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "input pipe");
+ fl_color_print(data->error.to.stream, data->context.set.error, ".%c", f_string_eol[0]);
}
}
if (F_status_is_error_not(status)) {
if (data->parameters[fss_basic_list_write_parameter_partial].result == f_console_result_found) {
- if (data->parameters[fss_basic_list_write_parameter_object].result == f_console_result_found) {
- content.used = 0;
+ if (data->parameters[fss_basic_list_write_parameter_object].result == f_console_result_additional) {
for (f_array_length_t i = 0; i < data->parameters[fss_basic_list_write_parameter_object].additional.used; i++) {
object.string = arguments.argv[data->parameters[fss_basic_list_write_parameter_object].additional.array[i]];
object.used = strnlen(object.string, f_console_length_size);
object.size = object.used;
- status = fss_basic_list_write_process(*data, output, object, content, quoted, &buffer);
+ status = fss_basic_list_write_process(*data, output, quote, &object, 0, &buffer);
if (F_status_is_error(status)) break;
} // for
}
else {
- object.used = 0;
-
- for (f_array_length_t i = 0; i < data->parameters[fss_basic_list_write_parameter_object].additional.used; i++) {
+ for (f_array_length_t i = 0; i < data->parameters[fss_basic_list_write_parameter_content].additional.used; i++) {
content.string = arguments.argv[data->parameters[fss_basic_list_write_parameter_content].additional.array[i]];
content.used = strnlen(content.string, f_console_length_size);
content.size = content.used;
- status = fss_basic_list_write_process(*data, output, object, content, quoted, &buffer);
+ status = fss_basic_list_write_process(*data, output, quote, 0, &content, &buffer);
if (F_status_is_error(status)) break;
} // for
}
content.used = strnlen(content.string, f_console_length_size);
content.size = content.used;
- status = fss_basic_list_write_process(*data, output, object, content, quoted, &buffer);
+ status = fss_basic_list_write_process(*data, output, quote, &object, &content, &buffer);
if (F_status_is_error(status)) break;
} // for
}
- // ensure there is always a newline at the end, unless in quiet mode.
- if (F_status_is_error_not(status) && data->error.verbosity != f_console_verbosity_quiet && data->parameters[fss_basic_list_write_parameter_file].result == f_console_result_none) {
+ if (F_status_is_error(status)) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sWhile processing the ", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "input arguments");
+ fl_color_print(data->error.to.stream, data->context.set.error, ".%c", f_string_eol[0]);
+ }
+ else if (data->error.verbosity != f_console_verbosity_quiet && data->parameters[fss_basic_list_write_parameter_file].result == f_console_result_none) {
+ // ensure there is always a newline at the end, unless in quiet mode.
fprintf(f_type_output, "%c", f_string_eol[0]);
}
}
#ifndef _di_fss_basic_list_write_delete_data_
f_return_status fss_basic_list_write_delete_data(fss_basic_list_write_data_t *data) {
- f_string_length_t i = 0;
- while (i < fss_basic_list_write_total_parameters) {
+ for (f_string_length_t i = 0; i < fss_basic_list_write_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
- i++;
- } // while
+ } // for
f_macro_string_lengths_t_delete_simple(data->remaining);
+
f_macro_color_context_t_delete_simple(data->context);
return F_none;
#endif // _di_fss_basic_list_write_name_
#ifndef _di_fss_basic_list_write_defines_
+ #define fss_basic_list_write_pipe_content_start '\0'
+ #define fss_basic_list_write_pipe_content_end '\f'
+
#define fss_basic_list_write_short_file "f"
#define fss_basic_list_write_short_content "c"
#define fss_basic_list_write_short_double "d"
#endif // _di_fss_basic_list_write_error_parameter_value_missing_print_
#ifndef _di_fss_basic_list_write_process_
- f_return_status fss_basic_list_write_process(const fss_basic_list_write_data_t data, const f_file_t output, const f_string_static_t object, const f_string_static_t content, const f_fss_quote_t quoted, f_string_dynamic_t *buffer) {
+ f_return_status fss_basic_list_write_process(const fss_basic_list_write_data_t data, const f_file_t output, const f_fss_quote_t quote, const f_string_static_t *object, const f_string_static_t *content, f_string_dynamic_t *buffer) {
f_status_t status = F_none;
- f_string_range_t range = f_macro_string_range_t_initialize(object.used);
+ f_string_range_t range = f_string_range_t_initialize;
- buffer->used = 0;
-
- if (data.parameters[fss_basic_list_write_parameter_object].result == f_console_result_found) {
+ if (object) {
+ if (object->used) {
+ range.start = 0;
+ range.stop = object->used - 1;
+ }
+ else {
+ range.start = 1;
+ range.stop = 0;
+ }
- status = fl_fss_basic_list_object_write(object, quoted, &range, buffer);
+ status = fl_fss_basic_list_object_write(*object, quote, &range, buffer);
- if (F_status_is_error(status) || status == F_data_not_stop || status == F_data_not_eos) {
- fll_error_print(data.error, F_status_set_fine(status), "fl_fss_basic_object_write", F_true);
+ if (status == F_data_not_stop || status == F_data_not_eos) {
+ fl_color_print(data.error.to.stream, data.context.set.error, "%sThis standard requires an object.%c", fll_error_print_error, f_string_eol[0]);
return F_status_set_error(status);
}
+ else if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_fss_basic_list_object_write", F_true);
+ return status;
+ }
}
- if (data.parameters[fss_basic_list_write_parameter_content].result == f_console_result_found) {
- if (content.used) {
+ if (content) {
+ if (content->used) {
range.start = 0;
- range.stop = content.used;
+ range.stop = content->used - 1;
}
else {
range.start = 1;
range.stop = 0;
}
- status = fl_fss_basic_list_content_write(content, &range, buffer);
+ status = fl_fss_basic_list_content_write(*content, &range, buffer);
- if (F_status_is_error(status) || data.parameters[fss_basic_list_write_parameter_content].result == f_console_result_found) {
- fll_error_print(data.error, F_status_set_fine(status), "fl_fss_basic_content_write", F_true);
- return F_status_set_error(status);
+ if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_fss_basic_list_content_write", F_true);
+ return status;
}
}
- status = fl_string_dynamic_terminate(buffer);
-
- if (F_status_is_error(status)) {
- fll_error_print(data.error, F_status_set_fine(status), "fl_string_dynamic_terminate", F_true);
- return F_status_set_error(status);
- }
-
f_print_dynamic(output.stream, *buffer);
+ buffer->used = 0;
return status;
}
#endif // _di_fss_basic_list_write_process_
+#ifndef _di_fss_basic_list_write_process_pipe_
+ f_return_status fss_basic_list_write_process_pipe(const fss_basic_list_write_data_t data, const f_file_t output, const f_fss_quote_t quote, f_string_dynamic_t *buffer) {
+ f_status_t status = F_none;
+ f_status_t status_pipe = F_none;
+
+ f_file_t input = f_file_t_initialize;
+
+ input.id = f_type_descriptor_input;
+ input.size_read = 2048;
+
+ f_string_length_t total = 0;
+ f_string_length_t previous = 0;
+ f_string_range_t range = f_string_range_t_initialize;
+
+ f_string_dynamic_t block = f_string_dynamic_t_initialize;
+ f_string_dynamic_t object = f_string_dynamic_t_initialize;
+ f_string_dynamic_t content = f_string_dynamic_t_initialize;
+
+ // 0x0 = start new object/content set, 0x1 = processing object, 0x2 = processing content, 0x3 = end object/content set.
+ uint8_t state = 0;
+
+ for (;;) {
+
+ if (range.start > range.stop) {
+ if (status_pipe == F_none_eof) break;
+
+ block.used = 0;
+
+ status_pipe = f_file_read_block(input, &block);
+
+ if (F_status_is_error(status_pipe)) {
+ fll_error_print(data.error, F_status_set_fine(status_pipe), "f_file_read_block", F_true);
+
+ status_pipe = F_status_set_error(F_pipe);
+ break;
+ }
+
+ range.start = 0;
+ range.stop = block.used - 1;
+ }
+
+ if (!state || state == 0x1) {
+ if (!state) {
+ object.used = 0;
+ content.used = 0;
+
+ state = 0x1;
+ }
+
+ if (object.used + block.used > object.size) {
+ status = fl_string_dynamic_size_increase(block.used, &object);
+
+ if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_string_dynamic_size_increase", F_true);
+ break;
+ }
+ }
+
+ for (; range.start <= range.stop; range.start++) {
+
+ if (block.string[range.start] == fss_basic_list_write_pipe_content_start) {
+ state = 0x2;
+ range.start++;
+ break;
+ }
+
+ object.string[object.used++] = block.string[range.start];
+ } // for
+
+ if (F_status_is_error(status)) break;
+
+ // if the start of content was not found, then fetch the next block.
+ if (state != 0x2) continue;
+
+ // if the end of the current block is reached, fetch the next block.
+ if (range.start > range.stop) continue;
+ }
+
+ if (state == 0x2) {
+ if (block.used && range.start <= range.stop) {
+ total = (range.stop - range.start) + 1;
+ }
+ else {
+ total = 0;
+ }
+
+ if (total) {
+ if (content.used + total > content.size) {
+ status = fl_string_dynamic_size_increase(total, &content);
+
+ if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_string_dynamic_size_increase", F_true);
+ break;
+ }
+ }
+
+ for (; range.start <= range.stop; range.start++) {
+
+ if (block.string[range.start] == fss_basic_list_write_pipe_content_start) {
+ fl_color_print(data.error.to.stream, data.context.set.error, "%sThis standard only supports one content per object.%c", fll_error_print_error, f_string_eol[0]);
+
+ status = F_status_set_error(F_unsupported);
+ break;
+ }
+ else if (block.string[range.start] == fss_basic_list_write_pipe_content_end) {
+ state = 0x3;
+ range.start++;
+ break;
+ }
+
+ content.string[content.used++] = block.string[range.start];
+ } // for
+
+ if (F_status_is_error(status)) break;
+ }
+ else {
+ state = 0x3;
+ }
+ }
+
+ if (state == 0x3) {
+ status = fss_basic_list_write_process(data, output, quote, &object, &content, buffer);
+ if (F_status_is_error(status)) break;
+
+ state = 0;
+ }
+ } // for
+
+ // if the pipe ended before finishing, then attempt to wrap up.
+ if (status_pipe == F_none_eof && state) {
+ status = fss_basic_list_write_process(data, output, quote, &object, &content, buffer);
+ }
+
+ f_macro_string_dynamic_t_delete_simple(block);
+ f_macro_string_dynamic_t_delete_simple(object);
+ f_macro_string_dynamic_t_delete_simple(content);
+ return status;
+ }
+#endif // _di_fss_basic_list_write_process_pipe_
+
#ifdef __cplusplus
} // extern "C"
#endif
* The program data.
* @param output
* The file to output to.
+ * @param quote
+ * The quote character to use.
+ * This is either single our double quote.
* @param object
* The object to validate and print.
* @param content
* The content to escape and print.
- * @param quoted
- * The quote character to use.
- * This is either single our double quote.
* @param buffer
* The buffer array used as a cache to construct the output before printing.
*
* F_failure (with error bit) for any othe failure.
*/
#ifndef _di_fss_basic_list_write_process_
- extern f_return_status fss_basic_list_write_process(const fss_basic_list_write_data_t data, const f_file_t output, const f_string_static_t object, const f_string_static_t content, const f_fss_quote_t quoted, f_string_dynamic_t *buffer) f_gcc_attribute_visibility_internal;
+ extern f_return_status fss_basic_list_write_process(const fss_basic_list_write_data_t data, const f_file_t output, const f_fss_quote_t quote, const f_string_static_t *object, const f_string_static_t *content, f_string_dynamic_t *buffer) f_gcc_attribute_visibility_internal;
#endif // _di_fss_basic_list_write_process_
+/**
+ * Process the pipe, reading from the pipe and writing to the output.
+ *
+ * @param data
+ * The program data.
+ * @param output
+ * The file to output to.
+ * @param quote
+ * The quote character to use.
+ * This is either single our double quote.
+ * @param buffer
+ * The buffer array used as a cache to construct the output before printing.
+ *
+ * @return
+ * F_none on success.
+ * F_failure (with error bit) for any othe failure.
+ */
+#ifndef _di_fss_basic_list_write_process_pipe_
+ extern f_return_status fss_basic_list_write_process_pipe(const fss_basic_list_write_data_t data, const f_file_t output, const f_fss_quote_t quote, f_string_dynamic_t *buffer) f_gcc_attribute_visibility_internal;
+#endif // _di_fss_basic_list_write_process_pipe_
+
#ifdef __cplusplus
} // extern "C"
#endif
#ifndef _di_fss_basic_read_delete_data_
f_return_status fss_basic_read_delete_data(fss_basic_read_data_t *data) {
- f_status_t status = F_none;
- f_string_length_t i = 0;
- while (i < fss_basic_read_total_parameters) {
+ for (f_string_length_t i = 0; i < fss_basic_read_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
- i++;
- } // while
+ } // for
f_macro_fss_contents_t_delete_simple(data->contents);
f_macro_fss_objects_t_delete_simple(data->objects);
fss_basic_write_error_parameter_value_missing_print(*data, f_console_symbol_long_enable, fss_basic_write_long_content);
status = F_status_set_error(F_parameter);
}
- else if (data->parameters[fss_basic_write_parameter_object].locations.used != data->parameters[fss_basic_write_parameter_content].locations.used) {
+ else if (data->parameters[fss_basic_write_parameter_object].locations.used != data->parameters[fss_basic_write_parameter_content].locations.used && data->parameters[fss_basic_write_parameter_partial].result == f_console_result_none) {
fss_basic_write_error_parameter_same_times_print(*data);
status = F_status_set_error(F_parameter);
}
status = F_status_set_error(F_parameter);
}
}
+
+ if (F_status_is_error_not(status)) {
+ if (data->parameters[fss_basic_write_parameter_content].result == f_console_result_additional) {
+ f_array_length_t location_object = 0;
+ f_array_length_t location_content = 0;
+ f_array_length_t location_sub_object = 0;
+ f_array_length_t location_sub_content = 0;
+
+ for (f_array_length_t i = 0; i < data->parameters[fss_basic_write_parameter_object].locations.used; i++) {
+ location_object = data->parameters[fss_basic_write_parameter_object].locations.array[i];
+ location_content = data->parameters[fss_basic_write_parameter_content].locations.array[i];
+ location_sub_object = data->parameters[fss_basic_write_parameter_object].locations_sub.array[i];
+ location_sub_content = data->parameters[fss_basic_write_parameter_content].locations_sub.array[i];
+
+ if (location_object > location_content || location_object == location_content && location_sub_object > location_sub_content) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sEach ", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "%s%s", f_console_symbol_long_enable, fss_basic_write_long_object);
+ fl_color_print(data->error.to.stream, data->context.set.error, "' parameter must be specified before a '");
+ fl_color_print(data->error.to.stream, data->context.set.notable, "%s%s", f_console_symbol_long_enable, fss_basic_write_long_content);
+ fl_color_print(data->error.to.stream, data->context.set.error, "' parameter.%c", f_string_eol[0]);
+
+ status = F_status_set_error(F_parameter);
+ break;
+ }
+ } // for
+ }
+ }
}
else if (data->parameters[fss_basic_write_parameter_content].locations.used) {
if (data->parameters[fss_basic_write_parameter_content].locations.used != data->parameters[fss_basic_write_parameter_content].additional.used) {
status = F_status_set_error(F_parameter);
}
+
+ if (F_status_is_error_not(status) && data->process_pipe) {
+ if (data->parameters[fss_basic_write_parameter_partial].result == f_console_result_found) {
+ if (data->error.verbosity != f_console_verbosity_quiet) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sThe '", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "%s%s", f_console_symbol_long_enable, fss_basic_write_long_partial);
+ fl_color_print(data->error.to.stream, data->context.set.error, "' parameter cannot be used when processing a pipe.%c", f_string_eol[0]);
+ }
+
+ status = F_status_set_error(F_parameter);
+ }
+ }
}
f_fss_quote_t quote = f_fss_delimit_quote_double;
f_string_dynamic_t escaped = f_string_dynamic_t_initialize;
if (data->process_pipe) {
- f_file_t input = f_file_t_initialize;
-
- input.id = f_type_descriptor_input;
- input.size_read = 1;
-
- bool object_ended = F_false;
-
- f_string_length_t previous = 0;
- f_string_range_t range = f_string_range_t_initialize;
-
- range.start = 0;
-
- if (data->parameters[fss_basic_write_parameter_partial].result == f_console_result_found) {
- for (f_status_t status_pipe = F_none; ; ) {
-
- if (status_pipe != F_none_eof) {
- status_pipe = f_file_read(input, &buffer);
-
- if (F_status_is_error(status_pipe)) {
- fll_error_file_print(data->error, F_status_set_fine(status), "f_file_read_to", F_true, "-", "read", fll_error_file_type_pipe);
-
- status = F_status_set_error(F_pipe);
- break;
- }
-
- if (!buffer.used) {
- if (data->error.verbosity != f_console_verbosity_quiet) {
- fl_color_print(data->error.to.stream, data->context.set.error, "%sThe pipe has no data.%c", fll_error_print_error, f_string_eol[0]);
- }
-
- status = F_status_set_error(F_parameter);
- break;
- }
-
- range.stop = buffer.used - 1;
- }
-
- previous = range.start;
- status = fl_string_dynamic_seek_line(buffer.string, &range);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_seek_line", F_true);
- break;
- }
-
- if (status == F_data_not_stop) {
- status = F_status_set_error(F_parameter);
-
- fll_error_print(data->error, F_parameter, "fl_string_dynamic_seek_line", F_true);
- break;
- }
-
- range.stop = range.start - 1;
- range.start = previous;
-
- if (data->parameters[fss_basic_write_parameter_object].result == f_console_result_found) {
- object.used = 0;
-
- if (buffer.used) {
- status = fl_string_dynamic_partial_append_nulless(buffer, range, &object);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_partial_append_nulless", F_true);
- break;
- }
- }
- }
- else {
- content.used = 0;
-
- if (buffer.used) {
- status = fl_string_dynamic_partial_append_nulless(buffer, range, &object);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_partial_append_nulless", F_true);
- break;
- }
- }
- }
-
- status = fss_basic_write_process(*data, output, object, content, quote, &buffer);
- if (F_status_is_error(status)) break;
-
- // restore the range, positioned after the newline.
- range.start = range.stop + 2;
- range.stop = buffer.used - 1;
-
- // only clear the buffer and reset the start when the entire buffer has been processed.
- if (range.start > range.stop) {
- range.start = 0;
- buffer.used = 0;
- }
-
- if (status_pipe == F_none_eof && !buffer.used && !object_ended) break;
- } // for
- }
- else {
- for (f_status_t status_pipe = F_none; ; ) {
-
- if (status_pipe != F_none_eof) {
- status_pipe = f_file_read(input, &buffer);
-
- if (F_status_is_error(status_pipe)) {
- fll_error_file_print(data->error, F_status_set_fine(status), "f_file_read_to", F_true, "-", "read", fll_error_file_type_pipe);
-
- status = F_status_set_error(F_pipe);
- break;
- }
-
- if (!buffer.used) {
- if (data->error.verbosity != f_console_verbosity_quiet) {
- fl_color_print(data->error.to.stream, data->context.set.error, "%sThe pipe has no data.%c", fll_error_print_error, f_string_eol[0]);
- }
-
- status = F_status_set_error(F_parameter);
- break;
- }
-
- range.stop = buffer.used - 1;
- }
-
- previous = range.start;
- status = fl_string_dynamic_seek_line(buffer.string, &range);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_seek_line", F_true);
- break;
- }
-
- if (status == F_data_not_stop) {
- status = F_status_set_error(F_parameter);
-
- fll_error_print(data->error, F_parameter, "fl_string_dynamic_seek_line", F_true);
- break;
- }
-
- if (object_ended && previous == range.start) {
- if (data->error.verbosity != f_console_verbosity_quiet) {
- fl_color_print(data->error.to.stream, data->context.set.error, "%sThe pipe has incorrectly placed newlines.%c", fll_error_print_error, f_string_eol[0]);
- }
-
- status = F_status_set_error(F_parameter);
- break;
- }
-
- range.stop = range.start - 1;
- range.start = previous;
-
- if (object_ended) {
- content.used = 0;
-
- if (buffer.used) {
- status = fl_string_dynamic_partial_append_nulless(buffer, range, &content);
+ status = fss_basic_write_process_pipe(*data, output, quote, &buffer);
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_partial_append_nulless", F_true);
- break;
- }
- }
-
- status = fss_basic_write_process(*data, output, object, content, quote, &buffer);
- if (F_status_is_error(status)) break;
-
- object_ended = F_false;
- }
- else {
- object.used = 0;
-
- status = fl_string_dynamic_partial_append_nulless(buffer, range, &object);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_partial_append_nulless", F_true);
- break;
- }
-
- object_ended = F_true;
- }
-
- // restore the range, positioned after the newline.
- range.start = range.stop + 2;
- range.stop = buffer.used - 1;
-
- // only clear the buffer and reset the start when the entire buffer has been processed.
- if (range.start > range.stop) {
- range.start = 0;
- buffer.used = 0;
- }
-
- if (status_pipe == F_none_eof && !buffer.used && !object_ended) break;
- } // for
-
- if (F_status_is_error_not(status) && object_ended) {
- if (data->error.verbosity != f_console_verbosity_quiet) {
- fl_color_print(data->error.to.stream, data->context.set.error, "%sThe pipe has an object without content.%c", fll_error_print_error, f_string_eol[0]);
- }
-
- status = F_status_set_error(F_parameter);
- }
+ if (F_status_is_error(status)) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sWhile processing the ", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "input pipe");
+ fl_color_print(data->error.to.stream, data->context.set.error, ".%c", f_string_eol[0]);
}
}
if (F_status_is_error_not(status)) {
if (data->parameters[fss_basic_write_parameter_partial].result == f_console_result_found) {
- if (data->parameters[fss_basic_write_parameter_object].result == f_console_result_found) {
+ if (data->parameters[fss_basic_write_parameter_object].result == f_console_result_additional) {
content.used = 0;
for (f_array_length_t i = 0; i < data->parameters[fss_basic_write_parameter_object].additional.used; i++) {
object.used = strnlen(object.string, f_console_length_size);
object.size = object.used;
- status = fss_basic_write_process(*data, output, object, content, quote, &buffer);
+ status = fss_basic_write_process(*data, output, quote, &object, 0, &buffer);
if (F_status_is_error(status)) break;
} // for
}
else {
object.used = 0;
- for (f_array_length_t i = 0; i < data->parameters[fss_basic_write_parameter_object].additional.used; i++) {
+ for (f_array_length_t i = 0; i < data->parameters[fss_basic_write_parameter_content].additional.used; i++) {
content.string = arguments.argv[data->parameters[fss_basic_write_parameter_content].additional.array[i]];
content.used = strnlen(content.string, f_console_length_size);
content.size = content.used;
- status = fss_basic_write_process(*data, output, object, content, quote, &buffer);
+ status = fss_basic_write_process(*data, output, quote, 0, &content, &buffer);
if (F_status_is_error(status)) break;
} // for
}
content.used = strnlen(content.string, f_console_length_size);
content.size = content.used;
- status = fss_basic_write_process(*data, output, object, content, quote, &buffer);
+ status = fss_basic_write_process(*data, output, quote, &object, &content, &buffer);
if (F_status_is_error(status)) break;
} // for
}
- // ensure there is always a newline at the end, unless in quiet mode.
- if (F_status_is_error_not(status) && data->error.verbosity != f_console_verbosity_quiet && data->parameters[fss_basic_write_parameter_file].result == f_console_result_none) {
+ if (F_status_is_error(status)) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sWhile processing the ", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "input arguments");
+ fl_color_print(data->error.to.stream, data->context.set.error, ".%c", f_string_eol[0]);
+ }
+ else if (data->error.verbosity != f_console_verbosity_quiet && data->parameters[fss_basic_write_parameter_file].result == f_console_result_none) {
+ // ensure there is always a newline at the end, unless in quiet mode.
fprintf(f_type_output, "%c", f_string_eol[0]);
}
}
#ifndef _di_fss_basic_write_delete_data_
f_return_status fss_basic_write_delete_data(fss_basic_write_data_t *data) {
- f_status_t status = F_none;
for (f_string_length_t i = 0; i < fss_basic_write_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
} // for
f_macro_string_lengths_t_delete_simple(data->remaining);
+
f_macro_color_context_t_delete_simple(data->context);
return F_none;
#endif // _di_fss_basic_write_name_
#ifndef _di_fss_basic_write_defines_
+ #define fss_basic_write_pipe_content_start '\0'
+ #define fss_basic_write_pipe_content_end '\f'
+
#define fss_basic_write_short_file "f"
#define fss_basic_write_short_content "c"
#define fss_basic_write_short_double "d"
const f_console_arguments_t arguments = { argc, argv };
fss_basic_write_data_t data = fss_basic_write_data_t_initialize;
+ if (f_pipe_input_exists()) {
+ data.process_pipe = F_true;
+ }
+
if (F_status_is_error(fss_basic_write_main(arguments, &data))) {
return 1;
}
#endif // _di_fss_basic_write_error_parameter_value_missing_print_
#ifndef _di_fss_basic_write_process_
- f_return_status fss_basic_write_process(const fss_basic_write_data_t data, const f_file_t output, const f_string_static_t object, const f_string_static_t content, const f_fss_quote_t quote, f_string_dynamic_t *buffer) {
- buffer->used = 0;
+ f_return_status fss_basic_write_process(const fss_basic_write_data_t data, const f_file_t output, const f_fss_quote_t quote, const f_string_static_t *object, const f_string_static_t *content, f_string_dynamic_t *buffer) {
+ f_status_t status = F_none;
+
+ f_string_range_t range = f_string_range_t_initialize;
+
+ if (object) {
+ if (object->used) {
+ range.start = 0;
+ range.stop = object->used - 1;
+ }
+ else {
+ range.start = 1;
+ range.stop = 0;
+ }
+
+ status = fl_fss_basic_object_write(*object, quote, content ? f_fss_complete_full : f_fss_complete_partial, &range, buffer);
- f_status_t status = fll_fss_basic_write(object, content, quote, buffer);
+ if (F_status_set_fine(status) == F_none_eol) {
+ fl_color_print(data.error.to.stream, data.context.set.error, "%sThis standard does not support end of line character '", fll_error_print_error);
+ fl_color_print(data.error.to.stream, data.context.set.notable, "\\n");
+ fl_color_print(data.error.to.stream, data.context.set.error, "'.%c", f_string_eol[0]);
- if (F_status_is_error(status)) {
- fll_error_print(data.error, F_status_set_fine(status), "fll_fss_basic_write", F_true);
- return F_status_set_error(status);
+ return F_status_set_error(F_unsupported);
+ }
+
+ if (status == F_data_not_stop || status == F_data_not_eos) {
+ fl_color_print(data.error.to.stream, data.context.set.error, "%sThis standard requires an object.%c", fll_error_print_error, f_string_eol[0]);
+ return F_status_set_error(status);
+ }
+ else if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_fss_basic_list_object_write", F_true);
+ return status;
+ }
+ }
+
+ if (content) {
+ if (content->used) {
+ range.start = 0;
+ range.stop = content->used - 1;
+ }
+ else {
+ range.start = 1;
+ range.stop = 0;
+ }
+
+ status = fl_fss_basic_content_write(*content, object ? f_fss_complete_full : f_fss_complete_partial, &range, buffer);
+
+ if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_fss_basic_content_write", F_true);
+ return status;
+ }
+ }
+ else {
+ // objects in this standard do not have EOL, so add an EOL for printing purposes when there is no desired content.
+ status = fl_string_append(f_string_eol, 1, buffer);
+
+ if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_fss_basic_content_write", F_true);
+ return status;
+ }
}
f_print_dynamic(output.stream, *buffer);
+ buffer->used = 0;
return status;
}
#endif // _di_fss_basic_write_process_
+#ifndef _di_fss_basic_write_process_pipe_
+ f_return_status fss_basic_write_process_pipe(const fss_basic_write_data_t data, const f_file_t output, const f_fss_quote_t quote, f_string_dynamic_t *buffer) {
+ f_status_t status = F_none;
+ f_status_t status_pipe = F_none;
+
+ f_file_t input = f_file_t_initialize;
+
+ input.id = f_type_descriptor_input;
+ input.size_read = 2048;
+
+ f_string_length_t total = 0;
+ f_string_length_t previous = 0;
+ f_string_range_t range = f_string_range_t_initialize;
+
+ f_string_dynamic_t block = f_string_dynamic_t_initialize;
+ f_string_dynamic_t object = f_string_dynamic_t_initialize;
+ f_string_dynamic_t content = f_string_dynamic_t_initialize;
+
+ // 0x0 = start new object/content set, 0x1 = processing object, 0x2 = processing content, 0x3 = end object/content set.
+ uint8_t state = 0;
+
+ for (;;) {
+
+ if (range.start > range.stop) {
+ if (status_pipe == F_none_eof) break;
+
+ block.used = 0;
+
+ status_pipe = f_file_read_block(input, &block);
+
+ if (F_status_is_error(status_pipe)) {
+ fll_error_print(data.error, F_status_set_fine(status_pipe), "f_file_read_block", F_true);
+
+ status_pipe = F_status_set_error(F_pipe);
+ break;
+ }
+
+ range.start = 0;
+ range.stop = block.used - 1;
+ }
+
+ if (!state || state == 0x1) {
+ if (!state) {
+ object.used = 0;
+ content.used = 0;
+
+ state = 0x1;
+ }
+
+ if (object.used + block.used > object.size) {
+ status = fl_string_dynamic_size_increase(block.used, &object);
+
+ if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_string_dynamic_size_increase", F_true);
+ break;
+ }
+ }
+
+ for (; range.start <= range.stop; range.start++) {
+
+ if (block.string[range.start] == fss_basic_write_pipe_content_start) {
+ state = 0x2;
+ range.start++;
+ break;
+ }
+
+ object.string[object.used++] = block.string[range.start];
+ } // for
+
+ if (F_status_is_error(status)) break;
+
+ // if the start of content was not found, then fetch the next block.
+ if (state != 0x2) continue;
+
+ // if the end of the current block is reached, fetch the next block.
+ if (range.start > range.stop) continue;
+ }
+
+ if (state == 0x2) {
+ if (block.used && range.start <= range.stop) {
+ total = (range.stop - range.start) + 1;
+ }
+ else {
+ total = 0;
+ }
+
+ if (total) {
+ if (content.used + total > content.size) {
+ status = fl_string_dynamic_size_increase(total, &content);
+
+ if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_string_dynamic_size_increase", F_true);
+ break;
+ }
+ }
+
+ for (; range.start <= range.stop; range.start++) {
+
+ if (block.string[range.start] == fss_basic_write_pipe_content_start) {
+ fl_color_print(data.error.to.stream, data.context.set.error, "%sThis standard only supports one content per object.%c", fll_error_print_error, f_string_eol[0]);
+
+ status = F_status_set_error(F_unsupported);
+ break;
+ }
+ else if (block.string[range.start] == fss_basic_write_pipe_content_end) {
+ state = 0x3;
+ range.start++;
+ break;
+ }
+
+ content.string[content.used++] = block.string[range.start];
+ } // for
+
+ if (F_status_is_error(status)) break;
+ }
+ else {
+ state = 0x3;
+ }
+ }
+
+ if (state == 0x3) {
+ status = fss_basic_write_process(data, output, quote, &object, &content, buffer);
+ if (F_status_is_error(status)) break;
+
+ state = 0;
+ }
+ } // for
+
+ // if the pipe ended before finishing, then attempt to wrap up.
+ if (status_pipe == F_none_eof && state) {
+ status = fss_basic_write_process(data, output, quote, &object, &content, buffer);
+ }
+
+ f_macro_string_dynamic_t_delete_simple(block);
+ f_macro_string_dynamic_t_delete_simple(object);
+ f_macro_string_dynamic_t_delete_simple(content);
+ return status;
+ }
+#endif // _di_fss_basic_write_process_pipe_
+
#ifdef __cplusplus
} // extern "C"
#endif
* The program data.
* @param output
* The file to output to.
- * @param object
- * The object to validate and print.
- * @param content
- * The content to escape and print.
* @param quote
* The quote character to use.
* This is either single our double quote.
+ * @param object
+ * A pointer to the object to validate and print.
+ * Set to 0 to disable.
+ * @param content
+ * A pointer to the content to escape and print.
+ * Set to 0 to disable.
* @param buffer
* The buffer array used as a cache to construct the output before printing.
*
* F_failure (with error bit) for any othe failure.
*/
#ifndef _di_fss_basic_write_process_
- extern f_return_status fss_basic_write_process(const fss_basic_write_data_t data, const f_file_t output, const f_string_static_t object, const f_string_static_t content, const f_fss_quote_t quote, f_string_dynamic_t *buffer) f_gcc_attribute_visibility_internal;
+ extern f_return_status fss_basic_write_process(const fss_basic_write_data_t data, const f_file_t output, const f_fss_quote_t quote, const f_string_static_t *object, const f_string_static_t *content, f_string_dynamic_t *buffer) f_gcc_attribute_visibility_internal;
#endif // _di_fss_basic_write_process_
+/**
+ * Process the pipe, reading from the pipe and writing to the output.
+ *
+ * @param data
+ * The program data.
+ * @param output
+ * The file to output to.
+ * @param quote
+ * The quote character to use.
+ * This is either single our double quote.
+ * @param buffer
+ * The buffer array used as a cache to construct the output before printing.
+ *
+ * @return
+ * F_none on success.
+ * F_failure (with error bit) for any othe failure.
+ */
+#ifndef _di_fss_basic_write_process_pipe_
+ extern f_return_status fss_basic_write_process_pipe(const fss_basic_write_data_t data, const f_file_t output, const f_fss_quote_t quote, f_string_dynamic_t *buffer) f_gcc_attribute_visibility_internal;
+#endif // _di_fss_basic_write_process_pipe_
+
#ifdef __cplusplus
} // extern "C"
#endif
#ifndef _di_fss_extended_list_read_delete_data_
f_return_status fss_extended_list_read_delete_data(fss_extended_list_read_data_t *data) {
- f_status_t status = F_none;
- f_string_length_t i = 0;
- while (i < fss_extended_list_read_total_parameters) {
+ for (f_string_length_t i = 0; i < fss_extended_list_read_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
- i++;
- } // while
+ } // for
f_macro_fss_nest_t_delete_simple(data->nest);
#ifndef _di_fss_extended_read_delete_data_
f_return_status fss_extended_read_delete_data(fss_extended_read_data_t *data) {
- f_status_t status = F_none;
- f_string_length_t i = 0;
- while (i < fss_extended_read_total_parameters) {
+ for (f_string_length_t i = 0; i < fss_extended_read_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
- i++;
- } // while
+ } // for
f_macro_fss_contents_t_delete_simple(data->contents);
f_macro_fss_objects_t_delete_simple(data->objects);
fss_extended_write_error_parameter_value_missing_print(*data, f_console_symbol_long_enable, fss_extended_write_long_content);
status = F_status_set_error(F_parameter);
}
- else if (data->parameters[fss_extended_write_parameter_object].locations.used != data->parameters[fss_extended_write_parameter_content].locations.used) {
- fss_extended_write_error_parameter_same_times_print(*data);
+ else if (!data->parameters[fss_extended_write_parameter_content].locations.used && data->parameters[fss_extended_write_parameter_partial].result == f_console_result_none) {
+ fss_extended_write_error_parameter_at_least_once(*data);
status = F_status_set_error(F_parameter);
}
else if (data->parameters[fss_extended_write_parameter_content].locations.used && data->parameters[fss_extended_write_parameter_partial].locations.used) {
status = F_status_set_error(F_parameter);
}
}
+
+ if (F_status_is_error_not(status)) {
+ if (data->parameters[fss_extended_write_parameter_content].result == f_console_result_additional) {
+ f_array_length_t location_object = data->parameters[fss_extended_write_parameter_object].locations.array[0];
+ f_array_length_t location_content = data->parameters[fss_extended_write_parameter_content].locations.array[0];
+ f_array_length_t location_sub_object = data->parameters[fss_extended_write_parameter_object].locations_sub.array[0];
+ f_array_length_t location_sub_content = data->parameters[fss_extended_write_parameter_content].locations_sub.array[0];
+
+ if (location_object > location_content || location_object == location_content && location_sub_object > location_sub_content) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sEach ", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "%s%s", f_console_symbol_long_enable, fss_extended_write_long_object);
+ fl_color_print(data->error.to.stream, data->context.set.error, "' parameter must be specified before a '");
+ fl_color_print(data->error.to.stream, data->context.set.notable, "%s%s", f_console_symbol_long_enable, fss_extended_write_long_content);
+ fl_color_print(data->error.to.stream, data->context.set.error, "' parameter.%c", f_string_eol[0]);
+
+ status = F_status_set_error(F_parameter);
+ }
+ else {
+ location_object = data->parameters[fss_extended_write_parameter_object].locations.array[data->parameters[fss_extended_write_parameter_object].locations.used - 1];
+ location_content = data->parameters[fss_extended_write_parameter_content].locations.array[data->parameters[fss_extended_write_parameter_content].locations.used - 1];
+ location_sub_object = data->parameters[fss_extended_write_parameter_object].locations_sub.array[data->parameters[fss_extended_write_parameter_object].locations_sub.used - 1];
+ location_sub_content = data->parameters[fss_extended_write_parameter_content].locations_sub.array[data->parameters[fss_extended_write_parameter_content].locations_sub.used - 1];
+
+ if (location_object > location_content || location_object == location_content && location_sub_object > location_sub_content) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sEach ", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "%s%s", f_console_symbol_long_enable, fss_extended_write_long_object);
+ fl_color_print(data->error.to.stream, data->context.set.error, "' parameter must have at least one '");
+ fl_color_print(data->error.to.stream, data->context.set.notable, "%s%s", f_console_symbol_long_enable, fss_extended_write_long_content);
+ fl_color_print(data->error.to.stream, data->context.set.error, "' parameter.%c", f_string_eol[0]);
+
+ status = F_status_set_error(F_parameter);
+ }
+ }
+ }
+ }
}
else if (data->parameters[fss_extended_write_parameter_content].locations.used) {
if (data->parameters[fss_extended_write_parameter_content].locations.used != data->parameters[fss_extended_write_parameter_content].additional.used) {
status = F_status_set_error(F_parameter);
}
else if (!data->parameters[fss_extended_write_parameter_partial].locations.used) {
- fss_extended_write_error_parameter_same_times_print(*data);
+ fss_extended_write_error_parameter_at_least_once(*data);
status = F_status_set_error(F_parameter);
}
}
status = F_status_set_error(F_parameter);
}
+
+ if (F_status_is_error_not(status) && data->process_pipe) {
+ if (data->parameters[fss_extended_write_parameter_partial].result == f_console_result_found) {
+ if (data->error.verbosity != f_console_verbosity_quiet) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sThe '", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "%s%s", f_console_symbol_long_enable, fss_extended_write_long_partial);
+ fl_color_print(data->error.to.stream, data->context.set.error, "' parameter cannot be used when processing a pipe.%c", f_string_eol[0]);
+ }
+
+ status = F_status_set_error(F_parameter);
+ }
+ }
}
f_fss_quote_t quote = f_fss_delimit_quote_double;
f_string_dynamic_t buffer = f_string_dynamic_t_initialize;
f_string_dynamic_t object = f_string_dynamic_t_initialize;
- f_string_dynamic_t content = f_string_dynamic_t_initialize;
+ f_string_dynamics_t contents = f_string_dynamics_t_initialize;
if (F_status_is_error_not(status)) {
f_string_dynamic_t escaped = f_string_dynamic_t_initialize;
if (data->process_pipe) {
- f_file_t input = f_file_t_initialize;
-
- input.id = f_type_descriptor_input;
- input.size_read = 1;
-
- bool object_ended = F_false;
-
- f_string_length_t previous = 0;
- f_string_range_t range = f_string_range_t_initialize;
+ status = fss_extended_write_process_pipe(*data, output, quote, &buffer);
- range.start = 0;
+ if (F_status_is_error(status)) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sWhile processing the ", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "input pipe");
+ fl_color_print(data->error.to.stream, data->context.set.error, ".%c", f_string_eol[0]);
+ }
+ }
+ if (F_status_is_error_not(status)) {
if (data->parameters[fss_extended_write_parameter_partial].result == f_console_result_found) {
- for (f_status_t status_pipe = F_none; ; ) {
+ if (data->parameters[fss_extended_write_parameter_object].result == f_console_result_additional) {
+ contents.used = 0;
- if (status_pipe != F_none_eof) {
- status_pipe = f_file_read(input, &buffer);
-
- if (F_status_is_error(status_pipe)) {
- fll_error_file_print(data->error, F_status_set_fine(status), "f_file_read_to", F_true, "-", "read", fll_error_file_type_pipe);
+ for (f_array_length_t i = 0; i < data->parameters[fss_extended_write_parameter_object].additional.used; i++) {
- status = F_status_set_error(F_pipe);
- break;
- }
+ object.string = arguments.argv[data->parameters[fss_extended_write_parameter_object].additional.array[i]];
+ object.used = strnlen(object.string, f_console_length_size);
+ object.size = object.used;
- if (!buffer.used) {
- if (data->error.verbosity != f_console_verbosity_quiet) {
- fl_color_print(data->error.to.stream, data->context.set.error, "%sThe pipe has no data.%c", fll_error_print_error, f_string_eol[0]);
- }
+ status = fss_extended_write_process(*data, output, quote, &object, 0, &buffer);
+ if (F_status_is_error(status)) break;
+ } // for
+ }
+ else {
+ object.used = 0;
- status = F_status_set_error(F_parameter);
- break;
- }
+ status = fl_string_dynamics_size_increase(data->parameters[fss_extended_write_parameter_content].additional.used, &contents);
- range.stop = buffer.used - 1;
+ if (status == F_buffer_too_large) {
+ status = F_status_set_error(status);
}
- previous = range.start;
- status = fl_string_dynamic_seek_line(buffer.string, &range);
-
if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_seek_line", F_true);
- break;
- }
-
- if (status == F_data_not_stop) {
- status = F_status_set_error(F_parameter);
-
- fll_error_print(data->error, F_parameter, "fl_string_dynamic_seek_line", F_true);
- break;
- }
-
- range.stop = range.start - 1;
- range.start = previous;
-
- if (data->parameters[fss_extended_write_parameter_object].result == f_console_result_found) {
- object.used = 0;
-
- if (buffer.used) {
- status = fl_string_dynamic_partial_append_nulless(buffer, range, &object);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_partial_append_nulless", F_true);
- break;
- }
- }
+ fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamics_size_increase", F_true);
}
else {
- content.used = 0;
-
- if (buffer.used) {
- status = fl_string_dynamic_partial_append_nulless(buffer, range, &object);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_partial_append_nulless", F_true);
- break;
- }
- }
- }
-
- status = fss_extended_write_process(*data, output, object, content, quote, &buffer);
- if (F_status_is_error(status)) break;
+ for (f_array_length_t i = 0; i < data->parameters[fss_extended_write_parameter_content].additional.used; i++) {
- // restore the range, positioned after the newline.
- range.start = range.stop + 2;
- range.stop = buffer.used - 1;
+ contents.array[contents.used].string = arguments.argv[data->parameters[fss_extended_write_parameter_content].additional.array[i]];
+ contents.array[contents.used].used = strnlen(contents.array[contents.used].string, f_console_length_size);
+ contents.array[contents.used].size = contents.array[contents.used].used;
+ contents.used++;
+ } // for
- // only clear the buffer and reset the start when the entire buffer has been processed.
- if (range.start > range.stop) {
- range.start = 0;
- buffer.used = 0;
+ status = fss_extended_write_process(*data, output, quote, 0, &contents, &buffer);
}
-
- if (status_pipe == F_none_eof && !buffer.used && !object_ended) break;
- } // for
+ }
}
else {
- for (f_status_t status_pipe = F_none; ; ) {
-
- if (status_pipe != F_none_eof) {
- status_pipe = f_file_read(input, &buffer);
-
- if (F_status_is_error(status_pipe)) {
- fll_error_file_print(data->error, F_status_set_fine(status), "f_file_read_to", F_true, "-", "read", fll_error_file_type_pipe);
-
- status = F_status_set_error(F_pipe);
- break;
- }
+ f_array_length_t i = 0;
+ f_array_length_t j = 0;
+ f_array_length_t object_current = 0;
+ f_array_length_t object_next = 0;
+ f_array_length_t content_current = 0;
- if (!buffer.used) {
- if (data->error.verbosity != f_console_verbosity_quiet) {
- fl_color_print(data->error.to.stream, data->context.set.error, "%sThe pipe has no data.%c", fll_error_print_error, f_string_eol[0]);
- }
+ for (; i < data->parameters[fss_extended_write_parameter_object].additional.used; i++) {
- status = F_status_set_error(F_parameter);
- break;
- }
+ object_current = data->parameters[fss_extended_write_parameter_object].locations.array[i];
- range.stop = buffer.used - 1;
+ if (i + 1 < data->parameters[fss_extended_write_parameter_object].additional.used) {
+ object_next = data->parameters[fss_extended_write_parameter_object].locations.array[i + 1];
}
- previous = range.start;
- status = fl_string_dynamic_seek_line(buffer.string, &range);
+ object.string = arguments.argv[data->parameters[fss_extended_write_parameter_object].additional.array[i]];
+ object.used = strnlen(object.string, f_console_length_size);
+ object.size = object.used;
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_seek_line", F_true);
- break;
- }
+ contents.used = 0;
- if (status == F_data_not_stop) {
- status = F_status_set_error(F_parameter);
+ for (; j < data->parameters[fss_extended_write_parameter_content].additional.used; j++) {
- fll_error_print(data->error, F_parameter, "fl_string_dynamic_seek_line", F_true);
- break;
- }
+ content_current = data->parameters[fss_extended_write_parameter_content].locations.array[j];
- if (object_ended && previous == range.start) {
- if (data->error.verbosity != f_console_verbosity_quiet) {
- fl_color_print(data->error.to.stream, data->context.set.error, "%sThe pipe has incorrectly placed newlines.%c", fll_error_print_error, f_string_eol[0]);
+ if (i + 1 < data->parameters[fss_extended_write_parameter_object].additional.used) {
+ if (content_current < object_current || content_current > object_next) break;
}
- status = F_status_set_error(F_parameter);
- break;
- }
+ status = fl_string_dynamics_size_increase(f_fss_default_allocation_step, &contents);
- range.stop = range.start - 1;
- range.start = previous;
-
- if (object_ended) {
- content.used = 0;
-
- if (buffer.used) {
- status = fl_string_dynamic_partial_append_nulless(buffer, range, &content);
-
- if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_partial_append_nulless", F_true);
- break;
- }
+ if (F_status_is_error(status)) {
+ fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamics_size_increase", F_true);
+ break;
}
- status = fss_extended_write_process(*data, output, object, content, quote, &buffer);
- if (F_status_is_error(status)) break;
-
- object_ended = F_false;
- }
- else {
- object.used = 0;
+ if (contents.array[contents.used].used) {
+ contents.array[contents.used].used = 0;
+ }
- status = fl_string_dynamic_partial_append_nulless(buffer, range, &object);
+ status = fl_string_append(arguments.argv[data->parameters[fss_extended_write_parameter_content].additional.array[j]], strnlen(arguments.argv[data->parameters[fss_extended_write_parameter_content].additional.array[j]], f_console_length_size), &contents.array[contents.used]);
if (F_status_is_error(status)) {
- fll_error_print(data->error, F_status_set_fine(status), "fl_string_dynamic_partial_append_nulless", F_true);
+ fll_error_print(data->error, F_status_set_fine(status), "fl_string_append", F_true);
break;
}
- object_ended = F_true;
- }
-
- // restore the range, positioned after the newline.
- range.start = range.stop + 2;
- range.stop = buffer.used - 1;
-
- // only clear the buffer and reset the start when the entire buffer has been processed.
- if (range.start > range.stop) {
- range.start = 0;
- buffer.used = 0;
- }
-
- if (status_pipe == F_none_eof && !buffer.used && !object_ended) break;
- } // for
-
- if (F_status_is_error_not(status) && object_ended) {
- if (data->error.verbosity != f_console_verbosity_quiet) {
- fl_color_print(data->error.to.stream, data->context.set.error, "%sThe pipe has an object without content.%c", fll_error_print_error, f_string_eol[0]);
- }
-
- status = F_status_set_error(F_parameter);
- }
- }
- }
-
- if (F_status_is_error_not(status)) {
- if (data->parameters[fss_extended_write_parameter_partial].result == f_console_result_found) {
- if (data->parameters[fss_extended_write_parameter_object].result == f_console_result_found) {
- content.used = 0;
-
- for (f_array_length_t i = 0; i < data->parameters[fss_extended_write_parameter_object].additional.used; i++) {
-
- object.string = arguments.argv[data->parameters[fss_extended_write_parameter_object].additional.array[i]];
- object.used = strnlen(object.string, f_console_length_size);
- object.size = object.used;
-
- status = fss_extended_write_process(*data, output, object, content, quote, &buffer);
- if (F_status_is_error(status)) break;
+ contents.used++;
} // for
- }
- else {
- object.used = 0;
- for (f_array_length_t i = 0; i < data->parameters[fss_extended_write_parameter_object].additional.used; i++) {
-
- content.string = arguments.argv[data->parameters[fss_extended_write_parameter_content].additional.array[i]];
- content.used = strnlen(content.string, f_console_length_size);
- content.size = content.used;
-
- status = fss_extended_write_process(*data, output, object, content, quote, &buffer);
- if (F_status_is_error(status)) break;
- } // for
- }
- }
- else {
- for (f_array_length_t i = 0; i < data->parameters[fss_extended_write_parameter_object].additional.used; i++) {
-
- object.string = arguments.argv[data->parameters[fss_extended_write_parameter_object].additional.array[i]];
- object.used = strnlen(object.string, f_console_length_size);
- object.size = object.used;
-
- content.string = arguments.argv[data->parameters[fss_extended_write_parameter_content].additional.array[i]];
- content.used = strnlen(content.string, f_console_length_size);
- content.size = content.used;
+ if (F_status_is_error(status)) break;
- status = fss_extended_write_process(*data, output, object, content, quote, &buffer);
+ status = fss_extended_write_process(*data, output, quote, &object, &contents, &buffer);
if (F_status_is_error(status)) break;
} // for
}
- // ensure there is always a newline at the end, unless in quiet mode.
- if (F_status_is_error_not(status) && data->error.verbosity != f_console_verbosity_quiet && data->parameters[fss_extended_write_parameter_file].result == f_console_result_none) {
+ if (F_status_is_error(status)) {
+ fl_color_print(data->error.to.stream, data->context.set.error, "%sWhile processing the ", fll_error_print_error);
+ fl_color_print(data->error.to.stream, data->context.set.notable, "input arguments");
+ fl_color_print(data->error.to.stream, data->context.set.error, ".%c", f_string_eol[0]);
+ }
+ else if (data->error.verbosity != f_console_verbosity_quiet && data->parameters[fss_extended_write_parameter_file].result == f_console_result_none) {
+ // ensure there is always a newline at the end, unless in quiet mode.
fprintf(f_type_output, "%c", f_string_eol[0]);
}
}
f_macro_string_dynamic_t_delete_simple(escaped);
- // object and content, though being a "dynamic" type, is being used statically, so clear them up to avoid invalid free().
+ // object, though being a "dynamic" type, is being used statically, so clear them up to avoid invalid free().
object.string = 0;
object.used = 0;
object.size = 0;
- content.string = 0;
- content.used = 0;
- content.size = 0;
+ // reset contents used, it is dynamically allocated so leave everything else alone.
+ contents.used = 0;
}
if (data->parameters[fss_extended_write_parameter_file].result == f_console_result_additional) {
f_macro_string_dynamic_t_delete_simple(buffer);
f_macro_string_dynamic_t_delete_simple(object);
- f_macro_string_dynamic_t_delete_simple(content);
+ f_macro_string_dynamics_t_delete_simple(contents);
fss_extended_write_delete_data(data);
return status;
}
#ifndef _di_fss_extended_write_delete_data_
f_return_status fss_extended_write_delete_data(fss_extended_write_data_t *data) {
- f_status_t status = F_none;
for (f_string_length_t i = 0; i < fss_extended_write_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
} // for
f_macro_string_lengths_t_delete_simple(data->remaining);
+
f_macro_color_context_t_delete_simple(data->context);
return F_none;
#endif // _di_fss_extended_write_name_
#ifndef _di_fss_extended_write_defines_
+ #define fss_extended_write_pipe_content_start '\0'
+ #define fss_extended_write_pipe_content_end '\f'
+
#define fss_extended_write_short_file "f"
#define fss_extended_write_short_content "c"
#define fss_extended_write_short_double "d"
extern "C" {
#endif
-#ifndef _di_fss_extended_write_error_parameter_same_times_print_
- void fss_extended_write_error_parameter_same_times_print(const fss_extended_write_data_t data) {
+#ifndef _di_fss_extended_write_error_parameter_at_least_once_print_
+ void fss_extended_write_error_parameter_at_least_once(const fss_extended_write_data_t data) {
if (data.error.verbosity == f_console_verbosity_quiet) {
return;
}
- fl_color_print(data.error.to.stream, data.context.set.error, "%sMust specify both the '", fll_error_print_error);
+ fl_color_print(data.error.to.stream, data.context.set.error, "%sMust specify the '", fll_error_print_error);
fl_color_print(data.error.to.stream, data.context.set.notable, "%s%s", f_console_symbol_long_enable, fss_extended_write_long_object);
- fl_color_print(data.error.to.stream, data.context.set.error, "' parameter and the '");
+ fl_color_print(data.error.to.stream, data.context.set.error, "' parameter at least once and the '");
fl_color_print(data.error.to.stream, data.context.set.notable, "%s%s", f_console_symbol_long_enable, fss_extended_write_long_content);
- fl_color_print(data.error.to.stream, data.context.set.error, "' parameter the same number of times when not specifying the ");
+ fl_color_print(data.error.to.stream, data.context.set.error, "' parameter one or more times when not specifying the ");
fl_color_print(data.error.to.stream, data.context.set.notable, "%s%s", f_console_symbol_long_enable, fss_extended_write_long_partial);
fl_color_print(data.error.to.stream, data.context.set.error, "' parameter.%c", f_string_eol[0]);
}
-#endif // _di_fss_extended_write_error_parameter_same_times_print_
+#endif // _di_fss_extended_write_error_parameter_at_least_once_print_
#ifndef _di_fss_extended_write_error_parameter_value_missing_print_
void fss_extended_write_error_parameter_value_missing_print(const fss_extended_write_data_t data, const f_string_t symbol, const f_string_t parameter) {
#endif // _di_fss_extended_write_error_parameter_value_missing_print_
#ifndef _di_fss_extended_write_process_
- f_return_status fss_extended_write_process(const fss_extended_write_data_t data, const f_file_t output, const f_string_static_t object, const f_string_statics_t contents, const f_fss_quote_t quote, f_string_dynamic_t *buffer) {
- buffer->used = 0;
+ f_return_status fss_extended_write_process(const fss_extended_write_data_t data, const f_file_t output, const f_fss_quote_t quote, const f_string_static_t *object, const f_string_statics_t *contents, f_string_dynamic_t *buffer) {
+ f_status_t status = F_none;
+
+ f_string_range_t range = f_string_range_t_initialize;
- f_status_t status = fll_fss_extended_write(object, contents, quote, buffer);
+ if (object) {
+ if (object->used) {
+ range.start = 0;
+ range.stop = object->used - 1;
+ }
+ else {
+ range.start = 1;
+ range.stop = 0;
+ }
- if (F_status_is_error(status)) {
- fll_error_print(data.error, F_status_set_fine(status), "fll_fss_extended_write", F_true);
- return F_status_set_error(status);
+ status = fl_fss_extended_object_write(*object, quote, contents ? f_fss_complete_full : f_fss_complete_partial, &range, buffer);
+
+ if (status == F_data_not_stop || status == F_data_not_eos) {
+ fl_color_print(data.error.to.stream, data.context.set.error, "%sThis standard requires an object.%c", fll_error_print_error, f_string_eol[0]);
+ return F_status_set_error(status);
+ }
+ else if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_fss_extended_object_write", F_true);
+ return F_status_set_error(status);
+ }
+ }
+
+ if (contents) {
+ for (f_array_length_t i = 0; i < contents->used; i++) {
+
+ if (contents->used) {
+ range.start = 0;
+ range.stop = contents->array[i].used - 1;
+ }
+ else {
+ range.start = 1;
+ range.stop = 0;
+ }
+
+ status = fl_fss_extended_content_write(contents->array[i], quote, i + 1 < contents->used ? f_fss_complete_next : f_fss_complete_end, &range, buffer);
+
+ if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_fss_extended_content_write", F_true);
+ return F_status_set_error(status);
+ }
+ } // for
}
f_print_dynamic(output.stream, *buffer);
+ buffer->used = 0;
return status;
}
#endif // _di_fss_extended_write_process_
+#ifndef _di_fss_extended_write_process_pipe_
+ f_return_status fss_extended_write_process_pipe(const fss_extended_write_data_t data, const f_file_t output, const f_fss_quote_t quote, f_string_dynamic_t *buffer) {
+ f_status_t status = F_none;
+ f_status_t status_pipe = F_none;
+
+ f_file_t input = f_file_t_initialize;
+
+ input.id = f_type_descriptor_input;
+ input.size_read = 2048;
+
+ f_string_length_t total = 0;
+ f_string_length_t previous = 0;
+ f_string_range_t range = f_string_range_t_initialize;
+
+ f_string_dynamic_t block = f_string_dynamic_t_initialize;
+ f_string_dynamic_t object = f_string_dynamic_t_initialize;
+ f_string_dynamics_t contents = f_string_dynamics_t_initialize;
+
+ // 0x0 = start new object/content set, 0x1 = processing object, 0x2 = processing content, 0x3 = end object/content set.
+ uint8_t state = 0;
+
+ for (;;) {
+
+ if (range.start > range.stop) {
+ if (status_pipe == F_none_eof) break;
+
+ block.used = 0;
+
+ status_pipe = f_file_read_block(input, &block);
+
+ if (F_status_is_error(status_pipe)) {
+ fll_error_print(data.error, F_status_set_fine(status_pipe), "f_file_read_block", F_true);
+
+ status_pipe = F_status_set_error(F_pipe);
+ break;
+ }
+
+ range.start = 0;
+ range.stop = block.used - 1;
+ }
+
+ if (!state || state == 0x1) {
+ if (!state) {
+ object.used = 0;
+ contents.used = 0;
+
+ state = 0x1;
+ }
+
+ if (object.used + block.used > object.size) {
+ status = fl_string_dynamic_size_increase(block.used, &object);
+
+ if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_string_dynamic_size_increase", F_true);
+ break;
+ }
+ }
+
+ for (; range.start <= range.stop; range.start++) {
+
+ if (block.string[range.start] == fss_extended_write_pipe_content_start) {
+ state = 0x2;
+ range.start++;
+ break;
+ }
+
+ object.string[object.used++] = block.string[range.start];
+ } // for
+
+ if (F_status_is_error(status)) break;
+
+ // if the start of content was not found, then fetch the next block.
+ if (state != 0x2) continue;
+
+ // if the end of the current block is reached, fetch the next block.
+ if (range.start > range.stop) continue;
+ }
+
+ if (state == 0x2) {
+ if (block.used && range.start <= range.stop) {
+ total = (range.stop - range.start) + 1;
+ }
+ else {
+ total = 0;
+ }
+
+ if (total) {
+ for (; range.start <= range.stop; range.start++) {
+
+ if (block.string[range.start] == fss_extended_write_pipe_content_start) {
+ contents.used++;
+
+ if (contents.used < contents.size && contents.array[contents.used].used) {
+ contents.array[contents.used].used = 0;
+ }
+
+ continue;
+ }
+ else if (block.string[range.start] == fss_extended_write_pipe_content_end) {
+ state = 0x3;
+ range.start++;
+ break;
+ }
+
+ if (contents.used + 1 > contents.size) {
+ status = fl_string_dynamics_size_increase(f_fss_default_allocation_step, &contents);
+
+ if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_string_dynamics_size_increase", F_true);
+ break;
+ }
+ }
+
+ if (contents.array[contents.used].used + 1 > contents.array[contents.used].size) {
+ status = fl_string_dynamic_size_increase(f_fss_default_allocation_step, &contents.array[contents.used]);
+
+ if (F_status_is_error(status)) {
+ fll_error_print(data.error, F_status_set_fine(status), "fl_string_dynamic_size_increase", F_true);
+ break;
+ }
+ }
+
+ contents.array[contents.used].string[contents.array[contents.used].used++] = block.string[range.start];
+ } // for
+
+ if (F_status_is_error(status)) break;
+ }
+ else {
+ state = 0x3;
+ }
+ }
+
+ if (state == 0x3) {
+ status = fss_extended_write_process(data, output, quote, &object, &contents, buffer);
+ if (F_status_is_error(status)) break;
+
+ state = 0;
+ }
+ } // for
+
+ // if the pipe ended before finishing, then attempt to wrap up.
+ if (status_pipe == F_none_eof && state) {
+ status = fss_extended_write_process(data, output, quote, &object, &contents, buffer);
+ }
+
+ f_macro_string_dynamic_t_delete_simple(block);
+ f_macro_string_dynamic_t_delete_simple(object);
+ f_macro_string_dynamics_t_delete_simple(contents);
+ return status;
+ }
+#endif // _di_fss_extended_write_process_pipe_
+
#ifdef __cplusplus
} // extern "C"
#endif
#endif
/**
- * Print an message about the object and content parameters not being specified the same number of times.
+ * Print an message about the object and content parameters not being specified the correct number of times.
*
* @param data
* The program data.
* F_none on success.
* F_failure (with error bit) for any othe failure.
*/
-#ifndef _di_fss_extended_write_error_parameter_same_times_print_
- void fss_extended_write_error_parameter_same_times_print(const fss_extended_write_data_t data) f_gcc_attribute_visibility_internal;
-#endif // _di_fss_extended_write_error_parameter_same_times_print_
+#ifndef _di_fss_extended_write_error_parameter_at_least_once_print_
+ void fss_extended_write_error_parameter_at_least_once(const fss_extended_write_data_t data) f_gcc_attribute_visibility_internal;
+#endif // _di_fss_extended_write_error_parameter_at_least_once_print_
/**
* Print an message about a parameter missing a value.
* The program data.
* @param output
* The file to output to.
- * @param object
- * The object to validate and print.
- * @param contents
- * An array of content to escape and print.
* @param quote
* The quote character to use.
* This is either single our double quote.
+ * @param object
+ * A pointer to the object to validate and print.
+ * Set to 0 to disable.
+ * @param content
+ * A pointer to the content to escape and print.
+ * Set to 0 to disable.
* @param buffer
* The buffer array used as a cache to construct the output before printing.
*
* F_failure (with error bit) for any othe failure.
*/
#ifndef _di_fss_extended_write_process_
- extern f_return_status fss_extended_write_process(const fss_extended_write_data_t data, const f_file_t output, const f_string_static_t object, const f_string_statics_t contents, const f_fss_quote_t quote, f_string_dynamic_t *buffer) f_gcc_attribute_visibility_internal;
+ extern f_return_status fss_extended_write_process(const fss_extended_write_data_t data, const f_file_t output, const f_fss_quote_t quote, const f_string_static_t *object, const f_string_statics_t *contents, f_string_dynamic_t *buffer) f_gcc_attribute_visibility_internal;
#endif // _di_fss_extended_write_process_
+/**
+ * Process the pipe, reading from the pipe and writing to the output.
+ *
+ * @param data
+ * The program data.
+ * @param output
+ * The file to output to.
+ * @param quote
+ * The quote character to use.
+ * This is either single our double quote.
+ * @param buffer
+ * The buffer array used as a cache to construct the output before printing.
+ *
+ * @return
+ * F_none on success.
+ * F_failure (with error bit) for any othe failure.
+ */
+#ifndef _di_fss_extended_write_process_pipe_
+ extern f_return_status fss_extended_write_process_pipe(const fss_extended_write_data_t data, const f_file_t output, const f_fss_quote_t quote, f_string_dynamic_t *buffer) f_gcc_attribute_visibility_internal;
+#endif // _di_fss_extended_write_process_pipe_
+
#ifdef __cplusplus
} // extern "C"
#endif
#ifndef _di_fss_status_code_delete_data_
f_return_status fss_status_code_delete_data(fss_status_code_data_t *data) {
- f_string_length_t i = 0;
- while (i < fss_status_code_total_parameters) {
+ for (f_string_length_t i = 0; i < fss_status_code_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
- i++;
- } // while
+ } // for
f_macro_string_lengths_t_delete_simple(data->remaining);
+
f_macro_color_context_t_delete_simple(data->context);
return F_none;
#ifndef _di_iki_read_delete_data_
f_return_status iki_read_delete_data(iki_read_data_t *data) {
- f_status_t status = F_none;
- f_string_length_t i = 0;
- while (i < iki_read_total_parameters) {
+ for (f_string_length_t i = 0; i < iki_read_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
- i++;
- } // while
+ } // for
f_macro_string_lengths_t_delete_simple(data->remaining);
f_macro_string_dynamic_t_delete_simple(data->buffer);
+
f_macro_color_context_t_delete_simple(data->context);
return F_none;
#ifndef _di_iki_write_delete_data_
f_return_status iki_write_delete_data(iki_write_data_t *data) {
- f_status_t status = F_none;
- f_string_length_t i = 0;
- while (i < iki_write_total_parameters) {
+ for (f_string_length_t i = 0; i < iki_write_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
- i++;
- } // while
+ } // for
f_macro_string_lengths_t_delete_simple(data->remaining);
f_macro_string_dynamic_t_delete_simple(data->buffer);
+
f_macro_color_context_t_delete_simple(data->context);
return F_none;
#ifndef _di_status_code_delete_data_
f_return_status status_code_delete_data(status_code_data_t *data) {
- f_string_length_t i = 0;
-
- while (i < status_code_total_parameters) {
+ for (f_string_length_t i = 0; i < status_code_total_parameters; i++) {
f_macro_string_lengths_t_delete_simple(data->parameters[i].locations);
+ f_macro_string_lengths_t_delete_simple(data->parameters[i].locations_sub);
f_macro_string_lengths_t_delete_simple(data->parameters[i].additional);
- i++;
- } // while
+ } // for
f_macro_string_lengths_t_delete_simple(data->remaining);
+
f_macro_color_context_t_delete_simple(data->context);
return F_none;