Module: sems
Branch: master
Commit: 36936606e55a3192422f9b2894104723015abbb9
URL:    
http://git.sip-router.org/cgi-bin/gitweb.cgi/sems/?a=commit;h=36936606e55a3192422f9b2894104723015abbb9

Author: Raphael Coeffic <[email protected]>
Committer: Raphael Coeffic <[email protected]>
Date:   Mon Mar 19 17:10:37 2012 +0100

rtmp: ported to new wideband code.

---

 apps/rtmp/RtmpAudio.cpp        |  168 ++++++++--------------------------------
 apps/rtmp/RtmpAudio.h          |   24 ++----
 apps/rtmp/flash_phone/Makefile |    3 +-
 apps/rtmp/flash_phone/sono.as  |   11 +++-
 4 files changed, 52 insertions(+), 154 deletions(-)

diff --git a/apps/rtmp/RtmpAudio.cpp b/apps/rtmp/RtmpAudio.cpp
index f4a0e36..f52d18c 100644
--- a/apps/rtmp/RtmpAudio.cpp
+++ b/apps/rtmp/RtmpAudio.cpp
@@ -67,179 +67,75 @@ static void dump_audio(unsigned char* buffer, unsigned int 
size)
 
 
 RtmpAudio::RtmpAudio(RtmpSender* s)
-  : playout_buffer(this,SPEEX_WB_SAMPLE_RATE), 
+  : AmAudio(new AmAudioFormat(CODEC_SPEEX_WB,SPEEX_WB_SAMPLE_RATE)),
+    playout_buffer(this,SPEEX_WB_SAMPLE_RATE), 
     sender(s), play_stream_id(0),
     recv_offset_i(false), recv_rtp_offset(0), recv_rtmp_offset(0),
     send_offset_i(false), send_rtmp_offset(0)
 {
-  init_codec();
 }
 
 RtmpAudio::~RtmpAudio()
 {
-  speex_encoder_destroy(enc_state.state);
-  speex_bits_destroy(&enc_state.bits);
-
-  speex_decoder_destroy(dec_state.state);
-  speex_bits_destroy(&dec_state.bits);
-}
-
-void RtmpAudio::init_codec()
-{
-  int val;
-
-  enc_state.state = speex_encoder_init(&speex_wb_mode);
-  speex_bits_init(&enc_state.bits);
-
-  val = 8;
-  speex_encoder_ctl(enc_state.state, SPEEX_SET_QUALITY, &val);
-
-  dec_state.state = speex_decoder_init(&speex_wb_mode);
-  speex_bits_init(&dec_state.bits);
-}
-
-
-int RtmpAudio::wb_decode(unsigned int size)
-{
-  // - decode into back-buffer
-  // - down-sample from back-buffer into front-buffer
-
-  short* pcm = (short*)samples.back_buffer();
-  speex_bits_read_from(&dec_state.bits, (char*)(unsigned char*)samples, size);
-
-  /* We don't know where frame boundaries are,
-     but the minimum frame size is 43 */
-  int out_size = 0;
-  while (speex_bits_remaining(&dec_state.bits)>40) {
-
-    switch(speex_decode_int(dec_state.state, &dec_state.bits, pcm)) {
-       
-    case -2:
-      ERROR("Corrupted stream!\n");
-      return -1;
-       
-    case -1: goto downsample;
-    default: break;
-    }
-
-    pcm      += SPEEX_WB_SAMPLES_PER_FRAME;
-    out_size += SPEEX_WB_SAMPLES_PER_FRAME*sizeof(short)/2;
-  }
-
- downsample:
-  
-  short* in  = (short*)samples.back_buffer();
-  short* out = (short*)(unsigned char*)samples;
-
-  for(int i=0; i<out_size;i++){
-    out[i] = in[i<<1];
-  }
-
-  return out_size;
-}
-
-int RtmpAudio::wb_encode(unsigned int size)
-{
-  //TODO:
-  // - up-sample into back-buffer
-  // - encode into front-buffer
-  
-  //DBG("size = %i\n",size);
-  short* out = (short*)samples.back_buffer();
-  short* in  = (short*)(unsigned char*)samples;
-
-  for(unsigned int i=0; i<size;i++){
-    out[i<<1]     = in[i];
-    out[(i<<1)+1] = in[i];
-  }
-  size *= 2;
-  //DBG("size = %i\n",size);
-  
-  div_t blocks = div(size, sizeof(short)*SPEEX_WB_SAMPLES_PER_FRAME);
-  if (blocks.rem) {
-    ERROR("non integral number of blocks %d.%d\n", blocks.quot, blocks.rem);
-    return -1;
-  }
-  //DBG("blocks.quot = %i; blocks.rem = %i\n",blocks.quot,blocks.rem);
-    
-  in = (short*)samples.back_buffer();
-  speex_bits_reset(&enc_state.bits);
-
-  while (blocks.quot--) {
-
-    speex_encode_int(enc_state.state, in, &enc_state.bits);
-    in += SPEEX_WB_SAMPLES_PER_FRAME;
-  }
-    
-  int out_size = speex_bits_write(&enc_state.bits, 
-                                 (char*)(unsigned char*)samples, 
-                                 AUDIO_BUFFER_SIZE);
-
-  //DBG("returning %u encoded bytes\n",out_size);
-  return out_size;
 }
 
