IPv4 for now.<br><br>I see that IPv6 is supported by libgeoip, so it should be straightforward to implement. <br><br><div class="gmail_quote">On Sun, Oct 14, 2012 at 11:45 AM, Peter Manev <span dir="ltr"><<a href="mailto:petermanev@gmail.com" target="_blank">petermanev@gmail.com</a>></span> wrote:<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Hi,<br>I was wondering if the geoip word is IPv4 only? or it supports both IPv6 and v4 ?<br><br>thanks<div class="HOEnZb">
<div class="h5"><br><br><div class="gmail_quote">On Sun, Oct 14, 2012 at 1:25 AM, I. Sanchez <span dir="ltr"><<a href="mailto:sanchezmartin.ji@gmail.com" target="_blank">sanchezmartin.ji@gmail.com</a>></span> wrote:<br>

<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">It is fixed now. It was a silly issue with one "if" (plus a few other minor issues in the option string parser).<br>

<br>Now everything seems to be working ok. <br><br>The match function looks like this now:<br><br>
<pre><div><div><span>static</span> <span>int</span> <span>DetectGeoipMatch</span><span>(</span><span>ThreadVars</span> <span>*</span><span>t</span><span>,</span> <span>DetectEngineThreadCtx</span> <span>*</span><span>det_ctx</span><span>,</span></div>


<div>                             <span>Packet</span> <span>*</span><span>p</span><span>,</span> <span>Signature</span> <span>*</span><span>s</span><span>,</span> <span>SigMatch</span> <span>*</span><span>m</span><span>)</span></div>


