From: Kevin Day Date: Mon, 10 Jul 2023 03:22:06 +0000 (-0500) Subject: Progress: Further work in TacocaT. X-Git-Url: https://git.kevux.org/?a=commitdiff_plain;h=0172454d2b6b2c6ee3f156f8106c948e58832c3c;p=kevux-tools Progress: Further work in TacocaT. Create a socket set and move all associated arrays into it. This allows for a receive and a send socket set to keep all of the associated properties together. Move a lot of the processing functionality into its own functions and reduce some of the redundancy. --- diff --git a/sources/c/tacocat/main/common.c b/sources/c/tacocat/main/common.c index 8083e09..ff6eaca 100644 --- a/sources/c/tacocat/main/common.c +++ b/sources/c/tacocat/main/common.c @@ -167,24 +167,9 @@ extern "C" { kt_tacocat_long_send_s, }; - f_files_t * const files[] = { - &main->setting.file_receives, - &main->setting.file_sends, - }; - - f_sockets_t * const sockets[] = { - &main->setting.socket_receives, - &main->setting.socket_sends, - }; - - f_statuss_t * const statuss[] = { - &main->setting.status_receives, - &main->setting.status_sends, - }; - - f_string_dynamics_t * const strings[] = { - &main->setting.receives, - &main->setting.sends, + kt_tacocat_socket_set_t * const sets[] = { + &main->setting.receive, + &main->setting.send, }; const bool const is_receive[] = { @@ -221,21 +206,26 @@ extern "C" { continue; } - strings[i]->used = 0; + sets[i]->names.used = 0; + sets[i]->buffers.used = 0; - main->setting.state.status = f_string_dynamics_increase_by(main->program.parameters.array[parameters[i]].values.used / 2, strings[i]); + main->setting.state.status = f_string_dynamics_increase_by(main->program.parameters.array[parameters[i]].values.used / 2, &sets[i]->names); macro_setting_load_handle_send_receive_error_continue_1(f_string_dynamics_increase_by); - main->setting.state.status = f_files_increase_by(main->program.parameters.array[parameters[i]].values.used / 2, files[i]); + main->setting.state.status = f_string_dynamics_increase_by(main->program.parameters.array[parameters[i]].values.used / 2, &sets[i]->buffers); + + macro_setting_load_handle_send_receive_error_continue_1(f_string_dynamics_increase_by); + + main->setting.state.status = f_files_increase_by(main->program.parameters.array[parameters[i]].values.used / 2, &sets[i]->files); macro_setting_load_handle_send_receive_error_continue_1(f_files_increase_by); - main->setting.state.status = f_sockets_increase_by(main->program.parameters.array[parameters[i]].values.used / 2, sockets[i]); + main->setting.state.status = f_sockets_increase_by(main->program.parameters.array[parameters[i]].values.used / 2, &sets[i]->sockets); macro_setting_load_handle_send_receive_error_continue_1(f_sockets_increase_by); - main->setting.state.status = f_statuss_increase_by(main->program.parameters.array[parameters[i]].values.used / 2, statuss[i]); + main->setting.state.status = f_statuss_increase_by(main->program.parameters.array[parameters[i]].values.used / 2, &sets[i]->statuss); macro_setting_load_handle_send_receive_error_continue_1(f_statuss_increase_by); @@ -243,35 +233,36 @@ extern "C" { // First parameter value represents the network address or the socket file path. index = main->program.parameters.array[parameters[i]].values.array[j]; - statuss[i]->array[j] = F_none; - strings[i]->array[j].used = 0; + sets[i]->statuss.array[j] = F_none; + sets[i]->names.array[j].used = 0; + sets[i]->buffers.array[j].used = 0; if (main->program.parameters.arguments.array[index].used) { if (f_path_is_absolute(main->program.parameters.arguments.array[index]) == F_true || f_path_is_relative_current(main->program.parameters.arguments.array[index]) == F_true) { - main->setting.state.status = f_string_dynamic_increase_by(main->program.parameters.arguments.array[index].used + 2, &strings[i]->array[j]); + main->setting.state.status = f_string_dynamic_increase_by(main->program.parameters.arguments.array[index].used + 2, &sets[i]->names.array[j]); macro_setting_load_handle_send_receive_error_continue_2(f_string_dynamic_increase_by); - main->setting.state.status = f_string_dynamic_append_nulless(main->program.parameters.arguments.array[index], &strings[i]->array[j]); + main->setting.state.status = f_string_dynamic_append_nulless(main->program.parameters.arguments.array[index], &sets[i]->names.array[j]); macro_setting_load_handle_send_receive_error_continue_2(f_string_dynamic_append_nulless); // Designate this as a socket file by appending after the terminating NULL, past the used length. - strings[i]->array[j].string[strings[i]->array[j].used] = 0; - strings[i]->array[j].string[strings[i]->array[j].used + 1] = f_string_ascii_slash_forward_s.string[0]; + sets[i]->names.array[j].string[sets[i]->names.array[j].used] = 0; + sets[i]->names.array[j].string[sets[i]->names.array[j].used + 1] = f_string_ascii_slash_forward_s.string[0]; if (is_receive[i]) { - main->setting.state.status = f_file_exists(strings[i]->array[j], F_true); + main->setting.state.status = f_file_exists(sets[i]->names.array[j], F_true); macro_setting_load_handle_send_receive_error_continue_2(f_string_dynamic_append_nulless); } - strings[i]->array[j].string[strings[i]->array[j].used] = 0; - sockets[i]->array[j].domain = f_socket_protocol_family_local_e; - sockets[i]->array[j].protocol = f_socket_protocol_tcp_e; - sockets[i]->array[j].type = f_socket_address_family_local_e; - sockets[i]->array[j].name = strings[i]->array[j]; + sets[i]->names.array[j].string[sets[i]->names.array[j].used] = 0; + sets[i]->sockets.array[j].domain = f_socket_protocol_family_local_e; + sets[i]->sockets.array[j].protocol = f_socket_protocol_tcp_e; + sets[i]->sockets.array[j].type = f_socket_address_family_local_e; + sets[i]->sockets.array[j].name = sets[i]->names.array[j]; } else if (main->setting.flag & kt_tacocat_main_flag_resolve_classic_e) { memset(&host, 0, sizeof(struct hostent)); @@ -315,7 +306,7 @@ extern "C" { } if (host.h_addrtype) { - main->setting.state.status = f_string_dynamic_append(address, &strings[i]->array[j]); + main->setting.state.status = f_string_dynamic_append(address, &sets[i]->names.array[j]); macro_setting_load_handle_send_receive_error_continue_2(f_string_dynamic_append); } @@ -338,12 +329,12 @@ extern "C" { failed = main->setting.state.status; } - statuss[i]->array[j] = main->setting.state.status; + sets[i]->statuss.array[j] = main->setting.state.status; continue; } - main->setting.state.status = f_string_dynamic_increase_by(INET6_ADDRSTRLEN + 1, &strings[i]->array[j]); + main->setting.state.status = f_string_dynamic_increase_by(INET6_ADDRSTRLEN + 1, &sets[i]->names.array[j]); macro_setting_load_handle_send_receive_error_continue_2(f_string_dynamic_increase_by); @@ -361,7 +352,7 @@ extern "C" { k = 0; } - main->setting.state.status = f_string_dynamic_increase_by(INET6_ADDRSTRLEN + 1, &strings[i]->array[j]); + main->setting.state.status = f_string_dynamic_increase_by(INET6_ADDRSTRLEN + 1, &sets[i]->names.array[j]); macro_setting_load_handle_send_receive_error_continue_2(f_string_dynamic_increase_by); @@ -374,7 +365,7 @@ extern "C" { family.address.v6 = *((struct in6_addr *) host.h_addr_list[k]); } - main->setting.state.status = f_network_to_ip_string(family, &strings[i]->array[j]); + main->setting.state.status = f_network_to_ip_string(family, &sets[i]->names.array[j]); if (main->setting.state.status == F_data_not || !host.h_addr_list || !host.h_addr_list[0]) { main->setting.state.status = F_status_set_error(F_parameter); @@ -388,36 +379,37 @@ extern "C" { failed = main->setting.state.status; } - statuss[i]->array[j] = main->setting.state.status; + sets[i]->statuss.array[j] = main->setting.state.status; continue; } - strings[i]->array[j].string[strings[i]->array[j].used] = 0; + sets[i]->names.array[j].string[sets[i]->names.array[j].used] = 0; } - sockets[i]->array[j].protocol = f_socket_protocol_tcp_e; - sockets[i]->array[j].type = host.h_addrtype; + sets[i]->sockets.array[j].protocol = f_socket_protocol_tcp_e; + sets[i]->sockets.array[j].type = host.h_addrtype; if (host.h_addrtype == f_socket_address_family_inet4_e) { - sockets[i]->array[j].domain = f_socket_protocol_family_inet4_e; - sockets[i]->array[j].address.inet4.sin_port = (in_port_t) port; - sockets[i]->array[j].address.inet4.sin_addr.s_addr = INADDR_ANY; + sets[i]->sockets.array[j].domain = f_socket_protocol_family_inet4_e; + sets[i]->sockets.array[j].address.inet4.sin_port = (in_port_t) port; + sets[i]->sockets.array[j].address.inet4.sin_addr.s_addr = INADDR_ANY; } else if (host.h_addrtype == f_socket_address_family_inet6_e) { - sockets[i]->array[j].domain = f_socket_protocol_family_inet6_e; - sockets[i]->array[j].address.inet6.sin6_port = (in_port_t) port; - sockets[i]->array[j].address.inet6.sin6_addr = in6addr_any; + sets[i]->sockets.array[j].domain = f_socket_protocol_family_inet6_e; + sets[i]->sockets.array[j].address.inet6.sin6_port = (in_port_t) port; + sets[i]->sockets.array[j].address.inet6.sin6_addr = in6addr_any; } } else { // @todo Kevux DNS resolution. } - ++files[i]->used; - ++sockets[i]->used; - ++statuss[i]->used; - ++strings[i]->used; + ++sets[i]->files.used; + ++sets[i]->sockets.used; + ++sets[i]->statuss.used; + ++sets[i]->names.used; + ++sets[i]->buffers.used; } else { main->setting.state.status = F_status_set_error(F_parameter); @@ -430,7 +422,7 @@ extern "C" { failed = main->setting.state.status; } - statuss[i]->array[j] = main->setting.state.status; + sets[i]->statuss.array[j] = main->setting.state.status; continue; } @@ -441,20 +433,13 @@ extern "C" { if (main->program.parameters.arguments.array[index].used) { // Make sure the current file is closed. - f_file_close(&files[i]->array[j]); + f_file_close(&sets[i]->files.array[j]); - if (is_receive[i]) { - files[i]->array[j].flag = F_file_flag_append_wo_d; - files[i]->array[j].size_read = main->setting.block_size_send; - files[i]->array[j].size_write = main->setting.block_size_send; - } - else { - files[i]->array[j].flag = F_file_flag_read_only_d; - files[i]->array[j].size_read = main->setting.block_size_receive; - files[i]->array[j].size_write = main->setting.block_size_receive; - } + sets[i]->files.array[j].flag = is_receive[i] ? F_file_flag_append_wo_d : F_file_flag_read_only_d; + sets[i]->files.array[j].size_read = sets[i]->block_size; + sets[i]->files.array[j].size_write = sets[i]->block_size; - main->setting.state.status = f_file_open(main->program.parameters.arguments.array[index], F_file_mode_all_rw_d, &files[i]->array[j]); + main->setting.state.status = f_file_open(main->program.parameters.arguments.array[index], F_file_mode_all_rw_d, &sets[i]->files.array[j]); if (F_status_is_error(main->setting.state.status)) { macro_setting_load_handle_send_receive_error_file_continue_1(f_file_open, main->program.parameters.arguments.array[index], f_file_operation_open_s, fll_error_file_type_file_e); @@ -463,7 +448,7 @@ extern "C" { failed = main->setting.state.status; } - statuss[i]->array[j] = main->setting.state.status; + sets[i]->statuss.array[j] = main->setting.state.status; } } else { @@ -477,7 +462,7 @@ extern "C" { failed = main->setting.state.status; } - statuss[i]->array[j] = main->setting.state.status; + sets[i]->statuss.array[j] = main->setting.state.status; continue; } diff --git a/sources/c/tacocat/main/common.h b/sources/c/tacocat/main/common.h index 5f265cd..b7a4aaf 100644 --- a/sources/c/tacocat/main/common.h +++ b/sources/c/tacocat/main/common.h @@ -28,7 +28,7 @@ extern "C" { * @param main * The main program and settings data. * - * This alters setting.status: + * This alters setting.state.status: * F_none on success. * * F_parameter (with error bit) on parameter error. diff --git a/sources/c/tacocat/main/common/define.h b/sources/c/tacocat/main/common/define.h index 2d8922a..771ccf2 100644 --- a/sources/c/tacocat/main/common/define.h +++ b/sources/c/tacocat/main/common/define.h @@ -27,9 +27,10 @@ extern "C" { * kt_tacocat_backlog_*_d: * - max: The max backlog size to use. * - * kt_tacocat_block_size_*_d: - * - receive: The block size in bytes to use when sending packets. - * - send: The block size in bytes to use when receiving packets. + * kt_tacocat_block_*_d: + * - size: The block size in bytes to use for either sending or receiving. + * - size_receive: The block size in bytes to use when sending packets. + * - size_send: The block size in bytes to use when receiving packets. * * kt_tacocat_signal_*_d: * - check: When not using threads, this is how often to perform the check (lower numbers incur more kernel I/O). @@ -42,8 +43,9 @@ extern "C" { #define kt_tacocat_backlog_max_d 1024 - #define kt_tacocat_block_size_receive_d 65535 - #define kt_tacocat_block_size_send_d 65535 + #define kt_tacocat_block_size_d 65535 + #define kt_tacocat_block_size_receive_d kt_tacocat_block_size_d + #define kt_tacocat_block_size_send_d kt_tacocat_block_size_d #define kt_tacocat_signal_check_d 20000 #define kt_tacocat_signal_check_failsafe_d 20000 @@ -91,7 +93,7 @@ extern "C" { failed = main->setting.state.status; \ } \ \ - statuss[i]->array[j] = main->setting.state.status; \ + sets[i]->statuss.array[j] = main->setting.state.status; \ \ continue; \ } @@ -106,7 +108,7 @@ extern "C" { failed = main->setting.state.status; \ } \ \ - statuss[i]->array[j] = main->setting.state.status; \ + sets[i]->statuss.array[j] = main->setting.state.status; \ \ continue; \ } diff --git a/sources/c/tacocat/main/common/print.c b/sources/c/tacocat/main/common/print.c index 1036b71..7b44ec8 100644 --- a/sources/c/tacocat/main/common/print.c +++ b/sources/c/tacocat/main/common/print.c @@ -28,6 +28,7 @@ extern "C" { "f_thread_create", "fll_program_parameter_process_context", "fll_program_parameter_process_verbosity", + "kt_tacocat_process_socket_set_error_has", "kt_tacocat_setting_load_address_port_extract", }; #endif // _di_kt_tacocat_f_a_ diff --git a/sources/c/tacocat/main/common/print.h b/sources/c/tacocat/main/common/print.h index a0fb409..75dc03e 100644 --- a/sources/c/tacocat/main/common/print.h +++ b/sources/c/tacocat/main/common/print.h @@ -61,6 +61,7 @@ extern "C" { kt_tacocat_f_f_thread_create_e, kt_tacocat_f_fll_program_parameter_process_context_e, kt_tacocat_f_fll_program_parameter_process_verbosity_e, + kt_tacocat_f_kt_tacocat_process_socket_set_error_has_e, kt_tacocat_f_kt_tacocat_setting_load_address_port_extract_e, }; // enum #endif // _di_kt_tacocat_f_e_ diff --git a/sources/c/tacocat/main/common/string.h b/sources/c/tacocat/main/common/string.h index 8c11a37..308ea81 100644 --- a/sources/c/tacocat/main/common/string.h +++ b/sources/c/tacocat/main/common/string.h @@ -104,21 +104,21 @@ extern "C" { * The main program parameters. */ #ifndef _di_kt_tacocat_parameter_s_ - #define KT_TACOCAT_short_receive_s "r" - #define KT_TACOCAT_short_resolve_s "R" - #define KT_TACOCAT_short_send_s "s" + #define KT_TACOCAT_short_receive_s "r" + #define KT_TACOCAT_short_resolve_s "R" + #define KT_TACOCAT_short_send_s "s" - #define KT_TACOCAT_long_receive_s "receive" - #define KT_TACOCAT_long_resolve_s "resolve" - #define KT_TACOCAT_long_send_s "send" + #define KT_TACOCAT_long_receive_s "receive" + #define KT_TACOCAT_long_resolve_s "resolve" + #define KT_TACOCAT_long_send_s "send" - #define KT_TACOCAT_short_receive_s_length 1 - #define KT_TACOCAT_short_resolve_s_length 1 - #define KT_TACOCAT_short_send_s_length 1 + #define KT_TACOCAT_short_receive_s_length 1 + #define KT_TACOCAT_short_resolve_s_length 1 + #define KT_TACOCAT_short_send_s_length 1 - #define KT_TACOCAT_long_receive_s_length 7 - #define KT_TACOCAT_long_resolve_s_length 7 - #define KT_TACOCAT_long_send_s_length 4 + #define KT_TACOCAT_long_receive_s_length 7 + #define KT_TACOCAT_long_resolve_s_length 7 + #define KT_TACOCAT_long_send_s_length 4 extern const f_string_static_t kt_tacocat_short_receive_s; extern const f_string_static_t kt_tacocat_short_resolve_s; diff --git a/sources/c/tacocat/main/common/type.c b/sources/c/tacocat/main/common/type.c index 5c13fb7..bd51e72 100644 --- a/sources/c/tacocat/main/common/type.c +++ b/sources/c/tacocat/main/common/type.c @@ -19,35 +19,32 @@ extern "C" { if (!setting) return F_status_set_error(F_parameter); - f_number_unsigned_t i = 0; + { + f_number_unsigned_t j = 0; - for (; i < setting->file_receives.used ; ++i) { - f_file_close(&setting->file_receives.array[i]); - } // for + kt_tacocat_socket_set_t * const sets[] = { + &setting->receive, + &setting->send, + }; - for (; i < setting->file_sends.used ; ++i) { - f_file_close(&setting->file_sends.array[i]); - } // for + for (uint8_t i = 0; i < 2; ++i) { - for (; i < setting->socket_receives.used ; ++i) { - f_socket_disconnect(&setting->socket_receives.array[i], program.signal_received ? f_socket_close_fast_e : f_socket_close_read_write_e); - } // for + for (; j < sets[i]->files.used ; ++j) { + f_file_close(&sets[i]->files.array[j]); + } // for - for (; i < setting->socket_sends.used ; ++i) { - f_socket_disconnect(&setting->socket_sends.array[i], program.signal_received ? f_socket_close_fast_e : f_socket_close_read_write_e); - } // for + for (; j < sets[i]->sockets.used ; ++j) { + f_socket_disconnect(&sets[i]->sockets.array[j], program.signal_received ? f_socket_close_fast_e : f_socket_close_read_write_e); + } // for - f_files_resize(0, &setting->file_receives); - f_files_resize(0, &setting->file_sends); + f_files_resize(0, &sets[i]->files); + f_sockets_resize(0, &sets[i]->sockets); + f_statuss_resize(0, &sets[i]->statuss); - f_sockets_resize(0, &setting->socket_receives); - f_sockets_resize(0, &setting->socket_sends); - - f_statuss_resize(0, &setting->status_receives); - f_statuss_resize(0, &setting->status_sends); - - f_string_dynamics_resize(0, &setting->receives); - f_string_dynamics_resize(0, &setting->sends); + f_string_dynamics_resize(0, &sets[i]->names); + f_string_dynamics_resize(0, &sets[i]->buffers); + } // for + } f_string_dynamic_resize(0, &setting->buffer); diff --git a/sources/c/tacocat/main/common/type.h b/sources/c/tacocat/main/common/type.h index a77a32a..7a8c116 100644 --- a/sources/c/tacocat/main/common/type.h +++ b/sources/c/tacocat/main/common/type.h @@ -17,6 +17,49 @@ extern "C" { #endif /** + * A set containing all socket related data sets. + * + * block_size: The size in bytes to used to represent a block when sending or receiving packets. + * + * files: An array of files for each socket. + * sockets: An array of the network sockets. + * statuss: An array of statuses for each socket. + * names: An array of names for each socket. + * buffers: An array of buffers for sending or receiving data between clients for each socket. + */ +#ifndef _di_kt_tacocat_socket_set_t_ + typedef struct { + f_number_unsigned_t block_size; + + f_files_t files; + f_sockets_t sockets; + f_statuss_t statuss; + f_string_dynamics_t names; + f_string_dynamics_t buffers; + } kt_tacocat_socket_set_t; + + #define kt_tacocat_socket_set_t_initialize \ + { \ + kt_tacocat_block_size_d, \ + f_files_t_initialize, \ + f_sockets_t_initialize, \ + f_statuss_t_initialize, \ + f_string_dynamics_t_initialize, \ + f_string_dynamics_t_initialize, \ + } + + #define macro_kt_tacocat_setting_t_initialize_1(block_size) \ + { \ + block_size, \ + f_files_t_initialize, \ + f_sockets_t_initialize, \ + f_statuss_t_initialize, \ + f_string_dynamics_t_initialize, \ + f_string_dynamics_t_initialize, \ + } +#endif // _di_kt_tacocat_socket_set_t_ + +/** * The main program settings. * * This is passed to the program-specific main entry point to designate program settings. @@ -24,23 +67,11 @@ extern "C" { * * flag: Flags passed to the main function. * - * block_size_receive: The size in bytes to used to represent a block when receiving packets. - * block_size_send: The size in bytes to used to represent a block when sending packets. - * * status_thread: A status used eclusively by the threaded signal handler. * state: The state data used when processing data. * - * file_receives: An array of files for receiving. - * file_sends: An array of files for sending. - * - * socket_receives: An array of the network sockets for receiving. - * socket_sends: An array of the network sockets for sending. - * - * status_receives: An array of statuses for receiving. - * status_sends: An array of statuses for sending. - * - * receives: An array of buffers for receiving data receive clients. - * sends: An array of buffers for sending data send clients. + * receive: The socket set for receiving data receive clients. + * send: The socket set for sending data send clients. * * buffer: A string buffer used for caching purposes. */ @@ -48,23 +79,11 @@ extern "C" { typedef struct { uint64_t flag; - f_number_unsigned_t block_size_receive; - f_number_unsigned_t block_size_send; - f_status_t status_thread; f_state_t state; - f_files_t file_receives; - f_files_t file_sends; - - f_sockets_t socket_receives; - f_sockets_t socket_sends; - - f_statuss_t status_receives; - f_statuss_t status_sends; - - f_string_dynamics_t receives; - f_string_dynamics_t sends; + kt_tacocat_socket_set_t receive; + kt_tacocat_socket_set_t send; f_string_dynamic_t buffer; } kt_tacocat_setting_t; @@ -72,18 +91,10 @@ extern "C" { #define kt_tacocat_setting_t_initialize \ { \ kt_tacocat_main_flag_none_e, \ - kt_tacocat_block_size_receive_d, \ - kt_tacocat_block_size_send_d, \ F_none, \ macro_f_state_t_initialize_1(kt_tacocat_allocation_large_d, kt_tacocat_allocation_small_d, F_none, 0, 0, &fll_program_standard_signal_handle, 0, 0, 0, 0), \ - f_files_t_initialize, \ - f_files_t_initialize, \ - f_sockets_t_initialize, \ - f_sockets_t_initialize, \ - f_statuss_t_initialize, \ - f_statuss_t_initialize, \ - f_string_dynamics_t_initialize, \ - f_string_dynamics_t_initialize, \ + macro_kt_tacocat_setting_t_initialize_1(kt_tacocat_block_size_receive_d), \ + macro_kt_tacocat_setting_t_initialize_1(kt_tacocat_block_size_send_d), \ f_string_dynamic_t_initialize, \ } #endif // _di_kt_tacocat_setting_t_ diff --git a/sources/c/tacocat/main/print/error.c b/sources/c/tacocat/main/print/error.c index f8179a3..b27b570 100644 --- a/sources/c/tacocat/main/print/error.c +++ b/sources/c/tacocat/main/print/error.c @@ -53,7 +53,7 @@ extern "C" { #endif // _di_kt_tacocat_print_error_parameter_value_resolve_unknown_ #ifndef _di_kt_tacocat_print_error_setting_socket_lengths_must_match_ - f_status_t kt_tacocat_print_error_setting_socket_lengths_must_match(fl_print_t * const print, const f_string_dynamic_t name, const f_number_unsigned_t names, const f_number_unsigned_t files, const f_number_unsigned_t sockets, const f_number_unsigned_t statuss) { + f_status_t kt_tacocat_print_error_setting_socket_lengths_must_match(fl_print_t * const print, const f_string_dynamic_t name, const kt_tacocat_socket_set_t set) { if (!print || !print->custom) return F_status_set_error(F_output_not); if (print->verbosity < f_console_verbosity_error_e) return F_output_not; @@ -63,13 +63,15 @@ extern "C" { fl_print_format("%[%QThe lengths of all%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format("%[%Q%]", print->to, print->set->notable, name, print->set->notable); fl_print_format(" %[arrays do not have the same length, name array length is '%]", print->to, print->set->error, print->set->error, f_string_eol_s); - fl_print_format("%[%ul%]", print->to, print->set->notable, names, print->set->notable); + fl_print_format("%[%ul%]", print->to, print->set->notable, set.names.used, print->set->notable); + fl_print_format("%', the buffer array length is '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%[%ul%]", print->to, print->set->notable, set.buffers.used, print->set->notable); fl_print_format("%', the file array length is '%]", print->to, print->set->error, print->set->error, f_string_eol_s); - fl_print_format("%[%ul%]", print->to, print->set->notable, files, print->set->notable); + fl_print_format("%[%ul%]", print->to, print->set->notable, set.files.used, print->set->notable); fl_print_format(" %[', the socket array length is '%]", print->to, print->set->error, print->set->error, f_string_eol_s); - fl_print_format("%[%ul%]", print->to, print->set->notable, sockets, print->set->notable); + fl_print_format("%[%ul%]", print->to, print->set->notable, set.sockets.used, print->set->notable); fl_print_format(" %[', and the status array length is '%]", print->to, print->set->error, print->set->error, f_string_eol_s); - fl_print_format("%[%ul%]", print->to, print->set->notable, statuss, print->set->notable); + fl_print_format("%[%ul%]", print->to, print->set->notable, set.statuss.used, print->set->notable); fl_print_format(" %['.%]%r", print->to, print->set->error, print->set->error, f_string_eol_s); f_file_stream_unlock(print->to); @@ -78,6 +80,26 @@ extern "C" { } #endif // _di_kt_tacocat_print_error_setting_socket_lengths_must_match_ +#ifndef _di_kt_tacocat_print_error_socket_protocol_unsupported_ + f_status_t kt_tacocat_print_error_socket_protocol_unsupported(fl_print_t * const print, const f_string_dynamic_t name, const f_number_unsigned_t protocol) { + + if (!print || !print->custom) return F_status_set_error(F_output_not); + if (print->verbosity < f_console_verbosity_error_e) return F_output_not; + + f_file_stream_lock(print->to); + + fl_print_format("%[%QUnsupported protocol%] ", print->to, print->set->error, print->prefix, print->set->error); + fl_print_format("%[%lu%]", print->to, print->set->notable, protocol, print->set->notable); + fl_print_format(" %[while processing '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%[%Q%]", print->to, print->set->notable, name, print->set->notable); + fl_print_format(" %['.%]%r", print->to, print->set->error, print->set->error, f_string_eol_s); + + f_file_stream_unlock(print->to); + + return F_none; + } +#endif // _di_kt_tacocat_print_error_socket_protocol_unsupported_ + #ifdef __cplusplus } // extern "C" #endif diff --git a/sources/c/tacocat/main/print/error.h b/sources/c/tacocat/main/print/error.h index 274bdf3..6012352 100644 --- a/sources/c/tacocat/main/print/error.h +++ b/sources/c/tacocat/main/print/error.h @@ -95,15 +95,9 @@ extern "C" { * * This does not alter print.custom.setting.state.status. * @param name - * The name of the set of arrays that must have the same length. - * @param names - * The length of the names array. - * @param files - * The length of the files array. - * @param sockets - * The length of the sockets array. - * @param statuss - * The length of the statuss array. + * The name representing the socket set whose array lengths must match. + * @param set + * The socket set. * * @return * F_none on success. @@ -114,9 +108,33 @@ extern "C" { * @see fll_error_file_print() */ #ifndef _di_kt_tacocat_print_error_setting_socket_lengths_must_match_ - extern f_status_t kt_tacocat_print_error_setting_socket_lengths_must_match(fl_print_t * const print, const f_string_dynamic_t name, const f_number_unsigned_t names, const f_number_unsigned_t files, const f_number_unsigned_t sockets, const f_number_unsigned_t statuss); + extern f_status_t kt_tacocat_print_error_setting_socket_lengths_must_match(fl_print_t * const print, const f_string_dynamic_t name, const kt_tacocat_socket_set_t set); #endif // _di_kt_tacocat_print_error_setting_socket_lengths_must_match_ +/** + * Print error message for when an unsupported protocol is used. + * + * @param print + * The output structure to print to. + * + * This does not alter print.custom.setting.state.status. + * @param name + * The file or network name associated with the unsupported protocol. + * @param protocol + * The protocol number representing the unsupported protocol + * + * @return + * F_none on success. + * F_output_not on success, but no printing is performed. + * + * F_output_not (with error bit) if setting is NULL. + * + * @see fll_error_file_print() + */ +#ifndef _di_kt_tacocat_print_error_socket_protocol_unsupported_ + extern f_status_t kt_tacocat_print_error_socket_protocol_unsupported(fl_print_t * const print, const f_string_dynamic_t name, const f_number_unsigned_t protocol); +#endif // _di_kt_tacocat_print_error_socket_protocol_unsupported_ + #ifdef __cplusplus } // extern "C" #endif diff --git a/sources/c/tacocat/main/process.c b/sources/c/tacocat/main/process.c index 8e87ada..0fbe9a3 100644 --- a/sources/c/tacocat/main/process.c +++ b/sources/c/tacocat/main/process.c @@ -8,63 +8,158 @@ extern "C" { void kt_tacocat_process_main(kt_tacocat_main_t * const main) { if (!main) return; + if (F_status_is_error(kt_tacocat_process_socket_set_error_has(main, kt_tacocat_long_receive_s, main->setting.receive))) return; + if (F_status_is_error(kt_tacocat_process_socket_set_error_has(main, kt_tacocat_long_send_s, main->setting.send))) return; - if (main->setting.socket_receives.used != main->setting.file_receives.used && main->setting.socket_receives.used != main->setting.receives.used && main->setting.socket_receives.used != main->setting.status_receives.used) { - main->setting.state.status = F_status_set_error(F_parameter); + // @todo Make this threaded, if threading is enabled (if threading is disabled then fork). + // TacocaT is intended to be simple, so be lazy and create a thread/fork for every single receive and send. + + kt_tacocat_process_socket_set_receive(main); + kt_tacocat_process_socket_set_send(main); + + // domain + // PF_INET = ipv4 + // PF_INET6 = ipv6 + // type + // SOCK_STREAM + // SOCK_DGRAM + // "struct sockaddr", "struct sockaddr_un", or "struct sockaddr_in" + // protocol + // f_socket_protocol_tcp + // f_socket_protocol_udp - kt_tacocat_print_error_setting_socket_lengths_must_match(&main->program.error, kt_tacocat_long_receive_s, main->setting.receives.used, main->setting.file_receives.used, main->setting.socket_receives.used, main->setting.status_receives.used); + //f_socket_connect + + // @todo: + // 1: Establish connections. + // 2: read / write from files. + // 3: work or wait until told to terminate. + // 4: terminate. + + kt_tacocat_process_socket_set_disconnect(main, &main->setting.receive); + kt_tacocat_process_socket_set_disconnect(main, &main->setting.send); + + kt_tacocat_process_socket_set_error_handle(main, main->setting.receive); + kt_tacocat_process_socket_set_error_handle(main, main->setting.send); + } +#endif // _di_kt_tacocat_process_main_ + +#ifndef _di_kt_tacocat_process_socket_set_disconnect_ + void kt_tacocat_process_socket_set_disconnect(kt_tacocat_main_t * const main, kt_tacocat_socket_set_t * const set) { + + if (!main) return; + + if (!set) { + main->setting.state.status = F_status_set_error(F_parameter); return; } - if (main->setting.socket_sends.used != main->setting.file_sends.used && main->setting.socket_sends.used != main->setting.sends.used && main->setting.socket_sends.used != main->setting.status_sends.used) { + f_status_t status = F_none; + + for (f_number_unsigned_t i = 0; i < set->sockets.used; ++i) { + + if (kt_tacocat_signal_check(main)) return; + + status = f_socket_disconnect(&set->sockets.array[i], f_socket_close_read_write_e); + + if (F_status_is_error_not(set->statuss.array[i]) && F_status_is_error(main->setting.state.status)) { + set->statuss.array[i] = status; + + kt_tacocat_print_error(&main->program.error, macro_kt_tacocat_f(f_socket_disconnect)); + } + } // for + } +#endif // _di_kt_tacocat_process_socket_set_disconnect_ + +#ifndef _di_kt_tacocat_process_socket_set_error_handle_ + void kt_tacocat_process_socket_set_error_handle(kt_tacocat_main_t * const main, const kt_tacocat_socket_set_t set) { + + if (!main) return; + if (F_status_is_error(main->setting.state.status)) return; + + main->setting.state.status = F_none; + + for (f_number_unsigned_t i = 0; i < set.statuss.used; ++i) { + + if (kt_tacocat_signal_check(main)) return; + + if (F_status_is_error(set.statuss.array[i])) { + main->setting.state.status = set.statuss.array[i]; + + return; + } + } // for + } +#endif // _di_kt_tacocat_process_socket_set_error_handle_ + +#ifndef _di_kt_tacocat_process_socket_set_error_has_ + f_status_t kt_tacocat_process_socket_set_error_has(kt_tacocat_main_t * const main, const f_string_static_t parameter, const kt_tacocat_socket_set_t set) { + + if (!main) { main->setting.state.status = F_status_set_error(F_parameter); - kt_tacocat_print_error_setting_socket_lengths_must_match(&main->program.error, kt_tacocat_long_send_s, main->setting.sends.used, main->setting.file_sends.used, main->setting.socket_sends.used, main->setting.status_sends.used); + kt_tacocat_print_error(&main->program.error, macro_kt_tacocat_f(kt_tacocat_process_socket_set_error_has)); - return; + return main->setting.state.status; } - f_number_unsigned_t i = 0; + if (set.sockets.used != set.files.used || set.sockets.used != set.files.used || set.sockets.used != set.statuss.used || set.sockets.used != set.names.used || set.sockets.used != set.buffers.used) { + main->setting.state.status = F_status_set_error(F_parameter); - // @todo Make this threaded, if threading is enabled (if threading is disabled then fork). - // TacocaT is intended to be simple, so be lazy and create a thread/fork for every single receive and send. + kt_tacocat_print_error_setting_socket_lengths_must_match(&main->program.error, parameter, set); + + return main->setting.state.status; + } + + return F_none; + } +#endif // _di_kt_tacocat_process_socket_set_error_has_ + +#ifndef _di_kt_tacocat_process_socket_set_receive_ + void kt_tacocat_process_socket_set_receive(kt_tacocat_main_t * const main) { + + if (!main) return; // Create, bind, and listen to the socket. - for (; i < main->setting.socket_receives.used; ++i) { + for (f_number_unsigned_t i = 0; i < main->setting.receive.sockets.used; ++i) { if (kt_tacocat_signal_check(main)) return; - if (F_status_is_error(main->setting.status_receives.array[i])) continue; + if (F_status_is_error(main->setting.receive.statuss.array[i])) continue; - main->setting.status_receives.array[i] = f_socket_create(&main->setting.socket_receives.array[i]); + main->setting.receive.statuss.array[i] = f_socket_create(&main->setting.receive.sockets.array[i]); - if (F_status_is_error(main->setting.status_receives.array[i])) { - main->setting.state.status = main->setting.status_receives.array[i]; + if (F_status_is_error(main->setting.receive.statuss.array[i])) { + main->setting.state.status = main->setting.receive.statuss.array[i]; kt_tacocat_print_error(&main->program.error, macro_kt_tacocat_f(f_socket_create)); continue; } - if (main->setting.socket_receives.array[i].domain == f_socket_protocol_family_inet4_e) { - main->setting.status_receives.array[i] = f_socket_bind_inet4(&main->setting.socket_receives.array[i]); + if (main->setting.receive.sockets.array[i].domain == f_socket_protocol_family_inet4_e) { + main->setting.receive.statuss.array[i] = f_socket_bind_inet4(&main->setting.receive.sockets.array[i]); } - else if (main->setting.socket_receives.array[i].domain == f_socket_protocol_family_inet6_e) { - main->setting.status_receives.array[i] = f_socket_bind_inet6(&main->setting.socket_receives.array[i]); + else if (main->setting.receive.sockets.array[i].domain == f_socket_protocol_family_inet6_e) { + main->setting.receive.statuss.array[i] = f_socket_bind_inet6(&main->setting.receive.sockets.array[i]); } - else if (main->setting.socket_receives.array[i].domain == f_socket_protocol_family_local_e) { - main->setting.status_receives.array[i] = f_socket_bind_local(&main->setting.socket_receives.array[i]); + else if (main->setting.receive.sockets.array[i].domain == f_socket_protocol_family_local_e) { + main->setting.receive.statuss.array[i] = f_socket_bind_local(&main->setting.receive.sockets.array[i]); } else { - // @todo error, not supported. + main->setting.state.status = F_status_set_error(F_parameter); + + kt_tacocat_print_error_socket_protocol_unsupported(&main->program.error, main->setting.receive.names.array[i], main->setting.receive.sockets.array[i].domain); + + return; } - if (F_status_is_error(main->setting.status_receives.array[i])) { - main->setting.state.status = main->setting.status_receives.array[i]; + if (F_status_is_error(main->setting.receive.statuss.array[i])) { + main->setting.state.status = main->setting.receive.statuss.array[i]; - kt_tacocat_print_error(&main->program.error, main->setting.socket_receives.array[i].domain == f_socket_protocol_family_inet4_e + kt_tacocat_print_error(&main->program.error, main->setting.receive.sockets.array[i].domain == f_socket_protocol_family_inet4_e ? macro_kt_tacocat_f(f_socket_bind_inet4) - : main->setting.socket_receives.array[i].domain == f_socket_protocol_family_inet6_e + : main->setting.receive.sockets.array[i].domain == f_socket_protocol_family_inet6_e ? macro_kt_tacocat_f(f_socket_bind_inet6) : macro_kt_tacocat_f(f_socket_bind_local) ); @@ -72,10 +167,10 @@ extern "C" { continue; } - main->setting.status_receives.array[i] = f_socket_listen(&main->setting.socket_receives.array[i], kt_tacocat_backlog_max_d); + main->setting.receive.statuss.array[i] = f_socket_listen(&main->setting.receive.sockets.array[i], kt_tacocat_backlog_max_d); - if (F_status_is_error(main->setting.status_receives.array[i])) { - main->setting.state.status = main->setting.status_receives.array[i]; + if (F_status_is_error(main->setting.receive.statuss.array[i])) { + main->setting.state.status = main->setting.receive.statuss.array[i]; kt_tacocat_print_error(&main->program.error, macro_kt_tacocat_f(f_socket_listen)); @@ -83,17 +178,26 @@ extern "C" { } } // for - for (i = 0; i < main->setting.socket_sends.used; ++i) { + if (F_status_is_error_not(main->setting.state.status)) { + main->setting.state.status = F_none; + } + } +#endif // _di_kt_tacocat_process_socket_set_receive_ - if (kt_tacocat_signal_check(main)) return; - if (F_status_is_error(main->setting.status_sends.array[i])) continue; +#ifndef _di_kt_tacocat_process_socket_set_send_ + void kt_tacocat_process_socket_set_send(kt_tacocat_main_t * const main) { + + if (!main) return; + + for (f_number_unsigned_t i = 0; i < main->setting.send.sockets.used; ++i) { - // @todo check to see if connection is one of "local", "inet" (ipv4), or "inet6" (ipv6) and configure socket appropriately. + if (kt_tacocat_signal_check(main)) return; + if (F_status_is_error(main->setting.send.statuss.array[i])) continue; - main->setting.status_sends.array[i] = f_socket_create(&main->setting.socket_sends.array[i]); + main->setting.send.statuss.array[i] = f_socket_create(&main->setting.send.sockets.array[i]); - if (F_status_is_error(main->setting.status_sends.array[i])) { - main->setting.state.status = main->setting.status_sends.array[i]; + if (F_status_is_error(main->setting.send.statuss.array[i])) { + main->setting.state.status = main->setting.send.statuss.array[i]; kt_tacocat_print_error(&main->program.error, macro_kt_tacocat_f(f_socket_create)); @@ -103,76 +207,11 @@ extern "C" { // @todo f_socket_bind(). } // for - // domain - // PF_INET = ipv4 - // PF_INET6 = ipv6 - // type - // SOCK_STREAM - // SOCK_DGRAM - // "struct sockaddr", "struct sockaddr_un", or "struct sockaddr_in" - // protocol - // f_socket_protocol_tcp - // f_socket_protocol_udp - - //f_socket_connect - - // @todo: - // 1: Establish connections. - // 2: read / write from files. - // 3: work or wait until told to terminate. - // 4: terminate. - - // Disconnect. - for (; i < main->setting.socket_receives.used; ++i) { - - if (kt_tacocat_signal_check(main)) return; - - main->setting.status_receives.array[i] = f_socket_disconnect(&main->setting.socket_receives.array[i], f_socket_close_read_write_e); - - if (F_status_is_error(main->setting.status_receives.array[i])) { - main->setting.state.status = main->setting.status_receives.array[i]; - - kt_tacocat_print_error(&main->program.error, macro_kt_tacocat_f(f_socket_disconnect)); - } - } // for - - for (i = 0; i < main->setting.socket_sends.used; ++i) { - - if (kt_tacocat_signal_check(main)) return; - - main->setting.status_sends.array[i] = f_socket_disconnect(&main->setting.socket_sends.array[i], f_socket_close_read_write_e); - - if (F_status_is_error(main->setting.status_sends.array[i])) { - main->setting.state.status = main->setting.status_sends.array[i]; - - kt_tacocat_print_error(&main->program.error, macro_kt_tacocat_f(f_socket_disconnect)); - } - } // for - - // Handle returning errors. if (F_status_is_error_not(main->setting.state.status)) { main->setting.state.status = F_none; - - for (i = 0; i < main->setting.socket_receives.used; ++i) { - - if (kt_tacocat_signal_check(main)) return; - - if (F_status_is_error(main->setting.status_receives.array[i])) { - main->setting.state.status = main->setting.status_receives.array[i]; - } - } // for - - for (i = 0; i < main->setting.socket_sends.used; ++i) { - - if (kt_tacocat_signal_check(main)) return; - - if (F_status_is_error(main->setting.status_sends.array[i])) { - main->setting.state.status = main->setting.status_sends.array[i]; - } - } // for } } -#endif // _di_kt_tacocat_process_main_ +#endif // _di_kt_tacocat_process_socket_set_send_ #ifdef __cplusplus } // extern "C" diff --git a/sources/c/tacocat/main/process.h b/sources/c/tacocat/main/process.h index 025e4c1..7a4af94 100644 --- a/sources/c/tacocat/main/process.h +++ b/sources/c/tacocat/main/process.h @@ -25,6 +25,96 @@ extern "C" { extern void kt_tacocat_process_main(kt_tacocat_main_t * const main); #endif // _di_kt_tacocat_process_main_ +/** + * Perform the disconnect for the socket given socket set. + * + * This handles errors and prints appropriate messages. + * + * @param main + * The main program and settings data. + * + * This alters main.setting.state.status: + * F_parameter (with error bit) on invalid parameter. + * + * This does not set parameter error on success or any socket disconnect error. + * @param set + * The socket set to disconnect all sockets of. + */ +#ifndef _di_kt_tacocat_process_socket_set_disconnect_ + extern void kt_tacocat_process_socket_set_disconnect(kt_tacocat_main_t * const main, kt_tacocat_socket_set_t * const set); +#endif // _di_kt_tacocat_process_socket_set_disconnect_ + +/** + * Traverse the sockets, grabbing the first error and setting the main.setting.state.status appropriately. + * + * This does not print messages. + * + * @param main + * The main program and settings data. + * + * This alters main.setting.state.status: + * F_none on success and no error is found. + * + * An status with error bit set from any socket that has a status failure. + * + * If this already has the error bit set, then no changes are performed. + * @param set + * The socket set to handle the errors of. + */ +#ifndef _di_kt_tacocat_process_socket_set_error_handle_ + extern void kt_tacocat_process_socket_set_error_handle(kt_tacocat_main_t * const main, const kt_tacocat_socket_set_t set); +#endif // _di_kt_tacocat_process_socket_set_error_handle_ + +/** + * Check the socket set and handle and print error if the array lengths do not match. + * + * @param main + * The main program and settings data. + * + * This alters main.setting.state.status: + * F_parameter (with error bit) on parameter error. + * + * This is not altered on success. + * @param parameter + * The parameter long name to use when printing errors. + * @param set + * The socket set to handle the errors of. + * + * @return + * F_none on no error. + * + * F_parameter (with error bit) on parameter error. + */ +#ifndef _di_kt_tacocat_process_socket_set_error_has_ + extern f_status_t kt_tacocat_process_socket_set_error_has(kt_tacocat_main_t * const main, const f_string_static_t parameter, const kt_tacocat_socket_set_t set); +#endif // _di_kt_tacocat_process_socket_set_error_has_ + +/** + * Process the receive socket set. + * + * @param main + * The main program and settings data. + * + * This alters main.setting.state.status: + * F_none on success. + */ +#ifndef _di_kt_tacocat_process_socket_set_receive_ + extern void kt_tacocat_process_socket_set_receive(kt_tacocat_main_t * const main); +#endif // _di_kt_tacocat_process_socket_set_receive_ + +/** + * Process the send socket set. + * + * @param main + * The main program and settings data. + * + * This alters main.setting.state.status: + * F_none on success. + */ +#ifndef _di_kt_tacocat_process_socket_set_send_ + extern void kt_tacocat_process_socket_set_send(kt_tacocat_main_t * const main); +#endif // _di_kt_tacocat_process_socket_set_send_ + #ifdef __cplusplus } // extern "C" #endif