haproxy/contrib/spoa_example
Thierry FOURNIER c4dcaff3f0 BUG/MEDIUM: spoe: Flags are not encoded in network order
The flags are direct copy of the "unsigned int" in the network stream,
so the stream contains a 32 bits field encoded with the host endian.
 - This is not reliable for stream betwen different architecture host
 - For x86, the bits doesn't correspond to the documentation.

This patch add some precision in the documentation and put the bitfield
in the stream usig network butes order.

Warning: this patch can break compatibility with existing agents.

This patch should be backported in all version supporing SPOE

Original network capture:

   12:28:16.181343 IP 127.0.0.1.46782 > 127.0.0.1.12345: Flags [P.], seq 134:168, ack 59, win 342, options [nop,nop,TS val 2855241281 ecr 2855241281], length 34
           0x0000:  4500 0056 6b94 4000 4006 d10b 7f00 0001  E..Vk.@.@.......
           0x0010:  7f00 0001 b6be 3039 a3d1 ee54 7d61 d6f7  ......09...T}a..
           0x0020:  8018 0156 fe4a 0000 0101 080a aa2f 8641  ...V.J......./.A
           0x0030:  aa2f 8641 0000 001e 0301 0000 0000 010f  ./.A............
                                          ^^^^^^^^^^
           0x0040:  6368 6563 6b2d 636c 6965 6e74 2d69 7001  check-client-ip.
           0x0050:  0006 7f00 0001                           ......

Fixed network capture:

   12:24:26.948165 IP 127.0.0.1.46706 > 127.0.0.1.12345: Flags [P.], seq 4066280627:4066280661, ack 3148908096, win 342, options [nop,nop,TS val 2855183972 ecr 2855177690], length 34
           0x0000:  4500 0056 0538 4000 4006 3768 7f00 0001  E..V.8@.@.7h....
           0x0010:  7f00 0001 b672 3039 f25e 84b3 bbb0 8640  .....r09.^.....@
           0x0020:  8018 0156 fe4a 0000 0101 080a aa2e a664  ...V.J.........d
           0x0030:  aa2e 8dda 0000 001e 0300 0000 0114 010f  ................
                                          ^^^^^^^^^^
           0x0040:  6368 6563 6b2d 636c 6965 6e74 2d69 7001  check-client-ip.
           0x0050:  0006 7f00 0001                           ......
2018-05-18 13:50:53 +02:00
..
include CONTRIB: spoa_example: remove SPOE enums that are useless for clients 2017-11-21 21:33:27 +01:00
Makefile BUILD: Fix LDFLAGS vs. LIBS re linking order in various makefiles 2017-12-02 14:36:15 +01:00
README MINOR: spoe: Remove useless 'timeout ack' option 2016-11-21 15:29:59 +01:00
spoa.c BUG/MEDIUM: spoe: Flags are not encoded in network order 2018-05-18 13:50:53 +02:00

A Random IP reputation service acting as a Stream Processing Offload Agent
--------------------------------------------------------------------------

This is a very simple service that implement a "random" ip reputation
service. It will return random scores for all checked IP addresses. It only
shows you how to implement a ip reputation service or such kind of services
using the SPOE.


  Start the service
---------------------

After you have compiled it, to start the service, you just need to use "spoa"
binary:

    $> ./spoa  -h
    Usage: ./spoa [-h] [-d] [-p <port>] [-n <num-workers>]
        -h                  Print this message
        -d                  Enable the debug mode
        -p <port>           Specify the port to listen on (default: 12345)
        -n <num-workers>    Specify the number of workers (default: 5)

Note: A worker is a thread.


  Configure a SPOE to use the service
---------------------------------------

All information about SPOE configuration can be found in "doc/SPOE.txt". Here is
the configuration template to use for your SPOE:

    [ip-reputation]

    spoe-agent iprep-agent
        messages check-client-ip

        option var-prefix iprep

        timeout hello      100ms
        timeout idle       30s
        timeout processing 15ms

        use-backend iprep-backend

    spoe-message check-client-ip
        args src
        event on-client-session


The engine is in the scope "ip-reputation". So to enable it, you must set the
following line in a frontend/listener section:

    frontend my-front
        ...
        filter spoe engine ip-reputation config /path/spoe-ip-reputation.conf
	....

where "/path/spoe-ip-reputation.conf" is the path to your SPOE configuration
file. The engine name is important here, it must be the same than the one used
in the SPOE configuration file.

IMPORTANT NOTE:
    Because we want to send a message on the "on-client-session" event, this
    SPOE must be attached to a proxy with the frontend capability. If it is
    declared in a backend section, it will have no effet.


Because, in SPOE configuration file, we declare to use the backend
"iprep-backend" to communicate with the service, you must define it in HAProxy
configuration. For example:

    backend iprep-backend
        mode tcp
	timeout server 1m
	server iprep-srv 127.0.0.1:12345 check maxconn 5


In reply to the "check-client-ip" message, this service will set the variable
"ip_score" for the session, an integer between 0 and 100. If unchanged, the
variable prefix is "iprep". So the full variable name will be
"sess.iprep.ip_score".

You can use it in ACLs to experiment the SPOE feature. For example:

    tcp-request content reject if { var(sess.iprep.ip_score) -m int lt 20 }

With this rule, all IP address with a score lower than 20 will be rejected
(Remember, this score is random).