<div><span>{</span></div><div>    <span>DetectGeoipData</span> <span>*</span><span>geoipdata</span> <span>=</span> <span>(</span><span>DetectGeoipData</span> <span>*</span><span>)</span><span>m</span><span>-></span><span>ctx</span><span>;</span></div>


<div>    <span>int</span> <span>match</span> <span>=</span> <span>0</span><span>;</span></div><div>    <span>int</span> <span>matches</span> <span>=</span> <span>0</span><span>;</span></div>
<div><br></div></div><div><div>    <span>if</span> <span>(</span><span>PKT_IS_IPV4</span><span>(</span><span>p</span><span>))</span></div>
<div>    <span>{</span></div><div>        <span>if</span> <span>(</span><span>geoipdata</span><span>-></span><span>flags</span> <span>&</span> <span>GEOIP_MATCH_SRC_FLAG</span> <span>||</span> <span>geoipdata</span><span>-></span><span>flags</span> <span>&</span> <span>GEOIP_MATCH_BOTH_FLAG</span><span>)</span></div>


<div>        <span>{</span>        </div><div>            <span>/* if there is a flow get SRC IP of the flow, not packet */</span>            </div><div>
            <span>if</span> <span>(</span><span>p</span><span>-></span><span>flowflags</span> <span>&</span> <span>FLOW_PKT_TOCLIENT</span><span>)</span></div>
</div><div><div>                <span>/* the dst (from server to client) is our src */</span></div></div><div>                <span>match</span> <span>=</span> <span>CheckGeoMatchIPv4</span><span>(</span><span>geoipdata</span><span>,</span> <span>GET_IPV4_DST_ADDR_U32</span><span>(</span><span>p</span><span>));</span></div>


<div>            <span>else</span> </div><div>                <span>match</span> <span>=</span> <span>CheckGeoMatchIPv4</span><span>(</span><span>geoipdata</span><span>,</span> <span>GET_IPV4_SRC_ADDR_U32</span><span>(</span><span>p</span><span>));</span></div>


<div>            <span>if</span> <span>(</span><span>match</span><span>)</span></div><div>            <span>{</span></div><div>
                <span>if</span> <span>(</span><span>geoipdata</span><span>-></span><span>flags</span> <span>&</span> <span>GEOIP_MATCH_BOTH_FLAG</span><span>)</span></div><div>
<div>                    <span>matches</span><span>++</span><span>;</span></div><div>                <span>else</span>                    </div>
<div>                    <span>return</span> <span>1</span><span>;</span></div><div>            <span>}</span></div><div>
        <span>}</span></div><div>        <span>if</span> <span>(</span><span>geoipdata</span><span>-></span><span>flags</span> <span>&</span> <span>GEOIP_MATCH_DST_FLAG</span> <span>||</span> <span>geoipdata</span><span>-></span><span>flags</span> <span>&</span> <span>GEOIP_MATCH_BOTH_FLAG</span><span>)</span></div>


<div>        <span>{</span>     </div><div>            <span>/* if there is a flow get DST IP of the flow, not packet */</span>            </div><div>
            <span>if</span> <span>(</span><span>p</span><span>-></span><span>flowflags</span> <span>&</span> <span>FLOW_PKT_TOCLIENT</span><span>)</span></div>
</div><div><div>                <span>/* the src (from server to client) is our dst */</span></div></div><div>                <span>match</span> <span>=</span> <span>CheckGeoMatchIPv4</span><span>(</span><span>geoipdata</span><span>,</span> <span>GET_IPV4_SRC_ADDR_U32</span><span>(</span><span>p</span><span>));</span></div>


<div>            <span>else</span> </div><div>                <span>match</span> <span>=</span> <span>CheckGeoMatchIPv4</span><span>(</span><span>geoipdata</span><span>,</span> <span>GET_IPV4_DST_ADDR_U32</span><span>(</span><span>p</span><span>));</span></div>


<div>            <span>if</span> <span>(</span><span>match</span><span>)</span></div><div>            <span>{</span></div><div>
                <span>if</span> <span>(</span><span>geoipdata</span><span>-></span><span>flags</span> <span>&</span> <span>GEOIP_MATCH_BOTH_FLAG</span><span>)</span></div><div>
<div>                    <span>matches</span><span>++</span><span>;</span></div><div>                <span>else</span>                    </div>
<div>                    <span>return</span> <span>1</span><span>;</span></div><div>            <span>}</span></div><div>
        <span>}</span></div><div>        <span>/* if matches == 2 is because match-on is "both" */</span></div><div>        <span>if</span> <span>(</span><span>matches</span> <span>==</span> <span>2</span><span>)</span> </div>


<div>            <span>return</span> <span>1</span><span>;</span></div><div>    <span>}</span></div><div>    </div>
<div>    <span>return</span> <span>0</span><span>;</span></div><div><span>}</span></div></div></pre><div><div><br><br><div class="gmail_quote">On Sat, Oct 13, 2012 at 9:46 PM, I. Sanchez <span dir="ltr"><<a href="mailto:sanchezmartin.ji@gmail.com" target="_blank">sanchezmartin.ji@gmail.com</a>></span> wrote:<br>


<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Ok, I have done an initial implementation (just country geolocation for now). It is available at <a href="https://github.com/owlsec/suricata/tree/geoip" target="_blank">https://github.com/owlsec/suricata/tree/geoip</a><br>


<br>When checking a packet, I take into account the flow source and destination IPs for the match-on condition, if a flow exists. However in my tests I have seen it is not working well... a geoip:src,US; rule will be triggered as well when talking HTTP to <a href="http://google.com" target="_blank">google.com</a> from a non US source IP address.<br>



<br>I am not sure about the reason of this behavior, so perhaps somebody could let me know what is wrong here.<br><br><a href="https://github.com/owlsec/suricata/blob/geoip/src/detect-geoip.c" target="_blank">https://github.com/owlsec/suricata/blob/geoip/src/detect-geoip.c</a><br>



<br>The relevant function is this one:<br><br><pre><div><span>static</span> <span>int</span> <span>DetectGeoipMatch</span><span>(</span><span>ThreadVars</span> <span>*</span><span>t</span><span>,</span> <span>DetectEngineThreadCtx</span> <span>*</span><span>det_ctx</span><span>,</span></div>



<div>                             <span>Packet</span> <span>*</span><span>p</span><span>,</span> <span>Signature</span> <span>*</span><span>s</span><span>,</span> <span>SigMatch</span> <span>*</span><span>m</span><span>)</span></div>



