Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
(Forgive the verbosity of this description. I copied it over from our internal repository as it was meant to educate those who were not very familiar with some of the workings of the underlying DA process)
During the deserialization of an object defined within a DA queue file, we will attempt to parse each property of an object in-order based on a ruleset. Each line within the object structure represents a property that is to be applied to the
var
struct. The type and values of the property are separated by:
s. Here's an example of an object structure:A property of an object is represented by the set of characters that precede the first
:
and are after the+
.+tTIMESTAMP:3:35:2:2017:6:14:23:51:48:435524:6:-:7:0:
would equate to atTIMESTAMP
property who's type is3
(VAR_SYSLOGTIMESTAMP). The characters after the next:
represents the value fortTIMESTAMP
, in this case35:2:2017:6:14:23:51:48:435524:6:-:7
.In the case that a single line (property) does not confirm to the specific syntax, rsyslog will stop processing the object and attempt to cleanup anything it has already created. Of particular interest is the Destruct function of the var_t type.
var_t
is a structure that essentially represents a single property during serialization. A type enum is assigned with the appropriate value. If the type isVARTYPE_STR
, the destruct function will do what is as expected which is to free up the memory allocated for thechar *
value that was assigned to it during deserialization. If thevar_t
struct is a number, for instance, there is nothing to do since we did not previously allocate any memory for the value.Now, what happens when a property is deserialized that isn't correctly named? Let's take an object definition like the following:
This is what an object looks like that would create a corrupt DA queue file. The line that will break the deserialization is
+tTIME<Obj:1:msg:1:
. This is because<Obj
is the entry point for any new object.When we attempt to deserialize the object, everything works out fine until we get to the property
+tTIME<Obj:1:msg:1:
. In the steps to deserialize the line, we will first grab the name (+tTIME<Obj
) then grab the type, which is1
orVARTYPE_STR
and then the number of characters that represents the value of the string.It is in step 3 of this use-case where the deserialization will fail. What is important to note here is that we've already assigned the
var_t
type variablepProp
as aVARTYPE_STR
. Since we failed to grab the size of the string from the valuemsg
(makes sense!), we break out of our deserialization process and attempt to cleanup what we have already created.Now, we're back to the
Destruct
function. Since thevar_t
struct is of typeVARTYPE_STR
will attempt to free up the memory allocated to the value of thevar_t
. But, in our deserialization process, we never got to that point. We now enter a place that is terrible for any C program which is attempting to free unallocated memory. At this point rsyslog dies without any indication as to what was going on.My solution is to ensure that if we get through the deserialization process of a property without having completed extraction of the
var_t
value, we reset the type of the property toVARTYPE_NULL
. That way when cleaning up after a deserialization failure, we do not attempt to free anything we do not own.