Adding separate payload types for stereo modes

BUG=Issue 452
TEST=audio_coding_test, voe_auto_test, voe_cmd_test

Edit: adding Patrik to review:
src/modules/rtp_rtcp/source/rtp_receiver.cc
...and Shijing to review:
src/voice_engine/main/source/channel.cc
src/voice_engine/main/test/cmd_test/voe_cmd_test.cc

Review URL: https://webrtc-codereview.appspot.com/540004

git-svn-id: http://webrtc.googlecode.com/svn/trunk@2340 4adac7df-926f-26a2-2b94-8c16560cd09d
diff --git a/src/modules/audio_coding/main/interface/audio_coding_module.h b/src/modules/audio_coding/main/interface/audio_coding_module.h
index 7c0ba4e..9fc27d6 100644
--- a/src/modules/audio_coding/main/interface/audio_coding_module.h
+++ b/src/modules/audio_coding/main/interface/audio_coding_module.h
@@ -108,42 +108,44 @@
 
   ///////////////////////////////////////////////////////////////////////////
   // WebRtc_Word32 Codec()
-  // Get supported codec with the given codec name and sampling frequency.
-  // If the sampling frequency is -1 then the search will be only based on
-  // codec name.
+  // Get supported codec with the given codec name, sampling frequency, and
+  // a given number of channels.
   //
   // Input:
-  //   -payloadName        : name of the codec.
-  //   -samplingFreqHz     : samling frequency of the codec.
+  //   -payload_name       : name of the codec.
+  //   -sampling_freq_hz   : sampling frequency of the codec. Note! for RED
+  //                         a sampling frequency of -1 is a valid input.
+  //   -channels           : number of channels ( 1 - mono, 2 - stereo).
   //
   // Output:
-  //   -codec              : a structure where the parameters of the codec,
-  //                         given by name is written to.
+  //   -codec              : a structure where the function returns the
+  //                         default parameters of the codec.
   //
   // Return value:
   //   -1 if the list number (listId) is invalid.
   //    0 if succeeded.
   //
-  static WebRtc_Word32 Codec(const char* payloadName, CodecInst& codec,
-                             const WebRtc_Word32 samplingFreqHz = -1);
+  static WebRtc_Word32 Codec(const char* payload_name, CodecInst& codec,
+                             int sampling_freq_hz, int channels);
 
   ///////////////////////////////////////////////////////////////////////////
   // WebRtc_Word32 Codec()
   //
-  // Returns the list number of the given codec name and sampling frequency.
-  // If the sampling frequency is -1 then the search will be only based on
-  // codec name.
+  // Returns the list number of the given codec name, sampling frequency, and
+  // a given number of channels.
   //
   // Input:
-  //   -payloadName        : name of the codec.
-  //   -samplingFreqHz     : samling frequency of the codec.
+  //   -payload_name        : name of the codec.
+  //   -sampling_freq_hz    : sampling frequency of the codec. Note! for RED
+  //                          a sampling frequency of -1 is a valid input.
+  //   -channels            : number of channels ( 1 - mono, 2 - stereo).
   //
   // Return value:
   //   if the codec is found, the index of the codec in the list,
   //   -1 if the codec is not found.
   //
-  static WebRtc_Word32 Codec(const char* payloadName,
-                             const WebRtc_Word32 samplingFreqHz = -1);
+  static WebRtc_Word32 Codec(const char* payload_name, int sampling_freq_hz,
+                             int channels);
 
   ///////////////////////////////////////////////////////////////////////////
   // bool IsCodecValid()
diff --git a/src/modules/audio_coding/main/source/acm_celt.cc b/src/modules/audio_coding/main/source/acm_celt.cc
index de347c5..d9678fd 100644
--- a/src/modules/audio_coding/main/source/acm_celt.cc
+++ b/src/modules/audio_coding/main/source/acm_celt.cc
@@ -223,14 +223,20 @@
   // "SET_CODEC_PAR" and "SET_CELT_FUNCTIONS" or "SET_CELTSLAVE_FUNCTIONS".
   // Then call NetEQ to add the codec to it's
   // database.
-  SET_CODEC_PAR((codecDef), kDecoderCELT_32, codecInst.pltype, dec_inst_ptr_,
-                32000);
+  if (codecInst.channels == 1) {
+    SET_CODEC_PAR(codecDef, kDecoderCELT_32, codecInst.pltype, dec_inst_ptr_,
+                  32000);
+  } else {
+    SET_CODEC_PAR(codecDef, kDecoderCELT_32_2ch, codecInst.pltype,
+                  dec_inst_ptr_, 32000);
+  }
+
   // If this is the master of NetEQ, regular decoder will be added, otherwise
   // the slave decoder will be used.
   if (_isMaster) {
-    SET_CELT_FUNCTIONS((codecDef));
+    SET_CELT_FUNCTIONS(codecDef);
   } else {
-    SET_CELTSLAVE_FUNCTIONS((codecDef));
+    SET_CELTSLAVE_FUNCTIONS(codecDef);
   }
   return 0;
 }
diff --git a/src/modules/audio_coding/main/source/acm_codec_database.cc b/src/modules/audio_coding/main/source/acm_codec_database.cc
index c623d29..185af33 100644
--- a/src/modules/audio_coding/main/source/acm_codec_database.cc
+++ b/src/modules/audio_coding/main/source/acm_codec_database.cc
@@ -101,18 +101,19 @@
 
 // We dynamically allocate some of the dynamic payload types to the defined
 // codecs. Note! There are a limited number of payload types. If more codecs
-// are defined they will receive reserved fixed payload types (values 67-95).
+// are defined they will receive reserved fixed payload types (values 69-95).
 const int kDynamicPayloadtypes[ACMCodecDB::kMaxNumCodecs] = {
-  105, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119,
-  120, 121, 122, 123, 124, 125, 126,  95,  94,  93,  92,  91,  90,  89,
-  88,  87,  86,  85,  84,  83,  82,  81,  80,  79,  78,  77,  76,  75,
-  74,  73,  72,  71,  70,  69,  68,  67
+  105, 107, 108, 109, 111, 112, 113, 114, 115, 116, 117, 120,
+  121, 122, 123, 124, 125, 126, 101, 100,  97,  96,  95,  94,
+   93,  92,  91,  90,  89,  88,  87,  86,  85,  84,  83,  82,
+   81,  80,  79,  78,  77,  76,  75,  74,  73,  72,  71,  70,
+   69,
 };
 
-// Creates database with all supported codec at compile time.
+// Creates database with all supported codecs at compile time.
 // Each entry needs the following parameters in the given order:
 // payload type, name, sampling frequency, packet size in samples,
-// default channel support, and default rate.
+// number of channels, and default rate.
 #if (defined(WEBRTC_CODEC_PCM16) || \
      defined(WEBRTC_CODEC_AMR) || defined(WEBRTC_CODEC_AMRWB) || \
      defined(WEBRTC_CODEC_CELT) || defined(WEBRTC_CODEC_G729_1) || \
@@ -129,13 +130,22 @@
 # endif
 #endif
 #ifdef WEBRTC_CODEC_PCM16
+  // Mono
   {kDynamicPayloadtypes[count_database++], "L16", 8000, 80, 1, 128000},
   {kDynamicPayloadtypes[count_database++], "L16", 16000, 160, 1, 256000},
   {kDynamicPayloadtypes[count_database++], "L16", 32000, 320, 1, 512000},
+  // Stereo
+  {kDynamicPayloadtypes[count_database++], "L16", 8000, 80, 2, 128000},
+  {kDynamicPayloadtypes[count_database++], "L16", 16000, 160, 2, 256000},
+  {kDynamicPayloadtypes[count_database++], "L16", 32000, 320, 2, 512000},
 #endif
   // G.711, PCM mu-law and A-law.
+  // Mono
   {0, "PCMU", 8000, 160, 1, 64000},
   {8, "PCMA", 8000, 160, 1, 64000},
+  // Stereo
+  {110, "PCMU", 8000, 160, 2, 64000},
+  {118, "PCMA", 8000, 160, 2, 64000},
 #ifdef WEBRTC_CODEC_ILBC
   {102, "ILBC", 8000, 240, 1, 13300},
 #endif
@@ -146,10 +156,16 @@
   {kDynamicPayloadtypes[count_database++], "AMR-WB", 16000, 320, 1, 20000},
 #endif
 #ifdef WEBRTC_CODEC_CELT
+  // Mono
+  {kDynamicPayloadtypes[count_database++], "CELT", 32000, 320, 1, 64000},
+  // Stereo
   {kDynamicPayloadtypes[count_database++], "CELT", 32000, 320, 2, 64000},
 #endif
 #ifdef WEBRTC_CODEC_G722
+  // Mono
   {9, "G722", 16000, 320, 1, 64000},
+  // Stereo
+  {119, "G722", 16000, 320, 2, 64000},
 #endif
 #ifdef WEBRTC_CODEC_G722_1
   {kDynamicPayloadtypes[count_database++], "G7221", 16000, 320, 1, 32000},
@@ -200,11 +216,20 @@
 # endif
 #endif
 #ifdef WEBRTC_CODEC_PCM16
+  // Mono
+  {4, {80, 160, 240, 320}, 0, 2},
+  {4, {160, 320, 480, 640}, 0, 2},
+  {2, {320, 640}, 0, 2},
+  // Stereo
   {4, {80, 160, 240, 320}, 0, 2},
   {4, {160, 320, 480, 640}, 0, 2},
   {2, {320, 640}, 0, 2},
 #endif
   // G.711, PCM mu-law and A-law.
+  // Mono
+  {6, {80, 160, 240, 320, 400, 480}, 0, 2},
+  {6, {80, 160, 240, 320, 400, 480}, 0, 2},
+  // Stereo
   {6, {80, 160, 240, 320, 400, 480}, 0, 2},
   {6, {80, 160, 240, 320, 400, 480}, 0, 2},
 #ifdef WEBRTC_CODEC_ILBC
@@ -217,20 +242,26 @@
   {3, {320, 640, 960}, 0, 1},
 #endif
 #ifdef WEBRTC_CODEC_CELT
+  // Mono
+  {1, {320}, 0, 2},
+  // Stereo
   {1, {320}, 0, 2},
 #endif
 #ifdef WEBRTC_CODEC_G722
+  // Mono
+  {6, {160, 320, 480, 640, 800, 960}, 0, 2},
+  // Stereo
   {6, {160, 320, 480, 640, 800, 960}, 0, 2},
 #endif
 #ifdef WEBRTC_CODEC_G722_1
-  {1, {320}, 320, 2},
-  {1, {320}, 320, 2},
-  {1, {320}, 320, 2},
+  {1, {320}, 320, 1},
+  {1, {320}, 320, 1},
+  {1, {320}, 320, 1},
 #endif
 #ifdef WEBRTC_CODEC_G722_1C
-  {1, {640}, 640, 2},
-  {1, {640}, 640, 2},
-  {1, {640}, 640, 2},
+  {1, {640}, 640, 1},
+  {1, {640}, 640, 1},
+  {1, {640}, 640, 1},
 #endif
 #ifdef WEBRTC_CODEC_G729
   {6, {80, 160, 240, 320, 400, 480}, 0, 1},
@@ -268,13 +299,22 @@
 # endif
 #endif
 #ifdef WEBRTC_CODEC_PCM16
+  // Mono
   kDecoderPCM16B,
   kDecoderPCM16Bwb,
   kDecoderPCM16Bswb32kHz,
+  // Stereo
+  kDecoderPCM16B_2ch,
+  kDecoderPCM16Bwb_2ch,
+  kDecoderPCM16Bswb32kHz_2ch,
 #endif
   // G.711, PCM mu-las and A-law.
+  // Mono
   kDecoderPCMu,
   kDecoderPCMa,
+  // Stereo
+  kDecoderPCMu_2ch,
+  kDecoderPCMa_2ch,
 #ifdef WEBRTC_CODEC_ILBC
   kDecoderILBC,
 #endif
@@ -285,10 +325,16 @@
   kDecoderAMRWB,
 #endif
 #ifdef WEBRTC_CODEC_CELT
+  // Mono
   kDecoderCELT_32,