<div><span>{</span></div><div>    <span>DetectGeoipData</span> <span>*</span><span>geoipdata</span> <span>=</span> <span>(</span><span>DetectGeoipData</span> <span>*</span><span>)</span><span>m</span><span>-></span><span>ctx</span><span>;</span></div>



<div>    <span>int</span> <span>match</span> <span>=</span> <span>0</span><span>;</span></div><div>    <span>int</span> <span>matches</span> <span>=</span> <span>0</span><span>;</span></div>
<div>    <span>uint32_t</span> <span>ip</span><span>;</span></div><div><br></div><div>    <span>if</span> <span>(</span><span>PKT_IS_IPV4</span><span>(</span><span>p</span><span>))</span></div>
<div>    <span>{</span></div><div>        <span>if</span> <span>(</span><span>geoipdata</span><span>-></span><span>flags</span> <span>&</span> <span>GEOIP_MATCH_SRC_FLAG</span> <span>||</span> <span>geoipdata</span><span>-></span><span>flags</span> <span>&</span> <span>GEOIP_MATCH_BOTH_FLAG</span><span>)</span></div>



<div>        <span>{</span>        </div><div>            <span>/* if there is a flow get SRC IP of the flow, not packet */</span>            </div><div>
            <span>if</span> <span>(</span><span>p</span><span>-></span><span>flowflags</span> <span>&</span> <span>FLOW_PKT_TOCLIENT</span><span>)</span></div>
<div>                <span>ip</span> <span>=</span> <span>GET_IPV4_DST_ADDR_U32</span><span>(</span><span>p</span><span>);</span> <span>/* the dst (from server to client) is our src */</span></div>
<div>            <span>else</span> </div><div>                <span>ip</span> <span>=</span> <span>GET_IPV4_SRC_ADDR_U32</span><span>(</span><span>p</span><span>);</span></div>
<div>            <span>match</span> <span>=</span> <span>CheckGeoMatchIPv4</span><span>(</span><span>geoipdata</span><span>,</span> <span>ip</span><span>);</span></div>
<div>            <span>if</span> <span>(</span><span>match</span> <span>&&</span> <span>geoipdata</span><span>-></span><span>flags</span> <span>&</span> <span>GEOIP_MATCH_BOTH_FLAG</span><span>)</span></div>



<div>                <span>matches</span><span>++</span><span>;</span></div><div>            <span>else</span>                    </div>
<div>                <span>return</span> <span>1</span><span>;</span></div><div>        <span>}</span></div><div>
        <span>if</span> <span>(</span><span>geoipdata</span><span>-></span><span>flags</span> <span>&</span> <span>GEOIP_MATCH_DST_FLAG</span> <span>||</span> <span>geoipdata</span><span>-></span><span>flags</span> <span>&</span> <span>GEOIP_MATCH_BOTH_FLAG</span><span>)</span></div>



<div>        <span>{</span>     </div><div>            <span>/* if there is a flow get DST IP of the flow, not packet */</span>            </div><div>
            <span>if</span> <span>(</span><span>p</span><span>-></span><span>flowflags</span> <span>&</span> <span>FLOW_PKT_TOCLIENT</span><span>)</span></div>
<div>                <span>ip</span> <span>=</span> <span>GET_IPV4_SRC_ADDR_U32</span><span>(</span><span>p</span><span>);</span> <span>/* the src (from server to client) is our dst */</span></div>
<div>            <span>else</span> </div><div>                <span>ip</span> <span>=</span> <span>GET_IPV4_DST_ADDR_U32</span><span>(</span><span>p</span><span>);</span></div>
<div>            <span>match</span> <span>=</span> <span>CheckGeoMatchIPv4</span><span>(</span><span>geoipdata</span><span>,</span> <span>ip</span><span>);</span></div>
<div>            <span>if</span> <span>(</span><span>match</span> <span>&&</span> <span>geoipdata</span><span>-></span><span>flags</span> <span>&</span> <span>GEOIP_MATCH_BOTH_FLAG</span><span>)</span></div>



<div>                <span>matches</span><span>++</span><span>;</span></div><div>            <span>else</span>                    </div>
<div>                <span>return</span> <span>1</span><span>;</span></div><div>        <span>}</span></div><div>
<br></div><div>        <span>/* if matches == 2 is because match-on is "both" */</span></div><div>        <span>if</span> <span>(</span><span>matches</span> <span>==</span> <span>2</span><span>)</span> </div>
<div>            <span>return</span> <span>1</span><span>;</span></div><div>    <span>}</span></div><div>    </div>
<div>    <span>return</span> <span>0</span><span>;</span></div><div><span>}<br></span></div></pre><div><div><br><br><div class="gmail_quote">On Fri, Oct 12, 2012 at 11:35 AM, I. Sanchez <span dir="ltr"><<a href="mailto:sanchezmartin.ji@gmail.com" target="_blank">sanchezmartin.ji@gmail.com</a>></span> wrote:<br>



