+ if (is_receive) {
+ expected = src->stats.max_seq + 1;
+ delta = gst_rtp_buffer_compare_seqnum (expected, seqnr);
+
+ /* if we are still on probation, check seqnum */
+ if (src->curr_probation) {
+ /* when in probation, we require consecutive seqnums */
+ if (delta == 0) {
+ /* expected packet */
+ GST_DEBUG ("probation: seqnr %d == expected %d", seqnr, expected);
+ src->curr_probation--;
+ if (seqnr < stats->max_seq) {
+ /* sequence number wrapped - count another 64K cycle. */
+ stats->cycles += RTP_SEQ_MOD;
+ }
+ src->stats.max_seq = seqnr;
+
+ if (src->curr_probation == 0) {
+ GST_DEBUG ("probation done!");
+ init_seq (src, seqnr);
+ } else {
+ GstBuffer *q;
+
+ GST_DEBUG ("probation %d: queue packet", src->curr_probation);
+ /* when still in probation, keep packets in a list. */
+ g_queue_push_tail (src->packets, pinfo->data);
+ pinfo->data = NULL;
+ /* remove packets from queue if there are too many */
+ while (g_queue_get_length (src->packets) > RTP_MAX_PROBATION_LEN) {
+ q = g_queue_pop_head (src->packets);
+ gst_buffer_unref (q);
+ }
+ goto done;
+ }
+ } else {
+ /* unexpected seqnum in probation
+ *
+ * There is no need to clean the queue at this point because the
+ * invalid packets in the queue are not going to be pushed as we are
+ * still in probation, and some cleanup will be performed at future
+ * probation attempts anyway if there are too many old packets in the
+ * queue.
+ */
+ goto probation_seqnum;
+ }
+ } else if (delta >= 0 && delta < max_dropout) {
+ /* Clear bad packets */
+ stats->bad_seq = RTP_SEQ_MOD + 1; /* so seq == bad_seq is false */
+ g_queue_foreach (src->packets, (GFunc) gst_buffer_unref, NULL);
+ g_queue_clear (src->packets);