[Bro] Running external command line programs
Chris Crawford
christopher.p.crawford at gmail.com
Fri Feb 22 08:59:09 PST 2013
Cool -- that did the trick. This is really good stuff.
I decided to try using this against other bro events, besides just
bro_init():
$ cat exec-test.bro
@load ./exec
event dns_message(c: connection, is_orig: bool, msg: dns_msg, len: count)
{
Exec::run("./hello", function(r: Exec::Result)
{
if ( ! r?$stdout )
{
print "nothing?!?";
return;
}
for ( i in r$stdout )
{
print r$stdout[i];
}
});
}
./hello is just a hello world program.
So, when I test that, I see the following.
$ bro -r test.pcap exec-test.bro
Hello World
Hello World
Hello World
nothing?!?
ERROR: 1361476370.202590 no such index (Exec::results[Exec::name])
(././exec.bro, line 25)
[...]
This got me wondering -- why would exec-test.bro ever have a case where (!
r?$stdout) is true, when I have a program that absolutely returns output
every time it's run? (And then print out "nothing?!?")
For convenience:
# exec.bro
21 event Exec::stdout_line(description: Input::EventDescription, tpe:
Input::Event, s: string)
22 {
23 local name = sub(description$name, /_[^_]*$/, "");
24
25 if ( ! results[name]?$stdout )
26 results[name]$stdout = vector(s);
27 else
28 results[name]$stdout[|results[name]$stdout|] = s;
29 }
It's also worth noting that exec.bro really trashes the /tmp directory at
this point.
# exec.bro
94 function run(cmd: string, cb: function(r: Result))
95 {
96 local tmpfile = "/tmp/bro-exec-" + unique_id("");
97 system(fmt("touch %s_done", tmpfile));
98 system(fmt("touch %s_stdout", tmpfile));
99 system(fmt("touch %s_stderr", tmpfile));
100 # Sleep for 1 sec before writing to the done file to avoid race
conditions
101 # This makes sure that all of the data is read from
102 system(fmt("%s 2>>%s_stderr 1>> %s_stdout; echo
\"exit_code:${?}\" > %s_done; sleep 1; echo \"done\" >> %s_done", cmd, tmpf
103
104 results[tmpfile] = [];
105 callbacks[tmpfile] = cb;
106
107 schedule 1msec { start_watching_files(tmpfile) };
108 }
That chunk of code probably needs something like this:
system(fmt("rm %s_done", tmpfile));
system(fmt("rm %s_stdout", tmpfile));
system(fmt("rm %s_stderr", tmpfile));
I'm just not sure where it should go.
-Chris
On Thu, Feb 21, 2013 at 4:54 PM, Seth Hall <seth at icir.org> wrote:
>
> On Feb 21, 2013, at 4:47 PM, Chris Crawford <
> christopher.p.crawford at gmail.com> wrote:
>
> > Is there another way to load the listen script?
>
> Oh, I think it's because you're reading a packet capture. When reading
> packets from a file you can't enable the communication framework.
>
> Just try taking out the -r argument. You should be able to just put
> frameworks/communication/listen on the command line too instead of the full
> file path. Also, Bro won't terminate until you kill it.
>
> .Seth
>
> --
> Seth Hall
> International Computer Science Institute
> (Bro) because everyone has a network
> http://www.bro-ids.org/
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://mailman.ICSI.Berkeley.EDU/pipermail/bro/attachments/20130222/9a226230/attachment.html
More information about the Bro
mailing list