<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Yes, I forgot to mention it. Negation will be supported.<div><div><br><br><div class="gmail_quote">
On Fri, Oct 12, 2012 at 10:03 AM, Peter Manev <span dir="ltr"><<a href="mailto:petermanev@gmail.com" target="_blank">petermanev@gmail.com</a>></span> wrote:<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Excellent - thank you.<br>comments bellow ...<br><br><div class="gmail_quote"><div>On Thu, Oct 11, 2012 at 10:07 PM, I. Sanchez <span dir="ltr"><<a href="mailto:sanchezmartin.ji@gmail.com" target="_blank">sanchezmartin.ji@gmail.com</a>></span> wrote:<br>





<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Good idea, I will implement multiple conditions(countries) in the same rule. Let's use the <match-on><condition>+ syntax where match-on can be src, dst, both or any.<div>





<br><br><div style="margin-left:40px">alert http any any -> any any (msg:"GEOIP: IP located in US/Germany/Canada/France";<b> geoip:src,US,DE,CA,FR</b>; sid:3450002; rev:1;)<br>
</div><br></div>I can also support geoip:US; by assuming geoip:any,US; , for simplicity. <br></blockquote></div><div><br>I agree with the assumption here - i think it is good to assume so. <br>I was thinking further on the matter and I am not sure if i am starting to sound annoying - but wouldn't it be nice if we can also negate geoip? :<br>





alert http any any -> any any (msg:"GEOIP: IP destination  <b>NOT</b> located in US/Canada";<b> </b>geoip:<b>dst,!</b>US,CA; sid:3450002; rev:1;)<br><br><br></div><div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">





<br>Regarding the city support, indeed the MaxMind DBs in their free versions support cities in addition to countries although the accuracy drops from 99.5% (for countries) to 78% in US (for cities), and I guess much less accuracy in other countries. <br>






<br>In the commercial DBs, they apparently support regions, organizations... <a href="http://www.maxmind.com/en/geolocation_landing" target="_blank">http://www.maxmind.com/en/geolocation_landing</a><br><br>For now I will just implement support for countries, but we should take this into account for the keyword syntax. I see some options:<br>






<ul><li>Autodetect city vs country. I could detect whether the condition is a known country code, and assume city otherwise. However this will not work for regions, organizations...</li><li>Allow -for future versions- the check type as an optional param of the <match-on> condition. ie: geoip:src,city,Madrid;</li>





</ul></blockquote></div><div><br>this would be awesome in my opinion. <br></div><div><div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><ul>
</ul>Regards,<div><div><br><br><br><br><br><div class="gmail_quote">On Thu, Oct 11, 2012 at 9:02 PM, Peter Manev <span dir="ltr"><<a href="mailto:petermanev@gmail.com" target="_blank">petermanev@gmail.com</a>></span> wrote:<br>






<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Hi,<br><br>I think i love that new geoip keyword - thank you for the efforts !<br><br>A couple of suggestions/requests if I may:<br>






<br>1.I agree/like the proposal - but I wonder if it would be possible to include multiples(maybe up to a certain number [32 or something] ) of countries - like:<br>
alert http any any -> any any (msg:"GEOIP: IP located in US/Germany/Canada/France";<b> geoip:src,US,DE,CA,FR</b>; sid:3450002; rev:1;)<br><br>2. As there is - <b>src, dst, both</b> - i think it would be nice if there is also "<b>any</b>" - <br>







