diff --git a/src/mm-base-call.c b/src/mm-base-call.c
index ab63a1d7a46aec343b1ff03016d9df021d05ef2d..dfbdb702191588815a2c0fed9ec83ace68de0a49 100644
--- a/src/mm-base-call.c
+++ b/src/mm-base-call.c
@@ -57,8 +57,37 @@ struct _MMBaseCallPrivate {
     /* Features */
     gboolean supports_dialing_to_ringing;
     gboolean supports_ringing_to_active;
+
+    guint incoming_timeout;
 };
 
+/*****************************************************************************/
+/* Incoming calls are reported via RING URCs. If the caller stops the call
+ * attempt before it has been answered, the only thing we would see is that the
+ * URCs are no longer received. So, we will start a timeout whenever a new RING
+ * URC is received, and we refresh the timeout any time a new URC arrives. If
+ * the timeout is expired (meaning no URCs were received in the last N seconds)
+ * then we assume the call attempt is finished and we transition to TERMINATED.
+ */
+
+#define INCOMING_TIMEOUT_SECS 5
+
+static gboolean
+incoming_timeout_cb (MMBaseCall *self)
+{
+    self->priv->incoming_timeout = 0;
+    mm_base_call_change_state (self, MM_CALL_STATE_TERMINATED, MM_CALL_STATE_REASON_TERMINATED);
+    return G_SOURCE_REMOVE;
+}
+
+void
+mm_base_call_incoming_refresh (MMBaseCall *self)
+{
+    if (self->priv->incoming_timeout)
+        g_source_remove (self->priv->incoming_timeout);
+    self->priv->incoming_timeout = g_timeout_add_seconds (INCOMING_TIMEOUT_SECS, (GSourceFunc)incoming_timeout_cb, self);
+}
+
 /*****************************************************************************/
 /* Start call (DBus call handling) */
 
@@ -205,6 +234,10 @@ handle_accept_ready (MMBaseCall *self,
         mm_base_call_change_state (self, MM_CALL_STATE_TERMINATED, MM_CALL_STATE_REASON_ERROR);
         g_dbus_method_invocation_take_error (ctx->invocation, error);
     } else {
+        if (ctx->self->priv->incoming_timeout) {
+            g_source_remove (ctx->self->priv->incoming_timeout);
+            ctx->self->priv->incoming_timeout = 0;
+        }
         mm_base_call_change_state (self, MM_CALL_STATE_ACTIVE, MM_CALL_STATE_REASON_ACCEPTED);
         mm_gdbus_call_complete_accept (MM_GDBUS_CALL (ctx->self), ctx->invocation);
     }
@@ -305,8 +338,13 @@ handle_hangup_ready (MMBaseCall *self,
 
     if (!MM_BASE_CALL_GET_CLASS (self)->hangup_finish (self, res, &error))
         g_dbus_method_invocation_take_error (ctx->invocation, error);
-    else
+    else {
+        if (ctx->self->priv->incoming_timeout) {
+            g_source_remove (ctx->self->priv->incoming_timeout);
+            ctx->self->priv->incoming_timeout = 0;
+        }
         mm_gdbus_call_complete_hangup (MM_GDBUS_CALL (ctx->self), ctx->invocation);
+    }
 
     handle_hangup_context_free (ctx);
 }
