There is a null-pointer dereference bug in libotr 4.0.0 that is triggered by using OTRL_INSTAG_RECENT with otrl_message_sending. When a new OTR context is created via the add_context part in otrl_message_sending, the recent_child field is not set. On the next message otrl_message_sending crashes because even though there is a context, otrl_context_find returns NULL.
The following (untested) patch lets otrl_context_find_recent_instance default to returning the master context when recent_child or one of its friends is not set.
--- a/src/context.c
+++ b/src/context.c
@@ -168,6 +168,7 @@ static ConnContext * new_context(const char * user, const char * accountname,
ConnContext * otrl_context_find_recent_instance(ConnContext * context,
otrl_instag_t recent_instag) {
ConnContext * m_context;
+ ConnContext * recent_child;
if (!context) return NULL;
@@ -177,14 +178,19 @@ ConnContext * otrl_context_find_recent_instance(ConnContext * context,
switch(recent_instag) {
case OTRL_INSTAG_RECENT:
- return m_context->recent_child;
+ recent_child = m_context->recent_child;
case OTRL_INSTAG_RECENT_RECEIVED:
- return m_context->recent_rcvd_child;
+ recent_child = m_context->recent_rcvd_child;
case OTRL_INSTAG_RECENT_SENT:
- return m_context->recent_sent_child;
+ recent_child = m_context->recent_sent_child;
default:
- return NULL;
+ recent_child = NULL;
}
+
+ if(recent_child)
+ return recent_child;
+ else
+ return m_context; /* default to master context */
}
/* Find the instance of this context that has the best security level,
After that, one might also consider removing the "dummy" initialization of recent_child et al. when using OTRL_INSTAG_MASTER, though I am not really sure what is intended.
--- a/src/context.c
+++ b/src/context.c
@@ -334,14 +334,6 @@ ConnContext * otrl_context_find(OtrlUserState us, const char *user,
protocol, OTRL_INSTAG_MASTER, 1, NULL, add_app_data, data);
}
- if (their_instance == OTRL_INSTAG_MASTER) {
- /* if we're adding a master, there are no children, so the most
- * recent context is the one we add. */
- newctx->recent_child = newctx;
- newctx->recent_rcvd_child = newctx;
- newctx->recent_sent_child = newctx;
- }
-
return *curp;
}
return NULL;
Cf. also: http://bugs.bitlbee.org/bitlbee/ticket/1110#comment:9