From af3158a1b457ac9632a952f2558ace02214d353e Mon Sep 17 00:00:00 2001 From: Federico Di Pierro Date: Tue, 22 Oct 2024 09:02:18 +0200 Subject: [PATCH 1/3] new(userspace,cmake): honor new plugins exposed suggested output formats. Signed-off-by: Federico Di Pierro --- falco.yaml | 6 ++++ .../falco/app/actions/init_falco_engine.cpp | 32 +++++++++++++++++++ userspace/falco/configuration.cpp | 2 ++ userspace/falco/configuration.h | 1 + 4 files changed, 41 insertions(+) diff --git a/falco.yaml b/falco.yaml index 80d7926b22c..0704a95d78c 100644 --- a/falco.yaml +++ b/falco.yaml @@ -571,6 +571,12 @@ buffered_outputs: false # deploying it in production. rule_matching: first +# [Incubating] `suggested_formats` +# +# When enabled, Falco will honor requests by extractor plugins +# that suggest certain fields to be part of outputs. +suggested_formats: true + # [Stable] `outputs_queue` # # Falco utilizes tbb::concurrent_bounded_queue for handling outputs, and this parameter diff --git a/userspace/falco/app/actions/init_falco_engine.cpp b/userspace/falco/app/actions/init_falco_engine.cpp index b44435ef4a4..ad2a42e972a 100644 --- a/userspace/falco/app/actions/init_falco_engine.cpp +++ b/userspace/falco/app/actions/init_falco_engine.cpp @@ -18,10 +18,23 @@ limitations under the License. #include "actions.h" #include #include +#include using namespace falco::app; using namespace falco::app::actions; +static inline std::string format_suggested_field(const filter_check_info* info) { + std::ostringstream out; + + // Replace "foo.bar" with "foo_bar" + auto name = info->m_name; + std::replace(name.begin(), name.end(), '.', '_'); + + // foo_bar=%foo.bar + out << name << "=%" << info->m_name; + return out.str(); +} + void configure_output_format(falco::app::state& s) { for(auto& eo : s.config->m_append_output) { if(eo.m_format != "") { @@ -45,6 +58,25 @@ void configure_output_format(falco::app::state& s) { } } + // Add suggested filtercheck formats to each source output + if(s.config->m_suggested_formats) { + for(auto& src : s.loaded_sources) { + auto src_info = s.source_infos.at(src); + auto& filterchecks = *src_info->filterchecks; + std::vector fields; + filterchecks.get_all_fields(fields); + for(const auto& fld : fields) { + if(fld->m_flags & EPF_FORMAT_SUGGESTED) { + s.engine->add_extra_output_format(format_suggested_field(fld), + src, + {}, + "", + false); + } + } + } + } + // See https://falco.org/docs/rules/style-guide/ const std::string container_info = "container_id=%container.id container_image=%container.image.repository " diff --git a/userspace/falco/configuration.cpp b/userspace/falco/configuration.cpp index b2359ed1da4..ac0d69e839c 100644 --- a/userspace/falco/configuration.cpp +++ b/userspace/falco/configuration.cpp @@ -72,6 +72,7 @@ falco_configuration::falco_configuration(): m_rule_matching(falco_common::rule_matching::FIRST), m_watch_config_files(true), m_buffered_outputs(false), + m_suggested_formats(true), m_outputs_queue_capacity(DEFAULT_OUTPUTS_QUEUE_CAPACITY_UNBOUNDED_MAX_LONG_VALUE), m_time_format_iso_8601(false), m_buffer_format_base64(false), @@ -483,6 +484,7 @@ void falco_configuration::load_yaml(const std::string &config_name) { } m_buffered_outputs = m_config.get_scalar("buffered_outputs", false); + m_suggested_formats = m_config.get_scalar("suggested_formats", true); m_outputs_queue_capacity = m_config.get_scalar("outputs_queue.capacity", DEFAULT_OUTPUTS_QUEUE_CAPACITY_UNBOUNDED_MAX_LONG_VALUE); diff --git a/userspace/falco/configuration.h b/userspace/falco/configuration.h index ba6eb201e01..96579db7037 100644 --- a/userspace/falco/configuration.h +++ b/userspace/falco/configuration.h @@ -155,6 +155,7 @@ class falco_configuration { bool m_time_format_iso_8601; bool m_buffer_format_base64; uint32_t m_output_timeout; + bool m_suggested_formats; bool m_grpc_enabled; uint32_t m_grpc_threadiness; From 71543655541370e35b1db64191265a68c9d2ad17 Mon Sep 17 00:00:00 2001 From: Federico Di Pierro Date: Tue, 22 Oct 2024 09:12:01 +0200 Subject: [PATCH 2/3] chore(userspace): update config schema. Signed-off-by: Federico Di Pierro --- userspace/falco/config_json_schema.h | 3 +++ 1 file changed, 3 insertions(+) diff --git a/userspace/falco/config_json_schema.h b/userspace/falco/config_json_schema.h index 92ae04fe109..1fbb2db04ba 100644 --- a/userspace/falco/config_json_schema.h +++ b/userspace/falco/config_json_schema.h @@ -101,6 +101,9 @@ const char config_schema_string[] = LONG_STRING_CONST( "buffered_outputs": { "type": "boolean" }, + "suggested_formats": { + "type": "boolean" + }, "rule_matching": { "type": "string" }, From 95cab3439d70a505e3d7e70ef8b8a0e44e44fa39 Mon Sep 17 00:00:00 2001 From: Federico Di Pierro Date: Wed, 23 Oct 2024 15:32:20 +0200 Subject: [PATCH 3/3] chore(userspace/falco): add new `suggested_output` option to `append_output` configuration. Signed-off-by: Federico Di Pierro --- falco.yaml | 14 ++--- .../falco/app/actions/init_falco_engine.cpp | 51 ++++++++++++------- userspace/falco/config_json_schema.h | 6 +-- userspace/falco/configuration.cpp | 2 - userspace/falco/configuration.h | 6 ++- 5 files changed, 48 insertions(+), 31 deletions(-) diff --git a/falco.yaml b/falco.yaml index 0704a95d78c..870cafac5d9 100644 --- a/falco.yaml +++ b/falco.yaml @@ -571,12 +571,6 @@ buffered_outputs: false # deploying it in production. rule_matching: first -# [Incubating] `suggested_formats` -# -# When enabled, Falco will honor requests by extractor plugins -# that suggest certain fields to be part of outputs. -suggested_formats: true - # [Stable] `outputs_queue` # # Falco utilizes tbb::concurrent_bounded_queue for handling outputs, and this parameter @@ -624,6 +618,7 @@ outputs_queue: # affect the regular Falco message in any way. These can be specified as a # custom name with a custom format or as any supported field # (see: https://falco.org/docs/reference/rules/supported-fields/) +# `suggested_output`: enable the use of extractor plugins suggested fields for the matching source output. # # Example: # @@ -640,6 +635,13 @@ outputs_queue: # property you will find three new ones: "evt.cpu", "home_directory" which will contain the value of the # environment variable $HOME, and "evt.hostname" which will contain the hostname. +# By default, we enable suggested_output for any source. +# This means that any extractor plugin that indicates some of its fields +# as suggested output formats, will see these fields in the output +# in the form "foo_bar=$foo.bar" +append_output: + - suggested_output: true + ########################## # Falco outputs channels # diff --git a/userspace/falco/app/actions/init_falco_engine.cpp b/userspace/falco/app/actions/init_falco_engine.cpp index ad2a42e972a..d750e82a2ec 100644 --- a/userspace/falco/app/actions/init_falco_engine.cpp +++ b/userspace/falco/app/actions/init_falco_engine.cpp @@ -35,6 +35,27 @@ static inline std::string format_suggested_field(const filter_check_info* info) return out.str(); } +static void add_suggested_output(const falco::app::state& s, + const std::string& src, + const falco_configuration::append_output_config& eo) { + auto src_info = s.source_infos.at(src); + if(!src_info) { + return; + } + auto& filterchecks = *src_info->filterchecks; + std::vector fields; + filterchecks.get_all_fields(fields); + for(const auto& fld : fields) { + if(fld->m_fields->is_format_suggested()) { + s.engine->add_extra_output_format(format_suggested_field(fld), + src, + eo.m_tags, + eo.m_rule, + false); + } + } +} + void configure_output_format(falco::app::state& s) { for(auto& eo : s.config->m_append_output) { if(eo.m_format != "") { @@ -45,6 +66,17 @@ void configure_output_format(falco::app::state& s) { false); } + // Add suggested filtercheck formats to each source output + if(eo.m_suggested_output) { + if(eo.m_source.empty()) { + for(auto& src : s.loaded_sources) { + add_suggested_output(s, src, eo); + } + } else { + add_suggested_output(s, eo.m_source, eo); + } + } + for(auto const& ff : eo.m_formatted_fields) { s.engine->add_extra_output_formatted_field(ff.first, ff.second, @@ -58,25 +90,6 @@ void configure_output_format(falco::app::state& s) { } } - // Add suggested filtercheck formats to each source output - if(s.config->m_suggested_formats) { - for(auto& src : s.loaded_sources) { - auto src_info = s.source_infos.at(src); - auto& filterchecks = *src_info->filterchecks; - std::vector fields; - filterchecks.get_all_fields(fields); - for(const auto& fld : fields) { - if(fld->m_flags & EPF_FORMAT_SUGGESTED) { - s.engine->add_extra_output_format(format_suggested_field(fld), - src, - {}, - "", - false); - } - } - } - } - // See https://falco.org/docs/rules/style-guide/ const std::string container_info = "container_id=%container.id container_image=%container.image.repository " diff --git a/userspace/falco/config_json_schema.h b/userspace/falco/config_json_schema.h index 1fbb2db04ba..dcfb08033ef 100644 --- a/userspace/falco/config_json_schema.h +++ b/userspace/falco/config_json_schema.h @@ -101,9 +101,6 @@ const char config_schema_string[] = LONG_STRING_CONST( "buffered_outputs": { "type": "boolean" }, - "suggested_formats": { - "type": "boolean" - }, "rule_matching": { "type": "string" }, @@ -276,6 +273,9 @@ const char config_schema_string[] = LONG_STRING_CONST( } ] } + }, + "suggested_output": { + "type": "boolean" } } }, diff --git a/userspace/falco/configuration.cpp b/userspace/falco/configuration.cpp index ac0d69e839c..b2359ed1da4 100644 --- a/userspace/falco/configuration.cpp +++ b/userspace/falco/configuration.cpp @@ -72,7 +72,6 @@ falco_configuration::falco_configuration(): m_rule_matching(falco_common::rule_matching::FIRST), m_watch_config_files(true), m_buffered_outputs(false), - m_suggested_formats(true), m_outputs_queue_capacity(DEFAULT_OUTPUTS_QUEUE_CAPACITY_UNBOUNDED_MAX_LONG_VALUE), m_time_format_iso_8601(false), m_buffer_format_base64(false), @@ -484,7 +483,6 @@ void falco_configuration::load_yaml(const std::string &config_name) { } m_buffered_outputs = m_config.get_scalar("buffered_outputs", false); - m_suggested_formats = m_config.get_scalar("suggested_formats", true); m_outputs_queue_capacity = m_config.get_scalar("outputs_queue.capacity", DEFAULT_OUTPUTS_QUEUE_CAPACITY_UNBOUNDED_MAX_LONG_VALUE); diff --git a/userspace/falco/configuration.h b/userspace/falco/configuration.h index 96579db7037..908a542cfc1 100644 --- a/userspace/falco/configuration.h +++ b/userspace/falco/configuration.h @@ -100,6 +100,7 @@ class falco_configuration { std::set m_tags; std::string m_rule; std::string m_format; + bool m_suggested_output = false; std::unordered_map m_formatted_fields; std::set m_raw_fields; }; @@ -155,7 +156,6 @@ class falco_configuration { bool m_time_format_iso_8601; bool m_buffer_format_base64; uint32_t m_output_timeout; - bool m_suggested_formats; bool m_grpc_enabled; uint32_t m_grpc_threadiness; @@ -291,6 +291,10 @@ struct convert { } } + if(node["suggested_output"]) { + rhs.m_suggested_output = node["suggested_output"].as(); + } + return true; } };