+  // Stereo
+  kDecoderCELT_32_2ch,
 #endif
 #ifdef WEBRTC_CODEC_G722
+  // Mono
   kDecoderG722,
+  // Stereo
+  kDecoderG722_2ch,
 #endif
 #ifdef WEBRTC_CODEC_G722_1
   kDecoderG722_1_32,
@@ -343,7 +389,6 @@
 // Enumerator for error codes when asking for codec database id.
 enum {
   kInvalidCodec = -10,
-  kInvalidFrequency = -20,
   kInvalidPayloadtype = -30,
   kInvalidPacketSize = -40,
   kInvalidRate = -50
@@ -361,12 +406,8 @@
     char my_err_msg[1000];
 
     if (codec_id == kInvalidCodec) {
-      sprintf(my_err_msg, "Call to ACMCodecDB::CodecNumber failed, plname=%s "
-              "is not a valid codec", codec_inst->plname);
-    } else if (codec_id == kInvalidFrequency) {
-      sprintf(my_err_msg, "Call to ACMCodecDB::CodecNumber failed, plfreq=%d "
-              "is not a valid frequency for the codec %s", codec_inst->plfreq,
-              codec_inst->plname);
+      sprintf(my_err_msg, "Call to ACMCodecDB::CodecNumber failed, Codec not "
+              "found");
     } else if (codec_id == kInvalidPayloadtype) {
       sprintf(my_err_msg, "Call to ACMCodecDB::CodecNumber failed, payload "
               "number %d is out of range for %s", codec_inst->pltype,
@@ -396,32 +437,12 @@
 // the codec settings, the function will return an error code.
 // NOTE! The first mismatch found will generate the return value.
 int ACMCodecDB::CodecNumber(const CodecInst* codec_inst, int* mirror_id) {
-  int codec_number = -1;
-  bool name_match = false;
+  // Look for a matching codec in the database.
+  int codec_id = CodecId(codec_inst);
 
-  // Looks for a matching payload name and frequency in the codec list.
-  // Need to check both since some codecs have several codec entries with
-  // different frequencies (like iSAC).
-  for (int i = 0; i < kNumCodecs; i++) {
-    if (STR_CASE_CMP(database_[i].plname, codec_inst->plname) == 0) {
-      // We have found a matching codec name in the list.
-      name_match = true;
-
-      // Checks if frequency match.
-      if (codec_inst->plfreq == database_[i].plfreq) {
-        codec_number = i;
-        break;
-      }
-    }
-  }
-
-  // Checks if the error is in the name or in the frequency.
-  if (codec_number == -1) {
-    if (!name_match) {
-      return kInvalidCodec;
-    } else {
-      return kInvalidFrequency;
-    }
+  // Checks if we found a matching codec.
+  if (codec_id == -1) {
+    return kInvalidCodec;
   }
 
   // Checks the validity of payload type
@@ -430,25 +451,25 @@
   }
 
   // Comfort Noise is special case, packet-size & rate is not checked.
-  if (STR_CASE_CMP(database_[codec_number].plname, "CN") == 0) {
-    *mirror_id = codec_number;
-    return codec_number;
+  if (STR_CASE_CMP(database_[codec_id].plname, "CN") == 0) {
+    *mirror_id = codec_id;
+    return codec_id;
   }
 
   // RED is special case, packet-size & rate is not checked.
-  if (STR_CASE_CMP(database_[codec_number].plname, "red") == 0) {
-    *mirror_id = codec_number;
-    return codec_number;
+  if (STR_CASE_CMP(database_[codec_id].plname, "red") == 0) {
+    *mirror_id = codec_id;
+    return codec_id;
   }
 
   // Checks the validity of packet size.
-  if (codec_settings_[codec_number].num_packet_sizes > 0) {
+  if (codec_settings_[codec_id].num_packet_sizes > 0) {
     bool packet_size_ok = false;
     int i;
     int packet_size_samples;
-    for (i = 0; i < codec_settings_[codec_number].num_packet_sizes; i++) {
+    for (i = 0; i < codec_settings_[codec_id].num_packet_sizes; i++) {
       packet_size_samples =
-          codec_settings_[codec_number].packet_sizes_samples[i];
+          codec_settings_[codec_id].packet_sizes_samples[i];
       if (codec_inst->pacsize == packet_size_samples) {
         packet_size_ok = true;
         break;
@@ -464,73 +485,90 @@
     return kInvalidPacketSize;
   }
 
-
   // Check the validity of rate. Codecs with multiple rates have their own
   // function for this.
-  *mirror_id = codec_number;
+  *mirror_id = codec_id;
   if (STR_CASE_CMP("isac", codec_inst->plname) == 0) {
     if (IsISACRateValid(codec_inst->rate)) {
       // Set mirrorID to iSAC WB which is only created once to be used both for
       // iSAC WB and SWB, because they need to share struct.
       *mirror_id = kISAC;
-      return  codec_number;
+      return  codec_id;
     } else {
       return kInvalidRate;
     }
   } else if (STR_CASE_CMP("ilbc", codec_inst->plname) == 0) {
     return IsILBCRateValid(codec_inst->rate, codec_inst->pacsize)
-        ? codec_number : kInvalidRate;
+        ? codec_id : kInvalidRate;
   } else if (STR_CASE_CMP("amr", codec_inst->plname) == 0) {
     return IsAMRRateValid(codec_inst->rate)
-        ? codec_number : kInvalidRate;
+        ? codec_id : kInvalidRate;
   } else if (STR_CASE_CMP("amr-wb", codec_inst->plname) == 0) {
     return IsAMRwbRateValid(codec_inst->rate)
-        ? codec_number : kInvalidRate;
+        ? codec_id : kInvalidRate;
   } else if (STR_CASE_CMP("g7291", codec_inst->plname) == 0) {
     return IsG7291RateValid(codec_inst->rate)
-        ? codec_number : kInvalidRate;
+        ? codec_id : kInvalidRate;
   } else if (STR_CASE_CMP("speex", codec_inst->plname) == 0) {
     return IsSpeexRateValid(codec_inst->rate)
-        ? codec_number : kInvalidRate;
+        ? codec_id : kInvalidRate;
   } else if (STR_CASE_CMP("celt", codec_inst->plname) == 0) {
     return IsCeltRateValid(codec_inst->rate)
-        ? codec_number : kInvalidRate;
+        ? codec_id : kInvalidRate;
   }
 
-  return IsRateValid(codec_number, codec_inst->rate) ?
-      codec_number : kInvalidRate;
+  return IsRateValid(codec_id, codec_inst->rate) ?
+      codec_id : kInvalidRate;
 }
 
-// Gets codec id number, and mirror id, from database for the receiver.
-int ACMCodecDB::ReceiverCodecNumber(const CodecInst* codec_inst,
-    int* mirror_id) {
-  int codec_number = -1;
+// Looks for a matching payload name, frequency, and channels in the
+// codec list. Need to check all three since some codecs have several codec
+// entries with different frequencies and/or channels.
+// Does not check other codec settings, such as payload type and packet size.
+// Returns the id of the codec, or -1 if no match is found.
+int ACMCodecDB::CodecId(const CodecInst* codec_inst) {
+  return (CodecId(codec_inst->plname, codec_inst->plfreq,
+                  codec_inst->channels));
+}
 
-  // Looks for a matching payload name and frequency in the codec list.
-  // Need to check both since some codecs have several codec entries with
-  // different frequencies (like iSAC).
-  for (int i = 0; i < kNumCodecs; i++) {
-    if (STR_CASE_CMP(database_[i].plname, codec_inst->plname) == 0) {
-      // We have found a matching codec name in the list.
+int ACMCodecDB::CodecId(const char* payload_name, int frequency, int channels) {
+  for (int id = 0; id < kNumCodecs; id++) {
+    bool name_match = false;
+    bool frequency_match = false;
+    bool channels_match = false;
 
-      // Check if frequency match.
-      if (codec_inst->plfreq == database_[i].plfreq) {
-        codec_number = i;
-        *mirror_id = codec_number;
+    // Payload name, sampling frequency and number of channels need to match.
+    // NOTE! If |frequency| is -1, the frequency is not applicable, and is
+    // always treated as true, like for RED.
+    name_match = (STR_CASE_CMP(database_[id].plname, payload_name) == 0);
+    frequency_match = (frequency == database_[id].plfreq) || (frequency == -1);
+    channels_match = (channels == database_[id].channels);
 
-        // Check if codec is iSAC, set mirrorID to iSAC WB which is only
-        // created once to be used both for iSAC WB and SWB, because they need
-        // to share struct.
-        if (STR_CASE_CMP(codec_inst->plname, "ISAC") == 0) {
-          *mirror_id = kISAC;
-        }
-
-        break;
-      }
+    if (name_match && frequency_match && channels_match) {
+      // We have found a matching codec in the list.
+      return id;
     }
   }
 
-  return codec_number;
+  // We didn't find a matching codec.
+  return -1;
+}
+// Gets codec id number, and mirror id, from database for the receiver.
+int ACMCodecDB::ReceiverCodecNumber(const CodecInst* codec_inst,
+    int* mirror_id) {
+  // Look for a matching codec in the database.
+  int codec_id = CodecId(codec_inst);
+
+  // Set |mirror_id| to |codec_id|, except for iSAC. In case of iSAC we always
+  // set |mirror_id| to iSAC WB (kISAC) which is only created once to be used
+  // both for iSAC WB and SWB, because they need to share struct.
+  if (STR_CASE_CMP(codec_inst->plname, "ISAC") != 0) {
+    *mirror_id = codec_id;
+  } else {
+    *mirror_id = kISAC;
+  }
+
+  return codec_id;
 }
 
 // Returns the codec sampling frequency for codec with id = "codec_id" in
@@ -701,9 +739,17 @@
     return new ACMISAC(kISAC);
 #endif
   } else if (!STR_CASE_CMP(codec_inst->plname, "PCMU")) {
-    return new ACMPCMU(kPCMU);
+    if (codec_inst->channels == 1) {
+      return new ACMPCMU(kPCMU);
+    } else {
+      return new ACMPCMU(kPCMU_2ch);
+    }
   } else if (!STR_CASE_CMP(codec_inst->plname, "PCMA")) {
-    return new ACMPCMA(kPCMA);
+    if (codec_inst->channels == 1) {
+      return new ACMPCMA(kPCMA);
+    } else {
+      return new ACMPCMA(kPCMA_2ch);
+    }
   } else if (!STR_CASE_CMP(codec_inst->plname, "ILBC")) {
 #ifdef WEBRTC_CODEC_ILBC
     return new ACMILBC(kILBC);
@@ -718,11 +764,19 @@
 #endif
   } else if (!STR_CASE_CMP(codec_inst->plname, "CELT")) {
 #ifdef WEBRTC_CODEC_CELT
-    return new ACMCELT(kCELT32);
+    if (codec_inst->channels == 1) {
+      return new ACMCELT(kCELT32);
+    } else {
+      return new ACMCELT(kCELT32_2ch);
+    }
 #endif
   } else if (!STR_CASE_CMP(codec_inst->plname, "G722")) {
 #ifdef WEBRTC_CODEC_G722
-    return new ACMG722(kG722);
+    if (codec_inst->channels == 1) {
+      return new ACMG722(kG722);
+    } else {
+      return new ACMG722(kG722_2ch);
+    }
 #endif
   } else if (!STR_CASE_CMP(codec_inst->plname, "G7221")) {
     switch (codec_inst->plfreq) {
@@ -845,21 +899,41 @@
 #ifdef WEBRTC_CODEC_PCM16
     // For L16 we need to check sampling frequency to know what codec to create.
     int codec_id;
-    switch (codec_inst->plfreq) {
-      case 8000: {
-        codec_id = kPCM16B;
-        break;
+    if (codec_inst->channels == 1) {
+      switch (codec_inst->plfreq) {
+        case 8000: {
+          codec_id = kPCM16B;
+          break;
+        }
+        case 16000: {
+          codec_id = kPCM16Bwb;
+          break;
+        }
+        case 32000: {
+          codec_id = kPCM16Bswb32kHz;
+          break;
+        }
+        default: {
+          return NULL;
+        }
       }
-      case 16000: {
-        codec_id =kPCM16Bwb;
-        break;
-      }
-      case 32000: {
-        codec_id = kPCM16Bswb32kHz;
-        break;
-      }
-      default: {
-        return NULL;
+    } else {
+      switch (codec_inst->plfreq) {
+        case 8000: {
+          codec_id = kPCM16B_2ch;
+          break;
+        }
+        case 16000: {
+          codec_id = kPCM16Bwb_2ch;
+          break;
+        }
+        case 32000: {
+          codec_id = kPCM16Bswb32kHz_2ch;
+          break;
+        }
+        default: {
+          return NULL;
+        }
       }
     }
     return new ACMPCM16B(codec_id);
diff --git a/src/modules/audio_coding/main/source/acm_codec_database.h b/src/modules/audio_coding/main/source/acm_codec_database.h
index 6830e65..c360126 100644
--- a/src/modules/audio_coding/main/source/acm_codec_database.h
+++ b/src/modules/audio_coding/main/source/acm_codec_database.h
@@ -36,12 +36,21 @@
 # endif
 #endif
 #ifdef WEBRTC_CODEC_PCM16
+    // Mono
     , kPCM16B
     , kPCM16Bwb
     , kPCM16Bswb32kHz
+    // Stereo
+    , kPCM16B_2ch
+    , kPCM16Bwb_2ch
+    , kPCM16Bswb32kHz_2ch
 #endif
+    // Mono
     , kPCMU
     , kPCMA
+    // Stereo
+    , kPCMU_2ch
+    , kPCMA_2ch
 #ifdef WEBRTC_CODEC_ILBC
     , kILBC
 #endif
@@ -52,10 +61,16 @@
     , kGSMAMRWB
 #endif
 #ifdef WEBRTC_CODEC_CELT
+    // Mono
     , kCELT32
+    // Stereo
+    , kCELT32_2ch
 #endif
 #ifdef WEBRTC_CODEC_G722
+    // Mono
     , kG722
+    // Stereo
+    , kG722_2ch
 #endif
 #ifdef WEBRTC_CODEC_G722_1
     , kG722_1_32
@@ -100,9 +115,14 @@
 # endif
 #endif
 #ifndef WEBRTC_CODEC_PCM16
+  // Mono
   enum {kPCM16B = -1};
   enum {kPCM16Bwb = -1};
   enum {kPCM16Bswb32kHz = -1};
+  // Stereo
+  enum {kPCM16B_2ch = -1};
+  enum {kPCM16Bwb_2ch = -1};
+  enum {kPCM16Bswb32kHz_2ch = -1};
 #endif
   // 48 kHz not supported, always set to -1.
   enum {kPCM16Bswb48kHz = -1};
@@ -116,10 +136,16 @@
   enum {kGSMAMRWB = -1};
 #endif
 #ifndef WEBRTC_CODEC_CELT
+  // Mono
   enum {kCELT32 = -1};
+  // Stereo
+  enum {kCELT32_2ch = -1};
 #endif
 #ifndef WEBRTC_CODEC_G722
+  // Mono
   enum {kG722 = -1};
+  // Stereo
+  enum {kG722_2ch = -1};
 #endif
 #ifndef WEBRTC_CODEC_G722_1
   enum {kG722_1_32 = -1};
@@ -212,6 +238,8 @@
   static int CodecNumber(const CodecInst* codec_inst, int* mirror_id,
                          char* err_message, int max_message_len_byte);
   static int CodecNumber(const CodecInst* codec_inst, int* mirror_id);
+  static int CodecId(const CodecInst* codec_inst);
+  static int CodecId(const char* payload_name, int frequency, int channels);
   static int ReceiverCodecNumber(const CodecInst* codec_inst, int* mirror_id);
 
   // Returns the codec sampling frequency for codec with id = "codec_id" in
diff --git a/src/modules/audio_coding/main/source/acm_g722.cc b/src/modules/audio_coding/main/source/acm_g722.cc
index 5fda199..12397be 100644
--- a/src/modules/audio_coding/main/source/acm_g722.cc
+++ b/src/modules/audio_coding/main/source/acm_g722.cc
@@ -187,8 +187,8 @@
 
     // Interleave the 4 bits per sample from left and right channel
     for (int i = 0, j = 0; i < lenInBytes; i += 2, j++) {
-      bitStream[i] = (outRight[j] & 0xF0) + (outLeft[j] >> 4);
-      bitStream[i + 1] = ((outRight[j] & 0x0F) << 4) + (outLeft[j] & 0x0F);
+      bitStream[i] = (outLeft[j] & 0xF0) + (outRight[j] >> 4);
+      bitStream[i + 1] = ((outLeft[j] & 0x0F) << 4) + (outRight[j] & 0x0F);
     }
   } else {
     *bitStreamLenByte = WebRtcG722_Encode(_encoderInstPtr,
@@ -244,9 +244,14 @@
   // "SET_CODEC_PAR" & "SET_G722_FUNCTION."
   // Then call NetEQ to add the codec to it's
   // database.
-  SET_CODEC_PAR((codecDef), kDecoderG722, codecInst.pltype, _decoderInstPtr,
-                16000);
-  SET_G722_FUNCTIONS((codecDef));
+  if (codecInst.channels == 1) {
+    SET_CODEC_PAR(codecDef, kDecoderG722, codecInst.pltype, _decoderInstPtr,
+                  16000);
+  } else {
+    SET_CODEC_PAR(codecDef, kDecoderG722_2ch, codecInst.pltype,
+                  _decoderInstPtr, 16000);
+  }
+  SET_G722_FUNCTIONS(codecDef);
   return 0;
 }
 
diff --git a/src/modules/audio_coding/main/source/acm_pcm16b.cc b/src/modules/audio_coding/main/source/acm_pcm16b.cc
index 971709c..3387567 100644
--- a/src/modules/audio_coding/main/source/acm_pcm16b.cc
+++ b/src/modules/audio_coding/main/source/acm_pcm16b.cc
@@ -8,10 +8,11 @@
  *  be found in the AUTHORS file in the root of the source tree.
  */
 
+#include "acm_pcm16b.h"
+
 #include "acm_codec_database.h"
 #include "acm_common_defs.h"
 #include "acm_neteq.h"
-#include "acm_pcm16b.h"
 #include "trace.h"
 #include "webrtc_neteq.h"
 #include "webrtc_neteq_help_macros.h"
@@ -20,267 +21,202 @@
     #include "pcm16b.h"
 #endif
 
-namespace webrtc
-{
+namespace webrtc {
 
 #ifndef WEBRTC_CODEC_PCM16
 
-ACMPCM16B::ACMPCM16B(
-    WebRtc_Word16 /* codecID */)
-{
-    return;
+ACMPCM16B::ACMPCM16B(WebRtc_Word16 /* codecID */) {
+  return;
 }
 
-
-ACMPCM16B::~ACMPCM16B()
-{
-    return;
+ACMPCM16B::~ACMPCM16B() {
+  return;
 }
 
-
-WebRtc_Word16
-ACMPCM16B::InternalEncode(
-    WebRtc_UWord8* /* bitStream        */,
-    WebRtc_Word16* /* bitStreamLenByte */)
-{
-    return -1;
+WebRtc_Word16 ACMPCM16B::InternalEncode(WebRtc_UWord8* /* bitStream */,
+                                        WebRtc_Word16* /* bitStreamLenByte */) {
+  return -1;
 }
 
-
-WebRtc_Word16
-ACMPCM16B::DecodeSafe(
-    WebRtc_UWord8* /* bitStream        */,
-    WebRtc_Word16  /* bitStreamLenByte */,
-    WebRtc_Word16* /* audio            */,
-    WebRtc_Word16* /* audioSamples     */,
-    WebRtc_Word8*  /* speechType       */)
-{
-    return -1;
+WebRtc_Word16 ACMPCM16B::DecodeSafe(WebRtc_UWord8* /* bitStream */,
+                                    WebRtc_Word16 /* bitStreamLenByte */,
+                                    WebRtc_Word16* /* audio */,
+                                    WebRtc_Word16* /* audioSamples */,
+                                    WebRtc_Word8* /* speechType */) {
+  return -1;
 }
 
-
-WebRtc_Word16
-ACMPCM16B::InternalInitEncoder(
-    WebRtcACMCodecParams* /* codecParams */)
-{
-    return -1;
+WebRtc_Word16 ACMPCM16B::InternalInitEncoder(
+    WebRtcACMCodecParams* /* codecParams */) {
+  return -1;
 }
 
-
-WebRtc_Word16
-ACMPCM16B::InternalInitDecoder(
-    WebRtcACMCodecParams* /* codecParams */)
-{
-   return -1;
+WebRtc_Word16 ACMPCM16B::InternalInitDecoder(
+    WebRtcACMCodecParams* /* codecParams */) {
+  return -1;
 }
 
-
-WebRtc_Word32
-ACMPCM16B::CodecDef(
-    WebRtcNetEQ_CodecDef& /* codecDef  */,
-    const CodecInst&      /* codecInst */)
-{
-    return -1;
+WebRtc_Word32 ACMPCM16B::CodecDef(WebRtcNetEQ_CodecDef& /* codecDef */,
+                                  const CodecInst& /* codecInst */) {
+  return -1;
 }
 
-
-ACMGenericCodec*
-ACMPCM16B::CreateInstance(void)
-{
-    return NULL;
+ACMGenericCodec* ACMPCM16B::CreateInstance(void) {
+  return NULL;
 }
 
-
-WebRtc_Word16
-ACMPCM16B::InternalCreateEncoder()
-{
-    return -1;
+WebRtc_Word16 ACMPCM16B::InternalCreateEncoder() {
+  return -1;
 }
 
-
-WebRtc_Word16
-ACMPCM16B::InternalCreateDecoder()
-{
-    return -1;
+WebRtc_Word16 ACMPCM16B::InternalCreateDec WEBRTC_CODEC_PCM16oder() {
+  return -1;
 }
 
-
-void
-ACMPCM16B::InternalDestructEncoderInst(
-    void* /* ptrInst */)
-{
-    return;
+void ACMPCM16B::InternalDestructEncoderInst(void* /* ptrInst */) {
+  return;
 }
 
-
-void
-ACMPCM16B::DestructEncoderSafe()
-{
-    return;
+void ACMPCM16B::DestructEncoderSafe() {
+  return;
 }
 
-void
-ACMPCM16B::DestructDecoderSafe()
-{
-    return;
+void ACMPCM16B::DestructDecoderSafe() {
+  return;
 }
 
 void ACMPCM16B::SplitStereoPacket(uint8_t* /*payload*/,
-                                  int32_t* /*payload_length*/) {}
+                                  int32_t* /*payload_length*/) {
+}
 
 #else     //===================== Actual Implementation =======================
 
-
-ACMPCM16B::ACMPCM16B(
-    WebRtc_Word16 codecID)
-{
-    _codecID = codecID;
-    _samplingFreqHz = ACMCodecDB::CodecFreq(_codecID);
+ACMPCM16B::ACMPCM16B(WebRtc_Word16 codecID) {
+  _codecID = codecID;
+  _samplingFreqHz = ACMCodecDB::CodecFreq(_codecID);
 }
 
-
-ACMPCM16B::~ACMPCM16B()
-{
-    return;
+ACMPCM16B::~ACMPCM16B() {
+  return;
 }
 
-
-WebRtc_Word16
-ACMPCM16B::InternalEncode(
-    WebRtc_UWord8* bitStream,
-    WebRtc_Word16* bitStreamLenByte)
-{
-    *bitStreamLenByte = WebRtcPcm16b_Encode(&_inAudio[_inAudioIxRead],
-                                            _frameLenSmpl*_noChannels,
-                                            bitStream);
-    // increment the read index to tell the caller that how far
-    // we have gone forward in reading the audio buffer
-    _inAudioIxRead += _frameLenSmpl*_noChannels;
-    return *bitStreamLenByte;
+WebRtc_Word16 ACMPCM16B::InternalEncode(WebRtc_UWord8* bitStream,
+                                        WebRtc_Word16* bitStreamLenByte) {
+  *bitStreamLenByte = WebRtcPcm16b_Encode(&_inAudio[_inAudioIxRead],
+                                          _frameLenSmpl * _noChannels,
+                                          bitStream);
+  // Increment the read index to tell the caller that how far
+  // we have gone forward in reading the audio buffer.
+  _inAudioIxRead += _frameLenSmpl * _noChannels;
+  return *bitStreamLenByte;
 }
 
-
-WebRtc_Word16
-ACMPCM16B::DecodeSafe(
-    WebRtc_UWord8* /* bitStream        */,
-    WebRtc_Word16  /* bitStreamLenByte */,
-    WebRtc_Word16* /* audio            */,
-    WebRtc_Word16* /* audioSamples     */,
-    WebRtc_Word8*  /* speechType       */)
-{
-    return 0;
+WebRtc_Word16 ACMPCM16B::DecodeSafe(WebRtc_UWord8* /* bitStream */,
+                                    WebRtc_Word16 /* bitStreamLenByte */,
+                                    WebRtc_Word16* /* audio */,
+                                    WebRtc_Word16* /* audioSamples */,
+                                    WebRtc_Word8* /* speechType */) {
+  return 0;
 }
 
-
-WebRtc_Word16
-ACMPCM16B::InternalInitEncoder(
-    WebRtcACMCodecParams* /* codecParams */)
-{
-    // This codec does not need initialization,
-    // PCM has no instance
-    return 0;
+WebRtc_Word16 ACMPCM16B::InternalInitEncoder(
+    WebRtcACMCodecParams* /* codecParams */) {
+  // This codec does not need initialization, PCM has no instance.
+  return 0;
 }
 
-
-WebRtc_Word16
-ACMPCM16B::InternalInitDecoder(
-    WebRtcACMCodecParams* /* codecParams */)
-{
-   // This codec does not need initialization,
-   // PCM has no instance
-   return 0;
+WebRtc_Word16 ACMPCM16B::InternalInitDecoder(
+    WebRtcACMCodecParams* /* codecParams */) {
+  // This codec does not need initialization, PCM has no instance.
+  return 0;
 }
 
-
-WebRtc_Word32
-ACMPCM16B::CodecDef(
-    WebRtcNetEQ_CodecDef& codecDef,
-    const CodecInst&      codecInst)
-{
-    // Fill up the structure by calling
-    // "SET_CODEC_PAR" & "SET_PCMU_FUNCTION."
-    // Then call NetEQ to add the codec to it's
-    // database.
-    switch(_samplingFreqHz)
-    {
-    case 8000:
-        {
-            SET_CODEC_PAR((codecDef), kDecoderPCM16B, codecInst.pltype,
-                NULL, 8000);
-            SET_PCM16B_FUNCTIONS((codecDef));
-            break;
-        }
-    case 16000:
-        {
-            SET_CODEC_PAR((codecDef), kDecoderPCM16Bwb, codecInst.pltype,
-                NULL, 16000);
-            SET_PCM16B_WB_FUNCTIONS((codecDef));
-            break;
-        }
-    case 32000:
-        {
-            SET_CODEC_PAR((codecDef), kDecoderPCM16Bswb32kHz,
-                codecInst.pltype, NULL, 32000);
-            SET_PCM16B_SWB32_FUNCTIONS((codecDef));
-            break;
-        }
-    default:
-        {
-            return -1;
-        }
+WebRtc_Word32 ACMPCM16B::CodecDef(WebRtcNetEQ_CodecDef& codecDef,
+                                  const CodecInst& codecInst) {
+  // Fill up the structure by calling "SET_CODEC_PAR" & "SET_PCMU_FUNCTION".
+  // Then call NetEQ to add the codec to it's database.
+  if (codecInst.channels == 1) {
+    switch(_samplingFreqHz) {
+      case 8000: {
+        SET_CODEC_PAR(codecDef, kDecoderPCM16B, codecInst.pltype, NULL, 8000);
+        SET_PCM16B_FUNCTIONS(codecDef);
+        break;
+      }
+      case 16000: {
+        SET_CODEC_PAR(codecDef, kDecoderPCM16Bwb, codecInst.pltype, NULL,
+                      16000);
+        SET_PCM16B_WB_FUNCTIONS(codecDef);
+        break;
+      }
+      case 32000: {
+        SET_CODEC_PAR(codecDef, kDecoderPCM16Bswb32kHz, codecInst.pltype,
+                      NULL, 32000);
+        SET_PCM16B_SWB32_FUNCTIONS(codecDef);
+        break;
+      }
+      default: {
+        return -1;
+      }
     }
-    return 0;
+  } else {
+    switch(_samplingFreqHz) {
+      case 8000: {
+        SET_CODEC_PAR(codecDef, kDecoderPCM16B_2ch, codecInst.pltype, NULL,
+                      8000);
+        SET_PCM16B_FUNCTIONS(codecDef);
+        break;
+      }
+      case 16000: {
+        SET_CODEC_PAR(codecDef, kDecoderPCM16Bwb_2ch, codecInst.pltype,
+                      NULL, 16000);
+        SET_PCM16B_WB_FUNCTIONS(codecDef);
+        break;
+      }
+      case 32000: {
+        SET_CODEC_PAR(codecDef, kDecoderPCM16Bswb32kHz_2ch, codecInst.pltype,
+                      NULL, 32000);
+        SET_PCM16B_SWB32_FUNCTIONS(codecDef);
+        break;
+      }
+      default: {
+        return -1;
+      }
+    }
+  }
+  return 0;
 }
 
-
-ACMGenericCodec*
-ACMPCM16B::CreateInstance(void)
-{
-    return NULL;
+ACMGenericCodec* ACMPCM16B::CreateInstance(void) {
+  return NULL;
 }
 
-
-WebRtc_Word16
-ACMPCM16B::InternalCreateEncoder()
-{
-    // PCM has no instance
-    return 0;
+WebRtc_Word16 ACMPCM16B::InternalCreateEncoder() {
+  // PCM has no instance.
+  return 0;
 }
 
-
-WebRtc_Word16
-ACMPCM16B::InternalCreateDecoder()
-{
-    // PCM has no instance
-    return 0;
+WebRtc_Word16 ACMPCM16B::InternalCreateDecoder() {
+  // PCM has no instance.
+  return 0;
 }
 
-
-void
-ACMPCM16B::InternalDestructEncoderInst(
-    void* /* ptrInst */)
-{
-    // PCM has no instance
-   return;
+void ACMPCM16B::InternalDestructEncoderInst(void* /* ptrInst */) {
+  // PCM has no instance.
+  return;
 }
 
-
-void
-ACMPCM16B::DestructEncoderSafe()
-{
-    // PCM has no instance
-    _encoderExist = false;
-    _encoderInitialized = false;
-     return;
+void ACMPCM16B::DestructEncoderSafe() {
+  // PCM has no instance.
+  _encoderExist = false;
+  _encoderInitialized = false;
+  return;
 }
 
-void
-ACMPCM16B::DestructDecoderSafe()
-{
-    // PCM has no instance
-    _decoderExist = false;
-    _decoderInitialized = false;
-    return;
+void ACMPCM16B::DestructDecoderSafe() {
+  // PCM has no instance.
+  _decoderExist = false;
+  _decoderInitialized = false;
+  return;
 }
 
 // Split the stereo packet and place left and right channel after each other
diff --git a/src/modules/audio_coding/main/source/acm_pcma.cc b/src/modules/audio_coding/main/source/acm_pcma.cc
index 6d13a5f..c459d25 100644
--- a/src/modules/audio_coding/main/source/acm_pcma.cc
+++ b/src/modules/audio_coding/main/source/acm_pcma.cc
@@ -8,9 +8,10 @@
  *  be found in the AUTHORS file in the root of the source tree.
  */
 
+#include "acm_pcma.h"
+
 #include "acm_common_defs.h"
 #include "acm_neteq.h"
-#include "acm_pcma.h"
 #include "trace.h"
 #include "webrtc_neteq.h"
 #include "webrtc_neteq_help_macros.h"
@@ -18,128 +19,92 @@
 // Codec interface
 #include "g711_interface.h"
 
-namespace webrtc
-{
+namespace webrtc {
 
-ACMPCMA::ACMPCMA(WebRtc_Word16 codecID)
-{
-    _codecID = codecID;
+ACMPCMA::ACMPCMA(WebRtc_Word16 codecID) {
+  _codecID = codecID;
 }
 
-
-ACMPCMA::~ACMPCMA()
-{
-    return;
+ACMPCMA::~ACMPCMA() {
+  return;
 }
 
-
-WebRtc_Word16 
-ACMPCMA::InternalEncode(
-    WebRtc_UWord8* bitStream,
-    WebRtc_Word16* bitStreamLenByte)
-{
-    *bitStreamLenByte = WebRtcG711_EncodeA(NULL, &_inAudio[_inAudioIxRead],
-        _frameLenSmpl*_noChannels, (WebRtc_Word16*)bitStream);
-    // increment the read index this tell the caller that how far 
-    // we have gone forward in reading the audio buffer
-    _inAudioIxRead += _frameLenSmpl*_noChannels;
-    return *bitStreamLenByte;
+WebRtc_Word16 ACMPCMA::InternalEncode(WebRtc_UWord8* bitStream,
+                                      WebRtc_Word16* bitStreamLenByte) {
+  *bitStreamLenByte = WebRtcG711_EncodeA(NULL, &_inAudio[_inAudioIxRead],
+                                         _frameLenSmpl * _noChannels,
+                                         (WebRtc_Word16*) bitStream);
+  // Increment the read index this tell the caller that how far
+  // we have gone forward in reading the audio buffer.
+  _inAudioIxRead += _frameLenSmpl * _noChannels;
+  return *bitStreamLenByte;
 }
 
-
-WebRtc_Word16 
-ACMPCMA::DecodeSafe(
-    WebRtc_UWord8* /* bitStream        */,
-    WebRtc_Word16  /* bitStreamLenByte */, 
-    WebRtc_Word16* /* audio            */, 
-    WebRtc_Word16* /* audioSamples     */, 
-    WebRtc_Word8*  /* speechType       */)
-{
-    return 0;
+WebRtc_Word16 ACMPCMA::DecodeSafe(WebRtc_UWord8* /* bitStream */,
+                                  WebRtc_Word16 /* bitStreamLenByte */,
+                                  WebRtc_Word16* /* audio */,
+                                  WebRtc_Word16* /* audioSamples */,
+                                  WebRtc_Word8* /* speechType */) {
+  return 0;
 }
 
-
-WebRtc_Word16 
-ACMPCMA::InternalInitEncoder(
-    WebRtcACMCodecParams* /* codecParams */)
-{
-    // This codec does not need initialization,
-    // PCM has no instance
-    return 0;    
+WebRtc_Word16 ACMPCMA::InternalInitEncoder(
+    WebRtcACMCodecParams* /* codecParams */) {
+  // This codec does not need initialization, PCM has no instance.
+  return 0;
 }
 
-
-WebRtc_Word16 
-ACMPCMA::InternalInitDecoder(
-    WebRtcACMCodecParams* /* codecParams */)
-{
-    // This codec does not need initialization,
-    // PCM has no instance
-    return 0;
+WebRtc_Word16 ACMPCMA::InternalInitDecoder(
+    WebRtcACMCodecParams* /* codecParams */) {
+  // This codec does not need initialization, PCM has no instance.
+  return 0;
 }
 
-
-WebRtc_Word32 ACMPCMA::CodecDef(
-    WebRtcNetEQ_CodecDef& codecDef,
-    const CodecInst&  codecInst)
-{
-    // Fill up the structure by calling 
-    // "SET_CODEC_PAR" & "SET_PCMA_FUNCTION."
-    // Then call NetEQ to add the codec to it's
-    // database.
-    SET_CODEC_PAR((codecDef), kDecoderPCMa, codecInst.pltype, NULL, 8000);
-    SET_PCMA_FUNCTIONS((codecDef));
-    return 0;
+WebRtc_Word32 ACMPCMA::CodecDef(WebRtcNetEQ_CodecDef& codecDef,
+                                const CodecInst& codecInst) {
+  // Fill up the structure by calling
+  // "SET_CODEC_PAR" & "SET_PCMA_FUNCTION."
+  // Then call NetEQ to add the codec to it's database.
+  if (codecInst.channels == 1) {
+    // Mono mode.
+    SET_CODEC_PAR(codecDef, kDecoderPCMa, codecInst.pltype, NULL, 8000);
+  } else {
+    // Stereo mode.
+    SET_CODEC_PAR(codecDef, kDecoderPCMa_2ch, codecInst.pltype, NULL, 8000);
+  }
+  SET_PCMA_FUNCTIONS(codecDef);
+  return 0;
 }
 
-
-ACMGenericCodec*
-ACMPCMA::CreateInstance(void)
-{
-    return NULL;
+ACMGenericCodec* ACMPCMA::CreateInstance(void) {
+  return NULL;
 }
 
-
-WebRtc_Word16
-ACMPCMA::InternalCreateEncoder()
-{
-    // PCM has no instance
-    return 0;
+WebRtc_Word16 ACMPCMA::InternalCreateEncoder() {
+  // PCM has no instance.
+  return 0;
 }
 
-
-WebRtc_Word16
-ACMPCMA::InternalCreateDecoder()
-{
-    // PCM has no instance
-    return 0;
+WebRtc_Word16 ACMPCMA::InternalCreateDecoder() {
+  // PCM has no instance.
+  return 0;
 }
 
-
-void 
-ACMPCMA::InternalDestructEncoderInst(
-    void* /* ptrInst */)
-{
-    // PCM has no instance
-    return;
+void ACMPCMA::InternalDestructEncoderInst(void* /* ptrInst */) {
+  // PCM has no instance.
+  return;
 }
 
-
-void 
-ACMPCMA::DestructEncoderSafe()
-{
-    // PCM has no instance
-    return;
+void ACMPCMA::DestructEncoderSafe() {
+  // PCM has no instance.
+  return;
 }
 
-
-void 
-ACMPCMA::DestructDecoderSafe()
-{
-    // PCM has no instance
-    _decoderInitialized = false;
-    _decoderExist = false;
-    return;
+void ACMPCMA::DestructDecoderSafe() {
+  // PCM has no instance.
+  _decoderInitialized = false;
+  _decoderExist = false;
+  return;
 }
 
 // Split the stereo packet and place left and right channel after each other
diff --git a/src/modules/audio_coding/main/source/acm_pcmu.cc b/src/modules/audio_coding/main/source/acm_pcmu.cc
index f1173f8..83240d4 100644
--- a/src/modules/audio_coding/main/source/acm_pcmu.cc
+++ b/src/modules/audio_coding/main/source/acm_pcmu.cc
@@ -8,9 +8,10 @@
  *  be found in the AUTHORS file in the root of the source tree.
  */
 
+#include "acm_pcmu.h"
+
 #include "acm_common_defs.h"
 #include "acm_neteq.h"
-#include "acm_pcmu.h"
 #include "trace.h"
 #include "webrtc_neteq.h"
 #include "webrtc_neteq_help_macros.h"
@@ -18,129 +19,94 @@
 // Codec interface
 #include "g711_interface.h"
 
-namespace webrtc
-{
+namespace webrtc {
 
-ACMPCMU::ACMPCMU(WebRtc_Word16 codecID)
-{
-    _codecID = codecID;
+ACMPCMU::ACMPCMU(WebRtc_Word16 codecID) {
+  _codecID = codecID;
 }
 
-
-ACMPCMU::~ACMPCMU()
-{
-    return;
+ACMPCMU::~ACMPCMU() {
+  return;
 }
 
-
-WebRtc_Word16
-ACMPCMU::InternalEncode(
-    WebRtc_UWord8* bitStream,
-    WebRtc_Word16* bitStreamLenByte)
-{
-    *bitStreamLenByte = WebRtcG711_EncodeU(NULL, &_inAudio[_inAudioIxRead],
-        _frameLenSmpl*_noChannels, (WebRtc_Word16*)bitStream);
-    // increment the read index this tell the caller that how far
-    // we have gone forward in reading the audio buffer
-    _inAudioIxRead += _frameLenSmpl*_noChannels;
-    return *bitStreamLenByte;
+WebRtc_Word16 ACMPCMU::InternalEncode(WebRtc_UWord8* bitStream,
+                                      WebRtc_Word16* bitStreamLenByte) {
+  *bitStreamLenByte = WebRtcG711_EncodeU(NULL, &_inAudio[_inAudioIxRead],
+                                         _frameLenSmpl * _noChannels,
+                                         (WebRtc_Word16*) bitStream);
+  // Increment the read index this tell the caller that how far
+  // we have gone forward in reading the audio buffer.
+  _inAudioIxRead += _frameLenSmpl * _noChannels;
+  return *bitStreamLenByte;
 }
 
-
-WebRtc_Word16
-ACMPCMU::DecodeSafe(
-    WebRtc_UWord8* /* bitStream        */,
-    WebRtc_Word16  /* bitStreamLenByte */,
-    WebRtc_Word16* /* audio            */,
-    WebRtc_Word16* /* audioSamples     */,
-    WebRtc_Word8*  /* speechType       */)
-{
-    return 0;
+WebRtc_Word16 ACMPCMU::DecodeSafe(WebRtc_UWord8* /* bitStream */,
+                                  WebRtc_Word16 /* bitStreamLenByte */,
+                                  WebRtc_Word16* /* audio */,
+                                  WebRtc_Word16* /* audioSamples */,
+                                  WebRtc_Word8* /* speechType */) {
+  return 0;
 }
 
-
-WebRtc_Word16
-ACMPCMU::InternalInitEncoder(
-    WebRtcACMCodecParams* /* codecParams */)
-{
-    // This codec does not need initialization,
-    // PCM has no instance
-    return 0;
+WebRtc_Word16 ACMPCMU::InternalInitEncoder(
+    WebRtcACMCodecParams* /* codecParams */) {
+  // This codec does not need initialization, PCM has no instance.
+  return 0;
 }
 
-
-WebRtc_Word16
-ACMPCMU::InternalInitDecoder(
-    WebRtcACMCodecParams* /* codecParams */)
-{
-   // This codec does not need initialization,
-   // PCM has no instance
+WebRtc_Word16 ACMPCMU::InternalInitDecoder(
+    WebRtcACMCodecParams* /* codecParams */) {
+   // This codec does not need initialization, PCM has no instance.
    return 0;
 }
 
-
-WebRtc_Word32
-ACMPCMU::CodecDef(
-    WebRtcNetEQ_CodecDef& codecDef,
-    const CodecInst&      codecInst)
-{
-    // Fill up the structure by calling
-    // "SET_CODEC_PAR" & "SET_PCMU_FUNCTION."
-    // Then call NetEQ to add the codec to it's
-    // database.
-    SET_CODEC_PAR((codecDef), kDecoderPCMu, codecInst.pltype, NULL, 8000);
-    SET_PCMU_FUNCTIONS((codecDef));
-    return 0;
+WebRtc_Word32 ACMPCMU::CodecDef(WebRtcNetEQ_CodecDef& codecDef,
+                                const CodecInst& codecInst) {
+  // Fill up the structure by calling
+  // "SET_CODEC_PAR" & "SET_PCMU_FUNCTION."
+  // Then call NetEQ to add the codec to it's database.
+  if (codecInst.channels == 1) {
+    // Mono mode.
+    SET_CODEC_PAR(codecDef, kDecoderPCMu, codecInst.pltype, NULL, 8000);
+  } else {
+    // Stereo mode.
+    SET_CODEC_PAR(codecDef, kDecoderPCMu_2ch, codecInst.pltype, NULL, 8000);
+  }
+  SET_PCMU_FUNCTIONS(codecDef);
+  return 0;
 }
 
-
-ACMGenericCodec*
-ACMPCMU::CreateInstance(void)
-{
-    return NULL;
+ACMGenericCodec* ACMPCMU::CreateInstance(void) {
+  return NULL;
 }
 
-
-WebRtc_Word16
-ACMPCMU::InternalCreateEncoder()
-{
-    // PCM has no instance
-    return 0;
+WebRtc_Word16 ACMPCMU::InternalCreateEncoder() {
+  // PCM has no instance.
+  return 0;
 }
 
-
-WebRtc_Word16
-ACMPCMU::InternalCreateDecoder()
-{
-    // PCM has no instance
-    return 0;
+WebRtc_Word16 ACMPCMU::InternalCreateDecoder() {
+  // PCM has no instance.
+  return 0;
 }
 
-
-void
-ACMPCMU::InternalDestructEncoderInst(
-    void* /* ptrInst */)
-{
-    // PCM has no instance
-    return;
+void ACMPCMU::InternalDestructEncoderInst(void* /* ptrInst */) {
+  // PCM has no instance.
+  return;
 }
 
-
-void
-ACMPCMU::DestructEncoderSafe()
-{
-    // PCM has no instance
-    _encoderExist = false;
-    _encoderInitialized = false;
-    return;
+void ACMPCMU::DestructEncoderSafe() {
+  // PCM has no instance.
+  _encoderExist = false;
+  _encoderInitialized = false;
+  return;
 }
 
-void ACMPCMU::DestructDecoderSafe()
-{
-    // PCM has no instance
-    _decoderInitialized = false;
-    _decoderExist = false;
-    return;
+void ACMPCMU::DestructDecoderSafe() {
+  // PCM has no instance.
+  _decoderInitialized = false;
+  _decoderExist = false;
+  return;
 }
 
 // Split the stereo packet and place left and right channel after each other
diff --git a/src/modules/audio_coding/main/source/audio_coding_module.cc b/src/modules/audio_coding/main/source/audio_coding_module.cc
index 2cd959d..4fe6dad 100644
--- a/src/modules/audio_coding/main/source/audio_coding_module.cc
+++ b/src/modules/audio_coding/main/source/audio_coding_module.cc
@@ -49,67 +49,37 @@
     return ACMCodecDB::Codec(listId, &codec);
 }
 
-// Get supported codec Param with name
-WebRtc_Word32
-AudioCodingModule::Codec(
-    const char* payloadName,
-    CodecInst&          codec,
-    const WebRtc_Word32 samplingFreqHz)
-{
-    // Search through codec list for a matching name
-    for(int codecCntr = 0; codecCntr < ACMCodecDB::kNumCodecs; codecCntr++)
-    {
-        // Store codec settings for codec number "codeCntr" in the output struct
-        ACMCodecDB::Codec(codecCntr, &codec);
+// Get supported codec Param with name, frequency and number of channels.
+WebRtc_Word32 AudioCodingModule::Codec(const char* payload_name,
+                                       CodecInst& codec,
+                                       int sampling_freq_hz,
+                                       int channels) {
+  int codec_id;
 
-        if(!STR_CASE_CMP(codec.plname, payloadName))
-        {
-            // If samplingFreqHz is set (!= -1), check if frequency matches
-            if((samplingFreqHz == codec.plfreq) || (samplingFreqHz == -1))
-            {
-                // We found a match, return OK
-                return 0;
-            }
-        }
-    }
-
-    // if we are here we couldn't find anything
-    // set the params to unacceptable values
+  // Get the id of the codec from the database.
+  codec_id = ACMCodecDB::CodecId(payload_name, sampling_freq_hz, channels);
+  if (codec_id < 0) {
+    // We couldn't find a matching codec, set the parameterss to unacceptable
+    // values and return.
     codec.plname[0] = '\0';
     codec.pltype    = -1;
     codec.pacsize   = 0;
     codec.rate      = 0;
     codec.plfreq    = 0;
     return -1;
+  }
+
+  // Get default codec settings.
+  ACMCodecDB::Codec(codec_id, &codec);
+
+  return 0;
 }
 
-// Get supported codec Index with name, and frequency if needed
-WebRtc_Word32
-AudioCodingModule::Codec(
-    const char* payloadName,
-    const WebRtc_Word32 samplingFreqHz)
-{
-    CodecInst codec;
-
-    // Search through codec list for a matching name
-    for(int codecCntr = 0; codecCntr < ACMCodecDB::kNumCodecs; codecCntr++)
-    {
-        // Temporally store codec settings for codec number "codeCntr" in "codec"
-        ACMCodecDB::Codec(codecCntr, &codec);
-
-        if(!STR_CASE_CMP(codec.plname, payloadName))
-        {
-            // If samplingFreqHz is set (!= -1), check if frequency matches
-            if((samplingFreqHz == codec.plfreq) || (samplingFreqHz == -1))
-            {
-                // We found a match, return codec list number (index)
-                return codecCntr;
-            }
-        }
-    }
-
-    // We did not find a matching codec in the list
-    return -1;
+// Get supported codec Index with name, frequency and number of channels.
+WebRtc_Word32 AudioCodingModule::Codec(const char* payload_name,
+                                       int sampling_freq_hz,
+                                       int channels) {
+  return ACMCodecDB::CodecId(payload_name, sampling_freq_hz, channels);
 }
 
 // Checks the validity of the parameters of the given codec
diff --git a/src/modules/audio_coding/main/source/audio_coding_module_impl.cc b/src/modules/audio_coding/main/source/audio_coding_module_impl.cc
index e2442f2..9171221 100644
--- a/src/modules/audio_coding/main/source/audio_coding_module_impl.cc
+++ b/src/modules/audio_coding/main/source/audio_coding_module_impl.cc
@@ -978,14 +978,14 @@
   // either mono-to-stereo or stereo-to-mono conversion.
   WebRtc_Word16 audio[WEBRTC_10MS_PCM_AUDIO];
   int audio_channels = _sendCodecInst.channels;
-  if (audio_frame.num_channels_ != _sendCodecInst.channels) {
-    if (_sendCodecInst.channels == 2) {
+  if (audio_frame.num_channels_ != audio_channels) {
+    if (audio_channels == 2) {
       // Do mono-to-stereo conversion by copying each sample.
       for (int k = 0; k < audio_frame.samples_per_channel_; k++) {
         audio[k * 2] = audio_frame.data_[k];
         audio[(k * 2) + 1] = audio_frame.data_[k];
       }
-    } else if (_sendCodecInst.channels == 1) {
+    } else if (audio_channels == 1) {
       // Do stereo-to-mono conversion by creating the average of the stereo
       // samples.
       for (int k = 0; k < audio_frame.samples_per_channel_; k++) {
diff --git a/src/modules/audio_coding/main/test/APITest.cc b/src/modules/audio_coding/main/test/APITest.cc
index f3b0a8d..f601567 100644
--- a/src/modules/audio_coding/main/test/APITest.cc
+++ b/src/modules/audio_coding/main/test/APITest.cc
@@ -1495,11 +1495,11 @@
             Wait(1000);   
 
             // After Initialization CN is lost, re-register them
-            if(AudioCodingModule::Codec("CN", myCodec, 8000) >= 0)
+            if(AudioCodingModule::Codec("CN", myCodec, 8000, 1) >= 0)
             {
                 CHECK_ERROR_MT(myACM->RegisterSendCodec(myCodec));
             }
-            if(AudioCodingModule::Codec("CN", myCodec, 16000) >= 0)
+            if(AudioCodingModule::Codec("CN", myCodec, 16000, 1) >= 0)
             {
                 CHECK_ERROR_MT(myACM->RegisterSendCodec(myCodec));
             }
diff --git a/src/modules/audio_coding/main/test/EncodeDecodeTest.cc b/src/modules/audio_coding/main/test/EncodeDecodeTest.cc
index 1127fa3..15e91be 100644
--- a/src/modules/audio_coding/main/test/EncodeDecodeTest.cc
+++ b/src/modules/audio_coding/main/test/EncodeDecodeTest.cc
@@ -149,9 +149,6 @@
   noOfCodecs = acm->NumberOfCodecs();
   for (int i = 0; i < noOfCodecs; i++) {
     acm->Codec((WebRtc_UWord8) i, recvCodec);
-    if (!strcmp(recvCodec.plname, "CELT")) {
-      recvCodec.channels = 1;
-    }
     if (acm->RegisterReceiveCodec(recvCodec) != 0) {
       printf("Unable to register codec: for run: codecId: %d\n", codeId);
       exit(1);
@@ -220,7 +217,6 @@
    if (ok != 0) {
      printf("Error when inserting packet to ACM, for run: codecId: %d\n",
             codeId);
-     exit(1);
    }
    _realPayloadSizeBytes = _rtpStream->Read(&_rtpInfo, _incomingPayload,
                                             _payloadSizeBytes, &_nextTime);
@@ -296,20 +292,24 @@
   }
 
   int numCodecs = 1;
-  int codePars[3]; //freq, pacsize, rate
-  int numPars[52]; //number of codec parameters sets (rate,freq,pacsize)to test,
-                   //for a given codec
+  int codePars[3]; // Frequency, packet size, rate.
+  int numPars[52]; // Number of codec parameters sets (freq, pacsize, rate)
+                   // to test, for a given codec.
 
   codePars[0] = 0;
   codePars[1] = 0;
   codePars[2] = 0;
 
+  AudioCodingModule *acmTmp = AudioCodingModule::Create(0);
+  struct CodecInst sendCodecTmp;
+  numCodecs = acmTmp->NumberOfCodecs();
+  AudioCodingModule::Destroy(acmTmp);
+
   if (_testMode == 1) {
-    AudioCodingModule *acmTmp = AudioCodingModule::Create(0);
-    struct CodecInst sendCodecTmp;
-    numCodecs = acmTmp->NumberOfCodecs();
     printf("List of supported codec.\n");
-    for(int n = 0; n < numCodecs; n++) {
+  }
+  if (_testMode != 2) {
+    for (int n = 0; n < numCodecs; n++) {
       acmTmp->Codec(n, sendCodecTmp);
       if (STR_CASE_CMP(sendCodecTmp.plname, "telephone-event") == 0) {
         numPars[n] = 0;
@@ -317,28 +317,13 @@
         numPars[n] = 0;
       } else if (STR_CASE_CMP(sendCodecTmp.plname, "red") == 0) {
         numPars[n] = 0;
+      } else if (sendCodecTmp.channels == 2) {
+        numPars[n] = 0;
       } else {
         numPars[n] = 1;
-        printf("%d %s\n", n, sendCodecTmp.plname);
-      }
-    }
-    AudioCodingModule::Destroy(acmTmp);
-  } else if (_testMode == 0) {
-    AudioCodingModule *acmTmp = AudioCodingModule::Create(0);
-    numCodecs = acmTmp->NumberOfCodecs();
-    AudioCodingModule::Destroy(acmTmp);
-    struct CodecInst dummyCodec;
-
-    //chose range of testing for codecs/parameters
-    for(int i = 0 ; i < numCodecs ; i++) {
-      numPars[i] = 1;
-      acmTmp->Codec(i, dummyCodec);
-      if (STR_CASE_CMP(dummyCodec.plname, "telephone-event") == 0) {
-        numPars[i] = 0;
-      } else if (STR_CASE_CMP(dummyCodec.plname, "cn") == 0) {
-        numPars[i] = 0;
-      } else if (STR_CASE_CMP(dummyCodec.plname, "red") == 0) {
-        numPars[i] = 0;
+        if (_testMode == 1) {
+          printf("%d %s\n", n, sendCodecTmp.plname);
+        }
       }
     }
   } else {
@@ -348,9 +333,9 @@
 
   _receiver.testMode = _testMode;
 
-  //loop over all codecs:
+  // Loop over all mono codecs:
   for (int codeId = 0; codeId < numCodecs; codeId++) {
-    //only encode using real encoders, not telephone-event anc cn
+    // Only encode using real mono encoders, not telephone-event and cng.
     for (int loopPars = 1; loopPars <= numPars[codeId]; loopPars++) {
       if (_testMode == 1) {
         printf("\n");
diff --git a/src/modules/audio_coding/main/test/TestAllCodecs.cc b/src/modules/audio_coding/main/test/TestAllCodecs.cc
index 188b57b..eea41e9 100644
--- a/src/modules/audio_coding/main/test/TestAllCodecs.cc
+++ b/src/modules/audio_coding/main/test/TestAllCodecs.cc
@@ -784,7 +784,8 @@
     CodecInst myCodecParam;
 
     // Get all codec paramters before registering
-    CHECK_ERROR(AudioCodingModule::Codec(codecName, myCodecParam, samplingFreqHz));
+    CHECK_ERROR(AudioCodingModule::Codec(codecName, myCodecParam,
+                                         samplingFreqHz, 1));
     myCodecParam.rate = rate;
     myCodecParam.pacsize = packSize;
     CHECK_ERROR(myACM->RegisterSendCodec(myCodecParam));
diff --git a/src/modules/audio_coding/main/test/TestFEC.cc b/src/modules/audio_coding/main/test/TestFEC.cc
index 17f8f6b..0f73c8f 100644
--- a/src/modules/audio_coding/main/test/TestFEC.cc
+++ b/src/modules/audio_coding/main/test/TestFEC.cc
@@ -553,7 +553,8 @@
     }
     CodecInst myCodecParam;
 
-    CHECK_ERROR(AudioCodingModule::Codec(codecName, myCodecParam, samplingFreqHz));
+    CHECK_ERROR(AudioCodingModule::Codec(codecName, myCodecParam,
+                                         samplingFreqHz, 1));
 
     CHECK_ERROR(myACM->RegisterSendCodec(myCodecParam));
 
diff --git a/src/modules/audio_coding/main/test/TestStereo.cc b/src/modules/audio_coding/main/test/TestStereo.cc
index aeced5e..c0c2b7b 100644
--- a/src/modules/audio_coding/main/test/TestStereo.cc
+++ b/src/modules/audio_coding/main/test/TestStereo.cc
@@ -69,7 +69,7 @@
       rtp_info.type.Audio.channel = (int) kMono;
     }
     status = receiver_acm_->IncomingPacket(payload_data, payload_size,
-                                          rtp_info);
+                                           rtp_info);
 
     if (frame_type != kAudioFrameCN) {
       payload_size_ = payload_size;
@@ -122,7 +122,7 @@
       cn_8khz_pltype_(-1),
       cn_16khz_pltype_(-1),
       cn_32khz_pltype_(-1) {
-  // testMode = 0 for silent test (auto test)
+  // test_mode = 0 for silent test (auto test)
   test_mode_ = test_mode;
 }
 
@@ -155,57 +155,49 @@
                  "---------- TestStereo ----------");
   }
 
+  // Open both mono and stereo test files in 32 kHz.
   strcpy(file_name_stereo, "./data/audio_coding/teststereo32kHz.pcm");
   strcpy(file_name_mono, "./data/audio_coding/testfile32kHz.pcm");
-  frequency_hz = 32000;
 
+  frequency_hz = 32000;
   in_file_stereo_ = new PCMFile();
   in_file_mono_ = new PCMFile();
-
   in_file_stereo_->Open(file_name_stereo, frequency_hz, "rb");
   in_file_stereo_->ReadStereo(true);
   in_file_mono_->Open(file_name_mono, frequency_hz, "rb");
   in_file_mono_->ReadStereo(false);
 
+  // Create and initialize two ACMs, one for each side of a one-to-one call.
   acm_a_ = AudioCodingModule::Create(0);
   acm_b_ = AudioCodingModule::Create(1);
-
-  acm_a_->InitializeReceiver();
-  acm_b_->InitializeReceiver();
-
-  WebRtc_UWord8 num_encoders = acm_a_->NumberOfCodecs();
-  CodecInst my_codec_param;
-
-  // Register receiving codecs, some of them as stereo.
-  for (WebRtc_UWord8 n = 0; n < num_encoders; n++) {
-    acm_b_->Codec(n, my_codec_param);
-    if (!strcmp(my_codec_param.plname, "L16")) {
-      if (my_codec_param.plfreq == 8000) {
-        l16_8khz_pltype_ = my_codec_param.pltype;
-      } else if (my_codec_param.plfreq == 16000) {
-        l16_16khz_pltype_ = my_codec_param.pltype;
-      } else if (my_codec_param.plfreq == 32000) {
-        l16_32khz_pltype_ = my_codec_param.pltype;
-      }
-      my_codec_param.channels = 2;
-    } else if (!strcmp(my_codec_param.plname, "PCMA")) {
-      pcma_pltype_ = my_codec_param.pltype;
-      my_codec_param.channels = 2;
-    } else if (!strcmp(my_codec_param.plname, "PCMU")) {
-      pcmu_pltype_ = my_codec_param.pltype;
-      my_codec_param.channels = 2;
-    } else if (!strcmp(my_codec_param.plname, "G722")) {
-      g722_pltype_ = my_codec_param.pltype;
-      my_codec_param.channels = 2;
-    } else if (!strcmp(my_codec_param.plname, "CELT")) {
-      celt_pltype_ = my_codec_param.pltype;
-      my_codec_param.channels = 2;
-    }
-
-    acm_b_->RegisterReceiveCodec(my_codec_param);
+  if ((acm_a_ == NULL) || (acm_b_ == NULL)) {
+    printf("Failed to create ACM.");
+  }
+  status = acm_a_->InitializeReceiver();
+  if (status < 0) {
+    printf("Error in InitializeReceiver()");
+  }
+  status = acm_b_->InitializeReceiver();
+  if (status < 0) {
+    printf("Error in InitializeReceiver()");
   }
 
-  // Test that unregister all receive codecs works for stereo.
+  // Register all available codes as receiving codecs.
+  WebRtc_UWord8 num_encoders = acm_a_->NumberOfCodecs();
+  CodecInst my_codec_param;
+  for (WebRtc_UWord8 n = 0; n < num_encoders; n++) {
+    status = acm_b_->Codec(n, my_codec_param);
+    if (status < 0) {
+      printf("Error in Codec(), no matching codec found");
+    }
+    status = acm_b_->RegisterReceiveCodec(my_codec_param);
+    if (status < 0) {
+      printf("Error in RegisterReceiveCodec() for payload type %d",
+             my_codec_param.pltype);
+    }
+  }
+
+  // Test that unregister all receive codecs works.
   for (WebRtc_UWord8 n = 0; n < num_encoders; n++) {
     status = acm_b_->Codec(n, my_codec_param);
     if (status < 0) {
@@ -218,97 +210,40 @@
     }
   }
 
-  // Register receiving mono codecs, except comfort noise.
+  // Register all available codes as receiving codecs once more.
   for (WebRtc_UWord8 n = 0; n < num_encoders; n++) {
     status = acm_b_->Codec(n, my_codec_param);
     if (status < 0) {
       printf("Error in Codec(), no matching codec found");
     }
-    if (!strcmp(my_codec_param.plname, "L16")
-        || !strcmp(my_codec_param.plname, "PCMA")
-        || !strcmp(my_codec_param.plname, "PCMU")
-        || !strcmp(my_codec_param.plname, "G722")
-        || !strcmp(my_codec_param.plname, "CELT")
-        || !strcmp(my_codec_param.plname, "CN")) {
-    } else {
-      status = acm_b_->RegisterReceiveCodec(my_codec_param);
-      if (status < 0) {
-        printf("Error in UnregisterReceiveCodec() for codec number %d", n);
-      }
+    status = acm_b_->RegisterReceiveCodec(my_codec_param);
+    if (status < 0) {
+      printf("Error in RegisterReceiveCodec() for payload type %d",
+             my_codec_param.pltype);
     }
   }
 
   // TODO(tlegrand): Take care of return values of all function calls.
-  // Re-register all stereo codecs needed in the test, with new payload
-  // numbers.
-  g722_pltype_ = 117;
-  l16_8khz_pltype_ = 120;
-  l16_16khz_pltype_ = 121;
-  l16_32khz_pltype_ = 122;
-  pcma_pltype_ = 110;
-  pcmu_pltype_ = 118;
-  celt_pltype_ = 119;
-  cn_8khz_pltype_ = 123;
-  cn_16khz_pltype_ = 124;
-  cn_32khz_pltype_ = 125;
 
-  // Register all stereo codecs with new payload types.
-#ifdef WEBRTC_CODEC_G722
-  // G722
-  acm_b_->Codec("G722", my_codec_param, 16000);
-  my_codec_param.pltype = g722_pltype_;
-  my_codec_param.channels = 2;
-  acm_b_->RegisterReceiveCodec(my_codec_param);
-#endif
-#ifdef WEBRTC_CODEC_PCM16
-  // L16
-  acm_b_->Codec("L16", my_codec_param, 8000);
-  my_codec_param.pltype = l16_8khz_pltype_;
-  my_codec_param.channels = 2;
-  acm_b_->RegisterReceiveCodec(my_codec_param);
-  acm_b_->Codec("L16", my_codec_param, 16000);
-  my_codec_param.pltype = l16_16khz_pltype_;
-  my_codec_param.channels = 2;
-  acm_b_->RegisterReceiveCodec(my_codec_param);
-  acm_b_->Codec("L16", my_codec_param, 32000);
-  my_codec_param.pltype = l16_32khz_pltype_;
-  my_codec_param.channels = 2;
-  acm_b_->RegisterReceiveCodec(my_codec_param);
-#endif
-  // PCM Alaw and u-law
-  acm_b_->Codec("PCMA", my_codec_param, 8000);
-  my_codec_param.pltype = pcma_pltype_;
-  my_codec_param.channels = 2;
-  acm_b_->RegisterReceiveCodec(my_codec_param);
-  acm_b_->Codec("PCMU", my_codec_param, 8000);
-  my_codec_param.pltype = pcmu_pltype_;
-  my_codec_param.channels = 2;
-  acm_b_->RegisterReceiveCodec(my_codec_param);
-#ifdef WEBRTC_CODEC_CELT
-  // Celt
-  acm_b_->Codec("CELT", my_codec_param, 32000);
-  my_codec_param.pltype = celt_pltype_;
-  my_codec_param.channels = 2;
-  acm_b_->RegisterReceiveCodec(my_codec_param);
-#endif
-
-  // Register CNG with new payload type on both send and receive side.
-  acm_b_->Codec("CN", my_codec_param, 8000);
-  my_codec_param.pltype = cn_8khz_pltype_;
-  acm_a_->RegisterSendCodec(my_codec_param);
-  acm_b_->RegisterReceiveCodec(my_codec_param);
-  acm_b_->Codec("CN", my_codec_param, 16000);
-  my_codec_param.pltype = cn_16khz_pltype_;
-  acm_a_->RegisterSendCodec(my_codec_param);
-  acm_b_->RegisterReceiveCodec(my_codec_param);
-  acm_b_->Codec("CN", my_codec_param, 32000);
-  my_codec_param.pltype = cn_32khz_pltype_;
-  acm_a_->RegisterSendCodec(my_codec_param);
-  acm_b_->RegisterReceiveCodec(my_codec_param);
+  // TODO(tlegrand): Re-register all stereo codecs needed in the test,
+  // with new payload numbers.
+  // g722_pltype_ = 117;
+  // l16_8khz_pltype_ = 120;
+  // l16_16khz_pltype_ = 121;
+  // l16_32khz_pltype_ = 122;
+  // pcma_pltype_ = 110;
+  // pcmu_pltype_ = 118;
+  // celt_pltype_ = 119;
+  // cn_8khz_pltype_ = 123;
+  // cn_16khz_pltype_ = 124;
+  // cn_32khz_pltype_ = 125;
 
   // Create and connect the channel.
   channel_a2b_ = new TestPackStereo;
-  acm_a_->RegisterTransportCallback(channel_a2b_);
+  status = acm_a_->RegisterTransportCallback(channel_a2b_);
+  if (status < 0) {
+    printf("Failed to register transport callback.");
+  }
   channel_a2b_->RegisterReceiverACM(acm_b_);
 
   //
@@ -636,29 +571,6 @@
   codec_channels = 1;
   channel_a2b_->set_codec_mode(kMono);
 
-  // Register receivers as mono.
-  for (WebRtc_UWord8 n = 0; n < num_encoders; n++) {
-    acm_b_->Codec(n, my_codec_param);
-    if (!strcmp(my_codec_param.plname, "L16")) {
-      if (my_codec_param.plfreq == 8000) {
-        my_codec_param.pltype = l16_8khz_pltype_;
-      } else if (my_codec_param.plfreq == 16000) {
-        my_codec_param.pltype = l16_16khz_pltype_;
-      } else if (my_codec_param.plfreq == 32000) {
-        my_codec_param.pltype = l16_32khz_pltype_;
-      }
-    } else if (!strcmp(my_codec_param.plname, "PCMA")) {
-      my_codec_param.pltype = pcma_pltype_;
-    } else if (!strcmp(my_codec_param.plname, "PCMU")) {
-      my_codec_param.pltype = pcmu_pltype_;
-    } else if (!strcmp(my_codec_param.plname, "G722")) {
-      my_codec_param.pltype = g722_pltype_;
-    } else if (!strcmp(my_codec_param.plname, "CELT")) {
-      my_codec_param.pltype = celt_pltype_;
-      my_codec_param.channels = 1;
-    }
-    acm_b_->RegisterReceiveCodec(my_codec_param);
-  }
 #ifdef WEBRTC_CODEC_G722
   // Run stereo audio and mono codec.
   if(test_mode_ != 0) {
@@ -818,11 +730,11 @@
   CodecInst my_codec_param;
   // Get all codec parameters before registering
   CHECK_ERROR(AudioCodingModule::Codec(codec_name, my_codec_param,
-                                       sampling_freq_hz));
+                                       sampling_freq_hz, channels));
   my_codec_param.rate = rate;
   my_codec_param.pacsize = pack_size;
-  my_codec_param.pltype = payload_type;
-  my_codec_param.channels = channels;
+ // my_codec_param.pltype = payload_type;
+ // my_codec_param.channels = channels;
   CHECK_ERROR(my_acm->RegisterSendCodec(my_codec_param));
 
   // Initialization was successful.
diff --git a/src/modules/audio_coding/main/test/TwoWayCommunication.cc b/src/modules/audio_coding/main/test/TwoWayCommunication.cc
index b43b39e..ac648a3 100644
--- a/src/modules/audio_coding/main/test/TwoWayCommunication.cc
+++ b/src/modules/audio_coding/main/test/TwoWayCommunication.cc
@@ -278,8 +278,8 @@
     CodecInst codecInst_B;
     CodecInst dummyCodec;
 
-    _acmA->Codec("ISAC", codecInst_A, 16000);
-    _acmB->Codec("L16", codecInst_B, 8000);
+    _acmA->Codec("ISAC", codecInst_A, 16000, 1);
+    _acmB->Codec("L16", codecInst_B, 8000, 1);
     _acmA->Codec(6, dummyCodec);
 
     //--- Set A codecs
@@ -445,7 +445,7 @@
             if(_testMode == 0)
             {
                 WEBRTC_TRACE(kTraceStateInfo, kTraceAudioCoding, -1,
-                             "---------- Errors epected");
+                             "---------- Errors expected");
                 printf(".");
             }
             else
@@ -460,7 +460,7 @@
             if(_testMode == 0)
             {
                 WEBRTC_TRACE(kTraceStateInfo, kTraceAudioCoding, -1,
-                             "----- END: Errors epected");
+                             "----- END: Errors expected");
                 printf(".");
             }
             else
@@ -478,7 +478,7 @@
             if(_testMode == 0)
             {
                 WEBRTC_TRACE(kTraceStateInfo, kTraceAudioCoding, -1,
-                             "---------- Errors epected");
+                             "---------- Errors expected");
                 printf(".");
             }
             else
@@ -494,7 +494,7 @@
             if(_testMode == 0)
             {
                 WEBRTC_TRACE(kTraceStateInfo, kTraceAudioCoding, -1,
-                             "----- END: Errors epected");
+                             "----- END: Errors expected");
                 printf(".");
             }
             else
diff --git a/src/modules/audio_coding/neteq/codec_db.c b/src/modules/audio_coding/neteq/codec_db.c
index cb63aea..e91e372 100644
--- a/src/modules/audio_coding/neteq/codec_db.c
+++ b/src/modules/audio_coding/neteq/codec_db.c
@@ -97,10 +97,13 @@
     {
 #ifdef NETEQ_PCM16B_CODEC
         case kDecoderPCM16B :
+        case kDecoderPCM16B_2ch :
 #endif
 #ifdef NETEQ_G711_CODEC
         case kDecoderPCMu :
         case kDecoderPCMa :
+        case kDecoderPCMu_2ch :
+        case kDecoderPCMa_2ch :
 #endif
 #ifdef NETEQ_ILBC_CODEC
         case kDecoderILBC :
@@ -113,12 +116,15 @@
 #endif
 #ifdef NETEQ_G722_CODEC
         case kDecoderG722 :
+        case kDecoderG722_2ch :
 #endif
 #ifdef NETEQ_WIDEBAND
         case kDecoderPCM16Bwb :
+        case kDecoderPCM16Bwb_2ch :
 #endif
 #ifdef NETEQ_32KHZ_WIDEBAND
         case kDecoderPCM16Bswb32kHz :
+        case kDecoderPCM16Bswb32kHz_2ch :
 #endif
 #ifdef NETEQ_CNG_CODEC
         case kDecoderCNG :
@@ -163,6 +169,7 @@
 #endif
 #ifdef NETEQ_CELT_CODEC
         case kDecoderCELT_32 :
+        case kDecoderCELT_32_2ch :
 #endif
 #ifdef NETEQ_GSMFR_CODEC
         case kDecoderGSMFR :
@@ -473,6 +480,7 @@
 #endif
 #ifdef NETEQ_CELT_CODEC
         case kDecoderCELT_32 :
+        case kDecoderCELT_32_2ch :
 #endif
 #ifdef NETEQ_G729_1_CODEC
         case kDecoderG729_1:
@@ -491,6 +499,8 @@
 #if (defined NETEQ_G711_CODEC)
         case kDecoderPCMu:
         case kDecoderPCMa:
+        case kDecoderPCMu_2ch:
+        case kDecoderPCMa_2ch:
         {
             inst->deltaBytes = -12;
             inst->deltaTime = 1;
@@ -499,6 +509,7 @@
 #endif
 #if (defined NETEQ_G722_CODEC)
         case kDecoderG722:
+        case kDecoderG722_2ch:
         {
             inst->deltaBytes = -14;
             inst->deltaTime = 0;
@@ -507,6 +518,7 @@
 #endif
 #if (defined NETEQ_PCM16B_CODEC)
         case kDecoderPCM16B:
+        case kDecoderPCM16B_2ch:
         {
             inst->deltaBytes = -12;
             inst->deltaTime = 2;
@@ -515,6 +527,7 @@
 #endif
 #if ((defined NETEQ_PCM16B_CODEC)&&(defined NETEQ_WIDEBAND))
         case kDecoderPCM16Bwb:
+        case kDecoderPCM16Bwb_2ch:
         {
             inst->deltaBytes = -14;
             inst->deltaTime = 2;
@@ -523,6 +536,7 @@
 #endif
 #if ((defined NETEQ_PCM16B_CODEC)&&(defined NETEQ_32KHZ_WIDEBAND))
         case kDecoderPCM16Bswb32kHz:
+        case kDecoderPCM16Bswb32kHz_2ch:
         {
             inst->deltaBytes = -18;
             inst->deltaTime = 2;
diff --git a/src/modules/audio_coding/neteq/interface/webrtc_neteq.h b/src/modules/audio_coding/neteq/interface/webrtc_neteq.h
index 909131b..aacfaeb 100644
--- a/src/modules/audio_coding/neteq/interface/webrtc_neteq.h
+++ b/src/modules/audio_coding/neteq/interface/webrtc_neteq.h
@@ -32,6 +32,8 @@
     kDecoderReservedStart,
     kDecoderPCMu,
     kDecoderPCMa,
+    kDecoderPCMu_2ch,
+    kDecoderPCMa_2ch,
     kDecoderILBC,
     kDecoderISAC,
     kDecoderISACswb,
@@ -39,7 +41,11 @@
     kDecoderPCM16Bwb,
     kDecoderPCM16Bswb32kHz,
     kDecoderPCM16Bswb48kHz,
+    kDecoderPCM16B_2ch,
+    kDecoderPCM16Bwb_2ch,
+    kDecoderPCM16Bswb32kHz_2ch,
     kDecoderG722,
+    kDecoderG722_2ch,
     kDecoderRED,
     kDecoderAVT,
     kDecoderCNG,
@@ -59,6 +65,7 @@
     kDecoderSPEEX_8,
     kDecoderSPEEX_16,
     kDecoderCELT_32,
+    kDecoderCELT_32_2ch,
     kDecoderGSMFR,
     kDecoderAMR,
     kDecoderAMRWB,
diff --git a/src/modules/audio_coding/neteq/packet_buffer.c b/src/modules/audio_coding/neteq/packet_buffer.c
index 8b9073c..2a94c8a 100644
--- a/src/modules/audio_coding/neteq/packet_buffer.c
+++ b/src/modules/audio_coding/neteq/packet_buffer.c
@@ -543,12 +543,13 @@
     {
         /* Find current codec and set parameters accordingly */
 
-        if (codecID[i] == kDecoderPCMu)
+        if ((codecID[i] == kDecoderPCMu) || (codecID[i] == kDecoderPCMu_2ch))
         {
             codecBytes = 1680; /* Up to 210ms @ 64kbps */
             codecBuffers = 30; /* Down to 5ms frames */
         }
-        else if (codecID[i] == kDecoderPCMa)
+        else if ((codecID[i] == kDecoderPCMa) ||
+            (codecID[i] == kDecoderPCMa_2ch))
         {
             codecBytes = 1680; /* Up to 210ms @ 64kbps */
             codecBuffers = 30; /* Down to 5ms frames */
@@ -568,17 +569,20 @@
             codecBytes = 1560; /* 240ms @ 52kbps (30ms frames) */
             codecBuffers = 8;
         }
-        else if (codecID[i] == kDecoderPCM16B)
+        else if ((codecID[i] == kDecoderPCM16B) ||
+            (codecID[i] == kDecoderPCM16B_2ch))
         {
             codecBytes = 3360; /* 210ms */
             codecBuffers = 15;
         }
-        else if (codecID[i] == kDecoderPCM16Bwb)
+        else if ((codecID[i] == kDecoderPCM16Bwb) ||
+            (codecID[i] == kDecoderPCM16Bwb_2ch))
         {
             codecBytes = 6720; /* 210ms */
             codecBuffers = 15;
         }
-        else if (codecID[i] == kDecoderPCM16Bswb32kHz)
+        else if ((codecID[i] == kDecoderPCM16Bswb32kHz) ||
+            (codecID[i] == kDecoderPCM16Bswb32kHz_2ch))
         {
             codecBytes = 13440; /* 210ms */
             codecBuffers = 15;
@@ -588,7 +592,8 @@
             codecBytes = 20160; /* 210ms */
             codecBuffers = 15;
         }
-        else if (codecID[i] == kDecoderG722)
+        else if ((codecID[i] == kDecoderG722) ||
+            (codecID[i] == kDecoderG722_2ch))
         {
             codecBytes = 1680; /* 210ms @ 64kbps */
             codecBuffers = 15;
@@ -678,7 +683,8 @@
             codecBytes = 1250; /* 210ms @ 50kbps */
             codecBuffers = 10;
         }
-        else if (codecID[i] == kDecoderCELT_32)
+        else if ((codecID[i] == kDecoderCELT_32) ||
+            (codecID[i] == kDecoderCELT_32_2ch))
         {
             codecBytes = 1250; /* 210ms @ 50kbps */
             codecBuffers = 10;
diff --git a/src/modules/audio_coding/neteq/recin.c b/src/modules/audio_coding/neteq/recin.c
index 608eb6e..bce7c48 100644
--- a/src/modules/audio_coding/neteq/recin.c
+++ b/src/modules/audio_coding/neteq/recin.c
@@ -1,5 +1,5 @@
 /*
- *  Copyright (c) 2011 The WebRTC project authors. All Rights Reserved.
+ *  Copyright (c) 2012 The WebRTC project authors. All Rights Reserved.
  *
  *  Use of this source code is governed by a BSD-style license
  *  that can be found in the LICENSE file in the root of the source
@@ -364,6 +364,7 @@
     switch (codec)
     {
         case kDecoderG722:
+        case kDecoderG722_2ch:
         {
             /* Use timestamp scaling with factor 2 (two output samples per RTP timestamp) */
             MCU_inst->scalingFactor = kTSscalingTwo;
diff --git a/src/modules/rtp_rtcp/source/rtp_receiver.cc b/src/modules/rtp_rtcp/source/rtp_receiver.cc
index 40eb6b0..7c5439e 100644
--- a/src/modules/rtp_rtcp/source/rtp_receiver.cc
+++ b/src/modules/rtp_rtcp/source/rtp_receiver.cc
@@ -358,7 +358,8 @@
         if (payload->audio) {
           if (payload->typeSpecific.Audio.frequency == frequency &&
               (payload->typeSpecific.Audio.rate == rate ||
-                  payload->typeSpecific.Audio.rate == 0 || rate == 0)) {
+                  payload->typeSpecific.Audio.rate == 0 || rate == 0) &&
+                  payload->typeSpecific.Audio.channels == channels) {
             // remove old setting
             delete payload;
             _payloadTypeMap.erase(audio_it);
diff --git a/src/voice_engine/main/source/channel.cc b/src/voice_engine/main/source/channel.cc
index 125c3e7..2ef7c88 100644
--- a/src/voice_engine/main/source/channel.cc
+++ b/src/voice_engine/main/source/channel.cc
@@ -654,7 +654,7 @@
     receiveCodec.rate = rate;
     strncpy(receiveCodec.plname, payloadName, RTP_PAYLOAD_NAME_SIZE - 1);
     
-    _audioCodingModule.Codec(payloadName, dummyCodec, frequency);
+    _audioCodingModule.Codec(payloadName, dummyCodec, frequency, channels);
     receiveCodec.pacsize = dummyCodec.pacsize;
 
     // Register the new codec to the ACM
@@ -1423,7 +1423,7 @@
         }
 
         // Ensure that PCMU is used as default codec on the sending side
-        if (!STR_CASE_CMP(codec.plname, "PCMU"))
+        if (!STR_CASE_CMP(codec.plname, "PCMU") && (codec.channels == 1))
         {
             SetSendCodec(codec);
         }
@@ -2472,12 +2472,13 @@
 
     CodecInst codec;
     WebRtc_Word32 samplingFreqHz(-1);
+    const int kMono = 1;
     if (frequency == kFreq32000Hz)
         samplingFreqHz = 32000;
     else if (frequency == kFreq16000Hz)
         samplingFreqHz = 16000;
 
-    if (_audioCodingModule.Codec("CN", codec, samplingFreqHz) == -1)
+    if (_audioCodingModule.Codec("CN", codec, samplingFreqHz, kMono) == -1)
     {
         _engineStatisticsPtr->SetLastError(
             VE_AUDIO_CODING_MODULE_ERROR, kTraceError,
diff --git a/src/voice_engine/main/test/cmd_test/voe_cmd_test.cc b/src/voice_engine/main/test/cmd_test/voe_cmd_test.cc
index bbcceff..e296fc6 100644
--- a/src/voice_engine/main/test/cmd_test/voe_cmd_test.cc
+++ b/src/voice_engine/main/test/cmd_test/voe_cmd_test.cc
@@ -338,12 +338,12 @@
     res = codec->GetCodec(i, cinst);
     VALIDATE;
     if (strncmp(cinst.plname, "ISAC", 4) == 0 && cinst.plfreq == 32000) {
-      printf("%i. ISAC-swb pltype:%i plfreqi:%i\n", i, cinst.pltype,
-             cinst.plfreq);
+      printf("%i. ISAC-swb pltype:%i plfreq:%i channels:%i\n", i, cinst.pltype,
+             cinst.plfreq, cinst.channels);
     }
     else {
-      printf("%i. %s pltype:%i plfreq:%i\n", i, cinst.plname,
-             cinst.pltype, cinst.plfreq);
+      printf("%i. %s pltype:%i plfreq:%i channels:%i\n", i, cinst.plname,
+             cinst.pltype, cinst.plfreq, cinst.channels);
     }
   }
 #ifdef DEBUG