-
 // returns bytes read, else -1 if error (0 is OK)
-int RtmpAudio::get(unsigned int user_ts, unsigned char* buffer, 
+int RtmpAudio::get(unsigned long long system_ts, unsigned char* buffer, 
                   int output_sample_rate, unsigned int nb_samples)
 {
   // - buffer RTMP audio
   // - read from RTMP recv buffer
 
+  unsigned int user_ts = scaleSystemTS(system_ts);
+
   //DBG("get(%u, %u)\n",user_ts,nb_samples);
   process_recv_queue(user_ts);
 
-  u_int32_t rlen = playout_buffer.
-    read(user_ts,
-        (ShortSample*)buffer,
-        nb_samples);
-
+  u_int32_t size =
+    PCM16_S2B(playout_buffer.read(user_ts,
+                                 (ShortSample*)((unsigned char*)samples),
+                                 nb_samples));
+  if(output_sample_rate != getSampleRate()) {
+    size = resampleOutput((unsigned char*)samples, size,
+                         getSampleRate(), output_sample_rate);
+  }
   
+  memcpy(buffer,(unsigned char*)samples,size);
 
-  return PCM16_S2B(rlen);
-}
-
-int RtmpAudio::read(unsigned int user_ts, unsigned int size)
-{
-  assert(0);
-  return 0;
+  return size;
 }
 
 // returns bytes written, else -1 if error (0 is OK)
-int RtmpAudio::put(unsigned int user_ts, unsigned char* buffer, 
+int RtmpAudio::put(unsigned long long system_ts, unsigned char* buffer, 
                   int input_sample_rate, unsigned int size)
 {
-  //dump_audio((unsigned char*)buffer,size);
-  //DBG("size = %i\n",size);
-
   if(!size){
     return 0;
   }
 
-  // TODO: check if still necessary
-  if(size>640)
-    size = 640;
+  //dump_audio((unsigned char*)buffer,size);
 
   // copy into internal buffer
   memcpy((unsigned char*)samples,buffer,size);
+  size = resampleInput((unsigned char*)samples, size, 
+                      input_sample_rate, getSampleRate());
 
-  // encode
-  int s = wb_encode(size);
-  if(s>0){
-    // send
-    return write(user_ts,(unsigned int)s);
-  }
-  else{
+  int s = encode(size);
+  //DBG("s = %i\n",s);
+  
+  if(s<=0){
     return s;
   }
+
+  return send(scaleSystemTS(system_ts),(unsigned int)s);
 }
 
-int RtmpAudio::write(unsigned int user_ts, unsigned int size)
+int RtmpAudio::send(unsigned int user_ts, unsigned int size)
 {
   m_sender.lock();
 
   if(!sender || !play_stream_id) {
+    //DBG("!sender || !play_stream_id");
     m_sender.unlock();
     return 0;
   }
@@ -263,7 +159,8 @@ int RtmpAudio::write(unsigned int user_ts, unsigned int 
size)
     send_offset_i = true;
   }
   
-  unsigned int rtmp_ts = (user_ts - send_rtmp_offset) / (8000/1000);
+  unsigned int rtmp_ts = (user_ts - send_rtmp_offset) 
+    / (SPEEX_WB_SAMPLE_RATE/1000);
   packet.m_nTimeStamp  = rtmp_ts;
 
   RTMPPacket_Alloc(&packet,size+1);
@@ -332,7 +229,7 @@ void RtmpAudio::process_recv_queue(unsigned int ref_ts)
       size = p.m_nBodySize-1;
       memcpy((unsigned char*)samples, p.m_body+1, size);
 
-      size = wb_decode(size);
+      size = decode(size);
       if(size <= 0){
        ERROR("decode() returned %i\n",size);
        return;
@@ -348,9 +245,9 @@ void RtmpAudio::process_recv_queue(unsigned int ref_ts)
        begin_talk = true;
       }
 
-      unsigned int rtp_ts = (p.m_nTimeStamp - recv_rtmp_offset) * (8000/1000);
+      unsigned int rtp_ts = (p.m_nTimeStamp - recv_rtmp_offset) * 
(SPEEX_WB_SAMPLE_RATE/1000);
 
-      playout_buffer.write(ref_ts, rtp_ts, (ShortSample*)((unsigned char 
*)samples), 
+      playout_buffer.write(ref_ts, rtp_ts, (ShortSample*)((unsigned char 
*)samples),
                           PCM16_B2S(size), begin_talk);
       
       RTMPPacket_Free(&p);    
@@ -382,6 +279,7 @@ void RtmpAudio::setSenderPtr(RtmpSender* s)
 void RtmpAudio::setPlayStreamID(unsigned int stream_id)
 {
   m_sender.lock();
+  DBG("play_stream_id = %i\n",stream_id);
   play_stream_id = stream_id;
   m_sender.unlock();
 }
diff --git a/apps/rtmp/RtmpAudio.h b/apps/rtmp/RtmpAudio.h
index e0765ac..bc92d31 100644
--- a/apps/rtmp/RtmpAudio.h
+++ b/apps/rtmp/RtmpAudio.h
@@ -33,7 +33,6 @@
 #include "AmRtpAudio.h"
 
 #include "librtmp/rtmp.h"
-#include <speex/speex.h>
 
 #include <queue>
 using std::queue;
@@ -44,11 +43,6 @@ class RtmpAudio
   : public AmAudio,
     public AmPLCBuffer
 {
-  struct SpeexState {
-    void *state;
-    SpeexBits bits;
-  };
-
   RtmpSender* sender;
   AmMutex     m_sender;
 
@@ -65,26 +59,18 @@ class RtmpAudio
   bool         send_offset_i;
   unsigned int send_rtmp_offset;
 
-  SpeexState dec_state;
-  SpeexState enc_state;
-
-  void init_codec();
-  int wb_decode(unsigned int size);
-  int wb_encode(unsigned int size);
-
   void process_recv_queue(unsigned int ref_ts);
+  int send(unsigned int user_ts, unsigned int size);
 
 public:
   RtmpAudio(RtmpSender* s);
   ~RtmpAudio();
 
   /* @see AmAudio */
-  int get(unsigned int user_ts, unsigned char* buffer, 
+  int get(unsigned long long system_ts, unsigned char* buffer, 
          int output_sample_rate, unsigned int nb_samples);
-  int put(unsigned int user_ts, unsigned char* buffer, 
+  int put(unsigned long long system_ts, unsigned char* buffer, 
          int output_sample_rate, unsigned int size);
-  int read(unsigned int user_ts, unsigned int size);
-  int write(unsigned int user_ts, unsigned int size);
 
   void bufferPacket(const RTMPPacket& p);
 
@@ -105,6 +91,10 @@ public:
    * method to propagate the stream ID.
    */
   void setPlayStreamID(unsigned int stream_id);
+
+protected:
+  int read(unsigned int user_ts, unsigned int size)  { return 0; }
+  int write(unsigned int user_ts, unsigned int size) { return 0; }
 };
 
 #endif
diff --git a/apps/rtmp/flash_phone/Makefile b/apps/rtmp/flash_phone/Makefile
index 0112306..c9044aa 100644
--- a/apps/rtmp/flash_phone/Makefile
+++ b/apps/rtmp/flash_phone/Makefile
@@ -15,7 +15,8 @@ MXMLC=$(FLEX_SDK)/bin/mxmlc
 MXMLC_OPTS= \
        --strict=true \
        --as3=true \
-       --target-player="10.3"
+       -target-player 11.0 \
+       -swf-version=13
 
 APP=sono
 SOURCES= $(APP).mxml $(wildcard *.as)
diff --git a/apps/rtmp/flash_phone/sono.as b/apps/rtmp/flash_phone/sono.as
index f197e5a..86138e2 100644
--- a/apps/rtmp/flash_phone/sono.as
+++ b/apps/rtmp/flash_phone/sono.as
@@ -30,6 +30,7 @@ import flash.events.Event;
 import flash.net.NetConnection;
 import flash.net.NetStream;
 import flash.media.Microphone;
+import flash.media.MicrophoneEnhancedMode;
 
 // application states
 private static const NOT_CONNECTED:uint = 0;
@@ -217,7 +218,15 @@ private function connectStreams():void
     g_micStream = new NetStream(g_netConnection);
     g_micStream.addEventListener(NetStatusEvent.NET_STATUS, netStatusHandler);
 
-    var micro:Microphone = Microphone.getEnhancedMicrophone();
+    var micro:Microphone = null;
+    if(Microphone['getEnhancedMicrophone'] != undefined) {
+       micro = Microphone['getEnhancedMicrophone'](-1);
+       lStatus.text = "Enhanced mike";
+    }
+    else {
+       micro = Microphone.getMicrophone(-1);
+       lStatus.text = "Normal mike";
+    }
 
     if(micro == null){
        //TODO: report error

_______________________________________________
Semsdev mailing list
[email protected]
http://lists.iptel.org/mailman/listinfo/semsdev

Reply via email to