* origin/topic/robin/interpreter-exceptions:
Adding test for new error handling.
Experimental code to better handle interpreter errors.
This seems to work fine and it catches some potentially nasty crashes
so I'm merging it in even though it's not the final word on error
handling yet. #646 tracks the work scheduled for later.
Currently, a lot of interpreter runtime errors, such as an access to
an unset optional record field, cause Bro to abort with an internal
error. This is an experimental branch that turns such errors into
non-fatal runtime errors by internally raising exceptions. These are
caught upstream and processing continues afterwards.
For now, not many errors actually raise exceptions (the example above
does though). We'll need to go through them eventually and adapt the
current Internal() calls (and potentially others). More generally, at
some point we should cleanup the interpreter error handling (unifying
errors reported at parse- and runtime; and switching to exceptions for
all Expr/Stmt/Vals). But that's a larger change and left for later.
The main question for now is if this code is already helpful enough to
go into 2.0. It will quite likely prevent a number of crashes due to
script errors.
Some of the changes only clean up at termination to make perftools
happt, but there were some "real" leaks as well.
This fixes all DNS leaks I could reproducem, including most likely
what's reported in #534. Closing #534.
I'm also adding a new btest subdir core/leaks with tests requiring
perftools support. These don't compare against base lines but abort
whenever perftools reports a leak (with stack information to track it
down). Right now, these are passing.
* origin/topic/jsiwek/path-func-record-demote:
Fix filter path_func to allow record argument as a subset of stream's columns.
Conflicts:
src/LogMgr.cc
Closes#600.
This required adding the ability for RecordVal::CoerceTo functions to
optionally allow orphaning fields. The default is to not allow it, but
now before writing to a log, the value of the stream's columns is coerced
down, if necessary, before passing it on to the filter's path_func.
Addresses #600.
When using a `print` statement to write to a file that has raw output
enabled, NUL characters in string are no longer interpreted into "\0",
no newline is appended afterwards, and each argument to `print` is
written to the file without any additional separation.
(Re)Assigning to identifiers with the &raw_output attribute should also
now correctly apply the attribute to the file value being assigned.
Note that the write_file BiF should already be capable of raw string
data to a file, expect it bypasses the print_hook event.
Addresses #474
The Logger class is now in charge of reporting all errors, warnings,
informational messages, weirds, and syslogs. All other components
route their messages through the global bro_logger singleton.
The Logger class comes with these reporting methods:
void Message(const char* fmt, ...);
void Warning(const char* fmt, ...);
void Error(const char* fmt, ...);
void FatalError(const char* fmt, ...); // Terminate Bro.
void Weird(const char* name);
[ .. some more Weird() variants ... ]
void Syslog(const char* fmt, ...);
void InternalWarning(const char* fmt, ...);
void InternalError(const char* fmt, ...); // Terminates Bro.
See Logger.h for more information on these.
Generally, the reporting now works as follows:
- All non-fatal message are reported in one of two ways:
(1) At startup (i.e., before we start processing packets),
they are logged to stderr.
(2) During processing, they turn into events:
event log_message%(msg: string, location: string%);
event log_warning%(msg: string, location: string%);
event log_error%(msg: string, location: string%);
The script level can then handle them as desired.
If we don't have an event handler, we fall back to
reporting on stderr.
- All fatal errors are logged to stderr and Bro terminates
immediately.
- Syslog(msg) directly syslogs, but doesn't do anything else.
The three main types of messages can also be generated on the
scripting layer via new Log::* bifs:
Log::error(msg: string);
Log::warning(msg: string);
Log::message(msg: string);
These pass through the bro_logger as well and thus are handled in the
same way. Their output includes location information.
More changes:
- Removed the alarm statement and the alarm_hook event.
- Adapted lots of locations to use the bro_logger, including some
of the messages that were previously either just written to
stdout, or even funneled through the alarm mechanism.
- No distinction anymore between Error() and RunTime(). There's
now only one class of errors; the line was quite blurred already
anyway.
- util.h: all the error()/warn()/message()/run_time()/pinpoint()
functions are gone. Use the bro_logger instead now.
- Script errors are formatted a bit differently due to the
changes. What I've seen so far looks ok to me, but let me know
if there's something odd.
Notes:
- The default handlers for the new log_* events are just dummy
implementations for now since we need to integrate all this into
the new scripts anyway.
- I'm not too happy with the names of the Logger class and its
instance bro_logger. We now have a LogMgr as well, which makes
this all a bit confusing. But I didn't have a good idea for
better names so I stuck with them for now.
Perhaps we should merge Logger and LogMgr?
This is obviously a change that break backwards-compatibility. I hope
I caught all cases where vectors are used ...
I've completely removed the VECTOR_MIN constant. Turns out that was
already not working: some code pieces were nevertheless hard-coding
the 1-based indexing ...
* topic/robin/record-coercion:
Fixing a bug with nested record ctors.
Enabling automatic coercion from record type A to be B as long as A has all the types that B has.
Conflicts:
src/Expr.cc
Changed BroType to track a char* instead of an ID* that represents
the declared type's identifier. It was also necessary to serialize
this information or else it can be lost (e.g. FieldDecl's in RecordType
always seem to get serialized at some point).
DescribeReST() functions added to many classes to get the output
closer to being reST compatible; still needs tweaking for Sphinx
(reST->HTML) compatibility.
* origin/topic/gregor/fix-val-64bit:
Fixing endianess error in XDR when data is not 4-byte aligned.
Fix for Val constructor with new int64 typedefs.
New fix for OS X 10.5 compile error wrt llabs()
Revert "Fix for OS X 10.5 compile error wrt llabs()"
logging framework.
- To enable passing a type into a bif, there's now a new
BroType-derived class TypeType and a corresponding TYPE_TYPE tag.
With that, a Val can now have a type as its value.
This is experimental for now.
- RecordVal's get a new method CoerceTo() to coerce their value into a
another record type with the usual semantics. Most of the code in
there was previously in RecordContructorExpr::InitVal(), which is
now calling the new CoerceTo() method.
Observed on FreeBSD build that the compiler would emit an error claiming
Val(abs(val.int_val), TYPE_COUNT)
is ambiguous because it can't make a choice between cstdlib's
"int abs(int)" or "long abs(long)" signatures. And actually, since
we now always use 64 bit integers for bro_int_t, we can use
"long long llabs(long long)".