diff --git a/include/osmocom/msc/signal.h b/include/osmocom/msc/signal.h index 915313131..77a9bcf34 100644 --- a/include/osmocom/msc/signal.h +++ b/include/osmocom/msc/signal.h @@ -86,4 +86,6 @@ struct sms_signal_data { struct gsm_sms *sms; /* true when paging was successful */ bool paging_result; + /* the id of the last inserted SMS */ + unsigned long long id; }; diff --git a/src/libmsc/db.c b/src/libmsc/db.c index 5959dae23..4dbf6b1f7 100644 --- a/src/libmsc/db.c +++ b/src/libmsc/db.c @@ -282,7 +282,7 @@ static const char *stmt_sql[] = { " WHERE sent IS NULL" " AND dest_addr = $dest_addr" " AND deliver_attempts <= $attempts" - " ORDER BY id LIMIT 1", + " ORDER BY deliver_attempts, id LIMIT 1", [DB_STMT_SMS_GET_NEXT_UNSENT_RR_MSISDN] = "SELECT " SEL_COLUMNS " FROM SMS" " WHERE sent IS NULL" diff --git a/src/libmsc/gsm_04_11.c b/src/libmsc/gsm_04_11.c index 3fc410ddb..85888c995 100644 --- a/src/libmsc/gsm_04_11.c +++ b/src/libmsc/gsm_04_11.c @@ -119,6 +119,7 @@ static void send_signal(int sig_no, struct sms_signal_data sig; sig.trans = trans; sig.sms = sms; + sig.id = sms->id; sig.paging_result = paging_result; osmo_signal_dispatch(SS_SMS, sig_no, &sig); } diff --git a/src/libmsc/sms_queue.c b/src/libmsc/sms_queue.c index 67473a0e8..db0f09f90 100644 --- a/src/libmsc/sms_queue.c +++ b/src/libmsc/sms_queue.c @@ -547,6 +547,8 @@ static int sub_ready_for_sm(struct gsm_network *net, struct vlr_subscr *vsub) return -1; _gsm411_send_sms(net, vsub, sms); + if (!sms_subscriber_is_pending(net->sms_queue, vsub)) + sms_send_next(vsub); return 0; } @@ -572,10 +574,46 @@ static int sms_sms_cb(unsigned int subsys, unsigned int signal, struct sms_signal_data *sig_sms = signal_data; struct gsm_sms_pending *pending; struct vlr_subscr *vsub; + struct gsm_sms *sms; /* We got a new SMS and maybe should launch the queue again. */ - if (signal == S_SMS_SUBMITTED || signal == S_SMS_SMMA) { - /* TODO: For SMMA we might want to re-use the radio connection. */ + if (signal == S_SMS_SUBMITTED) { + if (sig_sms->id) { + LOGP(DLSMS, LOGL_INFO, "Got Signal for new Sms Submitted with ID [%llu]\n", + sig_sms->id); + sms = db_sms_get(network, sig_sms->id); + if (!sms) + return -1; + if (!sms->receiver || !sms->receiver->lu_complete) { + LOGP(DLSMS, LOGL_DEBUG, + "Subscriber %s%s is not attached, skipping SMS.\n", + sms->receiver ? "" : "MSISDN-", + sms->receiver ? vlr_subscr_msisdn_or_name(sms->receiver) : sms->dst.addr); + return -1; + } + + /* Check somehow it's not already in the pending list */ + if (sms_queue_sms_is_pending(smq, sms->id)) { + sms_free(sms); + return 0; + } + /* Or that this sub is not already pending */ + if (sms_subscriber_is_pending(smq, sms->receiver)) { + sms_free(sms); + return 0; + } + /* Now add this SMS to the Queue for immediate sending. */ + pending = sms_pending_from(smq, sms); + sms_free(sms); + /* Schedule the timer to send this SMS */ + sms_pending_resend(pending); + return 0; + } + } + + if (signal == S_SMS_SMMA) { + /* TODO: For SMMA we might want to re-use the radio connection. + */ sms_queue_trigger(smq); return 0; } diff --git a/src/libsmpputil/smpp_msc.c b/src/libsmpputil/smpp_msc.c index d68dcc091..328fc59fc 100644 --- a/src/libsmpputil/smpp_msc.c +++ b/src/libsmpputil/smpp_msc.c @@ -306,6 +306,8 @@ int handle_smpp_submit(struct smpp_esme *esme, struct submit_sm_t *submit, case 1: /* datagram */ case 3: /* store-and-forward */ rc = db_sms_store(sms); + memset(&sig, 0, sizeof(sig)); + sig.id = sms->id; sms_free(sms); sms = NULL; if (rc < 0) { @@ -317,7 +319,6 @@ int handle_smpp_submit(struct smpp_esme *esme, struct submit_sm_t *submit, strcpy((char *)submit_r->message_id, "msg_id_not_implemented"); LOGP(DLSMS, LOGL_INFO, "SMPP SUBMIT-SM: Stored in DB\n"); - memset(&sig, 0, sizeof(sig)); osmo_signal_dispatch(SS_SMS, S_SMS_SUBMITTED, &sig); rc = 0; break;