From: Kevin Day Date: Tue, 13 Jan 2026 04:41:06 +0000 (-0600) Subject: Progress: Begin adding GPGME support. X-Git-Url: https://www.git.kevux.org/?a=commitdiff_plain;h=59ddc938e1e2ab38450b8f44ae9e066da3489c86;p=kevux-tools Progress: Begin adding GPGME support. The GPGME is not really that good. It calls the user space GNUPG program `gpg`. This is clunky and nasty. The project also handles memory poorly. Thanks to utilizing it, the `tacocat` now exists with reachable memory. ``` ==17190== HEAP SUMMARY: ==17190== in use at exit: 1,189 bytes in 39 blocks ==17190== total heap usage: 124 allocs, 85 frees, 42,076 bytes allocated ``` I should look into other projects as well once I get GPGME fully setup and working. Projects like libgit2 or even trying to directly use libgcrypt. --- diff --git a/data/build/tacocat/defines b/data/build/tacocat/defines index 6950822..27fc8c1 100644 --- a/data/build/tacocat/defines +++ b/data/build/tacocat/defines @@ -1,4 +1,7 @@ # fss-0000 _di_thread_support_ Disable thread support, handling signals without using a separate thread. + +_en_gpgme_support_ Enable use of GPGME for providing encryption during message transfer. + _kt_resolve_default_kevux_ Default to Kevux DNS resolution methods rather than classic DNS resolution methods. diff --git a/data/build/tacocat/settings b/data/build/tacocat/settings index da1cb83..ded54bc 100644 --- a/data/build/tacocat/settings +++ b/data/build/tacocat/settings @@ -10,6 +10,7 @@ # - fanalyzer: Compile using GCC's -fanalyzer compile time option. # - flex_arrays: Use GCC strict flex arrays (supported by GCC version 13 or greater). # - gcc: Use GCC specific settings. +# - gpgme: Enable the use of GPGME. # - individual: Compile using per project (individual) libraries, does not handle thread or threadless cases. # - individual_thread: This is required when compiling in individual mode with "thread" mode. # - level: Compile using per level libraries. @@ -29,8 +30,8 @@ version_micro 5 version_file micro version_target minor -modes android clang coverage debug fanalyzer flex_arrays gcc individual individual_thread level monolithic pinephone test thread threadless -modes_default debug gcc monolithic thread +modes android clang coverage debug fanalyzer flex_arrays gcc gpgme individual individual_thread level monolithic pinephone test thread threadless +modes_default debug gcc gpgme monolithic thread build_compiler gcc build_compiler-clang clang @@ -45,6 +46,7 @@ build_libraries_shared-individual -lf_abstruse -lf_color -lf_compare -lf_console build_libraries_shared-individual_thread -lf_thread build_libraries_shared-level -lfll_2 -lfll_1 -lfll_0 build_libraries_shared-monolithic -lfll +build_libraries_shared-gpgme -lgpgme -lassuan -lgpg-error build_libraries_static -l:libc.a build_libraries_static-individual -l:libfll_error.a -l:libfll_fss.a -l:libfll_print.a -l:libfll_program.a @@ -53,6 +55,7 @@ build_libraries_static-individual -l:libf_abstruse.a -l:libf_color.a -l:libf_com build_libraries_static-individual_thread -l:libf_thread.a build_libraries_static-level -l:libfll_2.a -l:libfll_1.a -l:libfll_0.a build_libraries_static-monolithic -l:libfll.a +build_libraries_static-gpgme -l:libgpgme.a -l:libassuan.a -l:libgpg-error.a build_sources_headers common.h common/define.h common/enumeration.h common/string.h common/type.h build_sources_headers print/error.h print/message.h print/verbose.h print/warning.h @@ -60,12 +63,16 @@ build_sources_headers packet.h process.h receive.h send.h signal.h tacocat.h thr build_sources_headers receive/step/check.h receive/step/control.h receive/step/done.h receive/step/extract.h receive/step/find.h receive/step/next.h receive/step/packet.h receive/step/write.h build_sources_headers send/step/build.h send/step/check.h send/step/done.h send/step/encode.h send/step/file.h send/step/header.h send/step/packet.h send/step/size.h send/step/wait.h +build_sources_headers-gpgme gpgme.h print/gpgme.h + build_sources_library common.c common/define.c common/enumeration.c common/string.c common/type.c build_sources_library print/error.c print/message.c print/verbose.c print/warning.c build_sources_library packet.c process.c receive.c send.c signal.c tacocat.c thread.c build_sources_library receive/step/check.c receive/step/control.c receive/step/done.c receive/step/extract.c receive/step/find.c receive/step/next.c receive/step/packet.c receive/step/write.c build_sources_library send/step/build.c send/step/check.c send/step/done.c send/step/encode.c send/step/file.c send/step/header.c send/step/packet.c send/step/size.c send/step/wait.c +build_sources_library-gpgme gpgme.c print/gpgme.c + build_sources_documentation man build_static no @@ -91,6 +98,7 @@ environment LANG LC_ALL LC_COLLATE LC_CTYPE LC_FASTMSG LC_MESSAGES LC_MONETARY L defines -D_libcap_legacy_only_ defines-android -D_di_f_thread_attribute_affinity_get_ -D_di_f_thread_attribute_affinity_set_ -D_di_f_thread_attribute_concurrency_get_ -D_di_f_thread_attribute_concurrency_set_ -D_di_f_thread_attribute_default_get_ -D_di_f_thread_attribute_default_set_ -D_di_f_thread_cancel_test_ -D_di_f_thread_join_try_ -D_di_f_thread_join_timed_ -D_pthread_mutex_prioceiling_unsupported_ -D_di_f_thread_semaphore_file_close_ -D_di_f_thread_semaphore_file_open_ -D_di_f_thread_semaphore_file_delete_ -D_di_f_thread_cancel_type_set_ -D_di_f_thread_mutex_consistent_ -D_di_f_thread_mutex_attribute_robust_get_ -D_di_f_thread_mutex_attribute_robust_set_ -D_pthread_kill_as_pthread_cancel_ defines-clang -D_clang_not_a_compile_time_constant_workaround_ +defines-gpgme -D_en_gpgme_support_ defines-pinephone -D_di_f_thread_mutex_priority_ceiling_get_ -D_di_f_thread_mutex_priority_ceiling_set_ -D_di_f_thread_mutex_attribute_priority_ceiling_get_ -D_di_f_thread_mutex_attribute_priority_ceiling_set_ defines-threadless -D_di_thread_support_ defines-thread -D_pthread_attr_unsupported_ -D_pthread_sigqueue_unsupported_ diff --git a/data/build/tacocat/settings.tacocat b/data/build/tacocat/settings.tacocat index c5f8c5d..702f9d6 100644 --- a/data/build/tacocat/settings.tacocat +++ b/data/build/tacocat/settings.tacocat @@ -10,6 +10,7 @@ # - fanalyzer: Compile using GCC's -fanalyzer compile time option. # - flex_arrays: Use GCC strict flex arrays (supported by GCC version 13 or greater). # - gcc: Use GCC specific settings. +# - gpgme: Enable the use of GPGME. # - individual: Compile using per project (individual) libraries, does not handle thread or threadless cases. # - individual_thread: This is required when compiling in individual mode with "thread" mode. # - level: Compile using per level libraries. @@ -29,8 +30,8 @@ version_micro 5 version_file micro version_target minor -modes android clang coverage debug fanalyzer flex_arrays gcc individual individual_thread level monolithic pinephone test thread threadless -modes_default debug gcc monolithic thread +modes android clang coverage debug fanalyzer flex_arrays gcc gpgme individual individual_thread level monolithic pinephone test thread threadless +modes_default debug gcc gpgme monolithic thread build_compiler gcc build_compiler-clang clang @@ -45,6 +46,7 @@ build_libraries_shared-individual -lf_abstruse -lf_color -lf_compare -lf_console build_libraries_shared-individual_thread -lf_thread build_libraries_shared-level -lfll_2 -lfll_1 -lfll_0 build_libraries_shared-monolithic -lfll +build_libraries_shared-gpgme -lgpgme -lassuan -lgpg-error build_libraries_static -l:libc.a -l:libtacocat.a build_libraries_static-individual -l:libfll_error.a -l:libfll_fss.a -l:libfll_print.a -l:libfll_program.a @@ -53,6 +55,7 @@ build_libraries_static-individual -l:libf_abstruse.a -l:libf_color.a -l:libf_com build_libraries_static-individual_thread -l:libf_thread.a build_libraries_static-level -l:libfll_2.a -l:libfll_1.a -l:libfll_0.a build_libraries_static-monolithic -l:libfll.a +build_libraries_static-gpgme -l:libgpgme.a -l:libassuan.a -l:libgpg-error.a build_sources_headers tacocat.h string.h @@ -86,6 +89,7 @@ defines -D_libcap_legacy_only_ defines-android -D_di_f_thread_attribute_affinity_get_ -D_di_f_thread_attribute_affinity_set_ -D_di_f_thread_attribute_concurrency_get_ -D_di_f_thread_attribute_concurrency_set_ -D_di_f_thread_attribute_default_get_ -D_di_f_thread_attribute_default_set_ -D_di_f_thread_cancel_test_ -D_di_f_thread_join_try_ -D_di_f_thread_join_timed_ -D_pthread_mutex_prioceiling_unsupported_ -D_di_f_thread_semaphore_file_close_ -D_di_f_thread_semaphore_file_open_ -D_di_f_thread_semaphore_file_delete_ -D_di_f_thread_cancel_type_set_ -D_di_f_thread_mutex_consistent_ -D_di_f_thread_mutex_attribute_robust_get_ -D_di_f_thread_mutex_attribute_robust_set_ -D_pthread_kill_as_pthread_cancel_ defines-clang -D_clang_not_a_compile_time_constant_workaround_ defines-debug -D_en_f_status_debug_ +defines-gpgme -D_en_gpgme_support_ defines-pinephone -D_di_f_thread_mutex_priority_ceiling_get_ -D_di_f_thread_mutex_priority_ceiling_set_ -D_di_f_thread_mutex_attribute_priority_ceiling_get_ -D_di_f_thread_mutex_attribute_priority_ceiling_set_ defines-threadless -D_di_thread_support_ defines-thread -D_pthread_attr_unsupported_ -D_pthread_sigqueue_unsupported_ diff --git a/sources/c/program/kevux/tools/tacocat/main/common/define.h b/sources/c/program/kevux/tools/tacocat/main/common/define.h index 13a4e70..98bc7ee 100644 --- a/sources/c/program/kevux/tools/tacocat/main/common/define.h +++ b/sources/c/program/kevux/tools/tacocat/main/common/define.h @@ -174,6 +174,7 @@ extern "C" { * kt_tacocat_main_flag_*_d: * - none: No flags set. * - copyright: Print copyright. + * - encrypt: Enable encryption (such as GPGME). * - headers: Print headers on send or receive. * - help: Print help. * - max_buffer: When set, a maximum buffer on receive is enforced. @@ -198,15 +199,16 @@ extern "C" { #ifndef _di_kt_tacocat_main_flag_d_ #define kt_tacocat_main_flag_none_d 0x0 #define kt_tacocat_main_flag_copyright_d 0x1 - #define kt_tacocat_main_flag_headers_d 0x2 - #define kt_tacocat_main_flag_help_d 0x4 - #define kt_tacocat_main_flag_max_buffer_d 0x8 - #define kt_tacocat_main_flag_receive_d 0x10 - #define kt_tacocat_main_flag_resolve_classic_d 0x20 - #define kt_tacocat_main_flag_resolve_kevux_d 0x40 - #define kt_tacocat_main_flag_send_d 0x80 - #define kt_tacocat_main_flag_version_d 0x100 - #define kt_tacocat_main_flag_version_copyright_help_d 0x105 + #define kt_tacocat_main_flag_encrypt_d 0x2 + #define kt_tacocat_main_flag_headers_d 0x4 + #define kt_tacocat_main_flag_help_d 0x8 + #define kt_tacocat_main_flag_max_buffer_d 0x10 + #define kt_tacocat_main_flag_receive_d 0x20 + #define kt_tacocat_main_flag_resolve_classic_d 0x40 + #define kt_tacocat_main_flag_resolve_kevux_d 0x80 + #define kt_tacocat_main_flag_send_d 0x100 + #define kt_tacocat_main_flag_version_d 0x200 + #define kt_tacocat_main_flag_version_copyright_help_d 0x209 #endif // _di_kt_tacocat_main_flag_d_ /** diff --git a/sources/c/program/kevux/tools/tacocat/main/common/type.c b/sources/c/program/kevux/tools/tacocat/main/common/type.c index 561d083..b77e389 100644 --- a/sources/c/program/kevux/tools/tacocat/main/common/type.c +++ b/sources/c/program/kevux/tools/tacocat/main/common/type.c @@ -37,6 +37,19 @@ extern "C" { } #endif // _di_kt_tacocat_setting_delete_ +#if defined(_en_gpgme_support_) && !defined(_di_kt_tacocat_gpgme_delete_) + void kt_tacocat_gpgme_delete(kt_tacocat_gpgme_t * const gpgme) { + + if (!gpgme) return; + + gpgme_release(gpgme->control); + + // @todo + + gpgme->version = f_string_empty_s.string; + } +#endif // defined(_en_gpgme_support_) && !defined(_di_kt_tacocat_gpgme_delete_) + #ifndef _di_kt_tacocat_socket_sets_delete_callback_ f_status_t kt_tacocat_socket_sets_delete_callback(const f_number_unsigned_t start, const f_number_unsigned_t stop, void * const void_array) { diff --git a/sources/c/program/kevux/tools/tacocat/main/common/type.h b/sources/c/program/kevux/tools/tacocat/main/common/type.h index e7e1ff6..5f9c144 100644 --- a/sources/c/program/kevux/tools/tacocat/main/common/type.h +++ b/sources/c/program/kevux/tools/tacocat/main/common/type.h @@ -26,55 +26,56 @@ extern "C" { /** * A set of all socket related properties. * - * size_block: The size in bytes to used to represent a block when sending or receiving packets. - * size_done: The size in bytes that are done being processed (generally used by send/write). - * size_total: The size in bytes tht represent the entire size to be processed (size_done should eventually equal this). - * - * flag: A set of flags. - * step: The current step the socket set is operating under (this is either a send or receive step define depending on whether or not flag has the send bit set). - * retry: The current number of retries performed. - * part: The current active part number. - * port: The current port number for the socket. - * - * file: The file structure. - * socket: Socket structure. - * status: The status of the socket operations. - * - * range: A generic range, often used for FSS processing. - * objects: An array of FSS Objects. - * objects_header: An array of FSS Objects, for the Header section. - * objects_signature: An array of FSS Objects, for the Signature section. - * contents: An array of FSS Contents. - * contents_header: An array of FSS Contents, for the Header section. - * contents_signature: An array of FSS Contents, for the Signature section. - * objects_delimits: An array of FSS Object delimits. - * objects_delimits_header: An array of FSS Object delimits, for the Header section. - * objects_delimits_signature: An array of FSS Object delimits, for the Signature section. - * contents_delimits: An array of FSS Content delimits. - * contents_delimits_header: An array of FSS Content delimits, for the Header section. - * contents_delimits_signature: An array of FSS Content delimits, for the Signature section. - * parts: An array of numbers where each index represents a part number. - * objects_quoted_header: An array of FSS Objects quoted flags, for the Header section. - * objects_quoted_signature: An array of FSS Objects quoted flags, for the Header section. - * contents_quoted_header: An array of FSS Content quoted flags, for the Header section. - * contents_quoted_signature: An array of FSS Content quoted flags, for the Header section. - * comments: An array of FSS comments. - * state: Basic state information, usually passed to the FSS functions. - * - * as: A custom name to use for the file rather than the actual file name. - * buffer: A buffer for sending or receiving data between clients. - * cache: A cache used for various purposes, but primarily for the building of the send packet. - * client: A single client address for some network connection. - * header: A buffer used for the header part and possibly the reset of a packet, except for the actual payload. - * id: The identifier. - * name: A file name for reading from or writing to. - * network: A network name for the socket. - * time: A representation of time added for informative purposes to the packet (in a human friendly format). - * packet: The simple packet range representing the parts of the packet for use during processing. - * write_state: State data for the packet write operation. - * - * abstruses: The abstruse header map array, used for building the headers when sending a response. - * headers: The map of the headers after being processed for use when buulding the headers when sending a response. + * Properties: + * - size_block: The size in bytes to used to represent a block when sending or receiving packets. + * - size_done: The size in bytes that are done being processed (generally used by send/write). + * - size_total: The size in bytes tht represent the entire size to be processed (size_done should eventually equal this). + * + * - flag: A set of flags. + * - step: The current step the socket set is operating under (this is either a send or receive step define depending on whether or not flag has the send bit set). + * - retry: The current number of retries performed. + * - part: The current active part number. + * - port: The current port number for the socket. + * + * - file: The file structure. + * - socket: Socket structure. + * - status: The status of the socket operations. + * + * - range: A generic range, often used for FSS processing. + * - objects: An array of FSS Objects. + * - objects_header: An array of FSS Objects, for the Header section. + * - objects_signature: An array of FSS Objects, for the Signature section. + * - contents: An array of FSS Contents. + * - contents_header: An array of FSS Contents, for the Header section. + * - contents_signature: An array of FSS Contents, for the Signature section. + * - objects_delimits: An array of FSS Object delimits. + * - objects_delimits_header: An array of FSS Object delimits, for the Header section. + * - objects_delimits_signature: An array of FSS Object delimits, for the Signature section. + * - contents_delimits: An array of FSS Content delimits. + * - contents_delimits_header: An array of FSS Content delimits, for the Header section. + * - contents_delimits_signature: An array of FSS Content delimits, for the Signature section. + * - parts: An array of numbers where each index represents a part number. + * - objects_quoted_header: An array of FSS Objects quoted flags, for the Header section. + * - objects_quoted_signature: An array of FSS Objects quoted flags, for the Header section. + * - contents_quoted_header: An array of FSS Content quoted flags, for the Header section. + * - contents_quoted_signature: An array of FSS Content quoted flags, for the Header section. + * - comments: An array of FSS comments. + * - state: Basic state information, usually passed to the FSS functions. + * + * - as: A custom name to use for the file rather than the actual file name. + * - buffer: A buffer for sending or receiving data between clients. + * - cache: A cache used for various purposes, but primarily for the building of the send packet. + * - client: A single client address for some network connection. + * - header: A buffer used for the header part and possibly the reset of a packet, except for the actual payload. + * - id: The identifier. + * - name: A file name for reading from or writing to. + * - network: A network name for the socket. + * - time: A representation of time added for informative purposes to the packet (in a human friendly format). + * - packet: The simple packet range representing the parts of the packet for use during processing. + * - write_state: State data for the packet write operation. + * + * - abstruses: The abstruse header map array, used for building the headers when sending a response. + * - headers: The map of the headers after being processed for use when buulding the headers when sending a response. */ #ifndef _di_kt_tacocat_socket_set_t_ typedef struct { @@ -274,9 +275,10 @@ extern "C" { /** * An array of socket sets. * - * array: The array of socket sets. - * used: Total number of allocated spaces used. - * size: Total amount of allocated space. + * Properties: + * - array: The array of socket sets. + * - used: Total number of allocated spaces used. + * - size: Total amount of allocated space. */ #ifndef _di_kt_tacocat_socket_sets_t_ typedef struct { @@ -323,23 +325,24 @@ extern "C" { * This is passed to the program-specific main entry point to designate program settings. * These program settings are often processed from the program arguments (often called the command line arguments). * - * flag: Flags passed to the main function. - * interval: The poll interval to use. - * interval_fast: A poll interval to use when needing the interval to be short. - * max_buffer: The maximum buffer size to use on receive. - * active_receive: The number of active receive processes, after initial connection is established. - * active_send: The number of active send processes, after initial connection is established. + * Properties: + * - flag: Flags passed to the main function. + * - interval: The poll interval to use. + * - interval_fast: A poll interval to use when needing the interval to be short. + * - max_buffer: The maximum buffer size to use on receive. + * - active_receive: The number of active receive processes, after initial connection is established. + * - active_send: The number of active send processes, after initial connection is established. * - * status_receive: A status used exclusively by the receive thread. - * status_send: A status used exclusively by the send thread. + * - status_receive: A status used exclusively by the receive thread. + * - status_send: A status used exclusively by the send thread. * - * state: The state data used when processing data. + * - state: The state data used when processing data. * - * receive_polls: An array of sockets to poll for receiving data, specifically for passing to f_file_poll(). - * send_polls: An array of sockets to poll for sending data, specifically for passing to f_file_poll(). + * - receive_polls: An array of sockets to poll for receiving data, specifically for passing to f_file_poll(). + * - send_polls: An array of sockets to poll for sending data, specifically for passing to f_file_poll(). * - * receive: The socket set for receiving data receive clients. - * send: The socket set for sending data send clients. + * - receive: The socket set for receiving data receive clients. + * - send: The socket set for sending data send clients. */ #ifndef _di_kt_tacocat_setting_t_ typedef struct { @@ -382,9 +385,10 @@ extern "C" { /** * The TacocaT caches. * - * peek: A static cache intended to be used for performing a peek on a given network stream. + * Properties: + * - peek: A static cache intended to be used for performing a peek on a given network stream. * - * buffer: A string buffer used for caching purposes. + * - buffer: A string buffer used for caching purposes. */ #ifndef _di_kt_tacocat_cache_t_ typedef struct { @@ -402,7 +406,8 @@ extern "C" { /** * The TacocaT callbacks. * - * setting_load_send_receive: Process loading the settings regarding send and receive, handling DNS resolution and file opening as needed. + * Properties: + * - setting_load_send_receive: Process loading the settings regarding send and receive, handling DNS resolution and file opening as needed. */ #ifndef _di_kt_tacocat_call_t_ typedef struct { @@ -416,6 +421,10 @@ extern "C" { /** * The main thread settings. + * + * Properties: + * - id_receive: The receive identifier. + * - id_send: The send identifier. */ #ifndef _di_kt_tacocat_thread_t_ typedef struct { @@ -430,14 +439,47 @@ extern "C" { #endif // _di_kt_tacocat_thread_t_ /** + * The GPGME data. + * + * Properties: + * - control: The GPGME control data. + * - data: The GPGME regular data. + * - engine: The GPGME engine inforrmation data. + * - error: The GPGME error data. + * + * - version: The GPGME reported version. + */ +#if defined(_en_gpgme_support_) && !defined(_di_kt_tacocat_gpgme_t_) + typedef struct { + gpgme_ctx_t control; + gpgme_data_t data; + gpgme_engine_info_t engine; + gpgme_error_t error; + + f_string_constant_t version; + } kt_tacocat_gpgme_t; + + #define kt_tacocat_gpgme_t_initialize { \ + .control = 0, \ + .data = 0, \ + .engine = 0, \ + .error = 0, \ + .version = f_string_empty_s.string, \ + } +#endif // defined(_en_gpgme_support_) && !defined(_di_kt_tacocat_gpgme_t_) + +/** * The main program data as a single structure. * - * program: The main program data. + * Properties: + * - program: The main program data. + * + * - cache: The program cache. + * - call: The program call backs. + * - setting: The settings data. + * - thread: The program thread data. * - * cache: The program cache. - * call: The program call backs. - * setting: The settings data. - * thread: The program thread data. + * - gpgme: The GPGME data, if supported. */ #ifndef _di_kt_tacocat_main_t_ struct kt_tacocat_main_t_ { @@ -447,15 +489,30 @@ extern "C" { kt_tacocat_call_t call; kt_tacocat_setting_t setting; kt_tacocat_thread_t thread; + + #ifdef _en_gpgme_support_ + kt_tacocat_gpgme_t gpgme; + #endif // _en_gpgme_support_ }; - #define kt_tacocat_main_t_initialize { \ - .program = fll_program_data_t_initialize, \ - .cache = kt_tacocat_cache_t_initialize, \ - .call = kt_tacocat_call_t_initialize, \ - .setting = kt_tacocat_setting_t_initialize, \ - .thread = kt_tacocat_thread_t_initialize, \ - } + #ifdef _en_gpgme_support_ + #define kt_tacocat_main_t_initialize { \ + .program = fll_program_data_t_initialize, \ + .cache = kt_tacocat_cache_t_initialize, \ + .call = kt_tacocat_call_t_initialize, \ + .setting = kt_tacocat_setting_t_initialize, \ + .thread = kt_tacocat_thread_t_initialize, \ + .gpgme = kt_tacocat_gpgme_t_initialize, \ + } + #else + #define kt_tacocat_main_t_initialize { \ + .program = fll_program_data_t_initialize, \ + .cache = kt_tacocat_cache_t_initialize, \ + .call = kt_tacocat_call_t_initialize, \ + .setting = kt_tacocat_setting_t_initialize, \ + .thread = kt_tacocat_thread_t_initialize, \ + } + #endif // _en_gpgme_support_ #endif // _di_kt_tacocat_main_t_ /** @@ -499,6 +556,18 @@ extern "C" { #endif // _di_kt_tacocat_setting_delete_ /** + * Delete the gpgme data. + * + * @param gpgme + * The gpgme data. + * + * Must not be NULL. + */ +#if defined(_en_gpgme_support_) && !defined(_di_kt_tacocat_gpgme_delete_) + extern void kt_tacocat_gpgme_delete(kt_tacocat_gpgme_t * const gpgme); +#endif // defined(_en_gpgme_support_) && !defined(_di_kt_tacocat_gpgme_delete_) + +/** * A call back intended to be passed to f_memory_arrays_resize() for an kt_tacocat_socket_sets_t structure. * * This is only called when shrinking the array and generally should perform deallocations. diff --git a/sources/c/program/kevux/tools/tacocat/main/gpgme.c b/sources/c/program/kevux/tools/tacocat/main/gpgme.c new file mode 100644 index 0000000..d84ada4 --- /dev/null +++ b/sources/c/program/kevux/tools/tacocat/main/gpgme.c @@ -0,0 +1,42 @@ +#include "tacocat.h" + +#ifdef __cplusplus +extern "C" { +#endif + +#if defined(_en_gpgme_support_) && !defined(_di_kt_tacocat_gpgme_setup_) + void kt_tacocat_gpgme_setup(kt_tacocat_main_t * const main) { + + if (!main) return; + + kt_tacocat_gpgme_t * const gpgme = &main->gpgme; + + gpgme->version = gpgme_check_version(0); + + gpgme->error = gpgme_new(&gpgme->control); + + if (gpgme->error) { + main->setting.state.status = F_status_set_error(F_failure); + + kt_tacocat_print_gpgme_error(&main->program.error, F_status_debug_source_d); + + return; + } + + gpgme->error = gpgme_engine_check_version(GPGME_PROTOCOL_OPENPGP); + + if (gpgme->error) { + main->setting.state.status = F_status_set_error(F_failure); + + kt_tacocat_print_gpgme_error(&main->program.error, F_status_debug_source_d); + + return; + } + + main->setting.state.status = F_okay; + } +#endif // defined(_en_gpgme_support_) && !defined(_di_kt_tacocat_gpgme_setup_) + +#ifdef __cplusplus +} // extern "C" +#endif diff --git a/sources/c/program/kevux/tools/tacocat/main/gpgme.h b/sources/c/program/kevux/tools/tacocat/main/gpgme.h new file mode 100644 index 0000000..0a42f3b --- /dev/null +++ b/sources/c/program/kevux/tools/tacocat/main/gpgme.h @@ -0,0 +1,46 @@ +/** + * Kevux Tools - TacocaT + * + * Project: Kevux Tools + * API Version: 0.7 + * Licenses: lgpl-2.1-or-later + */ +#ifndef _kt_tacocat_main_gpgme_h +#define _kt_tacocat_main_gpgme_h + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * Perform GPGME setup. + * + * For available GPGME protocols, see: https://www.gnupg.org/documentation/manuals/gpgme/Protocols-and-Engines.html . + * + * For GPGME signal handling, see: https://www.gnupg.org/documentation/manuals/gpgme/Signal-Handling.html . + * > If you do install a signal handler for SIGPIPE, you must be prepared to handle any SIGPIPE events that occur due to GPGME writing to a defunct pipe. + * > Furthermore, if your application is multi-threaded, and you install a signal action for SIGPIPE, you must make sure you do this either before gpgme_check_version is called or afterwards. + * + * @param main + * The main program and settings data. + * + * This does not alter main.setting.state.status, except on interrupt signal. + * + * Must not be NULL. + * + * This alters set.status: + * F_okay on success. + * + * F_failure (with error bit) on gpgme_check_version() error. + * + * @see gpgme_check_version() + */ +#if defined(_en_gpgme_support_) && !defined(_di_kt_tacocat_gpgme_setup_) + extern void kt_tacocat_gpgme_setup(kt_tacocat_main_t * const main); +#endif // defined(_en_gpgme_support_) && !defined(_di_kt_tacocat_gpgme_setup_) + +#ifdef __cplusplus +} // extern "C" +#endif + +#endif // _kt_tacocat_main_gpgme_h diff --git a/sources/c/program/kevux/tools/tacocat/main/print/error.c b/sources/c/program/kevux/tools/tacocat/main/print/error.c index 8b6ddc6..4a1c547 100644 --- a/sources/c/program/kevux/tools/tacocat/main/print/error.c +++ b/sources/c/program/kevux/tools/tacocat/main/print/error.c @@ -50,9 +50,9 @@ extern "C" { fl_print_format("%[%QNetwork error on%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, on, print->set->notable); - fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, network, print->set->notable); - fl_print_format("%[' with file '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%[' with file '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, name, print->set->notable); fl_print_format(f_string_format_sentence_end_quote_s.string, print->to, print->set->error, print->set->error, f_string_eol_s); @@ -74,9 +74,9 @@ extern "C" { fl_print_format("%[%QFile '%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, on, print->set->notable); - fl_print_format(" %[' for '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[' for '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, on, print->set->notable); - fl_print_format(" %[ for '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[ for '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, network, print->set->notable); fl_print_format("%[', the maximum size is%] ", print->to, print->set->error, print->set->error); fl_print_format("%[%ul%]", print->to, print->set->notable, size_expect, print->set->notable); @@ -100,7 +100,7 @@ extern "C" { fl_print_format("%[%QNetwork on%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, on, print->set->notable); - fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, network, print->set->notable); fl_print_format("%[' is busy.%]%r", print->to, print->set->error, print->set->error, f_string_eol_s); @@ -120,9 +120,9 @@ extern "C" { fl_print_format("%[%QNetwork on%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, on, print->set->notable); - fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, network, print->set->notable); - fl_print_format("%[' failed to receive data or write to file '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%[' failed to receive data or write to file '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, name, print->set->notable); fl_print_format(f_string_format_sentence_end_quote_s.string, print->to, print->set->error, print->set->error, f_string_eol_s); @@ -144,9 +144,9 @@ extern "C" { fl_print_format("%[%QNetwork on%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, on, print->set->notable); - fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, network, print->set->notable); - fl_print_format("%[' failed to send data or read from file '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%[' failed to send data or read from file '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, name, print->set->notable); fl_print_format(f_string_format_sentence_end_quote_s.string, print->to, print->set->error, print->set->error, f_string_eol_s); @@ -168,15 +168,15 @@ extern "C" { fl_print_format("%[%QNetwork packet header on%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, on, print->set->notable); - fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, network, print->set->notable); - fl_print_format("%[' with file '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%[' with file '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, name, print->set->notable); - fl_print_format("%[' is invalid for Object '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%[' is invalid for Object '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_range_single_s.string, print->to, print->set->notable, buffer, object, print->set->notable); - fl_print_format("%[' and Content '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%[' and Content '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_range_single_s.string, print->to, print->set->notable, buffer, content, print->set->notable); - fl_print_format("%[' with a status code of %]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%[' with a status code of %]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_ul_single_s.string, print->to, print->set->notable, F_status_set_fine(status), print->set->notable); fl_print_format(f_string_format_sentence_end_s.string, print->to, print->set->error, print->set->error, f_string_eol_s); @@ -196,11 +196,11 @@ extern "C" { fl_print_format("%[%QNetwork packet is invalid for%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, on, print->set->notable); - fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, network, print->set->notable); if (name.used) { - fl_print_format("%[' with file '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%[' with file '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, name, print->set->notable); } @@ -222,9 +222,9 @@ extern "C" { fl_print_format("%[%QMax retry on failure reached while trying to%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, kt_tacocat_receive_s, print->set->notable); - fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, set->network, print->set->notable); - fl_print_format("%[' with file '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%[' with file '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, set->name, print->set->notable); fl_print_format("%['", print->to, print->set->error); @@ -250,9 +250,9 @@ extern "C" { fl_print_format("%[%QMax retry on failure reached while trying to%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, kt_tacocat_send_s, print->set->notable); - fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, set->network, print->set->notable); - fl_print_format("%[' with file '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%[' with file '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, set->name, print->set->notable); fl_print_format(f_string_format_sentence_end_quote_s.string, print->to, print->set->error, print->set->error, f_string_eol_s); @@ -272,11 +272,11 @@ extern "C" { fl_print_format("%[%QNetwork on%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, on, print->set->notable); - fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, network, print->set->notable); fl_print_format("%[', the received packet is too large (expecting%] ", print->to, print->set->error, print->set->error); fl_print_format("%[%ul%]", print->to, print->set->notable, size_expect, print->set->notable); - fl_print_format(" %[bytes but instead got%] ", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[bytes but instead got%] ", print->to, print->set->error, print->set->error); fl_print_format("%[%ul%]", print->to, print->set->notable, size_got, print->set->notable); fl_print_format("%[ bytes).%]%r", print->to, print->set->error, print->set->error, f_string_eol_s); @@ -296,11 +296,11 @@ extern "C" { fl_print_format("%[%QNetwork on%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, on, print->set->notable); - fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[for '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, network, print->set->notable); fl_print_format("%[', the received packet is too small (expecting%] ", print->to, print->set->error, print->set->error); fl_print_format("%[%ul%]", print->to, print->set->notable, size_expect, print->set->notable); - fl_print_format(" %[bytes but instead got%] ", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[bytes but instead got%] ", print->to, print->set->error, print->set->error); fl_print_format("%[%ul%]", print->to, print->set->notable, size_got, print->set->notable); fl_print_format("%[ bytes).%]%r", print->to, print->set->error, print->set->error, f_string_eol_s); @@ -320,11 +320,11 @@ extern "C" { fl_print_format("%[%QThe parameter%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_QQ_single_s.string, print->to, print->set->notable, f_console_symbol_long_normal_s, kt_tacocat_long_resolve_s, print->set->notable); - fl_print_format(" %[may only be either '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[may only be either '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, kt_tacocat_classic_s, print->set->notable); - fl_print_format("%' or '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format("%' or '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, kt_tacocat_kevux_s, print->set->notable); - fl_print_format(" %[' but '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[' but '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, unknown, print->set->notable); fl_print_format("%[' is given.%]%r", print->to, print->set->error, print->set->error, f_string_eol_s); @@ -348,7 +348,7 @@ extern "C" { fl_print_format("%[%QUnknown or invalid port number%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format(f_string_format_Q_range_single_s.string, print->to, print->set->notable, address, range, print->set->notable); - fl_print_format(" %[from the address '%]", print->to, print->set->error, print->set->error, f_string_eol_s); + fl_print_format(" %[from the address '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, address, print->set->notable); fl_print_format(f_string_format_sentence_end_quote_s.string, print->to, print->set->error, print->set->error, f_string_eol_s); @@ -368,7 +368,7 @@ extern "C" { fl_print_format("%[%QUnsupported protocol%] ", print->to, print->set->error, print->prefix, print->set->error); fl_print_format("%[%ul%]", 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(" %[while processing '%]", print->to, print->set->error, print->set->error); fl_print_format(f_string_format_Q_single_s.string, print->to, print->set->notable, name, print->set->notable); fl_print_format(f_string_format_sentence_end_quote_s.string, print->to, print->set->error, print->set->error, f_string_eol_s); diff --git a/sources/c/program/kevux/tools/tacocat/main/print/gpgme.c b/sources/c/program/kevux/tools/tacocat/main/print/gpgme.c new file mode 100644 index 0000000..68b0a7c --- /dev/null +++ b/sources/c/program/kevux/tools/tacocat/main/print/gpgme.c @@ -0,0 +1,40 @@ +#include "../tacocat.h" + +#ifdef __cplusplus +extern "C" { +#endif + +#ifndef _di_kt_tacocat_print_gpgme_error_ + f_status_t kt_tacocat_print_gpgme_error(fl_print_t * const print, const f_string_t debug) { + + if (!print || !print->custom) return F_status_set_error(F_output_not); + if (print->verbosity < f_console_verbosity_error_e) return F_output_not; + + kt_tacocat_main_t * const main = (kt_tacocat_main_t *) print->custom; + + f_file_stream_lock(print->to); + + fl_print_format("%[%QGPGME error:%] ", print->to, print->set->error, print->prefix, print->set->error); + fl_print_format(f_string_format_S_single_s.string, print->to, print->set->notable, gpgme_strerror(main->gpgme.error), print->set->notable); + fl_print_format(" %[(%]", print->to, print->set->error, print->set->error); + fl_print_format(f_string_format_S_single_s.string, print->to, print->set->notable, gpgme_strsource(main->gpgme.error), print->set->notable); + fl_print_format("%[)", print->to, print->set->error); + + if (debug && *debug) { + fl_print_format(macro_fll_error_s(019_debug_open), print->to, print->context); + fl_print_format(f_string_format_S_single_s.string, print->to, print->notable, debug, print->notable); + fl_print_format(macro_fll_error_s(020_debug_close), print->to, print->context); + } + + fl_print_format(".%]%r", print->to, print->context, f_string_eol_s); + + + f_file_stream_unlock(print->to); + + return F_okay; + } +#endif // _di_kt_tacocat_print_gpgme_error_ + +#ifdef __cplusplus +} // extern "C" +#endif diff --git a/sources/c/program/kevux/tools/tacocat/main/print/gpgme.h b/sources/c/program/kevux/tools/tacocat/main/print/gpgme.h new file mode 100644 index 0000000..e83e160 --- /dev/null +++ b/sources/c/program/kevux/tools/tacocat/main/print/gpgme.h @@ -0,0 +1,51 @@ +/** + * Kevux Tools - TacocaT + * + * Project: Kevux Tools + * API Version: 0.7 + * Licenses: lgpl-2.1-or-later + * + * Provides the print gpgme functionality. + * + * This is auto-included and should not need to be explicitly included. + */ +#ifndef _kt_tacocat_print_gpgme_h +#define _kt_tacocat_print_gpgme_h + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * Print GPGME related error message regarding some failure. + * + * @param print + * The output structure to print to. + * + * This requires print.custom to be fake_main_t. + * + * Must not be NULL. + * + * This does not alter print.custom.setting.state.status. + * @param debug + * (optional) The debug details, such as file, line number, and function. + * + * Set to NULL to disable. + * + * @return + * F_okay 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_print() + */ +#ifndef _di_kt_tacocat_print_gpgme_error_ + extern f_status_t kt_tacocat_print_gpgme_error(fl_print_t * const print, const f_string_t debug); +#endif // _di_kt_tacocat_print_gpgme_error_ + +#ifdef __cplusplus +} // extern "C" +#endif + +#endif // _kt_tacocat_print_gpgme_h diff --git a/sources/c/program/kevux/tools/tacocat/main/process.c b/sources/c/program/kevux/tools/tacocat/main/process.c index 26939e1..5ea2fb8 100644 --- a/sources/c/program/kevux/tools/tacocat/main/process.c +++ b/sources/c/program/kevux/tools/tacocat/main/process.c @@ -11,6 +11,13 @@ extern "C" { if (F_status_is_error(kt_tacocat_process_socket_set_error_has(main, kt_tacocat_long_receive_s, main->setting.receive, &main->setting.status_receive))) return; if (F_status_is_error(kt_tacocat_process_socket_set_error_has(main, kt_tacocat_long_send_s, main->setting.send, &main->setting.status_send))) return; + #ifdef _en_gpgme_support_ + if (main->setting.flag & kt_tacocat_main_flag_encrypt_d) { + kt_tacocat_gpgme_setup(main); + if (F_status_is_error(main->setting.state.status)) return; + } + #endif // _en_gpgme_support_ + #ifdef _di_thread_support_ // @todo implement fork and wait for both receive and send. #else @@ -58,6 +65,10 @@ extern "C" { if (F_status_is_error_not(main->setting.state.status)) { main->setting.state.status = F_okay; } + + #ifdef _en_gpgme_support_ + kt_tacocat_gpgme_delete(&main->gpgme); + #endif // _en_gpgme_support_ } #endif // _di_kt_tacocat_process_main_ diff --git a/sources/c/program/kevux/tools/tacocat/main/tacocat.h b/sources/c/program/kevux/tools/tacocat/main/tacocat.h index b334398..fcc12c9 100644 --- a/sources/c/program/kevux/tools/tacocat/main/tacocat.h +++ b/sources/c/program/kevux/tools/tacocat/main/tacocat.h @@ -17,6 +17,11 @@ #include #include +// Other includes. +#ifdef _en_gpgme_support_ + #include +#endif // _en_gpgme_support_ + // FLL-0 includes. #include #include @@ -89,6 +94,11 @@ #include #include +#ifdef _en_gpgme_support_ + #include + #include +#endif // _en_gpgme_support_ + #ifdef __cplusplus extern "C" { #endif diff --git a/sources/c/program/kevux/tools/tacocat/tacocat/main.c b/sources/c/program/kevux/tools/tacocat/tacocat/main.c index 43aee80..26479c6 100644 --- a/sources/c/program/kevux/tools/tacocat/tacocat/main.c +++ b/sources/c/program/kevux/tools/tacocat/tacocat/main.c @@ -30,6 +30,12 @@ int main(const int argc, const f_string_t *argv, const f_string_t *envp) { data.call.setting_load_send_receive = kt_tacocat_setting_load_send_receive; + #ifdef _en_gpgme_support_ + data.setting.flag |= kt_tacocat_main_flag_encrypt_d; + #else + data.setting.flag &= ~kt_tacocat_main_flag_encrypt_d; + #endif // _en_gpgme_support_ + if (f_pipe_input_exists()) { data.program.pipe = fll_program_data_pipe_input_e; }