From 900394acf3564066571bc83cf9419037fa0fa003 Mon Sep 17 00:00:00 2001 From: Holger Hans Peter Freyther Date: Fri, 27 Dec 2013 20:10:24 +0100 Subject: db: Avoid crash we have seen with the dbi code when reading a SMS Avoid a crash when reading a SMS and a Subscriber could not be resolved. It is not clear why the read was failing. The sender_id and the receiver_id was valid for the given sms. I assume that the database has been locked due external access to it. The side-effect is that in case of such a failure the sms_queue will start to deliver starting from subscriber id = 0 again. #1 0x0000000000428bec in sms_from_result (net=0x156a270, result=0x15eda30) at db.c:1146 #2 0x000000000042a8e0 in db_sms_get_unsent_by_subscr (net=0x156a270, min_subscr_id=, failed=) at db.c:1255 #3 0x000000000042e900 in take_next_sms (smsq=) at sms_queue.c:193 #4 sms_submit_pending (_data=0x158e300) at sms_queue.c:227 #5 0x00007f3fd30de3bc in osmo_timers_update () at timer.c:243 #6 0x00007f3fd30de69b in osmo_select_main (polling=0) at select.c:133 #7 0x0000000000406fbc in main (argc=9, argv=) at bsc_hack.c:346 (gdb) frame 1 #1 0x0000000000428bec in sms_from_result (net=0x156a270, result=0x15eda30) at db.c:1146 1146 strncpy(sms->src.addr, sms->sender->extension, sizeof(sms->src.addr)-1); (gdb) p *sms (gdb) p sms->sender $1 = (struct gsm_subscriber *) 0x0 (gdb) p sender_id $2 = --- openbsc/src/libmsc/db.c | 15 +++++++++++++++ 1 file changed, 15 insertions(+) (limited to 'openbsc/src') diff --git a/openbsc/src/libmsc/db.c b/openbsc/src/libmsc/db.c index a842353e0..e720c7895 100644 --- a/openbsc/src/libmsc/db.c +++ b/openbsc/src/libmsc/db.c @@ -1143,10 +1143,25 @@ static struct gsm_sms *sms_from_result(struct gsm_network *net, dbi_result resul sender_id = dbi_result_get_ulonglong(result, "sender_id"); sms->sender = subscr_get_by_id(net, sender_id); + if (!sms->sender) { + LOGP(DLSMS, LOGL_ERROR, + "Failed to find sender(%llu) for id(%llu)\n", + sender_id, sms->id); + sms_free(sms); + return NULL; + } + strncpy(sms->src.addr, sms->sender->extension, sizeof(sms->src.addr)-1); receiver_id = dbi_result_get_ulonglong(result, "receiver_id"); sms->receiver = subscr_get_by_id(net, receiver_id); + if (!sms->receiver) { + LOGP(DLSMS, LOGL_ERROR, + "Failed to find receiver(%llu) for id(%llu)\n", + receiver_id, sms->id); + sms_free(sms); + return NULL; + } /* FIXME: validity */ /* FIXME: those should all be get_uchar, but sqlite3 is braindead */ -- cgit v1.2.3