@@ -963,6 +1001,11 @@ dispose (GObject *object)
 {
     MMBaseCall *self = MM_BASE_CALL (object);
 
+    if (self->priv->incoming_timeout) {
+        g_source_remove (self->priv->incoming_timeout);
+        self->priv->incoming_timeout = 0;
+    }
+
     if (self->priv->connection) {
         /* If we arrived here with a valid connection, make sure we unexport
          * the object */
diff --git a/src/mm-base-call.h b/src/mm-base-call.h
index da31a9b9d8b72d7b82d07923f2ab683b5840ac7d..5b8c06c670553c12baad11207a2a705992b76c88 100644
--- a/src/mm-base-call.h
+++ b/src/mm-base-call.h
@@ -97,13 +97,17 @@ MMBaseCall *mm_base_call_new_from_properties (MMBaseModem *modem,
                                               MMCallProperties *properties,
                                               GError **error);
 
-void         mm_base_call_export         (MMBaseCall *self);
-void         mm_base_call_unexport       (MMBaseCall *self);
-const gchar *mm_base_call_get_path       (MMBaseCall *self);
-void         mm_base_call_change_state   (MMBaseCall *self,
-                                          MMCallState new_state,
-                                          MMCallStateReason reason);
-void         mm_base_call_received_dtmf  (MMBaseCall *self,
-                                          const gchar *dtmf);
+void         mm_base_call_export   (MMBaseCall *self);
+void         mm_base_call_unexport (MMBaseCall *self);
+const gchar *mm_base_call_get_path (MMBaseCall *self);
+
+void         mm_base_call_change_state (MMBaseCall *self,
+                                        MMCallState new_state,
+                                        MMCallStateReason reason);
+
+void         mm_base_call_received_dtmf (MMBaseCall *self,
+                                         const gchar *dtmf);
+
+void         mm_base_call_incoming_refresh (MMBaseCall *self);
 
 #endif /* MM_BASE_CALL_H */
diff --git a/src/mm-broadband-modem.c b/src/mm-broadband-modem.c
index 7b11cd437639af86a2f665c3cc757f8be322b2be..93a3a3e0732f24ca6fae1f321cb8529ee67a57df 100644
--- a/src/mm-broadband-modem.c
+++ b/src/mm-broadband-modem.c
@@ -6928,7 +6928,7 @@ ring_received (MMPortSerialAt *port,
                MMBroadbandModem *self)
 {
     mm_dbg ("Ringing");
-    mm_iface_modem_voice_create_incoming_call (MM_IFACE_MODEM_VOICE (self));
+    mm_iface_modem_voice_incoming_call (MM_IFACE_MODEM_VOICE (self));
 }
 
 static void
@@ -6945,7 +6945,7 @@ cring_received (MMPortSerialAt *port,
     mm_dbg ("Ringing (%s)", str);
     g_free (str);
 
-    mm_iface_modem_voice_create_incoming_call (MM_IFACE_MODEM_VOICE (self));
+    mm_iface_modem_voice_incoming_call (MM_IFACE_MODEM_VOICE (self));
 }
 
 static void
diff --git a/src/mm-call-list.c b/src/mm-call-list.c
index b1950e3ab57d37cb8e67af09c6dd8299c1a2b1e2..91ccc8d08a8992a2e940b22af08c970b3cd40ea6 100644
--- a/src/mm-call-list.c
+++ b/src/mm-call-list.c
@@ -84,36 +84,33 @@ mm_call_list_get_paths (MMCallList *self)
 /*****************************************************************************/
 
 MMBaseCall *
-mm_call_list_get_new_incoming (MMCallList *self)
+mm_call_list_get_first_ringing_in_call (MMCallList *self)
 {
-    MMBaseCall *call = NULL;
     GList *l;
 
     for (l = self->priv->list; l; l = g_list_next (l)) {
-
+        MMBaseCall       *call;
         MMCallState       state;
-        MMCallStateReason reason;
-        MMCallDirection   direct;
+        MMCallDirection   direction;
 
-        g_object_get (MM_BASE_CALL (l->data),
-                      "state",        &state,
-                      "state-reason", &reason,
-                      "direction",    &direct,
+        call = MM_BASE_CALL (l->data);
+
+        g_object_get (call,
+                      "state",     &state,
+                      "direction", &direction,
                       NULL);
 
-        if (direct  == MM_CALL_DIRECTION_INCOMING &&
-            state   == MM_CALL_STATE_RINGING_IN &&
-            reason  == MM_CALL_STATE_REASON_INCOMING_NEW ) {
-            call = MM_BASE_CALL (l->data);
-            break;
+        if (direction == MM_CALL_DIRECTION_INCOMING &&
+            state     == MM_CALL_STATE_RINGING_IN) {
+            return call;
         }
     }
 
-    return call;
+    return NULL;
 }
 
 MMBaseCall *
-mm_call_list_get_first_ringing_call (MMCallList *self)
+mm_call_list_get_first_ringing_out_call (MMCallList *self)
 {
     MMBaseCall *call = NULL;
     GList *l;
diff --git a/src/mm-call-list.h b/src/mm-call-list.h
index 1c6685009b90d3ccfaf1b6fdfb9e99a1c6731e5b..53102d06107a4839a41b7d0cf575b2e225b3bc32 100644
--- a/src/mm-call-list.h
+++ b/src/mm-call-list.h
@@ -68,11 +68,11 @@ gboolean mm_call_list_delete_call (MMCallList   *self,
                                    const gchar  *call_path,
                                    GError      **error);
 
-MMBaseCall *mm_call_list_get_new_incoming               (MMCallList  *self);
-MMBaseCall *mm_call_list_get_first_ringing_call         (MMCallList  *self);
-MMBaseCall *mm_call_list_get_first_outgoing_dialing_call(MMCallList  *self);
-MMBaseCall *mm_call_list_get_first_non_terminated_call  (MMCallList  *self);
-gboolean    mm_call_list_send_dtmf_to_active_calls      (MMCallList  *self,
-                                                         const gchar *dtmf);
+MMBaseCall *mm_call_list_get_first_ringing_in_call       (MMCallList  *self);
+MMBaseCall *mm_call_list_get_first_ringing_out_call      (MMCallList  *self);
+MMBaseCall *mm_call_list_get_first_outgoing_dialing_call (MMCallList  *self);
+MMBaseCall *mm_call_list_get_first_non_terminated_call   (MMCallList  *self);
+gboolean    mm_call_list_send_dtmf_to_active_calls       (MMCallList  *self,
+                                                          const gchar *dtmf);
 
 #endif /* MM_CALL_LIST_H */
diff --git a/src/mm-iface-modem-voice.c b/src/mm-iface-modem-voice.c
index 844b83102e9a7a82a85efef5b43320d8df99742f..9cab1cdd276c8832bfdd5823ad0406bb3157ce95 100644
--- a/src/mm-iface-modem-voice.c
+++ b/src/mm-iface-modem-voice.c
@@ -46,8 +46,8 @@ mm_iface_modem_voice_create_call (MMIfaceModemVoice *self)
     return MM_IFACE_MODEM_VOICE_GET_INTERFACE (self)->create_call (self);
 }
 
-MMBaseCall *
-mm_iface_modem_voice_create_incoming_call (MMIfaceModemVoice *self)
+void
+mm_iface_modem_voice_incoming_call (MMIfaceModemVoice *self)
 {
     MMBaseCall *call = NULL;
     MMCallList *list = NULL;
@@ -56,29 +56,36 @@ mm_iface_modem_voice_create_incoming_call (MMIfaceModemVoice *self)
                   MM_IFACE_MODEM_VOICE_CALL_LIST, &list,
                   NULL);
 
-    if (list) {
-        call = mm_call_list_get_new_incoming (list);
-
-        if (!call) {
-            mm_dbg ("Creating new incoming call...");
-
-            call = mm_base_call_new (MM_BASE_MODEM (self));
-            g_object_set (call,
-                          "state",          MM_CALL_STATE_RINGING_IN,
-                          "state-reason",   MM_CALL_STATE_REASON_INCOMING_NEW,
-                          "direction",      MM_CALL_DIRECTION_INCOMING,
-                          NULL);
-
-            /* Only export once properly created */
-            mm_base_call_export (call);
-            mm_call_list_add_call (list, call);
-            g_object_unref (call);
-        }
+    if (!list) {
+        mm_warn ("Cannot create incoming call: missing call list");
+        return;
+    }
+
+    call = mm_call_list_get_first_ringing_in_call (list);
 
+    /* If call exists already, refresh its validity */
+    if (call) {
+        mm_base_call_incoming_refresh (call);
         g_object_unref (list);
+        return;
     }
 
-    return call;
+    mm_dbg ("Creating new incoming call...");
+    call = mm_base_call_new (MM_BASE_MODEM (self));
+    g_object_set (call,
+                  "state",          MM_CALL_STATE_RINGING_IN,
+                  "state-reason",   MM_CALL_STATE_REASON_INCOMING_NEW,
+                  "direction",      MM_CALL_DIRECTION_INCOMING,
+                  NULL);
+
+    /* Start its validity timeout */
+    mm_base_call_incoming_refresh (call);
+
+    /* Only export once properly created */
+    mm_base_call_export (call);
+    mm_call_list_add_call (list, call);
+    g_object_unref (call);
+    g_object_unref (list);
 }
 
 gboolean
@@ -96,7 +103,7 @@ mm_iface_modem_voice_update_incoming_call_number (MMIfaceModemVoice *self,
                   NULL);
 
     if (list) {
-        call = mm_call_list_get_new_incoming (list);
+        call = mm_call_list_get_first_ringing_in_call (list);
 
         if (call) {
             mm_gdbus_call_set_number (MM_GDBUS_CALL (call), number);
@@ -153,7 +160,7 @@ mm_iface_modem_voice_call_ringing_to_active (MMIfaceModemVoice *self)
                   NULL);
 
     if (list) {
-        call = mm_call_list_get_first_ringing_call (list);
+        call = mm_call_list_get_first_ringing_out_call (list);
 
         if (call) {
             mm_base_call_change_state (call, MM_CALL_STATE_ACTIVE, MM_CALL_STATE_REASON_ACCEPTED);
diff --git a/src/mm-iface-modem-voice.h b/src/mm-iface-modem-voice.h
index e182060a80bafab12741c789efd8b48bfec40722..229ebb5dad39eb5cfe115f6d061d871b64248d8b 100644
--- a/src/mm-iface-modem-voice.h
+++ b/src/mm-iface-modem-voice.h
@@ -118,7 +118,7 @@ void mm_iface_modem_voice_bind_simple_status (MMIfaceModemVoice *self,
 
 /* CALL creation */
 MMBaseCall *mm_iface_modem_voice_create_call                    (MMIfaceModemVoice *self);
-MMBaseCall *mm_iface_modem_voice_create_incoming_call           (MMIfaceModemVoice *self);
+void        mm_iface_modem_voice_incoming_call                  (MMIfaceModemVoice *self);
 gboolean    mm_iface_modem_voice_update_incoming_call_number    (MMIfaceModemVoice *self,
                                                                  gchar *number,
                                                                  guint type,