alert http any any -> any any (msg:"GEOIP: some traffic to/from the Cayman Islands";<b> geoip:any,KY</b>; sid:3450005; rev:1;)<br>any - meaning either source or destination.<br><br>thanks a bunch!<div>
<div><br><br><div class="gmail_quote">
On Thu, Oct 11, 2012 at 6:42 PM, Victor Julien <span dir="ltr"><<a href="mailto:victor@inliniac.net" target="_blank">victor@inliniac.net</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">







<div>On 10/11/2012 06:16 PM, I. Sanchez wrote:<br>
> Hi,<br>
><br>
> I am implementing support for IP address country geolocation in<br>
> Suricata, and I wanted to ask your opinion about the syntax to be used<br>
> for the geoip keyword options.<br>
><br>
> <a href="https://redmine.openinfosecfoundation.org/issues/559" target="_blank">https://redmine.openinfosecfoundation.org/issues/559</a><br>
><br>
> The keyword options would be:<br>
><br>
</div>>   * Country code. ie: US<br>
>   * Match condition: match on source IP, match on destination IP, or<br>
<div>>     match on both.<br>
><br>
> What do you think would be the best syntax for this?<br>
><br>
> Some possibilities:<br>
><br>
</div>>   * geoip:<src|dst|both>,<countrycode>;<br>
>       o alert http any any -> any any (msg:"GEOIP: IP located in<br>
>         US";*geoip:src,US*;sid:3450002;rev:1;)<br>
>   * geoip:<countrycode>,<src|dst|both>;<br>
>       o alert http any any -> any any (msg:"GEOIP: IP located in<br>
>         US";*geoip:US,src*;sid:3450002;rev:1;)<br>
<br>
Thanks for picking this up!<br>
<br>
Doesn't the geoip also allow for other types of data, such as city? I'm<br>
sure that if we have this in Suricata ppl will be interested in buying<br>
the more detailed databases as well.<br>
<span><font color="#888888"><br>
--<br>
---------------------------------------------<br>
Victor Julien<br>
<a href="http://www.inliniac.net/" target="_blank">http://www.inliniac.net/</a><br>
PGP: <a href="http://www.inliniac.net/victorjulien.asc" target="_blank">http://www.inliniac.net/victorjulien.asc</a><br>
---------------------------------------------<br>
</font></span><div><div><br>
_______________________________________________<br>
Oisf-devel mailing list<br>
<a href="mailto:Oisf-devel@openinfosecfoundation.org" target="_blank">Oisf-devel@openinfosecfoundation.org</a><br>
<a href="https://lists.openinfosecfoundation.org/mailman/listinfo/oisf-devel" target="_blank">https://lists.openinfosecfoundation.org/mailman/listinfo/oisf-devel</a><br>
</div></div></blockquote></div><br><br clear="all"><br></div></div><span><font color="#888888">-- <br><div>Regards,</div>
<div>Peter Manev</div><br>
</font></span><br>_______________________________________________<br>
Oisf-devel mailing list<br>
<a href="mailto:Oisf-devel@openinfosecfoundation.org" target="_blank">Oisf-devel@openinfosecfoundation.org</a><br>
<a href="https://lists.openinfosecfoundation.org/mailman/listinfo/oisf-devel" target="_blank">https://lists.openinfosecfoundation.org/mailman/listinfo/oisf-devel</a><br></blockquote></div><br>
</div></div></blockquote></div></div></div><span><font color="#888888"><br><br clear="all"><br>-- <br><div>Regards,</div>
<div>Peter Manev</div><br>
</font></span></blockquote></div><br>
</div></div></blockquote></div><br>
</div></div></blockquote></div><br>
</div></div></blockquote></div><br><br clear="all"><br></div></div><span class="HOEnZb"><font color="#888888">-- <br><div>Regards,</div>
<div>Peter Manev</div><br>
</font></span></blockquote></div><br>