suricata
app-layer.c
Go to the documentation of this file.
1 /* Copyright (C) 2007-2024 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  * \file
20  *
21  * \author Victor Julien <victor@inliniac.net>
22  * \author Anoop Saldanha <anoopsaldanha@gmail.com>
23  *
24  * Generic App-layer functions
25  */
26 
27 #include "suricata-common.h"
28 #include "suricata.h"
29 #include "app-layer.h"
30 #include "app-layer-parser.h"
31 #include "app-layer-protos.h"
32 #include "app-layer-expectation.h"
33 #include "app-layer-ftp.h"
34 #include "app-layer-htp-range.h"
35 #include "app-layer-detect-proto.h"
36 #include "app-layer-frames.h"
37 #include "app-layer-events.h"
38 #include "stream-tcp-reassemble.h"
39 #include "stream-tcp-private.h"
40 #include "stream-tcp-inline.h"
41 #include "stream-tcp.h"
42 #include "flow.h"
43 #include "flow-util.h"
44 #include "flow-private.h"
45 #include "ippair.h"
46 #include "util-debug.h"
47 #include "util-print.h"
48 #include "util-profiling.h"
49 #include "util-validate.h"
50 #include "decode-events.h"
51 #include "app-layer-htp-mem.h"
52 #include "util-exception-policy.h"
53 
55 /**
56  * \brief This is for the app layer in general and it contains per thread
57  * context relevant to both the alpd and alp.
58  */
60  /* App layer protocol detection thread context, from AppLayerProtoDetectGetCtxThread(). */
62  /* App layer parser thread context, from AppLayerParserThreadCtxAlloc(). */
64 
65 #ifdef PROFILING
66  uint64_t ticks_start;
67  uint64_t ticks_end;
68  uint64_t ticks_spent;
73 #endif
74 };
75 
76 #define FLOW_PROTO_CHANGE_MAX_DEPTH 4096
77 
78 #define MAX_COUNTER_SIZE 64
79 typedef struct AppLayerCounterNames_ {
88 
89 typedef struct AppLayerCounters_ {
90  uint16_t counter_id;
91  uint16_t counter_tx_id;
92  uint16_t gap_error_id;
93  uint16_t parser_error_id;
95  uint16_t alloc_error_id;
98 
99 /* counter names. Only used at init. */
101 /* counter id's. Used that runtime. */
103 /* Exception policy global counters ids */
105 
106 /* Settings order as in the enum */
107 // clang-format off
109  .valid_settings_ids = {
110  /* EXCEPTION_POLICY_NOT_SET */ false,
111  /* EXCEPTION_POLICY_AUTO */ false,
112  /* EXCEPTION_POLICY_PASS_PACKET */ true,
113  /* EXCEPTION_POLICY_PASS_FLOW */ true,
114  /* EXCEPTION_POLICY_BYPASS_FLOW */ true,
115  /* EXCEPTION_POLICY_DROP_PACKET */ false,
116  /* EXCEPTION_POLICY_DROP_FLOW */ false,
117  /* EXCEPTION_POLICY_REJECT */ true,
118  /* EXCEPTION_POLICY_REJECT_BOTH */ true,
119  },
120  .valid_settings_ips = {
121  /* EXCEPTION_POLICY_NOT_SET */ false,
122  /* EXCEPTION_POLICY_AUTO */ false,
123  /* EXCEPTION_POLICY_PASS_PACKET */ true,
124  /* EXCEPTION_POLICY_PASS_FLOW */ true,
125  /* EXCEPTION_POLICY_BYPASS_FLOW */ true,
126  /* EXCEPTION_POLICY_DROP_PACKET */ true,
127  /* EXCEPTION_POLICY_DROP_FLOW */ true,
128  /* EXCEPTION_POLICY_REJECT */ true,
129  /* EXCEPTION_POLICY_REJECT_BOTH */ true,
130  },
131 };
132 // clang-format on
133 
134 void AppLayerSetupCounters(void);
135 void AppLayerDeSetupCounters(void);
136 
137 /***** L7 layer dispatchers *****/
138 
139 static inline int ProtoDetectDone(const Flow *f, const TcpSession *ssn, uint8_t direction) {
140  const TcpStream *stream = (direction & STREAM_TOSERVER) ? &ssn->client : &ssn->server;
142  (FLOW_IS_PM_DONE(f, direction) && FLOW_IS_PP_DONE(f, direction)));
143 }
144 
145 /**
146  * \note id can be 0 if protocol parser is disabled but detection
147  * is enabled.
148  */
149 static void AppLayerIncFlowCounter(ThreadVars *tv, Flow *f)
150 {
151  const uint16_t id = applayer_counters[f->alproto][f->protomap].counter_id;
152  if (likely(tv && id > 0)) {
153  StatsIncr(tv, id);
154  }
155 }
156 
157 void AppLayerIncTxCounter(ThreadVars *tv, Flow *f, uint64_t step)
158 {
159  const uint16_t id = applayer_counters[f->alproto][f->protomap].counter_tx_id;
160  if (likely(tv && id > 0)) {
161  StatsAddUI64(tv, id, step);
162  }
163 }
164 
166 {
167  const uint16_t id = applayer_counters[f->alproto][f->protomap].gap_error_id;
168  if (likely(tv && id > 0)) {
169  StatsIncr(tv, id);
170  }
171 }
172 
174 {
175  const uint16_t id = applayer_counters[f->alproto][f->protomap].alloc_error_id;
176  if (likely(tv && id > 0)) {
177  StatsIncr(tv, id);
178  }
179 }
180 
182 {
183  const uint16_t id = applayer_counters[f->alproto][f->protomap].parser_error_id;
184  if (likely(tv && id > 0)) {
185  StatsIncr(tv, id);
186  }
187 }
188 
190 {
191  const uint16_t id = applayer_counters[f->alproto][f->protomap].internal_error_id;
192  if (likely(tv && id > 0)) {
193  StatsIncr(tv, id);
194  }
195 }
196 
197 static void AppLayerIncrErrorExcPolicyCounter(ThreadVars *tv, Flow *f, enum ExceptionPolicy policy)
198 {
199 #ifdef UNITTESTS
200  if (tv == NULL) {
201  return;
202  }
203 #endif
204  uint16_t id = applayer_counters[f->alproto][f->protomap].eps_error.eps_id[policy];
205  /* for the summary values */
206  uint16_t g_id = eps_error_summary.eps_id[policy];
207 
208  if (likely(id > 0)) {
209  StatsIncr(tv, id);
210  }
211  if (likely(g_id > 0)) {
212  StatsIncr(tv, g_id);
213  }
214 }
215 
216 /* in IDS mode protocol detection is done in reverse order:
217  * when TCP data is ack'd. We want to flag the correct packet,
218  * so in this case we set a flag in the flow so that the first
219  * packet in the correct direction can be tagged.
220  *
221  * For IPS we update packet and flow. */
222 static inline void FlagPacketFlow(Packet *p, Flow *f, uint8_t flags)
223 {
224  if (p->proto != IPPROTO_TCP || EngineModeIsIPS()) {
225  if (flags & STREAM_TOSERVER) {
226  if (p->flowflags & FLOW_PKT_TOSERVER) {
229  } else {
231  }
232  } else {
233  if (p->flowflags & FLOW_PKT_TOCLIENT) {
236  } else {
238  }
239  }
240  } else {
241  if (flags & STREAM_TOSERVER) {
243  } else {
245  }
246  }
247 }
248 
249 static void DisableAppLayer(ThreadVars *tv, Flow *f, Packet *p)
250 {
251  SCLogDebug("disable app layer for flow %p alproto %u ts %u tc %u",
252  f, f->alproto, f->alproto_ts, f->alproto_tc);
255  TcpSession *ssn = f->protoctx;
257  f->alproto = ALPROTO_FAILED;
258  AppLayerIncFlowCounter(tv, f);
259 
260  if (f->alproto_tc != ALPROTO_FAILED) {
261  if (f->alproto_tc == ALPROTO_UNKNOWN) {
263  }
264  FlagPacketFlow(p, f, STREAM_TOCLIENT);
265  }
266  if (f->alproto_ts != ALPROTO_FAILED) {
267  if (f->alproto_ts == ALPROTO_UNKNOWN) {
269  }
270  FlagPacketFlow(p, f, STREAM_TOSERVER);
271  }
272  SCLogDebug("disabled app layer for flow %p alproto %u ts %u tc %u",
273  f, f->alproto, f->alproto_ts, f->alproto_tc);
274 }
275 
276 /* See if we're going to have to give up:
277  *
278  * If we're getting a lot of data in one direction and the
279  * proto for this direction is unknown, proto detect will
280  * hold up segments in the segment list in the stream.
281  * They are held so that if we detect the protocol on the
282  * opposing stream, we can still parse this side of the stream
283  * as well. However, some sessions are very unbalanced. FTP
284  * data channels, large PUT/POST request and many others, can
285  * lead to cases where we would have to store many megabytes
286  * worth of segments before we see the opposing stream. This
287  * leads to risks of resource starvation.
288  *
289  * Here a cutoff point is enforced. If we've stored 100k in
290  * one direction and we've seen no data in the other direction,
291  * we give up.
292  *
293  * Giving up means we disable applayer an set an applayer event
294  */
295 static void TCPProtoDetectCheckBailConditions(ThreadVars *tv,
296  Flow *f, TcpSession *ssn, Packet *p)
297 {
298  if (ssn->state < TCP_ESTABLISHED) {
299  SCLogDebug("skip as long as TCP is not ESTABLISHED (TCP fast open)");
300  return;
301  }
302 
303  const uint32_t size_ts = StreamDataAvailableForProtoDetect(&ssn->client);
304  const uint32_t size_tc = StreamDataAvailableForProtoDetect(&ssn->server);
305  SCLogDebug("size_ts %" PRIu32 ", size_tc %" PRIu32, size_ts, size_tc);
306 
307  /* at least 100000 whatever the conditions
308  * and can be more if window is bigger and if configuration allows it */
309  const uint32_t size_tc_limit =
311  const uint32_t size_ts_limit =
313 
314  if (ProtoDetectDone(f, ssn, STREAM_TOSERVER) &&
315  ProtoDetectDone(f, ssn, STREAM_TOCLIENT))
316  {
317  goto failure;
318 
319  /* we bail out whatever the pp and pm states if
320  * we received too much data */
321  } else if (size_tc > 2 * size_tc_limit || size_ts > 2 * size_ts_limit) {
323  goto failure;
324 
325  } else if (FLOW_IS_PM_DONE(f, STREAM_TOSERVER) && FLOW_IS_PP_DONE(f, STREAM_TOSERVER) &&
326  size_ts > size_ts_limit && size_tc == 0) {
328  goto failure;
329 
330  } else if (FLOW_IS_PM_DONE(f, STREAM_TOCLIENT) && FLOW_IS_PP_DONE(f, STREAM_TOCLIENT) &&
331  size_tc > size_tc_limit && size_ts == 0) {
333  goto failure;
334 
335  /* little data in ts direction, pp done, pm not done (max
336  * depth not reached), ts direction done, lots of data in
337  * tc direction. */
338  } else if (size_tc > size_tc_limit && FLOW_IS_PP_DONE(f, STREAM_TOSERVER) &&
339  !(FLOW_IS_PM_DONE(f, STREAM_TOSERVER)) && FLOW_IS_PM_DONE(f, STREAM_TOCLIENT) &&
340  FLOW_IS_PP_DONE(f, STREAM_TOCLIENT)) {
342  goto failure;
343 
344  /* little data in tc direction, pp done, pm not done (max
345  * depth not reached), tc direction done, lots of data in
346  * ts direction. */
347  } else if (size_ts > size_ts_limit && FLOW_IS_PP_DONE(f, STREAM_TOCLIENT) &&
348  !(FLOW_IS_PM_DONE(f, STREAM_TOCLIENT)) && FLOW_IS_PM_DONE(f, STREAM_TOSERVER) &&
349  FLOW_IS_PP_DONE(f, STREAM_TOSERVER)) {
351  goto failure;
352  }
353  return;
354 
355 failure:
356  DisableAppLayer(tv, f, p);
357 }
358 
359 static int TCPProtoDetectTriggerOpposingSide(ThreadVars *tv, TcpReassemblyThreadCtx *ra_ctx,
360  Packet *p, TcpSession *ssn, const TcpStream *stream)
361 {
362  TcpStream *opposing_stream = NULL;
363  if (stream == &ssn->client) {
364  opposing_stream = &ssn->server;
365  } else {
366  opposing_stream = &ssn->client;
367  }
368 
369  /* if the opposing side is not going to work, then
370  * we just have to give up. */
371  if (opposing_stream->flags & STREAMTCP_STREAM_FLAG_NOREASSEMBLY) {
372  SCLogDebug("opposing dir has STREAMTCP_STREAM_FLAG_NOREASSEMBLY set");
373  return -1;
374  }
375 
376  enum StreamUpdateDir dir = StreamTcpInlineMode() ?
379  int ret = StreamTcpReassembleAppLayer(tv, ra_ctx, ssn,
380  opposing_stream, p, dir);
381  return ret;
382 }
383 
385 
386 /** \todo data const
387  * \retval int -1 error
388  * \retval int 0 ok
389  */
390 static int TCPProtoDetect(ThreadVars *tv, TcpReassemblyThreadCtx *ra_ctx,
391  AppLayerThreadCtx *app_tctx, Packet *p, Flow *f, TcpSession *ssn, TcpStream **stream,
392  uint8_t *data, uint32_t data_len, uint8_t flags, enum StreamUpdateDir app_update_dir)
393 {
394  AppProto *alproto;
395  AppProto *alproto_otherdir;
396  uint8_t direction = (flags & STREAM_TOSERVER) ? 0 : 1;
397 
398  if (flags & STREAM_TOSERVER) {
399  alproto = &f->alproto_ts;
400  alproto_otherdir = &f->alproto_tc;
401  } else {
402  alproto = &f->alproto_tc;
403  alproto_otherdir = &f->alproto_ts;
404  }
405 
406  SCLogDebug("Stream initializer (len %" PRIu32 ")", data_len);
407 #ifdef PRINT
408  if (data_len > 0) {
409  printf("=> Init Stream Data (app layer) -- start %s%s\n",
410  flags & STREAM_TOCLIENT ? "toclient" : "",
411  flags & STREAM_TOSERVER ? "toserver" : "");
412  PrintRawDataFp(stdout, data, data_len);
413  printf("=> Init Stream Data -- end\n");
414  }
415 #endif
416 
417  bool reverse_flow = false;
418  DEBUG_VALIDATE_BUG_ON(data == NULL && data_len > 0);
420  *alproto = AppLayerProtoDetectGetProto(app_tctx->alpd_tctx,
421  f, data, data_len,
422  IPPROTO_TCP, flags, &reverse_flow);
423  PACKET_PROFILING_APP_PD_END(app_tctx);
424  SCLogDebug("alproto %u rev %s", *alproto, reverse_flow ? "true" : "false");
425 
426  if (*alproto != ALPROTO_UNKNOWN) {
427  if (*alproto_otherdir != ALPROTO_UNKNOWN && *alproto_otherdir != *alproto) {
430 
432  /* if we already invoked the parser, we go with that proto */
433  f->alproto = *alproto_otherdir;
434  } else {
435  /* no data sent to parser yet, we can still choose
436  * we're trusting the server more. */
437  if (flags & STREAM_TOCLIENT)
438  f->alproto = *alproto;
439  else
440  f->alproto = *alproto_otherdir;
441  }
442  } else {
443  f->alproto = *alproto;
444  }
445 
449  FlagPacketFlow(p, f, flags);
450 
451  /* if protocol detection indicated that we need to reverse
452  * the direction of the flow, do it now. We flip the flow,
453  * packet and the direction flags */
454  if (reverse_flow &&
457  /* but only if we didn't already detect it on the other side. */
458  if (*alproto_otherdir == ALPROTO_UNKNOWN) {
459  SCLogDebug("reversing flow after proto detect told us so");
460  PacketSwap(p);
461  FlowSwap(f);
462  // Will reset signature groups in DetectRunSetup
463  f->de_ctx_version = UINT32_MAX;
464  SWAP_FLAGS(flags, STREAM_TOSERVER, STREAM_TOCLIENT);
465  if (*stream == &ssn->client) {
466  *stream = &ssn->server;
467  } else {
468  *stream = &ssn->client;
469  }
470  direction = 1 - direction;
471  } else {
472  // TODO event, error?
473  }
474  }
475 
476  /* account flow if we have both sides */
477  if (*alproto_otherdir != ALPROTO_UNKNOWN) {
478  AppLayerIncFlowCounter(tv, f);
479  }
480 
481  /* if we have seen data from the other direction first, send
482  * data for that direction first to the parser. This shouldn't
483  * be an issue, since each stream processing happens
484  * independently of the other stream direction. At this point of
485  * call, you need to know that this function's already being
486  * called by the very same StreamReassembly() function that we
487  * will now call shortly for the opposing direction. */
488  if ((ssn->data_first_seen_dir & (STREAM_TOSERVER | STREAM_TOCLIENT)) &&
489  !(flags & ssn->data_first_seen_dir))
490  {
491  SCLogDebug("protocol %s needs first data in other direction",
492  AppProtoToString(*alproto));
493 
494  if (TCPProtoDetectTriggerOpposingSide(tv, ra_ctx,
495  p, ssn, *stream) != 0)
496  {
497  goto detect_error;
498  }
499  if (FlowChangeProto(f)) {
500  /* We have the first data which requested a protocol change from P1 to P2
501  * even if it was not recognized at first as being P1
502  * As the second data was recognized as P1, the protocol did not change !
503  */
507  }
508  }
509 
510  /* if the parser operates such that it needs to see data from
511  * a particular direction first, we check if we have seen
512  * data from that direction first for the flow. IF it is not
513  * the same, we set an event and exit.
514  *
515  * \todo We need to figure out a more robust solution for this,
516  * as this can lead to easy evasion tactics, where the
517  * attacker can first send some dummy data in the wrong
518  * direction first to mislead our proto detection process.
519  * While doing this we need to update the parsers as well,
520  * since the parsers must be robust to see such wrong
521  * direction data.
522  * Either ways the moment we see the
523  * APPLAYER_WRONG_DIRECTION_FIRST_DATA event set for the
524  * flow, it shows something's fishy.
525  */
527  uint8_t first_data_dir;
528  first_data_dir = AppLayerParserGetFirstDataDir(f->proto, f->alproto);
529 
530  if (first_data_dir && !(first_data_dir & ssn->data_first_seen_dir)) {
533  goto detect_error;
534  }
535  /* This can happen if the current direction is not the
536  * right direction, and the data from the other(also
537  * the right direction) direction is available to be sent
538  * to the app layer, but it is not ack'ed yet and hence
539  * the forced call to STreamTcpAppLayerReassemble still
540  * hasn't managed to send data from the other direction
541  * to the app layer. */
542  if (first_data_dir && !(first_data_dir & flags)) {
548  SCReturnInt(-1);
549  }
550  }
551 
552  /* Set a value that is neither STREAM_TOSERVER, nor STREAM_TOCLIENT */
554 
555  /* finally, invoke the parser */
556  PACKET_PROFILING_APP_START(app_tctx, f->alproto);
557  int r = AppLayerParserParse(tv, app_tctx->alp_tctx, f, f->alproto,
558  flags, data, data_len);
559  PACKET_PROFILING_APP_END(app_tctx);
560  p->app_update_direction = (uint8_t)app_update_dir;
561  if (r != 1) {
562  StreamTcpUpdateAppLayerProgress(ssn, direction, data_len);
563  }
564  if (r == 0) {
565  if (*alproto_otherdir == ALPROTO_UNKNOWN) {
566  TcpStream *opposing_stream;
567  if (*stream == &ssn->client) {
568  opposing_stream = &ssn->server;
569  } else {
570  opposing_stream = &ssn->client;
571  }
573  // can happen in detection-only
574  AppLayerIncFlowCounter(tv, f);
575  }
576  }
577  }
578  if (r < 0) {
579  goto parser_error;
580  }
581  } else {
582  /* if the ssn is midstream, we may end up with a case where the
583  * start of an HTTP request is missing. We won't detect HTTP based
584  * on the request. However, the reply is fine, so we detect
585  * HTTP anyway. This leads to passing the incomplete request to
586  * the htp parser.
587  *
588  * This has been observed, where the http parser then saw many
589  * bogus requests in the incomplete data.
590  *
591  * To counter this case, a midstream session MUST find it's
592  * protocol in the toserver direction. If not, we assume the
593  * start of the request/toserver is incomplete and no reliable
594  * detection and parsing is possible. So we give up.
595  */
596  if ((ssn->flags & STREAMTCP_FLAG_MIDSTREAM) &&
598  {
599  if (FLOW_IS_PM_DONE(f, STREAM_TOSERVER) && FLOW_IS_PP_DONE(f, STREAM_TOSERVER)) {
600  SCLogDebug("midstream end pd %p", ssn);
601  /* midstream and toserver detection failed: give up */
602  DisableAppLayer(tv, f, p);
603  SCReturnInt(0);
604  }
605  }
606 
607  if (*alproto_otherdir != ALPROTO_UNKNOWN) {
608  uint8_t first_data_dir;
609  first_data_dir = AppLayerParserGetFirstDataDir(f->proto, *alproto_otherdir);
610 
611  /* this would handle this test case -
612  * http parser which says it wants to see toserver data first only.
613  * tcp handshake
614  * toclient data first received. - RUBBISH DATA which
615  * we don't detect as http
616  * toserver data next sent - we detect this as http.
617  * at this stage we see that toclient is the first data seen
618  * for this session and we try and redetect the app protocol,
619  * but we are unable to detect the app protocol like before.
620  * But since we have managed to detect the protocol for the
621  * other direction as http, we try to use that. At this
622  * stage we check if the direction of this stream matches
623  * to that acceptable by the app parser. If it is not the
624  * acceptable direction we error out.
625  */
627  (first_data_dir) && !(first_data_dir & flags))
628  {
629  goto detect_error;
630  }
631 
632  /* if protocol detection is marked done for our direction we
633  * pass our data on. We're only succeeded in finding one
634  * direction: the opposing stream
635  *
636  * If PD was not yet complete, we don't do anything.
637  */
638  if (FLOW_IS_PM_DONE(f, flags) && FLOW_IS_PP_DONE(f, flags)) {
639  if (data_len > 0)
641 
642  if (*alproto_otherdir != ALPROTO_FAILED) {
643  PACKET_PROFILING_APP_START(app_tctx, f->alproto);
644  int r = AppLayerParserParse(tv, app_tctx->alp_tctx, f,
645  f->alproto, flags,
646  data, data_len);
647  PACKET_PROFILING_APP_END(app_tctx);
648  p->app_update_direction = (uint8_t)app_update_dir;
649  if (r != 1) {
650  StreamTcpUpdateAppLayerProgress(ssn, direction, data_len);
651  }
652 
657  AppLayerIncFlowCounter(tv, f);
658 
659  *alproto = *alproto_otherdir;
660  SCLogDebug("packet %"PRIu64": pd done(us %u them %u), parser called (r==%d), APPLAYER_DETECT_PROTOCOL_ONLY_ONE_DIRECTION set",
661  p->pcap_cnt, *alproto, *alproto_otherdir, r);
662  if (r < 0) {
663  goto parser_error;
664  }
665  }
666  *alproto = ALPROTO_FAILED;
668  FlagPacketFlow(p, f, flags);
669 
670  } else if (flags & STREAM_EOF) {
671  *alproto = f->alproto;
673  AppLayerIncFlowCounter(tv, f);
674  }
675  } else {
676  /* both sides unknown, let's see if we need to give up */
677  if (FlowChangeProto(f)) {
678  /* TCPProtoDetectCheckBailConditions does not work well because
679  * size_tc from STREAM_RIGHT_EDGE is not reset to zero
680  * so, we set a lower limit to the data we inspect
681  * We could instead have set ssn->server.sb.stream_offset = 0;
682  */
683  if (data_len >= FLOW_PROTO_CHANGE_MAX_DEPTH || (flags & STREAM_EOF)) {
684  DisableAppLayer(tv, f, p);
685  }
686  } else {
687  TCPProtoDetectCheckBailConditions(tv, f, ssn, p);
688  }
689  }
690  }
691  SCReturnInt(0);
692 parser_error:
694  AppLayerIncrErrorExcPolicyCounter(tv, f, g_applayerparser_error_policy);
695  SCReturnInt(-1);
696 detect_error:
697  DisableAppLayer(tv, f, p);
698  SCReturnInt(-2);
699 }
700 
701 /** \brief handle TCP data for the app-layer.
702  *
703  * First run protocol detection and then when the protocol is known invoke
704  * the app layer parser.
705  *
706  * \param stream ptr-to-ptr to stream object. Might change if flow dir is
707  * reversed.
708  */
710  TcpSession *ssn, TcpStream **stream, uint8_t *data, uint32_t data_len, uint8_t flags,
711  enum StreamUpdateDir app_update_dir)
712 {
713  SCEnter();
714 
716  DEBUG_VALIDATE_BUG_ON(data_len > (uint32_t)INT_MAX);
717 
718  AppLayerThreadCtx *app_tctx = ra_ctx->app_tctx;
719  AppProto alproto;
720  int r = 0;
721 
722  SCLogDebug("data_len %u flags %02X", data_len, flags);
724  SCLogDebug("STREAMTCP_FLAG_APP_LAYER_DISABLED is set");
725  goto end;
726  }
727 
728  const uint8_t direction = (flags & STREAM_TOSERVER) ? 0 : 1;
729 
730  if (flags & STREAM_TOSERVER) {
731  alproto = f->alproto_ts;
732  } else {
733  alproto = f->alproto_tc;
734  }
735 
736  /* If a gap notification, relay the notification on to the
737  * app-layer if known. */
738  if (flags & STREAM_GAP) {
739  SCLogDebug("GAP of size %u", data_len);
740  if (alproto == ALPROTO_UNKNOWN) {
742  SCLogDebug("ALPROTO_UNKNOWN flow %p, due to GAP in stream start", f);
743  /* if the other side didn't already find the proto, we're done */
744  if (f->alproto == ALPROTO_UNKNOWN) {
745  goto failure;
746  }
747  AppLayerIncFlowCounter(tv, f);
748  }
749  if (FlowChangeProto(f)) {
751  SCLogDebug("Cannot handle gap while changing protocol");
752  goto failure;
753  }
754  PACKET_PROFILING_APP_START(app_tctx, f->alproto);
755  r = AppLayerParserParse(tv, app_tctx->alp_tctx, f, f->alproto,
756  flags, data, data_len);
757  PACKET_PROFILING_APP_END(app_tctx);
758  p->app_update_direction = (uint8_t)app_update_dir;
759  /* ignore parser result for gap */
760  StreamTcpUpdateAppLayerProgress(ssn, direction, data_len);
761  if (r < 0) {
763  AppLayerIncrErrorExcPolicyCounter(tv, f, g_applayerparser_error_policy);
764  SCReturnInt(-1);
765  }
766  goto end;
767  }
768 
769  /* if we don't know the proto yet and we have received a stream
770  * initializer message, we run proto detection.
771  * We receive 2 stream init msgs (one for each direction), we
772  * only run the proto detection for both and emit an event
773  * in the case protocols mismatch. */
774  if (alproto == ALPROTO_UNKNOWN && (flags & STREAM_START)) {
776  /* run protocol detection */
777  if (TCPProtoDetect(tv, ra_ctx, app_tctx, p, f, ssn, stream, data, data_len, flags,
778  app_update_dir) != 0) {
779  goto failure;
780  }
781  } else if (alproto != ALPROTO_UNKNOWN && FlowChangeProto(f)) {
782  SCLogDebug("protocol change, old %s", AppProtoToString(f->alproto_orig));
783  void *alstate_orig = f->alstate;
784  AppLayerParserState *alparser = f->alparser;
785  // we delay AppLayerParserStateCleanup because we may need previous parser state
789  /* rerun protocol detection */
790  int rd = TCPProtoDetect(
791  tv, ra_ctx, app_tctx, p, f, ssn, stream, data, data_len, flags, app_update_dir);
792  if (f->alproto == ALPROTO_UNKNOWN) {
793  DEBUG_VALIDATE_BUG_ON(alstate_orig != f->alstate);
794  // not enough data, revert AppLayerProtoDetectReset to rerun detection
795  f->alparser = alparser;
796  f->alproto = f->alproto_orig;
797  f->alproto_tc = f->alproto_orig;
798  f->alproto_ts = f->alproto_orig;
799  } else {
801  AppLayerParserStateProtoCleanup(f->protomap, f->alproto_orig, alstate_orig, alparser);
802  if (alstate_orig == f->alstate) {
803  // we just freed it
804  f->alstate = NULL;
805  }
806  }
807  if (rd != 0) {
808  SCLogDebug("proto detect failure");
809  goto failure;
810  }
811  SCLogDebug("protocol change, old %s, new %s",
813 
815  f->alproto != f->alproto_expect) {
817 
818  if (f->alproto_expect == ALPROTO_TLS && f->alproto != ALPROTO_TLS) {
821  }
822  }
823  } else {
824  SCLogDebug("stream data (len %" PRIu32 " alproto "
825  "%"PRIu16" (flow %p)", data_len, f->alproto, f);
826 #ifdef PRINT
827  if (data_len > 0) {
828  printf("=> Stream Data (app layer) -- start %s%s\n",
829  flags & STREAM_TOCLIENT ? "toclient" : "",
830  flags & STREAM_TOSERVER ? "toserver" : "");
831  PrintRawDataFp(stdout, data, data_len);
832  printf("=> Stream Data -- end\n");
833  }
834 #endif
835  /* if we don't have a data object here we are not getting it
836  * a start msg should have gotten us one */
837  if (f->alproto != ALPROTO_UNKNOWN) {
838  PACKET_PROFILING_APP_START(app_tctx, f->alproto);
839  r = AppLayerParserParse(tv, app_tctx->alp_tctx, f, f->alproto,
840  flags, data, data_len);
841  PACKET_PROFILING_APP_END(app_tctx);
842  p->app_update_direction = (uint8_t)app_update_dir;
843  if (r != 1) {
844  StreamTcpUpdateAppLayerProgress(ssn, direction, data_len);
845  if (r < 0) {
848  AppLayerIncrErrorExcPolicyCounter(tv, f, g_applayerparser_error_policy);
849  SCReturnInt(-1);
850  }
851  }
852  }
853  }
854 
855  goto end;
856  failure:
857  r = -1;
858  end:
859  SCReturnInt(r);
860 }
861 
862 /**
863  * \brief Handle a app layer UDP message
864  *
865  * If the protocol is yet unknown, the proto detection code is run first.
866  *
867  * \param dp_ctx Thread app layer detect context
868  * \param f *locked* flow
869  * \param p UDP packet
870  *
871  * \retval 0 ok
872  * \retval -1 error
873  */
875 {
876  SCEnter();
877  AppProto *alproto;
878  AppProto *alproto_otherdir;
879 
880  if (f->alproto_ts == ALPROTO_FAILED && f->alproto_tc == ALPROTO_FAILED) {
881  SCReturnInt(0);
882  }
883 
884  int r = 0;
885  uint8_t flags = 0;
886  if (p->flowflags & FLOW_PKT_TOSERVER) {
887  flags |= STREAM_TOSERVER;
888  alproto = &f->alproto_ts;
889  alproto_otherdir = &f->alproto_tc;
890  } else {
891  flags |= STREAM_TOCLIENT;
892  alproto = &f->alproto_tc;
893  alproto_otherdir = &f->alproto_ts;
894  }
895 
897 
898  /* if the protocol is still unknown, run detection */
899  if (*alproto == ALPROTO_UNKNOWN) {
900  SCLogDebug("Detecting AL proto on udp mesg (len %" PRIu32 ")",
901  p->payload_len);
902 
903  bool reverse_flow = false;
905  *alproto = AppLayerProtoDetectGetProto(
906  tctx->alpd_tctx, f, p->payload, p->payload_len, IPPROTO_UDP, flags, &reverse_flow);
908 
909  switch (*alproto) {
910  case ALPROTO_UNKNOWN:
911  if (*alproto_otherdir != ALPROTO_UNKNOWN) {
912  // Use recognized side
913  f->alproto = *alproto_otherdir;
914  // do not keep ALPROTO_UNKNOWN for this side so as not to loop
915  *alproto = *alproto_otherdir;
916  if (*alproto_otherdir == ALPROTO_FAILED) {
917  SCLogDebug("ALPROTO_UNKNOWN flow %p", f);
918  }
919  } else {
920  // First side of protocol is unknown
921  *alproto = ALPROTO_FAILED;
922  }
923  break;
924  case ALPROTO_FAILED:
925  if (*alproto_otherdir != ALPROTO_UNKNOWN) {
926  // Use recognized side
927  f->alproto = *alproto_otherdir;
928  if (*alproto_otherdir == ALPROTO_FAILED) {
929  SCLogDebug("ALPROTO_UNKNOWN flow %p", f);
930  }
931  }
932  // else wait for second side of protocol
933  break;
934  default:
935  if (*alproto_otherdir != ALPROTO_UNKNOWN && *alproto_otherdir != ALPROTO_FAILED) {
936  if (*alproto_otherdir != *alproto) {
939  // data already sent to parser, we cannot change the protocol to use the one
940  // of the server
941  }
942  } else {
943  f->alproto = *alproto;
944  }
945  }
946  if (*alproto_otherdir == ALPROTO_UNKNOWN) {
947  if (f->alproto == ALPROTO_UNKNOWN) {
948  // so as to increase stat about .app_layer.flow.failed_udp
949  f->alproto = ALPROTO_FAILED;
950  }
951  // If the other side is unknown, this is the first packet of the flow
952  AppLayerIncFlowCounter(tv, f);
953  }
954 
955  // parse the data if we recognized one protocol
956  if (f->alproto != ALPROTO_UNKNOWN && f->alproto != ALPROTO_FAILED) {
957  if (reverse_flow) {
958  SCLogDebug("reversing flow after proto detect told us so");
959  PacketSwap(p);
960  FlowSwap(f);
961  SWAP_FLAGS(flags, STREAM_TOSERVER, STREAM_TOCLIENT);
962  }
963 
965  r = AppLayerParserParse(tv, tctx->alp_tctx, f, f->alproto,
966  flags, p->payload, p->payload_len);
969  }
971  /* we do only inspection in one direction, so flag both
972  * sides as done here */
973  FlagPacketFlow(p, f, STREAM_TOSERVER);
974  FlagPacketFlow(p, f, STREAM_TOCLIENT);
975  } else {
976  SCLogDebug("data (len %" PRIu32 " ), alproto "
977  "%"PRIu16" (flow %p)", p->payload_len, f->alproto, f);
978 
979  /* run the parser */
981  r = AppLayerParserParse(tv, tctx->alp_tctx, f, f->alproto,
982  flags, p->payload, p->payload_len);
986  }
987  if (r < 0) {
989  AppLayerIncrErrorExcPolicyCounter(tv, f, g_applayerparser_error_policy);
990  SCReturnInt(-1);
991  }
992 
993  SCReturnInt(r);
994 }
995 
996 /***** Utility *****/
997 
998 AppProto AppLayerGetProtoByName(const char *alproto_name)
999 {
1000  SCEnter();
1001  AppProto r = AppLayerProtoDetectGetProtoByName(alproto_name);
1002  SCReturnCT(r, "AppProto");
1003 }
1004 
1005 const char *AppLayerGetProtoName(AppProto alproto)
1006 {
1007  SCEnter();
1008  const char * r = AppLayerProtoDetectGetProtoName(alproto);
1009  SCReturnCT(r, "char *");
1010 }
1011 
1013 {
1014  SCEnter();
1015 
1016  AppProto alproto;
1017  AppProto alprotos[g_alproto_max];
1018 
1020 
1021  printf("=========Supported App Layer Protocols=========\n");
1022  for (alproto = 0; alproto < g_alproto_max; alproto++) {
1023  if (alprotos[alproto] == 1)
1024  printf("%s\n", AppLayerGetProtoName(alproto));
1025  }
1026 
1027  SCReturn;
1028 }
1029 
1030 /***** Setup/General Registration *****/
1031 static void AppLayerNamesSetup(void)
1032 {
1072 }
1073 
1074 int AppLayerSetup(void)
1075 {
1076  SCEnter();
1077 
1078  AppLayerNamesSetup();
1081 
1084 
1086  FrameConfigInit();
1087 
1088  SCReturnInt(0);
1089 }
1090 
1092 {
1093  SCEnter();
1094 
1097 
1100 
1101  SCReturnInt(0);
1102 }
1103 
1105 {
1106  SCEnter();
1107 
1108  AppLayerThreadCtx *app_tctx = SCCalloc(1, sizeof(*app_tctx));
1109  if (app_tctx == NULL)
1110  goto error;
1111 
1112  if ((app_tctx->alpd_tctx = AppLayerProtoDetectGetCtxThread()) == NULL)
1113  goto error;
1114  if ((app_tctx->alp_tctx = AppLayerParserThreadCtxAlloc()) == NULL)
1115  goto error;
1116 
1117  goto done;
1118  error:
1119  AppLayerDestroyCtxThread(app_tctx);
1120  app_tctx = NULL;
1121  done:
1122  SCReturnPtr(app_tctx, "void *");
1123 }
1124 
1126 {
1127  SCEnter();
1128 
1129  if (app_tctx == NULL)
1130  SCReturn;
1131 
1132  if (app_tctx->alpd_tctx != NULL)
1134  if (app_tctx->alp_tctx != NULL)
1136  SCFree(app_tctx);
1137 
1138  SCReturn;
1139 }
1140 
1141 #ifdef PROFILING
1143 {
1144  PACKET_PROFILING_APP_RESET(app_tctx);
1145 }
1146 
1148 {
1149  PACKET_PROFILING_APP_STORE(app_tctx, p);
1150 }
1151 #endif
1152 
1153 /** \brief HACK to work around our broken unix manager (re)init loop
1154  */
1156 {
1161  StatsRegisterGlobalCounter("app_layer.expectations", ExpectationGetCounter);
1164  StatsRegisterGlobalCounter("ippair.memuse", IPPairGetMemuse);
1165  StatsRegisterGlobalCounter("ippair.memcap", IPPairGetMemcap);
1166  StatsRegisterGlobalCounter("host.memuse", HostGetMemuse);
1167  StatsRegisterGlobalCounter("host.memcap", HostGetMemcap);
1168 }
1169 
1170 static bool IsAppLayerErrorExceptionPolicyStatsValid(enum ExceptionPolicy policy)
1171 {
1172  if (EngineModeIsIPS()) {
1174  }
1176 }
1177 
1178 static void AppLayerSetupExceptionPolicyPerProtoCounters(
1179  uint8_t ipproto_map, AppProto alproto, const char *alproto_str, const char *ipproto_suffix)
1180 {
1183  for (enum ExceptionPolicy i = EXCEPTION_POLICY_NOT_SET + 1; i < EXCEPTION_POLICY_MAX; i++) {
1184  if (IsAppLayerErrorExceptionPolicyStatsValid(i)) {
1185  snprintf(applayer_counter_names[alproto][ipproto_map].eps_name[i],
1186  sizeof(applayer_counter_names[alproto][ipproto_map].eps_name[i]),
1187  "app_layer.error.%s%s.exception_policy.%s", alproto_str, ipproto_suffix,
1188  ExceptionPolicyEnumToString(i, true));
1189  }
1190  }
1191  }
1192 }
1193 
1195 {
1196  const uint8_t ipprotos[] = { IPPROTO_TCP, IPPROTO_UDP };
1197  AppProto alprotos[g_alproto_max];
1198  const char *str = "app_layer.flow.";
1199  const char *estr = "app_layer.error.";
1200 
1203  if (unlikely(applayer_counter_names == NULL)) {
1204  FatalError("Unable to alloc applayer_counter_names.");
1205  }
1207  if (unlikely(applayer_counters == NULL)) {
1208  FatalError("Unable to alloc applayer_counters.");
1209  }
1210  /* We don't log stats counters if exception policy is `ignore`/`not set` */
1212  /* Register global counters for app layer error exception policy summary */
1213  const char *eps_default_str = "exception_policy.app_layer.error.";
1214  for (enum ExceptionPolicy i = EXCEPTION_POLICY_NOT_SET + 1; i < EXCEPTION_POLICY_MAX; i++) {
1215  if (IsAppLayerErrorExceptionPolicyStatsValid(i)) {
1216  snprintf(app_layer_error_eps_stats.eps_name[i],
1217  sizeof(app_layer_error_eps_stats.eps_name[i]), "%s%s", eps_default_str,
1218  ExceptionPolicyEnumToString(i, true));
1219  }
1220  }
1221  }
1222 
1224 
1225  for (uint8_t p = 0; p < FLOW_PROTO_APPLAYER_MAX; p++) {
1226  const uint8_t ipproto = ipprotos[p];
1227  const uint8_t ipproto_map = FlowGetProtoMapping(ipproto);
1228  const char *ipproto_suffix = (ipproto == IPPROTO_TCP) ? "_tcp" : "_udp";
1229  uint8_t ipprotos_all[256 / 8];
1230 
1231  for (AppProto alproto = 0; alproto < g_alproto_max; alproto++) {
1232  if (alprotos[alproto] == 1) {
1233  const char *tx_str = "app_layer.tx.";
1234  const char *alproto_str = AppLayerGetProtoName(alproto);
1235 
1236  memset(ipprotos_all, 0, sizeof(ipprotos_all));
1237  AppLayerProtoDetectSupportedIpprotos(alproto, ipprotos_all);
1238  if ((ipprotos_all[IPPROTO_TCP / 8] & (1 << (IPPROTO_TCP % 8))) &&
1239  (ipprotos_all[IPPROTO_UDP / 8] & (1 << (IPPROTO_UDP % 8)))) {
1240  snprintf(applayer_counter_names[alproto][ipproto_map].name,
1241  sizeof(applayer_counter_names[alproto][ipproto_map].name), "%s%s%s",
1242  str, alproto_str, ipproto_suffix);
1243  snprintf(applayer_counter_names[alproto][ipproto_map].tx_name,
1244  sizeof(applayer_counter_names[alproto][ipproto_map].tx_name), "%s%s%s",
1245  tx_str, alproto_str, ipproto_suffix);
1246 
1247  if (ipproto == IPPROTO_TCP) {
1248  snprintf(applayer_counter_names[alproto][ipproto_map].gap_error,
1249  sizeof(applayer_counter_names[alproto][ipproto_map].gap_error),
1250  "%s%s%s.gap", estr, alproto_str, ipproto_suffix);
1251  }
1252  snprintf(applayer_counter_names[alproto][ipproto_map].alloc_error,
1253  sizeof(applayer_counter_names[alproto][ipproto_map].alloc_error),
1254  "%s%s%s.alloc", estr, alproto_str, ipproto_suffix);
1255  snprintf(applayer_counter_names[alproto][ipproto_map].parser_error,
1256  sizeof(applayer_counter_names[alproto][ipproto_map].parser_error),
1257  "%s%s%s.parser", estr, alproto_str, ipproto_suffix);
1258  snprintf(applayer_counter_names[alproto][ipproto_map].internal_error,
1259  sizeof(applayer_counter_names[alproto][ipproto_map].internal_error),
1260  "%s%s%s.internal", estr, alproto_str, ipproto_suffix);
1261 
1262  AppLayerSetupExceptionPolicyPerProtoCounters(
1263  ipproto_map, alproto, alproto_str, ipproto_suffix);
1264  } else {
1265  snprintf(applayer_counter_names[alproto][ipproto_map].name,
1266  sizeof(applayer_counter_names[alproto][ipproto_map].name), "%s%s", str,
1267  alproto_str);
1268  snprintf(applayer_counter_names[alproto][ipproto_map].tx_name,
1269  sizeof(applayer_counter_names[alproto][ipproto_map].tx_name), "%s%s",
1270  tx_str, alproto_str);
1271 
1272  if (ipproto == IPPROTO_TCP) {
1273  snprintf(applayer_counter_names[alproto][ipproto_map].gap_error,
1274  sizeof(applayer_counter_names[alproto][ipproto_map].gap_error),
1275  "%s%s.gap", estr, alproto_str);
1276  }
1277  snprintf(applayer_counter_names[alproto][ipproto_map].alloc_error,
1278  sizeof(applayer_counter_names[alproto][ipproto_map].alloc_error),
1279  "%s%s.alloc", estr, alproto_str);
1280  snprintf(applayer_counter_names[alproto][ipproto_map].parser_error,
1281  sizeof(applayer_counter_names[alproto][ipproto_map].parser_error),
1282  "%s%s.parser", estr, alproto_str);
1283  snprintf(applayer_counter_names[alproto][ipproto_map].internal_error,
1284  sizeof(applayer_counter_names[alproto][ipproto_map].internal_error),
1285  "%s%s.internal", estr, alproto_str);
1286  AppLayerSetupExceptionPolicyPerProtoCounters(
1287  ipproto_map, alproto, alproto_str, "");
1288  }
1289  } else if (alproto == ALPROTO_FAILED) {
1290  snprintf(applayer_counter_names[alproto][ipproto_map].name,
1291  sizeof(applayer_counter_names[alproto][ipproto_map].name), "%s%s%s", str,
1292  "failed", ipproto_suffix);
1293  if (ipproto == IPPROTO_TCP) {
1294  snprintf(applayer_counter_names[alproto][ipproto_map].gap_error,
1295  sizeof(applayer_counter_names[alproto][ipproto_map].gap_error),
1296  "%sfailed%s.gap", estr, ipproto_suffix);
1297  }
1298  }
1299  }
1300  }
1301 }
1302 
1304 {
1305  const uint8_t ipprotos[] = { IPPROTO_TCP, IPPROTO_UDP };
1306  AppProto alprotos[g_alproto_max];
1308 
1309  /* We don't log stats counters if exception policy is `ignore`/`not set` */
1311  /* Register global counters for app layer error exception policy summary */
1312  for (enum ExceptionPolicy i = EXCEPTION_POLICY_NOT_SET + 1; i < EXCEPTION_POLICY_MAX; i++) {
1313  if (IsAppLayerErrorExceptionPolicyStatsValid(i)) {
1316  }
1317  }
1318  }
1319 
1320  for (uint8_t p = 0; p < FLOW_PROTO_APPLAYER_MAX; p++) {
1321  const uint8_t ipproto = ipprotos[p];
1322  const uint8_t ipproto_map = FlowGetProtoMapping(ipproto);
1323 
1324  for (AppProto alproto = 0; alproto < g_alproto_max; alproto++) {
1325  if (alprotos[alproto] == 1) {
1326  applayer_counters[alproto][ipproto_map].counter_id =
1327  StatsRegisterCounter(applayer_counter_names[alproto][ipproto_map].name, tv);
1328 
1329  applayer_counters[alproto][ipproto_map].counter_tx_id = StatsRegisterCounter(
1330  applayer_counter_names[alproto][ipproto_map].tx_name, tv);
1331 
1332  if (ipproto == IPPROTO_TCP) {
1333  applayer_counters[alproto][ipproto_map].gap_error_id = StatsRegisterCounter(
1334  applayer_counter_names[alproto][ipproto_map].gap_error, tv);
1335  }
1336  applayer_counters[alproto][ipproto_map].alloc_error_id = StatsRegisterCounter(
1337  applayer_counter_names[alproto][ipproto_map].alloc_error, tv);
1338  applayer_counters[alproto][ipproto_map].parser_error_id = StatsRegisterCounter(
1339  applayer_counter_names[alproto][ipproto_map].parser_error, tv);
1341  applayer_counter_names[alproto][ipproto_map].internal_error, tv);
1342  /* We don't log stats counters if exception policy is `ignore`/`not set` */
1345  for (enum ExceptionPolicy i = EXCEPTION_POLICY_NOT_SET + 1;
1346  i < EXCEPTION_POLICY_MAX; i++) {
1347  if (IsAppLayerErrorExceptionPolicyStatsValid(i)) {
1348  applayer_counters[alproto][ipproto_map]
1350  applayer_counter_names[alproto][ipproto_map].eps_name[i], tv);
1351  }
1352  }
1353  }
1354  } else if (alproto == ALPROTO_FAILED) {
1355  applayer_counters[alproto][ipproto_map].counter_id =
1356  StatsRegisterCounter(applayer_counter_names[alproto][ipproto_map].name, tv);
1357 
1358  if (ipproto == IPPROTO_TCP) {
1359  applayer_counters[alproto][ipproto_map].gap_error_id = StatsRegisterCounter(
1360  applayer_counter_names[alproto][ipproto_map].gap_error, tv);
1361  }
1362  }
1363  }
1364  }
1365 }
1366 
1368 {
1371 }
1372 
1373 /***** Unittests *****/
1374 
1375 #ifdef UNITTESTS
1376 #include "pkt-var.h"
1377 #include "stream-tcp-util.h"
1378 #include "stream.h"
1379 #include "util-unittest.h"
1380 
1381 #define TEST_START \
1382  Packet *p = PacketGetFromAlloc(); \
1383  FAIL_IF_NULL(p); \
1384  Flow f; \
1385  ThreadVars tv; \
1386  StreamTcpThread *stt = NULL; \
1387  TCPHdr tcph; \
1388  PacketQueueNoLock pq; \
1389  memset(&pq, 0, sizeof(PacketQueueNoLock)); \
1390  memset(&f, 0, sizeof(Flow)); \
1391  memset(&tv, 0, sizeof(ThreadVars)); \
1392  memset(&tcph, 0, sizeof(TCPHdr)); \
1393  \
1394  FLOW_INITIALIZE(&f); \
1395  f.flags = FLOW_IPV4; \
1396  f.proto = IPPROTO_TCP; \
1397  p->flow = &f; \
1398  PacketSetTCP(p, (uint8_t *)&tcph); \
1399  \
1400  StreamTcpInitConfig(true); \
1401  IPPairInitConfig(true); \
1402  StreamTcpThreadInit(&tv, NULL, (void **)&stt); \
1403  \
1404  /* handshake */ \
1405  tcph.th_win = htons(5480); \
1406  tcph.th_flags = TH_SYN; \
1407  p->flowflags = FLOW_PKT_TOSERVER; \
1408  p->payload_len = 0; \
1409  p->payload = NULL; \
1410  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1); \
1411  TcpSession *ssn = (TcpSession *)f.protoctx; \
1412  \
1413  FAIL_IF(StreamTcpIsSetStreamFlagAppProtoDetectionCompleted(&ssn->server)); \
1414  FAIL_IF(StreamTcpIsSetStreamFlagAppProtoDetectionCompleted(&ssn->client)); \
1415  FAIL_IF(f.alproto != ALPROTO_UNKNOWN); \
1416  FAIL_IF(f.alproto_ts != ALPROTO_UNKNOWN); \
1417  FAIL_IF(f.alproto_tc != ALPROTO_UNKNOWN); \
1418  FAIL_IF(ssn->flags &STREAMTCP_FLAG_APP_LAYER_DISABLED); \
1419  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER)); \
1420  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER)); \
1421  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT)); \
1422  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT)); \
1423  FAIL_IF(ssn->data_first_seen_dir != 0); \
1424  \
1425  /* handshake */ \
1426  tcph.th_ack = htonl(1); \
1427  tcph.th_flags = TH_SYN | TH_ACK; \
1428  p->flowflags = FLOW_PKT_TOCLIENT; \
1429  p->payload_len = 0; \
1430  p->payload = NULL; \
1431  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1); \
1432  FAIL_IF(StreamTcpIsSetStreamFlagAppProtoDetectionCompleted(&ssn->server)); \
1433  FAIL_IF(StreamTcpIsSetStreamFlagAppProtoDetectionCompleted(&ssn->client)); \
1434  FAIL_IF(f.alproto != ALPROTO_UNKNOWN); \
1435  FAIL_IF(f.alproto_ts != ALPROTO_UNKNOWN); \
1436  FAIL_IF(f.alproto_tc != ALPROTO_UNKNOWN); \
1437  FAIL_IF(ssn->flags &STREAMTCP_FLAG_APP_LAYER_DISABLED); \
1438  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER)); \
1439  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER)); \
1440  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT)); \
1441  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT)); \
1442  FAIL_IF(ssn->data_first_seen_dir != 0); \
1443  \
1444  /* handshake */ \
1445  tcph.th_ack = htonl(1); \
1446  tcph.th_seq = htonl(1); \
1447  tcph.th_flags = TH_ACK; \
1448  p->flowflags = FLOW_PKT_TOSERVER; \
1449  p->payload_len = 0; \
1450  p->payload = NULL; \
1451  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1); \
1452  FAIL_IF(StreamTcpIsSetStreamFlagAppProtoDetectionCompleted(&ssn->server)); \
1453  FAIL_IF(StreamTcpIsSetStreamFlagAppProtoDetectionCompleted(&ssn->client)); \
1454  FAIL_IF(f.alproto != ALPROTO_UNKNOWN); \
1455  FAIL_IF(f.alproto_ts != ALPROTO_UNKNOWN); \
1456  FAIL_IF(f.alproto_tc != ALPROTO_UNKNOWN); \
1457  FAIL_IF(ssn->flags &STREAMTCP_FLAG_APP_LAYER_DISABLED); \
1458  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER)); \
1459  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER)); \
1460  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT)); \
1461  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT)); \
1462  FAIL_IF(ssn->data_first_seen_dir != 0);
1463 #define TEST_END \
1464  StreamTcpSessionClear(p->flow->protoctx); \
1465  StreamTcpThreadDeinit(&tv, (void *)stt); \
1466  StreamTcpFreeConfig(true); \
1467  PacketFree(p); \
1468  FLOW_DESTROY(&f); \
1469  IPPairShutdown(); \
1470  StatsThreadCleanup(&tv);
1471 
1472 /**
1473  * \test GET -> HTTP/1.1
1474  */
1475 static int AppLayerTest01(void)
1476 {
1477  TEST_START;
1478 
1479  /* full request */
1480  uint8_t request[] = {
1481  0x47, 0x45, 0x54, 0x20, 0x2f, 0x69, 0x6e, 0x64,
1482  0x65, 0x78, 0x2e, 0x68, 0x74, 0x6d, 0x6c, 0x20,
1483  0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x30,
1484  0x0d, 0x0a, 0x48, 0x6f, 0x73, 0x74, 0x3a, 0x20,
1485  0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x68, 0x6f, 0x73,
1486  0x74, 0x0d, 0x0a, 0x55, 0x73, 0x65, 0x72, 0x2d,
1487  0x41, 0x67, 0x65, 0x6e, 0x74, 0x3a, 0x20, 0x41,
1488  0x70, 0x61, 0x63, 0x68, 0x65, 0x42, 0x65, 0x6e,
1489  0x63, 0x68, 0x2f, 0x32, 0x2e, 0x33, 0x0d, 0x0a,
1490  0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x3a, 0x20,
1491  0x2a, 0x2f, 0x2a, 0x0d, 0x0a, 0x0d, 0x0a };
1492  tcph.th_ack = htonl(1);
1493  tcph.th_seq = htonl(1);
1494  tcph.th_flags = TH_PUSH | TH_ACK;
1496  p->payload_len = sizeof(request);
1497  p->payload = request;
1498  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1505  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1506  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1507  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1508  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1509  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
1510 
1511  /* full response - request ack */
1512  uint8_t response[] = {
1513  0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x31,
1514  0x20, 0x32, 0x30, 0x30, 0x20, 0x4f, 0x4b, 0x0d,
1515  0x0a, 0x44, 0x61, 0x74, 0x65, 0x3a, 0x20, 0x46,
1516  0x72, 0x69, 0x2c, 0x20, 0x32, 0x33, 0x20, 0x53,
1517  0x65, 0x70, 0x20, 0x32, 0x30, 0x31, 0x31, 0x20,
1518  0x30, 0x36, 0x3a, 0x32, 0x39, 0x3a, 0x33, 0x39,
1519  0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a, 0x53, 0x65,
1520  0x72, 0x76, 0x65, 0x72, 0x3a, 0x20, 0x41, 0x70,
1521  0x61, 0x63, 0x68, 0x65, 0x2f, 0x32, 0x2e, 0x32,
1522  0x2e, 0x31, 0x35, 0x20, 0x28, 0x55, 0x6e, 0x69,
1523  0x78, 0x29, 0x20, 0x44, 0x41, 0x56, 0x2f, 0x32,
1524  0x0d, 0x0a, 0x4c, 0x61, 0x73, 0x74, 0x2d, 0x4d,
1525  0x6f, 0x64, 0x69, 0x66, 0x69, 0x65, 0x64, 0x3a,
1526  0x20, 0x54, 0x68, 0x75, 0x2c, 0x20, 0x30, 0x34,
1527  0x20, 0x4e, 0x6f, 0x76, 0x20, 0x32, 0x30, 0x31,
1528  0x30, 0x20, 0x31, 0x35, 0x3a, 0x30, 0x34, 0x3a,
1529  0x34, 0x36, 0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a,
1530  0x45, 0x54, 0x61, 0x67, 0x3a, 0x20, 0x22, 0x61,
1531  0x62, 0x38, 0x39, 0x36, 0x35, 0x2d, 0x32, 0x63,
1532  0x2d, 0x34, 0x39, 0x34, 0x33, 0x62, 0x37, 0x61,
1533  0x37, 0x66, 0x37, 0x66, 0x38, 0x30, 0x22, 0x0d,
1534  0x0a, 0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x2d,
1535  0x52, 0x61, 0x6e, 0x67, 0x65, 0x73, 0x3a, 0x20,
1536  0x62, 0x79, 0x74, 0x65, 0x73, 0x0d, 0x0a, 0x43,
1537  0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x4c,
1538  0x65, 0x6e, 0x67, 0x74, 0x68, 0x3a, 0x20, 0x34,
1539  0x34, 0x0d, 0x0a, 0x43, 0x6f, 0x6e, 0x6e, 0x65,
1540  0x63, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0x63,
1541  0x6c, 0x6f, 0x73, 0x65, 0x0d, 0x0a, 0x43, 0x6f,
1542  0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x54, 0x79,
1543  0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74,
1544  0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x0d, 0x0a, 0x58,
1545  0x2d, 0x50, 0x61, 0x64, 0x3a, 0x20, 0x61, 0x76,
1546  0x6f, 0x69, 0x64, 0x20, 0x62, 0x72, 0x6f, 0x77,
1547  0x73, 0x65, 0x72, 0x20, 0x62, 0x75, 0x67, 0x0d,
1548  0x0a, 0x0d, 0x0a, 0x3c, 0x68, 0x74, 0x6d, 0x6c,
1549  0x3e, 0x3c, 0x62, 0x6f, 0x64, 0x79, 0x3e, 0x3c,
1550  0x68, 0x31, 0x3e, 0x49, 0x74, 0x20, 0x77, 0x6f,
1551  0x72, 0x6b, 0x73, 0x21, 0x3c, 0x2f, 0x68, 0x31,
1552  0x3e, 0x3c, 0x2f, 0x62, 0x6f, 0x64, 0x79, 0x3e,
1553  0x3c, 0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x3e };
1554  tcph.th_ack = htonl(88);
1555  tcph.th_seq = htonl(1);
1556  tcph.th_flags = TH_PUSH | TH_ACK;
1558  p->payload_len = sizeof(response);
1559  p->payload = response;
1560  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1567  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1568  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1569  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1570  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1572 
1573  /* response ack */
1574  tcph.th_ack = htonl(328);
1575  tcph.th_seq = htonl(88);
1576  tcph.th_flags = TH_ACK;
1578  p->payload_len = 0;
1579  p->payload = NULL;
1580  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1587  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1588  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1589  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1590  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1592 
1593  TEST_END;
1594  PASS;
1595 }
1596 
1597 /**
1598  * \test GE -> T -> HTTP/1.1
1599  */
1600 static int AppLayerTest02(void)
1601 {
1602  TEST_START;
1603 
1604  /* partial request */
1605  uint8_t request1[] = { 0x47, 0x45, };
1606  tcph.th_ack = htonl(1);
1607  tcph.th_seq = htonl(1);
1608  tcph.th_flags = TH_PUSH | TH_ACK;
1610  p->payload_len = sizeof(request1);
1611  p->payload = request1;
1612  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1619  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1620  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1621  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1622  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1623  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
1624 
1625  /* response ack against partial request */
1626  tcph.th_ack = htonl(3);
1627  tcph.th_seq = htonl(1);
1628  tcph.th_flags = TH_ACK;
1630  p->payload_len = 0;
1631  p->payload = NULL;
1632  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1639  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1640  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1641  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1642  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1643  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
1644 
1645  /* complete partial request */
1646  uint8_t request2[] = {
1647  0x54, 0x20, 0x2f, 0x69, 0x6e, 0x64,
1648  0x65, 0x78, 0x2e, 0x68, 0x74, 0x6d, 0x6c, 0x20,
1649  0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x30,
1650  0x0d, 0x0a, 0x48, 0x6f, 0x73, 0x74, 0x3a, 0x20,
1651  0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x68, 0x6f, 0x73,
1652  0x74, 0x0d, 0x0a, 0x55, 0x73, 0x65, 0x72, 0x2d,
1653  0x41, 0x67, 0x65, 0x6e, 0x74, 0x3a, 0x20, 0x41,
1654  0x70, 0x61, 0x63, 0x68, 0x65, 0x42, 0x65, 0x6e,
1655  0x63, 0x68, 0x2f, 0x32, 0x2e, 0x33, 0x0d, 0x0a,
1656  0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x3a, 0x20,
1657  0x2a, 0x2f, 0x2a, 0x0d, 0x0a, 0x0d, 0x0a };
1658  tcph.th_ack = htonl(1);
1659  tcph.th_seq = htonl(3);
1660  tcph.th_flags = TH_PUSH | TH_ACK;
1662  p->payload_len = sizeof(request2);
1663  p->payload = request2;
1664  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1671  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1672  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1673  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1674  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1675  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
1676 
1677  /* response - request ack */
1678  uint8_t response[] = {
1679  0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x31,
1680  0x20, 0x32, 0x30, 0x30, 0x20, 0x4f, 0x4b, 0x0d,
1681  0x0a, 0x44, 0x61, 0x74, 0x65, 0x3a, 0x20, 0x46,
1682  0x72, 0x69, 0x2c, 0x20, 0x32, 0x33, 0x20, 0x53,
1683  0x65, 0x70, 0x20, 0x32, 0x30, 0x31, 0x31, 0x20,
1684  0x30, 0x36, 0x3a, 0x32, 0x39, 0x3a, 0x33, 0x39,
1685  0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a, 0x53, 0x65,
1686  0x72, 0x76, 0x65, 0x72, 0x3a, 0x20, 0x41, 0x70,
1687  0x61, 0x63, 0x68, 0x65, 0x2f, 0x32, 0x2e, 0x32,
1688  0x2e, 0x31, 0x35, 0x20, 0x28, 0x55, 0x6e, 0x69,
1689  0x78, 0x29, 0x20, 0x44, 0x41, 0x56, 0x2f, 0x32,
1690  0x0d, 0x0a, 0x4c, 0x61, 0x73, 0x74, 0x2d, 0x4d,
1691  0x6f, 0x64, 0x69, 0x66, 0x69, 0x65, 0x64, 0x3a,
1692  0x20, 0x54, 0x68, 0x75, 0x2c, 0x20, 0x30, 0x34,
1693  0x20, 0x4e, 0x6f, 0x76, 0x20, 0x32, 0x30, 0x31,
1694  0x30, 0x20, 0x31, 0x35, 0x3a, 0x30, 0x34, 0x3a,
1695  0x34, 0x36, 0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a,
1696  0x45, 0x54, 0x61, 0x67, 0x3a, 0x20, 0x22, 0x61,
1697  0x62, 0x38, 0x39, 0x36, 0x35, 0x2d, 0x32, 0x63,
1698  0x2d, 0x34, 0x39, 0x34, 0x33, 0x62, 0x37, 0x61,
1699  0x37, 0x66, 0x37, 0x66, 0x38, 0x30, 0x22, 0x0d,
1700  0x0a, 0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x2d,
1701  0x52, 0x61, 0x6e, 0x67, 0x65, 0x73, 0x3a, 0x20,
1702  0x62, 0x79, 0x74, 0x65, 0x73, 0x0d, 0x0a, 0x43,
1703  0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x4c,
1704  0x65, 0x6e, 0x67, 0x74, 0x68, 0x3a, 0x20, 0x34,
1705  0x34, 0x0d, 0x0a, 0x43, 0x6f, 0x6e, 0x6e, 0x65,
1706  0x63, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0x63,
1707  0x6c, 0x6f, 0x73, 0x65, 0x0d, 0x0a, 0x43, 0x6f,
1708  0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x54, 0x79,
1709  0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74,
1710  0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x0d, 0x0a, 0x58,
1711  0x2d, 0x50, 0x61, 0x64, 0x3a, 0x20, 0x61, 0x76,
1712  0x6f, 0x69, 0x64, 0x20, 0x62, 0x72, 0x6f, 0x77,
1713  0x73, 0x65, 0x72, 0x20, 0x62, 0x75, 0x67, 0x0d,
1714  0x0a, 0x0d, 0x0a, 0x3c, 0x68, 0x74, 0x6d, 0x6c,
1715  0x3e, 0x3c, 0x62, 0x6f, 0x64, 0x79, 0x3e, 0x3c,
1716  0x68, 0x31, 0x3e, 0x49, 0x74, 0x20, 0x77, 0x6f,
1717  0x72, 0x6b, 0x73, 0x21, 0x3c, 0x2f, 0x68, 0x31,
1718  0x3e, 0x3c, 0x2f, 0x62, 0x6f, 0x64, 0x79, 0x3e,
1719  0x3c, 0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x3e };
1720  tcph.th_ack = htonl(88);
1721  tcph.th_seq = htonl(1);
1722  tcph.th_flags = TH_PUSH | TH_ACK;
1724  p->payload_len = sizeof(response);
1725  p->payload = response;
1726  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1733  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1734  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1735  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1736  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1738 
1739  /* response ack */
1740  tcph.th_ack = htonl(328);
1741  tcph.th_seq = htonl(88);
1742  tcph.th_flags = TH_ACK;
1744  p->payload_len = 0;
1745  p->payload = NULL;
1746  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1753  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1754  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1755  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1756  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1758 
1759  TEST_END;
1760  PASS;
1761 }
1762 
1763 /**
1764  * \test GET -> RUBBISH(PM AND PP DONE IN ONE GO)
1765  */
1766 static int AppLayerTest03(void)
1767 {
1768  TEST_START;
1769 
1770  /* request */
1771  uint8_t request[] = {
1772  0x47, 0x45, 0x54, 0x20, 0x2f, 0x69, 0x6e, 0x64,
1773  0x65, 0x78, 0x2e, 0x68, 0x74, 0x6d, 0x6c, 0x20,
1774  0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x30,
1775  0x0d, 0x0a, 0x48, 0x6f, 0x73, 0x74, 0x3a, 0x20,
1776  0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x68, 0x6f, 0x73,
1777  0x74, 0x0d, 0x0a, 0x55, 0x73, 0x65, 0x72, 0x2d,
1778  0x41, 0x67, 0x65, 0x6e, 0x74, 0x3a, 0x20, 0x41,
1779  0x70, 0x61, 0x63, 0x68, 0x65, 0x42, 0x65, 0x6e,
1780  0x63, 0x68, 0x2f, 0x32, 0x2e, 0x33, 0x0d, 0x0a,
1781  0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x3a, 0x20,
1782  0x2a, 0x2f, 0x2a, 0x0d, 0x0a, 0x0d, 0x0a };
1783  tcph.th_ack = htonl(1);
1784  tcph.th_seq = htonl(1);
1785  tcph.th_flags = TH_PUSH | TH_ACK;
1787  p->payload_len = sizeof(request);
1788  p->payload = request;
1789  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1796  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1797  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1798  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1799  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1800  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
1801 
1802  /* rubbish response */
1803  uint8_t response[] = {
1804  0x58, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x31,
1805  0x20, 0x32, 0x30, 0x30, 0x20, 0x4f, 0x4b, 0x0d,
1806  0x0a, 0x44, 0x61, 0x74, 0x65, 0x3a, 0x20, 0x46,
1807  0x72, 0x69, 0x2c, 0x20, 0x32, 0x33, 0x20, 0x53,
1808  0x65, 0x70, 0x20, 0x32, 0x30, 0x31, 0x31, 0x20,
1809  0x30, 0x36, 0x3a, 0x32, 0x39, 0x3a, 0x33, 0x39,
1810  0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a, 0x53, 0x65,
1811  0x72, 0x76, 0x65, 0x72, 0x3a, 0x20, 0x41, 0x70,
1812  0x61, 0x63, 0x68, 0x65, 0x2f, 0x32, 0x2e, 0x32,
1813  0x2e, 0x31, 0x35, 0x20, 0x28, 0x55, 0x6e, 0x69,
1814  0x78, 0x29, 0x20, 0x44, 0x41, 0x56, 0x2f, 0x32,
1815  0x0d, 0x0a, 0x4c, 0x61, 0x73, 0x74, 0x2d, 0x4d,
1816  0x6f, 0x64, 0x69, 0x66, 0x69, 0x65, 0x64, 0x3a,
1817  0x20, 0x54, 0x68, 0x75, 0x2c, 0x20, 0x30, 0x34,
1818  0x20, 0x4e, 0x6f, 0x76, 0x20, 0x32, 0x30, 0x31,
1819  0x30, 0x20, 0x31, 0x35, 0x3a, 0x30, 0x34, 0x3a,
1820  0x34, 0x36, 0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a,
1821  0x45, 0x54, 0x61, 0x67, 0x3a, 0x20, 0x22, 0x61,
1822  0x62, 0x38, 0x39, 0x36, 0x35, 0x2d, 0x32, 0x63,
1823  0x2d, 0x34, 0x39, 0x34, 0x33, 0x62, 0x37, 0x61,
1824  0x37, 0x66, 0x37, 0x66, 0x38, 0x30, 0x22, 0x0d,
1825  0x0a, 0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x2d,
1826  0x52, 0x61, 0x6e, 0x67, 0x65, 0x73, 0x3a, 0x20,
1827  0x62, 0x79, 0x74, 0x65, 0x73, 0x0d, 0x0a, 0x43,
1828  0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x4c,
1829  0x65, 0x6e, 0x67, 0x74, 0x68, 0x3a, 0x20, 0x34,
1830  0x34, 0x0d, 0x0a, 0x43, 0x6f, 0x6e, 0x6e, 0x65,
1831  0x63, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0x63,
1832  0x6c, 0x6f, 0x73, 0x65, 0x0d, 0x0a, 0x43, 0x6f,
1833  0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x54, 0x79,
1834  0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74,
1835  0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x0d, 0x0a, 0x58,
1836  0x2d, 0x50, 0x61, 0x64, 0x3a, 0x20, 0x61, 0x76,
1837  0x6f, 0x69, 0x64, 0x20, 0x62, 0x72, 0x6f, 0x77,
1838  0x73, 0x65, 0x72, 0x20, 0x62, 0x75, 0x67, 0x0d,
1839  0x0a, 0x0d, 0x0a, 0x3c, 0x68, 0x74, 0x6d, 0x6c,
1840  0x3e, 0x3c, 0x62, 0x6f, 0x64, 0x79, 0x3e, 0x3c,
1841  0x68, 0x31, 0x3e, 0x49, 0x74, 0x20, 0x77, 0x6f,
1842  0x72, 0x6b, 0x73, 0x21, 0x3c, 0x2f, 0x68, 0x31,
1843  0x3e, 0x3c, 0x2f, 0x62, 0x6f, 0x64, 0x79, 0x3e,
1844  0x3c, 0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x3e };
1845  tcph.th_ack = htonl(88);
1846  tcph.th_seq = htonl(1);
1847  tcph.th_flags = TH_PUSH | TH_ACK;
1849  p->payload_len = sizeof(response);
1850  p->payload = response;
1851  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1858  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1859  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1860  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1861  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1863 
1864  /* response ack */
1865  tcph.th_ack = htonl(328);
1866  tcph.th_seq = htonl(88);
1867  tcph.th_flags = TH_ACK;
1869  p->payload_len = 0;
1870  p->payload = NULL;
1871  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1878  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1879  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1880  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1881  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1883 
1884  TEST_END;
1885  PASS;
1886 }
1887 
1888 /**
1889  * \test GE -> RUBBISH(TC - PM AND PP NOT DONE) -> RUBBISH(TC - PM AND PP DONE).
1890  */
1891 static int AppLayerTest04(void)
1892 {
1893  TEST_START;
1894 
1895  /* request */
1896  uint8_t request[] = {
1897  0x47, 0x45, 0x54, 0x20, 0x2f, 0x69, 0x6e, 0x64,
1898  0x65, 0x78, 0x2e, 0x68, 0x74, 0x6d, 0x6c, 0x20,
1899  0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x30,
1900  0x0d, 0x0a, 0x48, 0x6f, 0x73, 0x74, 0x3a, 0x20,
1901  0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x68, 0x6f, 0x73,
1902  0x74, 0x0d, 0x0a, 0x55, 0x73, 0x65, 0x72, 0x2d,
1903  0x41, 0x67, 0x65, 0x6e, 0x74, 0x3a, 0x20, 0x41,
1904  0x70, 0x61, 0x63, 0x68, 0x65, 0x42, 0x65, 0x6e,
1905  0x63, 0x68, 0x2f, 0x32, 0x2e, 0x33, 0x0d, 0x0a,
1906  0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x3a, 0x20,
1907  0x2a, 0x2f, 0x2a, 0x0d, 0x0a, 0x0d, 0x0a };
1908  PrintRawDataFp(stdout, request, sizeof(request));
1909  tcph.th_ack = htonl(1);
1910  tcph.th_seq = htonl(1);
1911  tcph.th_flags = TH_PUSH | TH_ACK;
1913  p->payload_len = sizeof(request);
1914  p->payload = request;
1915  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1922  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1923  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1924  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1925  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1926  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER); // TOSERVER data now seen
1927 
1928  /* partial response */
1929  uint8_t response1[] = { 0x58, 0x54, 0x54, 0x50, };
1930  PrintRawDataFp(stdout, response1, sizeof(response1));
1931  tcph.th_ack = htonl(88);
1932  tcph.th_seq = htonl(1);
1933  tcph.th_flags = TH_PUSH | TH_ACK;
1935  p->payload_len = sizeof(response1);
1936  p->payload = response1;
1937  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1940  FAIL_IF(f.alproto != ALPROTO_HTTP1); // http based on ts
1941  FAIL_IF(f.alproto_ts != ALPROTO_HTTP1); // ts complete
1944  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1945  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1946  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1947  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
1948  FAIL_IF(ssn->data_first_seen_dir != APP_LAYER_DATA_ALREADY_SENT_TO_APP_LAYER); // first data sent to applayer
1949 
1950  /* partial response ack */
1951  tcph.th_ack = htonl(5);
1952  tcph.th_seq = htonl(88);
1953  tcph.th_flags = TH_ACK;
1955  p->payload_len = 0;
1956  p->payload = NULL;
1957  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
1960  FAIL_IF(f.alproto != ALPROTO_HTTP1); // http based on ts
1961  FAIL_IF(f.alproto_ts != ALPROTO_HTTP1); // ts complete
1964  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
1965  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
1966  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
1967  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT)); // to client pp got nothing
1968  FAIL_IF(ssn->data_first_seen_dir != APP_LAYER_DATA_ALREADY_SENT_TO_APP_LAYER); // first data sent to applayer
1969 
1970  /* remaining response */
1971  uint8_t response2[] = {
1972  0x2f, 0x31, 0x2e, 0x31,
1973  0x20, 0x32, 0x30, 0x30, 0x20, 0x4f, 0x4b, 0x0d,
1974  0x0a, 0x44, 0x61, 0x74, 0x65, 0x3a, 0x20, 0x46,
1975  0x72, 0x69, 0x2c, 0x20, 0x32, 0x33, 0x20, 0x53,
1976  0x65, 0x70, 0x20, 0x32, 0x30, 0x31, 0x31, 0x20,
1977  0x30, 0x36, 0x3a, 0x32, 0x39, 0x3a, 0x33, 0x39,
1978  0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a, 0x53, 0x65,
1979  0x72, 0x76, 0x65, 0x72, 0x3a, 0x20, 0x41, 0x70,
1980  0x61, 0x63, 0x68, 0x65, 0x2f, 0x32, 0x2e, 0x32,
1981  0x2e, 0x31, 0x35, 0x20, 0x28, 0x55, 0x6e, 0x69,
1982  0x78, 0x29, 0x20, 0x44, 0x41, 0x56, 0x2f, 0x32,
1983  0x0d, 0x0a, 0x4c, 0x61, 0x73, 0x74, 0x2d, 0x4d,
1984  0x6f, 0x64, 0x69, 0x66, 0x69, 0x65, 0x64, 0x3a,
1985  0x20, 0x54, 0x68, 0x75, 0x2c, 0x20, 0x30, 0x34,
1986  0x20, 0x4e, 0x6f, 0x76, 0x20, 0x32, 0x30, 0x31,
1987  0x30, 0x20, 0x31, 0x35, 0x3a, 0x30, 0x34, 0x3a,
1988  0x34, 0x36, 0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a,
1989  0x45, 0x54, 0x61, 0x67, 0x3a, 0x20, 0x22, 0x61,
1990  0x62, 0x38, 0x39, 0x36, 0x35, 0x2d, 0x32, 0x63,
1991  0x2d, 0x34, 0x39, 0x34, 0x33, 0x62, 0x37, 0x61,
1992  0x37, 0x66, 0x37, 0x66, 0x38, 0x30, 0x22, 0x0d,
1993  0x0a, 0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x2d,
1994  0x52, 0x61, 0x6e, 0x67, 0x65, 0x73, 0x3a, 0x20,
1995  0x62, 0x79, 0x74, 0x65, 0x73, 0x0d, 0x0a, 0x43,
1996  0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x4c,
1997  0x65, 0x6e, 0x67, 0x74, 0x68, 0x3a, 0x20, 0x34,
1998  0x34, 0x0d, 0x0a, 0x43, 0x6f, 0x6e, 0x6e, 0x65,
1999  0x63, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0x63,
2000  0x6c, 0x6f, 0x73, 0x65, 0x0d, 0x0a, 0x43, 0x6f,
2001  0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x54, 0x79,
2002  0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74,
2003  0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x0d, 0x0a, 0x58,
2004  0x2d, 0x50, 0x61, 0x64, 0x3a, 0x20, 0x61, 0x76,
2005  0x6f, 0x69, 0x64, 0x20, 0x62, 0x72, 0x6f, 0x77,
2006  0x73, 0x65, 0x72, 0x20, 0x62, 0x75, 0x67, 0x0d,
2007  0x0a, 0x0d, 0x0a, 0x3c, 0x68, 0x74, 0x6d, 0x6c,
2008  0x3e, 0x3c, 0x62, 0x6f, 0x64, 0x79, 0x3e, 0x3c,
2009  0x68, 0x31, 0x3e, 0x49, 0x74, 0x20, 0x77, 0x6f,
2010  0x72, 0x6b, 0x73, 0x21, 0x3c, 0x2f, 0x68, 0x31,
2011  0x3e, 0x3c, 0x2f, 0x62, 0x6f, 0x64, 0x79, 0x3e,
2012  0x3c, 0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x3e };
2013  PrintRawDataFp(stdout, response2, sizeof(response2));
2014  tcph.th_ack = htonl(88);
2015  tcph.th_seq = htonl(5);
2016  tcph.th_flags = TH_PUSH | TH_ACK;
2018  p->payload_len = sizeof(response2);
2019  p->payload = response2;
2020  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2023  FAIL_IF(f.alproto != ALPROTO_HTTP1); // http based on ts
2024  FAIL_IF(f.alproto_ts != ALPROTO_HTTP1); // ts complete
2027  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2028  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2029  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2030  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT)); // to client pp got nothing
2031  FAIL_IF(ssn->data_first_seen_dir != APP_LAYER_DATA_ALREADY_SENT_TO_APP_LAYER); // first data sent to applayer
2032 
2033  /* response ack */
2034  tcph.th_ack = htonl(328);
2035  tcph.th_seq = htonl(88);
2036  tcph.th_flags = TH_ACK;
2038  p->payload_len = 0;
2039  p->payload = NULL;
2040  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2041  FAIL_IF(!StreamTcpIsSetStreamFlagAppProtoDetectionCompleted(&ssn->server)); // toclient complete (failed)
2043  FAIL_IF(f.alproto != ALPROTO_HTTP1); // http based on ts
2044  FAIL_IF(f.alproto_ts != ALPROTO_HTTP1); // ts complete
2045  FAIL_IF(f.alproto_tc != ALPROTO_FAILED); // tc failed
2047  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2048  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2049  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2050  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT)); // to client pp got nothing
2051  FAIL_IF(ssn->data_first_seen_dir != APP_LAYER_DATA_ALREADY_SENT_TO_APP_LAYER); // first data sent to applayer
2052 
2053  TEST_END;
2054  PASS;
2055 }
2056 
2057 /**
2058  * \test RUBBISH -> HTTP/1.1
2059  */
2060 static int AppLayerTest05(void)
2061 {
2062  TEST_START;
2063 
2064  /* full request */
2065  uint8_t request[] = {
2066  0x48, 0x45, 0x54, 0x20, 0x2f, 0x69, 0x6e, 0x64,
2067  0x65, 0x78, 0x2e, 0x68, 0x74, 0x6d, 0x6c, 0x20,
2068  0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x30,
2069  0x0d, 0x0a, 0x48, 0x6f, 0x73, 0x74, 0x3a, 0x20,
2070  0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x68, 0x6f, 0x73,
2071  0x74, 0x0d, 0x0a, 0x55, 0x73, 0x65, 0x72, 0x2d,
2072  0x41, 0x67, 0x65, 0x6e, 0x74, 0x3a, 0x20, 0x41,
2073  0x70, 0x61, 0x63, 0x68, 0x65, 0x42, 0x65, 0x6e,
2074  0x63, 0x68, 0x2f, 0x32, 0x2e, 0x33, 0x0d, 0x0a,
2075  0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x3a, 0x20,
2076  0x2a, 0x2f, 0x2a, 0x0d, 0x0a, 0x0d, 0x0a };
2077  PrintRawDataFp(stdout, request, sizeof(request));
2078  tcph.th_ack = htonl(1);
2079  tcph.th_seq = htonl(1);
2080  tcph.th_flags = TH_PUSH | TH_ACK;
2082  p->payload_len = sizeof(request);
2083  p->payload = request;
2084  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2091  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2092  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2093  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2094  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2095  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2096 
2097  /* full response - request ack */
2098  uint8_t response[] = {
2099  0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x31,
2100  0x20, 0x32, 0x30, 0x30, 0x20, 0x4f, 0x4b, 0x0d,
2101  0x0a, 0x44, 0x61, 0x74, 0x65, 0x3a, 0x20, 0x46,
2102  0x72, 0x69, 0x2c, 0x20, 0x32, 0x33, 0x20, 0x53,
2103  0x65, 0x70, 0x20, 0x32, 0x30, 0x31, 0x31, 0x20,
2104  0x30, 0x36, 0x3a, 0x32, 0x39, 0x3a, 0x33, 0x39,
2105  0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a, 0x53, 0x65,
2106  0x72, 0x76, 0x65, 0x72, 0x3a, 0x20, 0x41, 0x70,
2107  0x61, 0x63, 0x68, 0x65, 0x2f, 0x32, 0x2e, 0x32,
2108  0x2e, 0x31, 0x35, 0x20, 0x28, 0x55, 0x6e, 0x69,
2109  0x78, 0x29, 0x20, 0x44, 0x41, 0x56, 0x2f, 0x32,
2110  0x0d, 0x0a, 0x4c, 0x61, 0x73, 0x74, 0x2d, 0x4d,
2111  0x6f, 0x64, 0x69, 0x66, 0x69, 0x65, 0x64, 0x3a,
2112  0x20, 0x54, 0x68, 0x75, 0x2c, 0x20, 0x30, 0x34,
2113  0x20, 0x4e, 0x6f, 0x76, 0x20, 0x32, 0x30, 0x31,
2114  0x30, 0x20, 0x31, 0x35, 0x3a, 0x30, 0x34, 0x3a,
2115  0x34, 0x36, 0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a,
2116  0x45, 0x54, 0x61, 0x67, 0x3a, 0x20, 0x22, 0x61,
2117  0x62, 0x38, 0x39, 0x36, 0x35, 0x2d, 0x32, 0x63,
2118  0x2d, 0x34, 0x39, 0x34, 0x33, 0x62, 0x37, 0x61,
2119  0x37, 0x66, 0x37, 0x66, 0x38, 0x30, 0x22, 0x0d,
2120  0x0a, 0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x2d,
2121  0x52, 0x61, 0x6e, 0x67, 0x65, 0x73, 0x3a, 0x20,
2122  0x62, 0x79, 0x74, 0x65, 0x73, 0x0d, 0x0a, 0x43,
2123  0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x4c,
2124  0x65, 0x6e, 0x67, 0x74, 0x68, 0x3a, 0x20, 0x34,
2125  0x34, 0x0d, 0x0a, 0x43, 0x6f, 0x6e, 0x6e, 0x65,
2126  0x63, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0x63,
2127  0x6c, 0x6f, 0x73, 0x65, 0x0d, 0x0a, 0x43, 0x6f,
2128  0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x54, 0x79,
2129  0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74,
2130  0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x0d, 0x0a, 0x58,
2131  0x2d, 0x50, 0x61, 0x64, 0x3a, 0x20, 0x61, 0x76,
2132  0x6f, 0x69, 0x64, 0x20, 0x62, 0x72, 0x6f, 0x77,
2133  0x73, 0x65, 0x72, 0x20, 0x62, 0x75, 0x67, 0x0d,
2134  0x0a, 0x0d, 0x0a, 0x3c, 0x68, 0x74, 0x6d, 0x6c,
2135  0x3e, 0x3c, 0x62, 0x6f, 0x64, 0x79, 0x3e, 0x3c,
2136  0x68, 0x31, 0x3e, 0x49, 0x74, 0x20, 0x77, 0x6f,
2137  0x72, 0x6b, 0x73, 0x21, 0x3c, 0x2f, 0x68, 0x31,
2138  0x3e, 0x3c, 0x2f, 0x62, 0x6f, 0x64, 0x79, 0x3e,
2139  0x3c, 0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x3e };
2140  PrintRawDataFp(stdout, response, sizeof(response));
2141  tcph.th_ack = htonl(88);
2142  tcph.th_seq = htonl(1);
2143  tcph.th_flags = TH_PUSH | TH_ACK;
2145  p->payload_len = sizeof(response);
2146  p->payload = response;
2147  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2154  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2155  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2156  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2157  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2158  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2159 
2160  /* response ack */
2161  tcph.th_ack = htonl(328);
2162  tcph.th_seq = htonl(88);
2163  tcph.th_flags = TH_ACK;
2165  p->payload_len = 0;
2166  p->payload = NULL;
2167  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2174  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2175  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2176  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2177  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2179 
2180  TEST_END;
2181  PASS;
2182 }
2183 
2184 /**
2185  * \test HTTP/1.1 -> GET
2186  */
2187 static int AppLayerTest06(void)
2188 {
2189  TEST_START;
2190 
2191  /* full response - request ack */
2192  uint8_t response[] = {
2193  0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x31,
2194  0x20, 0x32, 0x30, 0x30, 0x20, 0x4f, 0x4b, 0x0d,
2195  0x0a, 0x44, 0x61, 0x74, 0x65, 0x3a, 0x20, 0x46,
2196  0x72, 0x69, 0x2c, 0x20, 0x32, 0x33, 0x20, 0x53,
2197  0x65, 0x70, 0x20, 0x32, 0x30, 0x31, 0x31, 0x20,
2198  0x30, 0x36, 0x3a, 0x32, 0x39, 0x3a, 0x33, 0x39,
2199  0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a, 0x53, 0x65,
2200  0x72, 0x76, 0x65, 0x72, 0x3a, 0x20, 0x41, 0x70,
2201  0x61, 0x63, 0x68, 0x65, 0x2f, 0x32, 0x2e, 0x32,
2202  0x2e, 0x31, 0x35, 0x20, 0x28, 0x55, 0x6e, 0x69,
2203  0x78, 0x29, 0x20, 0x44, 0x41, 0x56, 0x2f, 0x32,
2204  0x0d, 0x0a, 0x4c, 0x61, 0x73, 0x74, 0x2d, 0x4d,
2205  0x6f, 0x64, 0x69, 0x66, 0x69, 0x65, 0x64, 0x3a,
2206  0x20, 0x54, 0x68, 0x75, 0x2c, 0x20, 0x30, 0x34,
2207  0x20, 0x4e, 0x6f, 0x76, 0x20, 0x32, 0x30, 0x31,
2208  0x30, 0x20, 0x31, 0x35, 0x3a, 0x30, 0x34, 0x3a,
2209  0x34, 0x36, 0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a,
2210  0x45, 0x54, 0x61, 0x67, 0x3a, 0x20, 0x22, 0x61,
2211  0x62, 0x38, 0x39, 0x36, 0x35, 0x2d, 0x32, 0x63,
2212  0x2d, 0x34, 0x39, 0x34, 0x33, 0x62, 0x37, 0x61,
2213  0x37, 0x66, 0x37, 0x66, 0x38, 0x30, 0x22, 0x0d,
2214  0x0a, 0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x2d,
2215  0x52, 0x61, 0x6e, 0x67, 0x65, 0x73, 0x3a, 0x20,
2216  0x62, 0x79, 0x74, 0x65, 0x73, 0x0d, 0x0a, 0x43,
2217  0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x4c,
2218  0x65, 0x6e, 0x67, 0x74, 0x68, 0x3a, 0x20, 0x34,
2219  0x34, 0x0d, 0x0a, 0x43, 0x6f, 0x6e, 0x6e, 0x65,
2220  0x63, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0x63,
2221  0x6c, 0x6f, 0x73, 0x65, 0x0d, 0x0a, 0x43, 0x6f,
2222  0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x54, 0x79,
2223  0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74,
2224  0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x0d, 0x0a, 0x58,
2225  0x2d, 0x50, 0x61, 0x64, 0x3a, 0x20, 0x61, 0x76,
2226  0x6f, 0x69, 0x64, 0x20, 0x62, 0x72, 0x6f, 0x77,
2227  0x73, 0x65, 0x72, 0x20, 0x62, 0x75, 0x67, 0x0d,
2228  0x0a, 0x0d, 0x0a, 0x3c, 0x68, 0x74, 0x6d, 0x6c,
2229  0x3e, 0x3c, 0x62, 0x6f, 0x64, 0x79, 0x3e, 0x3c,
2230  0x68, 0x31, 0x3e, 0x49, 0x74, 0x20, 0x77, 0x6f,
2231  0x72, 0x6b, 0x73, 0x21, 0x3c, 0x2f, 0x68, 0x31,
2232  0x3e, 0x3c, 0x2f, 0x62, 0x6f, 0x64, 0x79, 0x3e,
2233  0x3c, 0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x3e };
2234  tcph.th_ack = htonl(1);
2235  tcph.th_seq = htonl(1);
2236  tcph.th_flags = TH_PUSH | TH_ACK;
2238  p->payload_len = sizeof(response);
2239  p->payload = response;
2240  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2247  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2248  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2249  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2250  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2251  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOCLIENT);
2252 
2253  /* full request - response ack*/
2254  uint8_t request[] = {
2255  0x47, 0x45, 0x54, 0x20, 0x2f, 0x69, 0x6e, 0x64,
2256  0x65, 0x78, 0x2e, 0x68, 0x74, 0x6d, 0x6c, 0x20,
2257  0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x30,
2258  0x0d, 0x0a, 0x48, 0x6f, 0x73, 0x74, 0x3a, 0x20,
2259  0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x68, 0x6f, 0x73,
2260  0x74, 0x0d, 0x0a, 0x55, 0x73, 0x65, 0x72, 0x2d,
2261  0x41, 0x67, 0x65, 0x6e, 0x74, 0x3a, 0x20, 0x41,
2262  0x70, 0x61, 0x63, 0x68, 0x65, 0x42, 0x65, 0x6e,
2263  0x63, 0x68, 0x2f, 0x32, 0x2e, 0x33, 0x0d, 0x0a,
2264  0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x3a, 0x20,
2265  0x2a, 0x2f, 0x2a, 0x0d, 0x0a, 0x0d, 0x0a };
2266  tcph.th_ack = htonl(328);
2267  tcph.th_seq = htonl(1);
2268  tcph.th_flags = TH_PUSH | TH_ACK;
2270  p->payload_len = sizeof(request);
2271  p->payload = request;
2272  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2279  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2280  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2281  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2282  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2284 
2285  tcph.th_ack = htonl(1 + sizeof(request));
2286  tcph.th_seq = htonl(328);
2287  tcph.th_flags = TH_PUSH | TH_ACK;
2289  p->payload_len = 0;
2290  p->payload = NULL;
2291  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2298  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2299  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2300  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2301  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2303 
2304  TEST_END;
2305  PASS;
2306 }
2307 
2308 /**
2309  * \test GET -> DCERPC
2310  */
2311 static int AppLayerTest07(void)
2312 {
2313  TEST_START;
2314 
2315  /* full request */
2316  uint8_t request[] = {
2317  0x47, 0x45, 0x54, 0x20, 0x2f, 0x69, 0x6e, 0x64,
2318  0x65, 0x78, 0x2e, 0x68, 0x74, 0x6d, 0x6c, 0x20,
2319  0x48, 0x54, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x30,
2320  0x0d, 0x0a, 0x48, 0x6f, 0x73, 0x74, 0x3a, 0x20,
2321  0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x68, 0x6f, 0x73,
2322  0x74, 0x0d, 0x0a, 0x55, 0x73, 0x65, 0x72, 0x2d,
2323  0x41, 0x67, 0x65, 0x6e, 0x74, 0x3a, 0x20, 0x41,
2324  0x70, 0x61, 0x63, 0x68, 0x65, 0x42, 0x65, 0x6e,
2325  0x63, 0x68, 0x2f, 0x32, 0x2e, 0x33, 0x0d, 0x0a,
2326  0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x3a, 0x20,
2327  0x2a, 0x2f, 0x2a, 0x0d, 0x0a, 0x0d, 0x0a };
2328  tcph.th_ack = htonl(1);
2329  tcph.th_seq = htonl(1);
2330  tcph.th_flags = TH_PUSH | TH_ACK;
2332  p->payload_len = sizeof(request);
2333  p->payload = request;
2334  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2341  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2342  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2343  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2344  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2345  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2346 
2347  /* full response - request ack */
2348  uint8_t response[] = { 0x05, 0x00, 0x4d, 0x42, 0x00, 0x01, 0x2e, 0x31, 0x20, 0x32, 0x30, 0x30,
2349  0x20, 0x4f, 0x4b, 0x0d, 0x0a, 0x44, 0x61, 0x74, 0x65, 0x3a, 0x20, 0x46, 0x72, 0x69, 0x2c,
2350  0x20, 0x32, 0x33, 0x20, 0x53, 0x65, 0x70, 0x20, 0x32, 0x30, 0x31, 0x31, 0x20, 0x30, 0x36,
2351  0x3a, 0x32, 0x39, 0x3a, 0x33, 0x39, 0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a, 0x53, 0x65, 0x72,
2352  0x76, 0x65, 0x72, 0x3a, 0x20, 0x41, 0x70, 0x61, 0x63, 0x68, 0x65, 0x2f, 0x32, 0x2e, 0x32,
2353  0x2e, 0x31, 0x35, 0x20, 0x28, 0x55, 0x6e, 0x69, 0x78, 0x29, 0x20, 0x44, 0x41, 0x56, 0x2f,
2354  0x32, 0x0d, 0x0a, 0x4c, 0x61, 0x73, 0x74, 0x2d, 0x4d, 0x6f, 0x64, 0x69, 0x66, 0x69, 0x65,
2355  0x64, 0x3a, 0x20, 0x54, 0x68, 0x75, 0x2c, 0x20, 0x30, 0x34, 0x20, 0x4e, 0x6f, 0x76, 0x20,
2356  0x32, 0x30, 0x31, 0x30, 0x20, 0x31, 0x35, 0x3a, 0x30, 0x34, 0x3a, 0x34, 0x36, 0x20, 0x47,
2357  0x4d, 0x54, 0x0d, 0x0a, 0x45, 0x54, 0x61, 0x67, 0x3a, 0x20, 0x22, 0x61, 0x62, 0x38, 0x39,
2358  0x36, 0x35, 0x2d, 0x32, 0x63, 0x2d, 0x34, 0x39, 0x34, 0x33, 0x62, 0x37, 0x61, 0x37, 0x66,
2359  0x37, 0x66, 0x38, 0x30, 0x22, 0x0d, 0x0a, 0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x2d, 0x52,
2360  0x61, 0x6e, 0x67, 0x65, 0x73, 0x3a, 0x20, 0x62, 0x79, 0x74, 0x65, 0x73, 0x0d, 0x0a, 0x43,
2361  0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x4c, 0x65, 0x6e, 0x67, 0x74, 0x68, 0x3a, 0x20,
2362  0x34, 0x34, 0x0d, 0x0a, 0x43, 0x6f, 0x6e, 0x6e, 0x65, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x3a,
2363  0x20, 0x63, 0x6c, 0x6f, 0x73, 0x65, 0x0d, 0x0a, 0x43, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74,
2364  0x2d, 0x54, 0x79, 0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74, 0x2f, 0x68, 0x74, 0x6d,
2365  0x6c, 0x0d, 0x0a, 0x58, 0x2d, 0x50, 0x61, 0x64, 0x3a, 0x20, 0x61, 0x76, 0x6f, 0x69, 0x64,
2366  0x20, 0x62, 0x72, 0x6f, 0x77, 0x73, 0x65, 0x72, 0x20, 0x62, 0x75, 0x67, 0x0d, 0x0a, 0x0d,
2367  0x0a, 0x3c, 0x68, 0x74, 0x6d, 0x6c, 0x3e, 0x3c, 0x62, 0x6f, 0x64, 0x79, 0x3e, 0x3c, 0x68,
2368  0x31, 0x3e, 0x49, 0x74, 0x20, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x21, 0x3c, 0x2f, 0x68, 0x31,
2369  0x3e, 0x3c, 0x2f, 0x62, 0x6f, 0x64, 0x79, 0x3e, 0x3c, 0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x3e };
2370  tcph.th_ack = htonl(88);
2371  tcph.th_seq = htonl(1);
2372  tcph.th_flags = TH_PUSH | TH_ACK;
2374  p->payload_len = sizeof(response);
2375  p->payload = response;
2376  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2383  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2384  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2385  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2386  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2388 
2389  /* response ack */
2390  tcph.th_ack = htonl(328);
2391  tcph.th_seq = htonl(88);
2392  tcph.th_flags = TH_ACK;
2394  p->payload_len = 0;
2395  p->payload = NULL;
2396  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2403  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2404  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2405  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2406  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2408 
2409  TEST_END;
2410  PASS;
2411 }
2412 
2413 /**
2414  * \test RUBBISH(TC - PM and PP NOT DONE) ->
2415  * RUBBISH(TC - PM and PP DONE) ->
2416  * RUBBISH(TS - PM and PP DONE)
2417  */
2418 static int AppLayerTest09(void)
2419 {
2420  TEST_START;
2421 
2422  /* full request */
2423  uint8_t request1[] = {
2424  0x47, 0x47, 0x49, 0x20, 0x2f, 0x69, 0x6e, 0x64 };
2425  tcph.th_ack = htonl(1);
2426  tcph.th_seq = htonl(1);
2427  tcph.th_flags = TH_PUSH | TH_ACK;
2429  p->payload_len = sizeof(request1);
2430  p->payload = request1;
2431  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2438  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2439  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2440  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2441  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2442  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2443 
2444  /* response - request ack */
2445  tcph.th_ack = htonl(9);
2446  tcph.th_seq = htonl(1);
2447  tcph.th_flags = TH_PUSH | TH_ACK;
2449  p->payload_len = 0;
2450  p->payload = NULL;
2451  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2458  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2459  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2460  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2461  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2462  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2463 
2464  /* full request */
2465  uint8_t request2[] = {
2466  0x44, 0x44, 0x45, 0x20, 0x2f, 0x69, 0x6e, 0x64, 0xff };
2467  tcph.th_ack = htonl(1);
2468  tcph.th_seq = htonl(9);
2469  tcph.th_flags = TH_PUSH | TH_ACK;
2471  p->payload_len = sizeof(request2);
2472  p->payload = request2;
2473  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2480  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2481  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2482  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2483  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2484  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2485 
2486  /* full response - request ack */
2487  uint8_t response[] = {
2488  0x55, 0x74, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x31,
2489  0x20, 0x32, 0x30, 0x30, 0x20, 0x4f, 0x4b, 0x0d,
2490  0x0a, 0x44, 0x61, 0x74, 0x65, 0x3a, 0x20, 0x46,
2491  0x72, 0x69, 0x2c, 0x20, 0x32, 0x33, 0x20, 0x53,
2492  0x65, 0x70, 0x20, 0x32, 0x30, 0x31, 0x31, 0x20,
2493  0x30, 0x36, 0x3a, 0x32, 0x39, 0x3a, 0x33, 0x39,
2494  0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a, 0x53, 0x65,
2495  0x72, 0x76, 0x65, 0x72, 0x3a, 0x20, 0x41, 0x70,
2496  0x61, 0x63, 0x68, 0x65, 0x2f, 0x32, 0x2e, 0x32,
2497  0x2e, 0x31, 0x35, 0x20, 0x28, 0x55, 0x6e, 0x69,
2498  0x78, 0x29, 0x20, 0x44, 0x41, 0x56, 0x2f, 0x32,
2499  0x0d, 0x0a, 0x4c, 0x61, 0x73, 0x74, 0x2d, 0x4d,
2500  0x6f, 0x64, 0x69, 0x66, 0x69, 0x65, 0x64, 0x3a,
2501  0x20, 0x54, 0x68, 0x75, 0x2c, 0x20, 0x30, 0x34,
2502  0x20, 0x4e, 0x6f, 0x76, 0x20, 0x32, 0x30, 0x31,
2503  0x30, 0x20, 0x31, 0x35, 0x3a, 0x30, 0x34, 0x3a,
2504  0x34, 0x36, 0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a,
2505  0x45, 0x54, 0x61, 0x67, 0x3a, 0x20, 0x22, 0x61,
2506  0x62, 0x38, 0x39, 0x36, 0x35, 0x2d, 0x32, 0x63,
2507  0x2d, 0x34, 0x39, 0x34, 0x33, 0x62, 0x37, 0x61,
2508  0x37, 0x66, 0x37, 0x66, 0x38, 0x30, 0x22, 0x0d,
2509  0x0a, 0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x2d,
2510  0x52, 0x61, 0x6e, 0x67, 0x65, 0x73, 0x3a, 0x20,
2511  0x62, 0x79, 0x74, 0x65, 0x73, 0x0d, 0x0a, 0x43,
2512  0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x4c,
2513  0x65, 0x6e, 0x67, 0x74, 0x68, 0x3a, 0x20, 0x34,
2514  0x34, 0x0d, 0x0a, 0x43, 0x6f, 0x6e, 0x6e, 0x65,
2515  0x63, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0x63,
2516  0x6c, 0x6f, 0x73, 0x65, 0x0d, 0x0a, 0x43, 0x6f,
2517  0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x54, 0x79,
2518  0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74,
2519  0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x0d, 0x0a, 0x58,
2520  0x2d, 0x50, 0x61, 0x64, 0x3a, 0x20, 0x61, 0x76,
2521  0x6f, 0x69, 0x64, 0x20, 0x62, 0x72, 0x6f, 0x77,
2522  0x73, 0x65, 0x72, 0x20, 0x62, 0x75, 0x67, 0x0d,
2523  0x0a, 0x0d, 0x0a, 0x3c, 0x68, 0x74, 0x6d, 0x6c,
2524  0x3e, 0x3c, 0x62, 0x6f, 0x64, 0x79, 0x3e, 0x3c,
2525  0x68, 0x31, 0x3e, 0x49, 0x74, 0x20, 0x77, 0x6f,
2526  0x72, 0x6b, 0x73, 0x21, 0x3c, 0x2f, 0x68, 0x31,
2527  0x3e, 0x3c, 0x2f, 0x62, 0x6f, 0x64, 0x79, 0x3e,
2528  0x3c, 0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x3e };
2529  tcph.th_ack = htonl(18);
2530  tcph.th_seq = htonl(1);
2531  tcph.th_flags = TH_PUSH | TH_ACK;
2533  p->payload_len = sizeof(response);
2534  p->payload = response;
2535  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2542  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2543  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2544  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2545  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2546  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2547 
2548  /* response ack */
2549  tcph.th_ack = htonl(328);
2550  tcph.th_seq = htonl(18);
2551  tcph.th_flags = TH_ACK;
2553  p->payload_len = 0;
2554  p->payload = NULL;
2555  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2562  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2563  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2564  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2565  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2567 
2568  TEST_END;
2569  PASS;
2570 }
2571 
2572 /**
2573  * \test RUBBISH(TC - PM and PP DONE) ->
2574  * RUBBISH(TS - PM and PP DONE)
2575  */
2576 static int AppLayerTest10(void)
2577 {
2578  TEST_START;
2579 
2580  /* full request */
2581  uint8_t request1[] = {
2582  0x47, 0x47, 0x49, 0x20, 0x2f, 0x69, 0x6e, 0x64,
2583  0x47, 0x47, 0x49, 0x20, 0x2f, 0x69, 0x6e, 0x64, 0xff };
2584  tcph.th_ack = htonl(1);
2585  tcph.th_seq = htonl(1);
2586  tcph.th_flags = TH_PUSH | TH_ACK;
2588  p->payload_len = sizeof(request1);
2589  p->payload = request1;
2590  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2597  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2598  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2599  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2600  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2601  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2602 
2603  /* response - request ack */
2604  tcph.th_ack = htonl(18);
2605  tcph.th_seq = htonl(1);
2606  tcph.th_flags = TH_PUSH | TH_ACK;
2608  p->payload_len = 0;
2609  p->payload = NULL;
2610  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2617  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2618  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2619  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2620  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2621  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2622 
2623  /* full response - request ack */
2624  uint8_t response[] = {
2625  0x55, 0x74, 0x54, 0x50, 0x2f, 0x31, 0x2e, 0x31,
2626  0x20, 0x32, 0x30, 0x30, 0x20, 0x4f, 0x4b, 0x0d,
2627  0x0a, 0x44, 0x61, 0x74, 0x65, 0x3a, 0x20, 0x46,
2628  0x72, 0x69, 0x2c, 0x20, 0x32, 0x33, 0x20, 0x53,
2629  0x65, 0x70, 0x20, 0x32, 0x30, 0x31, 0x31, 0x20,
2630  0x30, 0x36, 0x3a, 0x32, 0x39, 0x3a, 0x33, 0x39,
2631  0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a, 0x53, 0x65,
2632  0x72, 0x76, 0x65, 0x72, 0x3a, 0x20, 0x41, 0x70,
2633  0x61, 0x63, 0x68, 0x65, 0x2f, 0x32, 0x2e, 0x32,
2634  0x2e, 0x31, 0x35, 0x20, 0x28, 0x55, 0x6e, 0x69,
2635  0x78, 0x29, 0x20, 0x44, 0x41, 0x56, 0x2f, 0x32,
2636  0x0d, 0x0a, 0x4c, 0x61, 0x73, 0x74, 0x2d, 0x4d,
2637  0x6f, 0x64, 0x69, 0x66, 0x69, 0x65, 0x64, 0x3a,
2638  0x20, 0x54, 0x68, 0x75, 0x2c, 0x20, 0x30, 0x34,
2639  0x20, 0x4e, 0x6f, 0x76, 0x20, 0x32, 0x30, 0x31,
2640  0x30, 0x20, 0x31, 0x35, 0x3a, 0x30, 0x34, 0x3a,
2641  0x34, 0x36, 0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a,
2642  0x45, 0x54, 0x61, 0x67, 0x3a, 0x20, 0x22, 0x61,
2643  0x62, 0x38, 0x39, 0x36, 0x35, 0x2d, 0x32, 0x63,
2644  0x2d, 0x34, 0x39, 0x34, 0x33, 0x62, 0x37, 0x61,
2645  0x37, 0x66, 0x37, 0x66, 0x38, 0x30, 0x22, 0x0d,
2646  0x0a, 0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x2d,
2647  0x52, 0x61, 0x6e, 0x67, 0x65, 0x73, 0x3a, 0x20,
2648  0x62, 0x79, 0x74, 0x65, 0x73, 0x0d, 0x0a, 0x43,
2649  0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x4c,
2650  0x65, 0x6e, 0x67, 0x74, 0x68, 0x3a, 0x20, 0x34,
2651  0x34, 0x0d, 0x0a, 0x43, 0x6f, 0x6e, 0x6e, 0x65,
2652  0x63, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0x63,
2653  0x6c, 0x6f, 0x73, 0x65, 0x0d, 0x0a, 0x43, 0x6f,
2654  0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x54, 0x79,
2655  0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74,
2656  0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x0d, 0x0a, 0x58,
2657  0x2d, 0x50, 0x61, 0x64, 0x3a, 0x20, 0x61, 0x76,
2658  0x6f, 0x69, 0x64, 0x20, 0x62, 0x72, 0x6f, 0x77,
2659  0x73, 0x65, 0x72, 0x20, 0x62, 0x75, 0x67, 0x0d,
2660  0x0a, 0x0d, 0x0a, 0x3c, 0x68, 0x74, 0x6d, 0x6c,
2661  0x3e, 0x3c, 0x62, 0x6f, 0x64, 0x79, 0x3e, 0x3c,
2662  0x68, 0x31, 0x3e, 0x49, 0x74, 0x20, 0x77, 0x6f,
2663  0x72, 0x6b, 0x73, 0x21, 0x3c, 0x2f, 0x68, 0x31,
2664  0x3e, 0x3c, 0x2f, 0x62, 0x6f, 0x64, 0x79, 0x3e,
2665  0x3c, 0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x3e };
2666  tcph.th_ack = htonl(18);
2667  tcph.th_seq = htonl(1);
2668  tcph.th_flags = TH_PUSH | TH_ACK;
2670  p->payload_len = sizeof(response);
2671  p->payload = response;
2672  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2679  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2680  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2681  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2682  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2683  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2684 
2685  /* response ack */
2686  tcph.th_ack = htonl(328);
2687  tcph.th_seq = htonl(18);
2688  tcph.th_flags = TH_ACK;
2690  p->payload_len = 0;
2691  p->payload = NULL;
2692  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2699  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2700  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2701  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2702  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2704 
2705  TEST_END;
2706  PASS;
2707 }
2708 
2709 /**
2710  * \test RUBBISH(TC - PM and PP DONE) ->
2711  * RUBBISH(TS - PM and PP NOT DONE) ->
2712  * RUBBISH(TS - PM and PP DONE)
2713  */
2714 static int AppLayerTest11(void)
2715 {
2716  TEST_START;
2717 
2718  /* full request */
2719  uint8_t request1[] = {
2720  0x47, 0x47, 0x49, 0x20, 0x2f, 0x69, 0x6e, 0x64,
2721  0x47, 0x47, 0x49, 0x20, 0x2f, 0x69, 0x6e, 0x64, 0xff };
2722  tcph.th_ack = htonl(1);
2723  tcph.th_seq = htonl(1);
2724  tcph.th_flags = TH_PUSH | TH_ACK;
2726  p->payload_len = sizeof(request1);
2727  p->payload = request1;
2728  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2735  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2736  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2737  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2738  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2739  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2740 
2741  /* response - request ack */
2742  tcph.th_ack = htonl(18);
2743  tcph.th_seq = htonl(1);
2744  tcph.th_flags = TH_PUSH | TH_ACK;
2746  p->payload_len = 0;
2747  p->payload = NULL;
2748  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2755  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2756  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2757  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2758  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2759  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2760 
2761  /* full response - request ack */
2762  uint8_t response1[] = {
2763  0x55, 0x74, 0x54, 0x50, };
2764  tcph.th_ack = htonl(18);
2765  tcph.th_seq = htonl(1);
2766  tcph.th_flags = TH_PUSH | TH_ACK;
2768  p->payload_len = sizeof(response1);
2769  p->payload = response1;
2770  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2777  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2778  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2779  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2780  FAIL_IF(FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2781  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2782 
2783  /* response ack from request */
2784  tcph.th_ack = htonl(5);
2785  tcph.th_seq = htonl(18);
2786  tcph.th_flags = TH_ACK;
2788  p->payload_len = 0;
2789  p->payload = NULL;
2790  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2797  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2798  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2799  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2800  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2801  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2802 
2803  uint8_t response2[] = {
2804  0x2f, 0x31, 0x2e, 0x31,
2805  0x20, 0x32, 0x30, 0x30, 0x20, 0x4f, 0x4b, 0x0d,
2806  0x0a, 0x44, 0x61, 0x74, 0x65, 0x3a, 0x20, 0x46,
2807  0x72, 0x69, 0x2c, 0x20, 0x32, 0x33, 0x20, 0x53,
2808  0x65, 0x70, 0x20, 0x32, 0x30, 0x31, 0x31, 0x20,
2809  0x30, 0x36, 0x3a, 0x32, 0x39, 0x3a, 0x33, 0x39,
2810  0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a, 0x53, 0x65,
2811  0x72, 0x76, 0x65, 0x72, 0x3a, 0x20, 0x41, 0x70,
2812  0x61, 0x63, 0x68, 0x65, 0x2f, 0x32, 0x2e, 0x32,
2813  0x2e, 0x31, 0x35, 0x20, 0x28, 0x55, 0x6e, 0x69,
2814  0x78, 0x29, 0x20, 0x44, 0x41, 0x56, 0x2f, 0x32,
2815  0x0d, 0x0a, 0x4c, 0x61, 0x73, 0x74, 0x2d, 0x4d,
2816  0x6f, 0x64, 0x69, 0x66, 0x69, 0x65, 0x64, 0x3a,
2817  0x20, 0x54, 0x68, 0x75, 0x2c, 0x20, 0x30, 0x34,
2818  0x20, 0x4e, 0x6f, 0x76, 0x20, 0x32, 0x30, 0x31,
2819  0x30, 0x20, 0x31, 0x35, 0x3a, 0x30, 0x34, 0x3a,
2820  0x34, 0x36, 0x20, 0x47, 0x4d, 0x54, 0x0d, 0x0a,
2821  0x45, 0x54, 0x61, 0x67, 0x3a, 0x20, 0x22, 0x61,
2822  0x62, 0x38, 0x39, 0x36, 0x35, 0x2d, 0x32, 0x63,
2823  0x2d, 0x34, 0x39, 0x34, 0x33, 0x62, 0x37, 0x61,
2824  0x37, 0x66, 0x37, 0x66, 0x38, 0x30, 0x22, 0x0d,
2825  0x0a, 0x41, 0x63, 0x63, 0x65, 0x70, 0x74, 0x2d,
2826  0x52, 0x61, 0x6e, 0x67, 0x65, 0x73, 0x3a, 0x20,
2827  0x62, 0x79, 0x74, 0x65, 0x73, 0x0d, 0x0a, 0x43,
2828  0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x4c,
2829  0x65, 0x6e, 0x67, 0x74, 0x68, 0x3a, 0x20, 0x34,
2830  0x34, 0x0d, 0x0a, 0x43, 0x6f, 0x6e, 0x6e, 0x65,
2831  0x63, 0x74, 0x69, 0x6f, 0x6e, 0x3a, 0x20, 0x63,
2832  0x6c, 0x6f, 0x73, 0x65, 0x0d, 0x0a, 0x43, 0x6f,
2833  0x6e, 0x74, 0x65, 0x6e, 0x74, 0x2d, 0x54, 0x79,
2834  0x70, 0x65, 0x3a, 0x20, 0x74, 0x65, 0x78, 0x74,
2835  0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x0d, 0x0a, 0x58,
2836  0x2d, 0x50, 0x61, 0x64, 0x3a, 0x20, 0x61, 0x76,
2837  0x6f, 0x69, 0x64, 0x20, 0x62, 0x72, 0x6f, 0x77,
2838  0x73, 0x65, 0x72, 0x20, 0x62, 0x75, 0x67, 0x0d,
2839  0x0a, 0x0d, 0x0a, 0x3c, 0x68, 0x74, 0x6d, 0x6c,
2840  0x3e, 0x3c, 0x62, 0x6f, 0x64, 0x79, 0x3e, 0x3c,
2841  0x68, 0x31, 0x3e, 0x49, 0x74, 0x20, 0x77, 0x6f,
2842  0x72, 0x6b, 0x73, 0x21, 0x3c, 0x2f, 0x68, 0x31,
2843  0x3e, 0x3c, 0x2f, 0x62, 0x6f, 0x64, 0x79, 0x3e,
2844  0x3c, 0x2f, 0x68, 0x74, 0x6d, 0x6c, 0x3e };
2845  tcph.th_ack = htonl(18);
2846  tcph.th_seq = htonl(5);
2847  tcph.th_flags = TH_PUSH | TH_ACK;
2849  p->payload_len = sizeof(response2);
2850  p->payload = response2;
2851  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2858  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2859  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2860  FAIL_IF(FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2861  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2862  FAIL_IF(ssn->data_first_seen_dir != STREAM_TOSERVER);
2863 
2864  /* response ack from request */
2865  tcph.th_ack = htonl(328);
2866  tcph.th_seq = htonl(18);
2867  tcph.th_flags = TH_ACK;
2869  p->payload_len = 0;
2870  p->payload = NULL;
2871  FAIL_IF(StreamTcpPacket(&tv, p, stt, &pq) == -1);
2878  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOSERVER));
2879  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOSERVER));
2880  FAIL_IF(!FLOW_IS_PM_DONE(&f, STREAM_TOCLIENT));
2881  FAIL_IF(!FLOW_IS_PP_DONE(&f, STREAM_TOCLIENT));
2883 
2884  TEST_END;
2885  PASS;
2886 }
2887 
2889 {
2890  SCEnter();
2891 
2892  UtRegisterTest("AppLayerTest01", AppLayerTest01);
2893  UtRegisterTest("AppLayerTest02", AppLayerTest02);
2894  UtRegisterTest("AppLayerTest03", AppLayerTest03);
2895  UtRegisterTest("AppLayerTest04", AppLayerTest04);
2896  UtRegisterTest("AppLayerTest05", AppLayerTest05);
2897  UtRegisterTest("AppLayerTest06", AppLayerTest06);
2898  UtRegisterTest("AppLayerTest07", AppLayerTest07);
2899  UtRegisterTest("AppLayerTest09", AppLayerTest09);
2900  UtRegisterTest("AppLayerTest10", AppLayerTest10);
2901  UtRegisterTest("AppLayerTest11", AppLayerTest11);
2902 
2903  SCReturn;
2904 }
2905 
2906 #endif /* UNITTESTS */
AppLayerCounters_::alloc_error_id
uint16_t alloc_error_id
Definition: app-layer.c:95
APP_LAYER_DATA_ALREADY_SENT_TO_APP_LAYER
#define APP_LAYER_DATA_ALREADY_SENT_TO_APP_LAYER
Definition: app-layer.h:40
AppLayerCounters_::counter_id
uint16_t counter_id
Definition: app-layer.c:90
FLOW_RESET_PP_DONE
#define FLOW_RESET_PP_DONE(f, dir)
Definition: flow.h:279
UPDATE_DIR_PACKET
@ UPDATE_DIR_PACKET
Definition: stream-tcp-reassemble.h:56
FlowUnsetChangeProtoFlag
void FlowUnsetChangeProtoFlag(Flow *f)
Unset flag to indicate to change proto for the flow.
Definition: flow.c:187
Packet_::proto
uint8_t proto
Definition: decode.h:523
AppLayerParserDeSetup
int AppLayerParserDeSetup(void)
Definition: app-layer-parser.c:285
TcpStream_
Definition: stream-tcp-private.h:106
APPLAYER_UNEXPECTED_PROTOCOL
@ APPLAYER_UNEXPECTED_PROTOCOL
Definition: app-layer-events.h:51
ExceptionPolicyApply
void ExceptionPolicyApply(Packet *p, enum ExceptionPolicy policy, enum PacketDropReason drop_reason)
Definition: util-exception-policy.c:138
AppLayerCounters_::gap_error_id
uint16_t gap_error_id
Definition: app-layer.c:92
AppLayerCounters_
Definition: app-layer.c:89
ippair.h
app-layer-htp-range.h
FlowCleanupAppLayer
void FlowCleanupAppLayer(Flow *f)
Definition: flow.c:140
AppLayerProtoDetectSetup
int AppLayerProtoDetectSetup(void)
The first function to be called. This initializes a global protocol detection context.
Definition: app-layer-detect-proto.c:1661
ALPROTO_IKE
@ ALPROTO_IKE
Definition: app-layer-protos.h:55
ExpectationGetCounter
uint64_t ExpectationGetCounter(void)
Definition: app-layer-expectation.c:140
AppLayerCounterNames_::eps_name
char eps_name[EXCEPTION_POLICY_MAX][MAX_COUNTER_SIZE]
Definition: app-layer.c:86
StatsIncr
void StatsIncr(ThreadVars *tv, uint16_t id)
Increments the local counter.
Definition: counters.c:166
AppLayerCounters_::counter_tx_id
uint16_t counter_tx_id
Definition: app-layer.c:91
AppLayerCounters
struct AppLayerCounters_ AppLayerCounters
stream-tcp-inline.h
ALPROTO_DCERPC
@ ALPROTO_DCERPC
Definition: app-layer-protos.h:44
flow-util.h
ALPROTO_DNS
@ ALPROTO_DNS
Definition: app-layer-protos.h:47
stream-tcp.h
ALPROTO_ENIP
@ ALPROTO_ENIP
Definition: app-layer-protos.h:49
StreamTcpInlineMode
bool StreamTcpInlineMode(void)
See if stream engine is operating in inline mode.
Definition: stream-tcp.c:7221
unlikely
#define unlikely(expr)
Definition: util-optimize.h:35
UtRegisterTest
void UtRegisterTest(const char *name, int(*TestFn)(void))
Register unit test.
Definition: util-unittest.c:103
AppLayerGetProtoByName
AppProto AppLayerGetProtoByName(const char *alproto_name)
Given a protocol string, returns the corresponding internal protocol id.
Definition: app-layer.c:998
ALPROTO_TLS
@ ALPROTO_TLS
Definition: app-layer-protos.h:39
SCLogDebug
#define SCLogDebug(...)
Definition: util-debug.h:279
Packet_::pcap_cnt
uint64_t pcap_cnt
Definition: decode.h:626
AppLayerCounterNames_::parser_error
char parser_error[MAX_COUNTER_SIZE]
Definition: app-layer.c:83
StatsRegisterGlobalCounter
uint16_t StatsRegisterGlobalCounter(const char *name, uint64_t(*Func)(void))
Registers a counter, which represents a global value.
Definition: counters.c:1026
ALPROTO_MODBUS
@ ALPROTO_MODBUS
Definition: app-layer-protos.h:48
AppLayerProfilingStoreInternal
void AppLayerProfilingStoreInternal(AppLayerThreadCtx *app_tctx, Packet *p)
Definition: app-layer.c:1147
Flow_::proto
uint8_t proto
Definition: flow.h:370
AppProto
uint16_t AppProto
Definition: app-layer-protos.h:86
ALPROTO_QUIC
@ ALPROTO_QUIC
Definition: app-layer-protos.h:57
Packet_::payload
uint8_t * payload
Definition: decode.h:605
ALPROTO_POP3
@ ALPROTO_POP3
Definition: app-layer-protos.h:71
TcpReassemblyThreadCtx_::app_tctx
void * app_tctx
Definition: stream-tcp-reassemble.h:62
Packet_::flags
uint32_t flags
Definition: decode.h:544
AppLayerThreadCtx_::proto_detect_ticks_spent
uint64_t proto_detect_ticks_spent
Definition: app-layer.c:72
PACKET_PROFILING_APP_PD_END
#define PACKET_PROFILING_APP_PD_END(dp)
Definition: util-profiling.h:186
ALPROTO_JABBER
@ ALPROTO_JABBER
Definition: app-layer-protos.h:42
TcpStreamCnf_::reassembly_depth
uint32_t reassembly_depth
Definition: stream-tcp.h:75
AppLayerThreadCtx_::alp_tctx
AppLayerParserThreadCtx * alp_tctx
Definition: app-layer.c:63
flow-private.h
Flow_
Flow data structure.
Definition: flow.h:348
AppLayerIncGapErrorCounter
void AppLayerIncGapErrorCounter(ThreadVars *tv, Flow *f)
Definition: app-layer.c:165
AppLayerCounters_::internal_error_id
uint16_t internal_error_id
Definition: app-layer.c:94
Flow_::protomap
uint8_t protomap
Definition: flow.h:437
AppProtoToString
const char * AppProtoToString(AppProto alproto)
Maps the ALPROTO_*, to its string equivalent.
Definition: app-layer-protos.c:41
AppLayerThreadCtx_::ticks_spent
uint64_t ticks_spent
Definition: app-layer.c:68
ALPROTO_IRC
@ ALPROTO_IRC
Definition: app-layer-protos.h:45
ExceptionPolicyStatsSetts_
Definition: util-exception-policy-types.h:57
AppLayerParserGetFirstDataDir
uint8_t AppLayerParserGetFirstDataDir(uint8_t ipproto, AppProto alproto)
Definition: app-layer-parser.c:1135
g_stats_eps_per_app_proto_errors
bool g_stats_eps_per_app_proto_errors
Definition: suricata.c:220
StreamTcpReassembleAppLayer
int StreamTcpReassembleAppLayer(ThreadVars *tv, TcpReassemblyThreadCtx *ra_ctx, TcpSession *ssn, TcpStream *stream, Packet *p, enum StreamUpdateDir app_update_dir)
Update the stream reassembly upon receiving a packet.
Definition: stream-tcp-reassemble.c:1396
StreamTcpResetStreamFlagAppProtoDetectionCompleted
#define StreamTcpResetStreamFlagAppProtoDetectionCompleted(stream)
Definition: stream-tcp-private.h:305
AppLayerRegisterThreadCounters
void AppLayerRegisterThreadCounters(ThreadVars *tv)
Registers per flow counters for all protocols.
Definition: app-layer.c:1303
Flow_::alproto_orig
AppProto alproto_orig
Definition: flow.h:448
AppLayerProtoDetectSupportedIpprotos
void AppLayerProtoDetectSupportedIpprotos(AppProto alproto, uint8_t *ipprotos)
Definition: app-layer-detect-proto.c:2025
FTPMemuseGlobalCounter
uint64_t FTPMemuseGlobalCounter(void)
Definition: app-layer-ftp.c:79
ALPROTO_SIP
@ ALPROTO_SIP
Definition: app-layer-protos.h:59
AppLayerProfilingResetInternal
void AppLayerProfilingResetInternal(AppLayerThreadCtx *app_tctx)
Definition: app-layer.c:1142
AppLayerCounterNames_
Definition: app-layer.c:79
AppLayerParserStateProtoCleanup
void AppLayerParserStateProtoCleanup(uint8_t protomap, AppProto alproto, void *alstate, AppLayerParserState *pstate)
Definition: app-layer-parser.c:1633
AppLayerParserThreadCtxFree
void AppLayerParserThreadCtxFree(AppLayerParserThreadCtx *tctx)
Destroys the app layer parser thread context obtained using AppLayerParserThreadCtxAlloc().
Definition: app-layer-parser.c:324
AppLayerHandleTCPData
int AppLayerHandleTCPData(ThreadVars *tv, TcpReassemblyThreadCtx *ra_ctx, Packet *p, Flow *f, TcpSession *ssn, TcpStream **stream, uint8_t *data, uint32_t data_len, uint8_t flags, enum StreamUpdateDir app_update_dir)
handle TCP data for the app-layer.
Definition: app-layer.c:709
FLOW_PKT_TOSERVER
#define FLOW_PKT_TOSERVER
Definition: flow.h:225
ALPROTO_LDAP
@ ALPROTO_LDAP
Definition: app-layer-protos.h:65
TCP_ESTABLISHED
@ TCP_ESTABLISHED
Definition: stream-tcp-private.h:155
MIN
#define MIN(x, y)
Definition: suricata-common.h:408
StreamTcpUpdateAppLayerProgress
void StreamTcpUpdateAppLayerProgress(TcpSession *ssn, char direction, const uint32_t progress)
update reassembly progress
Definition: stream-tcp.c:6796
ALPROTO_FTP
@ ALPROTO_FTP
Definition: app-layer-protos.h:37
app_layer_error_eps_stats
ExceptionPolicyStatsSetts app_layer_error_eps_stats
Definition: app-layer.c:108
stream-tcp-reassemble.h
AppLayerThreadCtx_::proto_detect_ticks_end
uint64_t proto_detect_ticks_end
Definition: app-layer.c:71
TcpStream_::flags
uint16_t flags
Definition: stream-tcp-private.h:107
AppLayerUnittestsRegister
void AppLayerUnittestsRegister(void)
Definition: app-layer.c:2888
APPLAYER_PROTO_DETECTION_SKIPPED
@ APPLAYER_PROTO_DETECTION_SKIPPED
Definition: app-layer-events.h:49
HTPMemuseGlobalCounter
uint64_t HTPMemuseGlobalCounter(void)
Definition: app-layer-htp-mem.c:80
AppLayerListSupportedProtocols
void AppLayerListSupportedProtocols(void)
Definition: app-layer.c:1012
AppLayerSetupCounters
void AppLayerSetupCounters(void)
Definition: app-layer.c:1194
ALPROTO_SSH
@ ALPROTO_SSH
Definition: app-layer-protos.h:40
app-layer-ftp.h
ALPROTO_DHCP
@ ALPROTO_DHCP
Definition: app-layer-protos.h:58
Packet_::flowflags
uint8_t flowflags
Definition: decode.h:532
AppLayerThreadCtx_::alproto
AppProto alproto
Definition: app-layer.c:69
stream_config
TcpStreamCnf stream_config
Definition: stream-tcp.c:227
MAX
#define MAX(x, y)
Definition: suricata-common.h:412
Flow_::protoctx
void * protoctx
Definition: flow.h:433
AppLayerCounterNames_::tx_name
char tx_name[MAX_COUNTER_SIZE]
Definition: app-layer.c:81
AppLayerIncAllocErrorCounter
void AppLayerIncAllocErrorCounter(ThreadVars *tv, Flow *f)
Definition: app-layer.c:173
EXCEPTION_POLICY_NOT_SET
@ EXCEPTION_POLICY_NOT_SET
Definition: util-exception-policy-types.h:26
Packet_::payload_len
uint16_t payload_len
Definition: decode.h:606
Packet_::app_layer_events
AppLayerDecoderEvents * app_layer_events
Definition: decode.h:632
util-unittest.h
PACKET_PROFILING_APP_PD_START
#define PACKET_PROFILING_APP_PD_START(dp)
Definition: util-profiling.h:181
AppLayerCounters_::parser_error_id
uint16_t parser_error_id
Definition: app-layer.c:93
AppLayerDeSetup
int AppLayerDeSetup(void)
De initializes the app layer.
Definition: app-layer.c:1091
HostGetMemcap
uint64_t HostGetMemcap(void)
Return memcap value.
Definition: host.c:83
SCAppLayerDecoderEventsSetEventRaw
void SCAppLayerDecoderEventsSetEventRaw(AppLayerDecoderEvents **sevents, uint8_t event)
Set an app layer decoder event.
Definition: app-layer-events.c:96
PKT_PROTO_DETECT_TS_DONE
#define PKT_PROTO_DETECT_TS_DONE
Definition: decode.h:1301
MAX_COUNTER_SIZE
#define MAX_COUNTER_SIZE
Definition: app-layer.c:78
ALPROTO_KRB5
@ ALPROTO_KRB5
Definition: app-layer-protos.h:56
STREAMTCP_FLAG_MIDSTREAM
#define STREAMTCP_FLAG_MIDSTREAM
Definition: stream-tcp-private.h:170
TcpSession_::flags
uint32_t flags
Definition: stream-tcp-private.h:294
FLOW_IS_PM_DONE
#define FLOW_IS_PM_DONE(f, dir)
Definition: flow.h:270
APPLAYER_NO_TLS_AFTER_STARTTLS
@ APPLAYER_NO_TLS_AFTER_STARTTLS
Definition: app-layer-events.h:50
Flow_::alparser
AppLayerParserState * alparser
Definition: flow.h:470
EXCEPTION_POLICY_MAX
#define EXCEPTION_POLICY_MAX
Definition: util-exception-policy-types.h:37
AppLayerParserRegisterProtocolParsers
void AppLayerParserRegisterProtocolParsers(void)
Definition: app-layer-parser.c:1773
AppLayerThreadCtx_::proto_detect_ticks_start
uint64_t proto_detect_ticks_start
Definition: app-layer.c:70
AppLayerSetup
int AppLayerSetup(void)
Setup the app layer.
Definition: app-layer.c:1074
app-layer-expectation.h
app-layer-detect-proto.h
AppLayerProtoDetectThreadCtx_
The app layer protocol detection thread context.
Definition: app-layer-detect-proto.c:179
util-debug.h
AppLayerParserState_
Definition: app-layer-parser.c:135
PASS
#define PASS
Pass the test.
Definition: util-unittest.h:105
ExceptionPolicyCounters_
Definition: util-exception-policy-types.h:52
APPLAYER_MISMATCH_PROTOCOL_BOTH_DIRECTIONS
@ APPLAYER_MISMATCH_PROTOCOL_BOTH_DIRECTIONS
Definition: app-layer-events.h:46
g_alproto_max
AppProto g_alproto_max
Definition: app-layer-protos.c:30
FLOW_IS_PP_DONE
#define FLOW_IS_PP_DONE(f, dir)
Definition: flow.h:271
AppLayerRegisterGlobalCounters
void AppLayerRegisterGlobalCounters(void)
HACK to work around our broken unix manager (re)init loop.
Definition: app-layer.c:1155
ALPROTO_DNP3
@ ALPROTO_DNP3
Definition: app-layer-protos.h:50
PKT_DROP_REASON_APPLAYER_ERROR
@ PKT_DROP_REASON_APPLAYER_ERROR
Definition: decode.h:387
AppLayerThreadCtx_::ticks_end
uint64_t ticks_end
Definition: app-layer.c:67
PacketSwap
void PacketSwap(Packet *p)
switch direction of a packet
Definition: decode.c:581
util-exception-policy.h
ALPROTO_SMTP
@ ALPROTO_SMTP
Definition: app-layer-protos.h:38
AppProtoRegisterProtoString
void AppProtoRegisterProtoString(AppProto alproto, const char *proto_name)
Definition: app-layer-protos.c:81
HTPByteRangeMemuseGlobalCounter
uint64_t HTPByteRangeMemuseGlobalCounter(void)
Definition: app-layer-htp-range.c:62
AppLayerThreadCtx_
This is for the app layer in general and it contains per thread context relevant to both the alpd and...
Definition: app-layer.c:59
ExceptionPolicyCounters_::eps_id
uint16_t eps_id[EXCEPTION_POLICY_MAX]
Definition: util-exception-policy-types.h:54
util-print.h
IPPairGetMemcap
uint64_t IPPairGetMemcap(void)
Return memcap value.
Definition: ippair.c:81
SCEnter
#define SCEnter(...)
Definition: util-debug.h:281
ThreadVars_
Per thread variable structure.
Definition: threadvars.h:58
pkt-var.h
StreamTcpPacket
int StreamTcpPacket(ThreadVars *tv, Packet *p, StreamTcpThread *stt, PacketQueueNoLock *pq)
Definition: stream-tcp.c:5664
AppLayerProtoDetectReset
void AppLayerProtoDetectReset(Flow *f)
Reset proto detect for flow.
Definition: app-layer-detect-proto.c:1853
TcpSession_::state
uint8_t state
Definition: stream-tcp-private.h:285
TEST_START
#define TEST_START
Definition: app-layer.c:1381
ExceptionPolicyStatsSetts_::valid_settings_ids
bool valid_settings_ids[EXCEPTION_POLICY_MAX]
Definition: util-exception-policy-types.h:59
TH_ACK
#define TH_ACK
Definition: decode-tcp.h:38
HostGetMemuse
uint64_t HostGetMemuse(void)
Return memuse value.
Definition: host.c:94
PACKET_PROFILING_APP_STORE
#define PACKET_PROFILING_APP_STORE(dp, p)
Definition: util-profiling.h:206
PrintRawDataFp
void PrintRawDataFp(FILE *fp, const uint8_t *buf, uint32_t buflen)
Definition: util-print.c:112
app-layer-parser.h
FLOW_PROTO_DETECT_TC_DONE
#define FLOW_PROTO_DETECT_TC_DONE
Definition: flow.h:105
AppLayerCounterNames
struct AppLayerCounterNames_ AppLayerCounterNames
util-profiling.h
AppLayerParserSetup
int AppLayerParserSetup(void)
Definition: app-layer-parser.c:259
SCReturn
#define SCReturn
Definition: util-debug.h:283
FLOW_RESET_PM_DONE
#define FLOW_RESET_PM_DONE(f, dir)
Definition: flow.h:278
stream.h
FlowGetProtoMapping
uint8_t FlowGetProtoMapping(uint8_t proto)
Function to map the protocol to the defined FLOW_PROTO_* enumeration.
Definition: flow-util.c:99
StreamTcpIsSetStreamFlagAppProtoDetectionCompleted
#define StreamTcpIsSetStreamFlagAppProtoDetectionCompleted(stream)
Definition: stream-tcp-private.h:303
Packet_
Definition: decode.h:501
ALPROTO_IMAP
@ ALPROTO_IMAP
Definition: app-layer-protos.h:41
stream-tcp-private.h
ALPROTO_RDP
@ ALPROTO_RDP
Definition: app-layer-protos.h:68
FLOW_PROTO_APPLAYER_MAX
#define FLOW_PROTO_APPLAYER_MAX
Definition: flow-private.h:75
applayer_counters
AppLayerCounters(* applayer_counters)[FLOW_PROTO_APPLAYER_MAX]
Definition: app-layer.c:102
AppLayerHandleUdp
int AppLayerHandleUdp(ThreadVars *tv, AppLayerThreadCtx *tctx, Packet *p, Flow *f)
Handle a app layer UDP message.
Definition: app-layer.c:874
DEBUG_ASSERT_FLOW_LOCKED
#define DEBUG_ASSERT_FLOW_LOCKED(f)
Definition: util-validate.h:99
StreamTcpSetStreamFlagAppProtoDetectionCompleted
#define StreamTcpSetStreamFlagAppProtoDetectionCompleted(stream)
Definition: stream-tcp-private.h:301
PACKET_PROFILING_APP_END
#define PACKET_PROFILING_APP_END(dp)
Definition: util-profiling.h:173
TcpStream_::window
uint32_t window
Definition: stream-tcp-private.h:117
ALPROTO_TELNET
@ ALPROTO_TELNET
Definition: app-layer-protos.h:63
ALPROTO_DOH2
@ ALPROTO_DOH2
Definition: app-layer-protos.h:66
name
const char * name
Definition: tm-threads.c:2163
SCReturnPtr
#define SCReturnPtr(x, type)
Definition: util-debug.h:297
AppLayerThreadCtx_::alpd_tctx
AppLayerProtoDetectThreadCtx * alpd_tctx
Definition: app-layer.c:61
StreamDataAvailableForProtoDetect
uint32_t StreamDataAvailableForProtoDetect(TcpStream *stream)
Definition: stream-tcp-reassemble.c:722
AppLayerGetCtxThread
AppLayerThreadCtx * AppLayerGetCtxThread(void)
Creates a new app layer thread context.
Definition: app-layer.c:1104
ALPROTO_TFTP
@ ALPROTO_TFTP
Definition: app-layer-protos.h:54
AppLayerThreadCtx_::ticks_start
uint64_t ticks_start
Definition: app-layer.c:66
AppLayerIncParserErrorCounter
void AppLayerIncParserErrorCounter(ThreadVars *tv, Flow *f)
Definition: app-layer.c:181
ALPROTO_HTTP2
@ ALPROTO_HTTP2
Definition: app-layer-protos.h:69
FTPMemcapGlobalCounter
uint64_t FTPMemcapGlobalCounter(void)
Definition: app-layer-ftp.c:85
FLOW_PKT_TOCLIENT
#define FLOW_PKT_TOCLIENT
Definition: flow.h:226
Flow_::alproto_expect
AppProto alproto_expect
Definition: flow.h:451
decode-events.h
UPDATE_DIR_OPPOSING
@ UPDATE_DIR_OPPOSING
Definition: stream-tcp-reassemble.h:57
AppLayerParserThreadCtxAlloc
AppLayerParserThreadCtx * AppLayerParserThreadCtxAlloc(void)
Gets a new app layer protocol's parser thread context.
Definition: app-layer-parser.c:297
TH_PUSH
#define TH_PUSH
Definition: decode-tcp.h:37
app-layer-frames.h
FAIL_IF
#define FAIL_IF(expr)
Fail a test if expression evaluates to true.
Definition: util-unittest.h:71
flags
uint8_t flags
Definition: decode-gre.h:0
AppLayerParserParse
int AppLayerParserParse(ThreadVars *tv, AppLayerParserThreadCtx *alp_tctx, Flow *f, AppProto alproto, uint8_t flags, const uint8_t *input, uint32_t input_len)
Definition: app-layer-parser.c:1277
StreamTcpDisableAppLayer
void StreamTcpDisableAppLayer(Flow *f)
Definition: stream-tcp-reassemble.c:447
suricata-common.h
FLOW_RESET_PE_DONE
#define FLOW_RESET_PE_DONE(f, dir)
Definition: flow.h:280
AppLayerProtoDetectDeSetup
int AppLayerProtoDetectDeSetup(void)
Cleans up the app layer protocol detection phase.
Definition: app-layer-detect-proto.c:1702
ALPROTO_HTTP1
@ ALPROTO_HTTP1
Definition: app-layer-protos.h:36
ALPROTO_PGSQL
@ ALPROTO_PGSQL
Definition: app-layer-protos.h:62
IPPairGetMemuse
uint64_t IPPairGetMemuse(void)
Return memuse value.
Definition: ippair.c:92
Packet_::app_update_direction
uint8_t app_update_direction
Definition: decode.h:535
FLOW_PROTO_DETECT_TS_DONE
#define FLOW_PROTO_DETECT_TS_DONE
Definition: flow.h:104
ALPROTO_FTPDATA
@ ALPROTO_FTPDATA
Definition: app-layer-protos.h:53
AppLayerIncInternalErrorCounter
void AppLayerIncInternalErrorCounter(ThreadVars *tv, Flow *f)
Definition: app-layer.c:189
eps_error_summary
ExceptionPolicyCounters eps_error_summary
Definition: app-layer.c:104
FatalError
#define FatalError(...)
Definition: util-debug.h:514
APPLAYER_DETECT_PROTOCOL_ONLY_ONE_DIRECTION
@ APPLAYER_DETECT_PROTOCOL_ONLY_ONE_DIRECTION
Definition: app-layer-events.h:48
STREAMTCP_FLAG_MIDSTREAM_SYNACK
#define STREAMTCP_FLAG_MIDSTREAM_SYNACK
Definition: stream-tcp-private.h:174
applayer_counter_names
AppLayerCounterNames(* applayer_counter_names)[FLOW_PROTO_APPLAYER_MAX]
Definition: app-layer.c:100
ALPROTO_WEBSOCKET
@ ALPROTO_WEBSOCKET
Definition: app-layer-protos.h:64
TcpSession_::client
TcpStream client
Definition: stream-tcp-private.h:297
PKT_PROTO_DETECT_TC_DONE
#define PKT_PROTO_DETECT_TC_DONE
Definition: decode.h:1302
FrameConfigInit
void FrameConfigInit(void)
Definition: app-layer-frames.c:40
AppLayerParserGetStreamDepth
uint32_t AppLayerParserGetStreamDepth(const Flow *f)
Definition: app-layer-parser.c:1565
tv
ThreadVars * tv
Definition: fuzz_decodepcapfile.c:32
app-layer-events.h
util-validate.h
FlowSwap
void FlowSwap(Flow *f)
swap the flow's direction
Definition: flow.c:246
StatsAddUI64
void StatsAddUI64(ThreadVars *tv, uint16_t id, uint64_t x)
Adds a value of type uint64_t to the local counter.
Definition: counters.c:146
AppLayerProtoDetectSupportedAppProtocols
void AppLayerProtoDetectSupportedAppProtocols(AppProto *alprotos)
Definition: app-layer-detect-proto.c:2087
AppLayerProtoDetectGetProto
AppProto AppLayerProtoDetectGetProto(AppLayerProtoDetectThreadCtx *tctx, Flow *f, const uint8_t *buf, uint32_t buflen, uint8_t ipproto, uint8_t flags, bool *reverse_flow)
Returns the app layer protocol given a buffer.
Definition: app-layer-detect-proto.c:1394
AppLayerProtoDetectGetCtxThread
AppLayerProtoDetectThreadCtx * AppLayerProtoDetectGetCtxThread(void)
Inits and returns an app layer protocol detection thread context.
Definition: app-layer-detect-proto.c:1946
TcpSession_::server
TcpStream server
Definition: stream-tcp-private.h:296
AppLayerProtoDetectGetProtoByName
AppProto AppLayerProtoDetectGetProtoByName(const char *alproto_name)
Definition: app-layer-detect-proto.c:2045
str
#define str(s)
Definition: suricata-common.h:308
SWAP_FLAGS
#define SWAP_FLAGS(flags, a, b)
Definition: suricata-common.h:434
ExceptionPolicyEnumToString
const char * ExceptionPolicyEnumToString(enum ExceptionPolicy policy, bool is_json)
Definition: util-exception-policy.c:39
SCFree
#define SCFree(p)
Definition: util-mem.h:61
AppLayerCounterNames_::gap_error
char gap_error[MAX_COUNTER_SIZE]
Definition: app-layer.c:82
Flow_::alproto_ts
AppProto alproto_ts
Definition: flow.h:443
ExceptionPolicyStatsSetts_::valid_settings_ips
bool valid_settings_ips[EXCEPTION_POLICY_MAX]
Definition: util-exception-policy-types.h:60
TcpSessionSetReassemblyDepth
void TcpSessionSetReassemblyDepth(TcpSession *ssn, uint32_t size)
Definition: stream-tcp.c:7227
Flow_::alstate
void * alstate
Definition: flow.h:471
AppLayerDestroyCtxThread
void AppLayerDestroyCtxThread(AppLayerThreadCtx *app_tctx)
Destroys the context created by AppLayerGetCtxThread().
Definition: app-layer.c:1125
PACKET_PROFILING_APP_START
#define PACKET_PROFILING_APP_START(dp, id)
Definition: util-profiling.h:167
HTPByteRangeMemcapGlobalCounter
uint64_t HTPByteRangeMemcapGlobalCounter(void)
Definition: app-layer-htp-range.c:56
Flow_::flags
uint32_t flags
Definition: flow.h:413
ALPROTO_MDNS
@ ALPROTO_MDNS
Definition: app-layer-protos.h:72
HTPMemcapGlobalCounter
uint64_t HTPMemcapGlobalCounter(void)
Definition: app-layer-htp-mem.c:86
ALPROTO_MQTT
@ ALPROTO_MQTT
Definition: app-layer-protos.h:61
AppLayerGetProtoName
const char * AppLayerGetProtoName(AppProto alproto)
Given the internal protocol id, returns a string representation of the protocol.
Definition: app-layer.c:1005
g_applayerparser_error_policy
enum ExceptionPolicy g_applayerparser_error_policy
Definition: app-layer-parser.c:155
ALPROTO_HTTP
@ ALPROTO_HTTP
Definition: app-layer-protos.h:76
AppLayerCounters_::eps_error
ExceptionPolicyCounters eps_error
Definition: app-layer.c:96
AppLayerIncTxCounter
void AppLayerIncTxCounter(ThreadVars *tv, Flow *f, uint64_t step)
Definition: app-layer.c:157
stream-tcp-util.h
ALPROTO_UNKNOWN
@ ALPROTO_UNKNOWN
Definition: app-layer-protos.h:29
ALPROTO_FAILED
@ ALPROTO_FAILED
Definition: app-layer-protos.h:33
ALPROTO_TEMPLATE
@ ALPROTO_TEMPLATE
Definition: app-layer-protos.h:67
AppLayerCounterNames_::internal_error
char internal_error[MAX_COUNTER_SIZE]
Definition: app-layer.c:84
TcpReassemblyThreadCtx_
Definition: stream-tcp-reassemble.h:61
SCReturnCT
#define SCReturnCT(x, type)
Definition: util-debug.h:295
app-layer-protos.h
AppLayerProfilingReset
#define AppLayerProfilingReset(app_tctx)
Definition: app-layer.h:127
app-layer-htp-mem.h
EngineModeIsIPS
int EngineModeIsIPS(void)
Definition: suricata.c:242
STREAMTCP_FLAG_APP_LAYER_DISABLED
#define STREAMTCP_FLAG_APP_LAYER_DISABLED
Definition: stream-tcp-private.h:201
STREAMTCP_STREAM_FLAG_NOREASSEMBLY
#define STREAMTCP_STREAM_FLAG_NOREASSEMBLY
Definition: stream-tcp-private.h:219
suricata.h
ALPROTO_RFB
@ ALPROTO_RFB
Definition: app-layer-protos.h:60
TEST_END
#define TEST_END
Definition: app-layer.c:1463
StreamUpdateDir
StreamUpdateDir
Definition: stream-tcp-reassemble.h:54
AppLayerProtoDetectDestroyCtxThread
void AppLayerProtoDetectDestroyCtxThread(AppLayerProtoDetectThreadCtx *alpd_tctx)
Destroys the app layer protocol detection thread context.
Definition: app-layer-detect-proto.c:1999
ALPROTO_BITTORRENT_DHT
@ ALPROTO_BITTORRENT_DHT
Definition: app-layer-protos.h:70
ALPROTO_NTP
@ ALPROTO_NTP
Definition: app-layer-protos.h:52
ALPROTO_SMB
@ ALPROTO_SMB
Definition: app-layer-protos.h:43
likely
#define likely(expr)
Definition: util-optimize.h:32
AppLayerParserThreadCtx_
Definition: app-layer-parser.c:60
AppLayerCounterNames_::name
char name[MAX_COUNTER_SIZE]
Definition: app-layer.c:80
FlowChangeProto
int FlowChangeProto(Flow *f)
Check if change proto flag is set for flow.
Definition: flow.c:197
TcpSession_
Definition: stream-tcp-private.h:283
FrameConfigDeInit
void FrameConfigDeInit(void)
Definition: app-layer-frames.c:51
TcpSession_::data_first_seen_dir
int8_t data_first_seen_dir
Definition: stream-tcp-private.h:288
flow.h
Flow_::alproto_tc
AppProto alproto_tc
Definition: flow.h:444
FLOW_PROTO_CHANGE_MAX_DEPTH
#define FLOW_PROTO_CHANGE_MAX_DEPTH
Definition: app-layer.c:76
AppLayerProtoDetectPrepareState
int AppLayerProtoDetectPrepareState(void)
Prepares the internal state for protocol detection. This needs to be called once all the patterns and...
Definition: app-layer-detect-proto.c:1482
Flow_::alproto
AppProto alproto
application level protocol
Definition: flow.h:442
ExceptionPolicy
ExceptionPolicy
Definition: util-exception-policy-types.h:25
StatsRegisterCounter
uint16_t StatsRegisterCounter(const char *name, struct ThreadVars_ *tv)
Registers a normal, unqualified counter.
Definition: counters.c:968
SCCalloc
#define SCCalloc(nm, sz)
Definition: util-mem.h:53
AppLayerCounterNames_::alloc_error
char alloc_error[MAX_COUNTER_SIZE]
Definition: app-layer.c:85
SCReturnInt
#define SCReturnInt(x)
Definition: util-debug.h:285
PACKET_PROFILING_APP_RESET
#define PACKET_PROFILING_APP_RESET(dp)
Definition: util-profiling.h:195
APPLAYER_WRONG_DIRECTION_FIRST_DATA
@ APPLAYER_WRONG_DIRECTION_FIRST_DATA
Definition: app-layer-events.h:47
AppLayerDeSetupCounters
void AppLayerDeSetupCounters(void)
Definition: app-layer.c:1367
DEBUG_VALIDATE_BUG_ON
#define DEBUG_VALIDATE_BUG_ON(exp)
Definition: util-validate.h:102
ALPROTO_NFS
@ ALPROTO_NFS
Definition: app-layer-protos.h:51
ExceptionPolicyStatsSetts_::eps_name
char eps_name[EXCEPTION_POLICY_MAX][EXCEPTION_POLICY_COUNTER_MAX_LEN]
Definition: util-exception-policy-types.h:58
STREAMTCP_STREAM_FLAG_APPPROTO_DETECTION_COMPLETED
#define STREAMTCP_STREAM_FLAG_APPPROTO_DETECTION_COMPLETED
Definition: stream-tcp-private.h:232
AppLayerProtoDetectGetProtoName
const char * AppLayerProtoDetectGetProtoName(AppProto alproto)
Definition: app-layer-detect-proto.c:2070
app-layer.h
Flow_::de_ctx_version
uint32_t de_ctx_version
Definition: flow.h:456