Ticket #8382: Faad.Patch

File Faad.Patch, 3.9 KB (added by psgman24@…, 14 years ago)

Gstreamer patch 1

Line 
1diff --git a/ext/faad/gstfaad.c b/ext/faad/gstfaad.c
2index b9de36d..bb49da1 100644
3--- a/ext/faad/gstfaad.c
4+++ b/ext/faad/gstfaad.c
5@@ -210,6 +210,7 @@ gst_faad_init (GstFaad * faad)
6   faad->handle = NULL;
7   faad->samplerate = -1;
8   faad->channels = -1;
9+  faad->fr_channels = 0;
10   faad->tempbuf = NULL;
11   faad->need_channel_setup = TRUE;
12   faad->channel_positions = NULL;
13@@ -1115,6 +1116,8 @@ gst_faad_update_caps (GstFaad * faad, faacDecFrameInfo * info)
14   gboolean channel_map_failed;
15   GstCaps *caps;
16 
17+  GST_DEBUG_OBJECT (faad, "update_caps. ch:%d->%d sr:%d->%d",
18+      faad->channels, info->channels, faad->samplerate, info->samplerate);
19   /* store new negotiation information */
20   faad->samplerate = info->samplerate;
21   faad->channels = info->channels;
22@@ -1193,6 +1196,9 @@ gst_faad_sync (GstBuffer * buf, guint * off)
23       *off = n;
24       len = ((data[n + 3] & 0x03) << 11) |
25           (data[n + 4] << 3) | ((data[n + 5] & 0xe0) >> 5);
26+      // rescue un-labled framed input
27+      if (!n && n + len + 2 == size)
28+        return TRUE;
29       if (n + len + 2 >= size) {
30         GST_DEBUG ("Next frame is not within reach");
31         return FALSE;
32@@ -1342,7 +1348,7 @@ gst_faad_chain (GstPad * pad, GstBuffer * buffer)
33     run_loop = (input_size >= FAAD_MIN_STREAMSIZE);
34   }
35 
36-  while ((input_size > 0) && run_loop) {
37+  while ((input_size > FAAD_MIN_STREAMSIZE) && run_loop) {
38 
39     if (faad->packetised) {
40       /* Only one packet per buffer, no matter how much is really consumed */
41@@ -1353,6 +1359,53 @@ gst_faad_chain (GstPad * pad, GstBuffer * buffer)
42       }
43     }
44 
45+    /* sync */
46+    while (input_size > FAAD_MIN_STREAMSIZE) {
47+      if (looks_like_valid_header (input_data, input_size))
48+        break;
49+      input_data++;
50+      input_size--;
51+    }
52+    if (input_size <= FAAD_MIN_STREAMSIZE) {
53+      GST_DEBUG_OBJECT (faad, "found some garbage data.");
54+      goto next;
55+    }
56+
57+    if ((GST_READ_UINT16_BE (input_data) & 0xFFF6) == 0xFFF0) {
58+      guint fr_ch;
59+      static const guint32 sample_rate[] = {
60+        96000, 88200, 64000, 48000, 44100, 32000,
61+        24000, 22050, 16000, 12000, 11025, 8000, 0, 0, 0, 0
62+      };
63+#if FAAD2_MINOR_VERSION >= 7
64+      unsigned long rate;
65+#else
66+      guint32 rate;
67+#endif
68+      guint8 ch;
69+      /* guint profile; */
70+
71+      fr_ch = (input_data[2] & 0x01) << 2 | (input_data[3] >> 6);
72+      rate = sample_rate[(input_data[2] & 0x3C) >> 2];
73+      /* profile = (input_data[2] & 0xC0) >> 6; */
74+
75+      if (faad->fr_channels != fr_ch || faad->samplerate != rate) {
76+        GST_INFO_OBJECT (faad, "Changing configuration. rate=%u,channels=%u",
77+            rate, fr_ch);
78+        faacDecClose (faad->handle);
79+        faad->init = FALSE;
80+        if (!gst_faad_open_decoder (faad) ||
81+            faacDecInit (faad->handle, input_data, input_size, &rate, &ch) < 0)
82+          goto out;
83+
84+        faad->init = TRUE;
85+        faad->fr_channels = fr_ch;
86+        faad->samplerate = rate;
87+        /* make sure we create new caps below */
88+        faad->channels = 0;
89+      }
90+    }
91+
92     out = faacDecDecode (faad->handle, &info, input_data + skip_bytes,
93         input_size - skip_bytes);
94 
95@@ -1552,6 +1605,7 @@ gst_faad_change_state (GstElement * element, GstStateChange transition)
96     case GST_STATE_CHANGE_PAUSED_TO_READY:
97       faad->samplerate = -1;
98       faad->channels = -1;
99+      faad->fr_channels = 0;
100       faad->need_channel_setup = TRUE;
101       faad->init = FALSE;
102       g_free (faad->channel_positions);
103diff --git a/ext/faad/gstfaad.h b/ext/faad/gstfaad.h
104index fd989b6..424ddf8 100644
105--- a/ext/faad/gstfaad.h
106+++ b/ext/faad/gstfaad.h
107@@ -48,6 +48,7 @@ typedef struct _GstFaad {
108 
109   guint      samplerate; /* sample rate of the last MPEG frame    */
110   guint      channels;   /* number of channels of the last frame  */
111+  guint      fr_channels;/* number of input channels of the last frame */
112   guint      bps;        /* bytes per sample                      */
113 
114   guint8     fake_codec_data[2];
115