]> git.ipfire.org Git - people/ms/suricata.git/blob - src/detect-ike-nonce-payload-length.c
ikev1: add ikev1 parser
[people/ms/suricata.git] / src / detect-ike-nonce-payload-length.c
1 /* Copyright (C) 2020 Open Information Security Foundation
2 *
3 * You can copy, redistribute or modify this Program under the terms of
4 * the GNU General Public License version 2 as published by the Free
5 * Software Foundation.
6 *
7 * This program is distributed in the hope that it will be useful,
8 * but WITHOUT ANY WARRANTY; without even the implied warranty of
9 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10 * GNU General Public License for more details.
11 *
12 * You should have received a copy of the GNU General Public License
13 * version 2 along with this program; if not, write to the Free Software
14 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
15 * 02110-1301, USA.
16 */
17
18 /**
19 *
20 * \author Frank Honza <frank.honza@dcso.de>
21 */
22
23 #include "suricata-common.h"
24 #include "conf.h"
25 #include "detect.h"
26 #include "detect-parse.h"
27 #include "detect-engine.h"
28 #include "detect-engine-content-inspection.h"
29 #include "detect-ike-nonce-payload-length.h"
30 #include "app-layer-parser.h"
31 #include "util-byte.h"
32 #include "detect-engine-uint.h"
33
34 #include "rust-bindings.h"
35
36 /**
37 * [ike.nonce_payload_length]:[=|<|>|<=|>=]<length>;
38 */
39 static int DetectIkeNoncePayloadLengthSetup(DetectEngineCtx *, Signature *s, const char *str);
40 static void DetectIkeNoncePayloadLengthFree(DetectEngineCtx *, void *);
41 static int g_ike_nonce_payload_length_buffer_id = 0;
42
43 static int DetectEngineInspectIkeNoncePayloadLengthGeneric(DetectEngineCtx *de_ctx,
44 DetectEngineThreadCtx *det_ctx, const struct DetectEngineAppInspectionEngine_ *engine,
45 const Signature *s, Flow *f, uint8_t flags, void *alstate, void *txv, uint64_t tx_id);
46
47 static int DetectIkeNoncePayloadLengthMatch(DetectEngineThreadCtx *, Flow *, uint8_t, void *,
48 void *, const Signature *, const SigMatchCtx *);
49
50 /**
51 * \brief Registration function for ike.nonce_payload_length keyword.
52 */
53 void DetectIkeNoncePayloadLengthRegister(void)
54 {
55 sigmatch_table[DETECT_AL_IKE_NONCE_PAYLOAD_LENGTH].name = "ike.nonce_payload_length";
56 sigmatch_table[DETECT_AL_IKE_NONCE_PAYLOAD_LENGTH].desc = "match IKE nonce payload length";
57 sigmatch_table[DETECT_AL_IKE_NONCE_PAYLOAD_LENGTH].url =
58 "/rules/ike-keywords.html#ike-nonce-payload-length";
59 sigmatch_table[DETECT_AL_IKE_NONCE_PAYLOAD_LENGTH].AppLayerTxMatch =
60 DetectIkeNoncePayloadLengthMatch;
61 sigmatch_table[DETECT_AL_IKE_NONCE_PAYLOAD_LENGTH].Setup = DetectIkeNoncePayloadLengthSetup;
62 sigmatch_table[DETECT_AL_IKE_NONCE_PAYLOAD_LENGTH].Free = DetectIkeNoncePayloadLengthFree;
63
64 DetectAppLayerInspectEngineRegister2("ike.nonce_payload_length", ALPROTO_IKE, SIG_FLAG_TOSERVER,
65 1, DetectEngineInspectIkeNoncePayloadLengthGeneric, NULL);
66
67 DetectAppLayerInspectEngineRegister2("ike.nonce_payload_length", ALPROTO_IKE, SIG_FLAG_TOCLIENT,
68 1, DetectEngineInspectIkeNoncePayloadLengthGeneric, NULL);
69
70 g_ike_nonce_payload_length_buffer_id = DetectBufferTypeGetByName("ike.nonce_payload_length");
71
72 DetectUintRegister();
73 }
74
75 static int DetectEngineInspectIkeNoncePayloadLengthGeneric(DetectEngineCtx *de_ctx,
76 DetectEngineThreadCtx *det_ctx, const struct DetectEngineAppInspectionEngine_ *engine,
77 const Signature *s, Flow *f, uint8_t flags, void *alstate, void *txv, uint64_t tx_id)
78 {
79 return DetectEngineInspectGenericList(
80 de_ctx, det_ctx, s, engine->smd, f, flags, alstate, txv, tx_id);
81 }
82
83 /**
84 * \internal
85 * \brief Function to match nonce length of a IKE state
86 *
87 * \param det_ctx Pointer to the pattern matcher thread.
88 * \param f Pointer to the current flow.
89 * \param flags Flags.
90 * \param state App layer state.
91 * \param txv Pointer to the Ike Transaction.
92 * \param s Pointer to the Signature.
93 * \param ctx Pointer to the sigmatch that we will cast into DetectU32Data.
94 *
95 * \retval 0 no match.
96 * \retval 1 match.
97 */
98 static int DetectIkeNoncePayloadLengthMatch(DetectEngineThreadCtx *det_ctx, Flow *f, uint8_t flags,
99 void *state, void *txv, const Signature *s, const SigMatchCtx *ctx)
100 {
101 SCEnter();
102
103 uint32_t length;
104 if (!rs_ike_state_get_nonce_payload_length(txv, &length))
105 SCReturnInt(0);
106 const DetectU32Data *du32 = (const DetectU32Data *)ctx;
107 return DetectU32Match(length, du32);
108 }
109
110 /**
111 * \brief Function to add the parsed IKE nonce length field into the current signature.
112 *
113 * \param de_ctx Pointer to the Detection Engine Context.
114 * \param s Pointer to the Current Signature.
115 * \param rawstr Pointer to the user provided flags options.
116 *
117 * \retval 0 on Success.
118 * \retval -1 on Failure.
119 */
120 static int DetectIkeNoncePayloadLengthSetup(
121 DetectEngineCtx *de_ctx, Signature *s, const char *rawstr)
122 {
123 if (DetectSignatureSetAppProto(s, ALPROTO_IKE) != 0)
124 return -1;
125
126 DetectU32Data *nonce_payload_length = DetectU32Parse(rawstr);
127 if (nonce_payload_length == NULL)
128 return -1;
129
130 /* okay so far so good, lets get this into a SigMatch
131 * and put it in the Signature. */
132 SigMatch *sm = SigMatchAlloc();
133 if (sm == NULL)
134 goto error;
135
136 sm->type = DETECT_AL_IKE_NONCE_PAYLOAD_LENGTH;
137 sm->ctx = (SigMatchCtx *)nonce_payload_length;
138
139 SigMatchAppendSMToList(s, sm, g_ike_nonce_payload_length_buffer_id);
140 return 0;
141
142 error:
143 DetectIkeNoncePayloadLengthFree(de_ctx, nonce_payload_length);
144 return -1;
145 }
146
147 /**
148 * \internal
149 * \brief Function to free memory associated with DetectU32Data.
150 *
151 * \param de_ptr Pointer to DetectU32Data.
152 */
153 static void DetectIkeNoncePayloadLengthFree(DetectEngineCtx *de_ctx, void *ptr)
154 {
155 SCFree(ptr);
156 }