Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Applayer plugin 5053 v3.9 #12066

Closed
wants to merge 14 commits into from

Conversation

catenacyber
Copy link
Contributor

Link to ticket: https://redmine.openinfosecfoundation.org/issues/
https://redmine.openinfosecfoundation.org/issues/5053

Describe changes:

  • get ready to use dynamic number of app-layer protos (also work with static constant) in some places
  • preventive fix of macro with parenthesis cc @jufajardini

#12060 with profiling fix and clean history

Example plugin at https://github.com/catenacyber/suricata-zabbix

instead of a global variable.

For easier initialization with dynamic number of protocols
for expectation_proto

Ticket: 5053
so that we can use safely EXCEPTION_POLICY_MAX*sizeof(x)
Ticket: 5053

delay after initialization so that StringToAppProto works
As too many cases are found when splitting tcp payload
As it is also used for HTTP/1
Ticket: 5053

The names are nwo dynamic
Copy link

codecov bot commented Oct 30, 2024

Codecov Report

Attention: Patch coverage is 74.43182% with 90 lines in your changes missing coverage. Please review.

Project coverage is 83.29%. Comparing base (3a7eef8) to head (b34acb1).
Report is 33 commits behind head on master.

Additional details and impacted files
@@            Coverage Diff             @@
##           master   #12066      +/-   ##
==========================================
- Coverage   83.42%   83.29%   -0.14%     
==========================================
  Files         910      910              
  Lines      257642   257757     +115     
==========================================
- Hits       214949   214698     -251     
- Misses      42693    43059     +366     
Flag Coverage Δ
fuzzcorpus 61.06% <68.01%> (-0.59%) ⬇️
livemode 19.42% <57.92%> (+0.01%) ⬆️
pcap 44.48% <70.02%> (+<0.01%) ⬆️
suricata-verify 62.76% <74.06%> (+<0.01%) ⬆️
unittests 59.35% <57.67%> (-0.02%) ⬇️

Flags with carried forward coverage won't be shown. Click here to find out more.

@suricata-qa
Copy link

Information: QA ran without warnings.

Pipeline 23220

Copy link
Member

@victorjulien victorjulien left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code looks mostly ok, have some style issues and minor other things inline.

Does need a lot more documentation in the commit messages, as well as more comments in the new functions, structs and global variables.

@@ -24,56 +24,19 @@

#include "suricata-common.h"
#include "app-layer-protos.h"
#include "rust.h"

AppProto ALPROTO_FAILED = ALPROTO_MAX_STATIC;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't like the coding style violations here, macro style name for vars, function style name for a var, etc.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can also imagine that the now global var ALPROTO_MAX would be replaced by a function AppProtoMax() or something.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why a function instead of a variable ?

if (strcmp(proto_name, AppProtoStrings[i].str) == 0)
return AppProtoStrings[i].alproto;
}

return ALPROTO_UNKNOWN;
}

void RegisterAppProtoString(AppProto alproto, const char *proto_name)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can ALPROTO_FAILED just be a constant instead of having it be a dynamic value for no real reason I can see?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ALPROTO_FAILED is used in comparison like < ALPROTO_FAILED ...
Will think about it again

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks like we can move ALPROTO_FAILED to 1 and change the comparisons... in next PR version

rust/src/sip/sip.rs Show resolved Hide resolved
rust/src/core.rs Show resolved Hide resolved
src/app-layer-protos.h Show resolved Hide resolved
src/app-layer-protos.h Show resolved Hide resolved
@@ -1027,11 +1024,56 @@ void AppLayerListSupportedProtocols(void)
}

/***** Setup/General Registration *****/
static void AppLayerNamesSetup(void)
{
RegisterAppProtoString(ALPROTO_UNKNOWN, "unknown");
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should this move into the actual parser implementations?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe as a next step that makes a protocol like SNMP behave like a plugin ? (no static definition of ALPROTO_SNMP)

src/app-layer-protos.c Show resolved Hide resolved
src/detect-engine-file.h Show resolved Hide resolved
@@ -52,4 +52,15 @@ typedef struct SCCapturePlugin_ {

int SCPluginRegisterCapture(SCCapturePlugin *);

typedef struct SCAppLayerPlugin_ {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

needs some struct docs

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@catenacyber Do you see this as being only used for app-layer plugins? Or become the new way to register app-layers? If the latter, it should be more generic than plugin context. Also its a lot odd to be here, but then used in detect-engine-register.c, I think it should be localized to plugin specific code.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just for some context, if "plugin" is mentioned outside of a file with plugin in the name, its probably suspect to a leaky abstraction. We have this for capture plugins still, but have got rid of it for other types of plugins.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do you see this as being only used for app-layer plugins?

That is what I thought at first

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok, then I'd move the usage of the Plugin struct out of the app-layer. Keep it within the plugin API, and not the app-layer API. Then register it from there so the plugin interface doesn't leak into the app-layer API if that makes sense.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What do you mean ? For example, Which line of code should I move from which file to which file ?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I guess this:

#ifdef HAVE_PLUGINS
    for (size_t i = 0; i < app_layer_plugins_nb; i++) {
        SCAppLayerPlugin *app_layer_plugin = SCPluginFindAppLayerByIndex(i);
        if (app_layer_plugin == NULL) {
            break;
        }
        app_layer_plugin->Register();
    }
#endif

it doesn't really need HAVE_PLUGINS, its simply dynamic app-layer registration right?

It just feels weird that the app-layer "layer" is plugin aware, instead the plugin-layer would be app-layer aware.

Can we get a sample plugin for CI purposes to make sure it works? Might help reason about it.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we get a sample plugin for CI purposes to make sure it works?

Example plugin at https://github.com/catenacyber/suricata-zabbix ;-)

It just feels weird that the app-layer "layer" is plugin aware, instead the plugin-layer would be app-layer aware.

I see what you mean.
The problem is different initialization timings :

  1. plugin is initialized
  2. app-layer are registered (and then keywords, and then outputs)

So the plugin init cannot call directly its app-layer registration.
Instead, it registers a callback that will be called during app-layer registration...

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Example plugin at https://github.com/catenacyber/suricata-zabbix ;-)

I think we need some minimal in-tree so we can make sure it works. For example, this is the reason why examples/plugins/ci-capture/ exists - however we also now have 2 in-tree capture methods that are plugins as well.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done in #12116

@victorjulien victorjulien added the needs rebase Needs rebase to master label Nov 6, 2024
@catenacyber
Copy link
Contributor Author

Replaced by #12110

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
needs rebase Needs rebase to master
Development

Successfully merging this pull request may close these issues.

4 participants