Bug 906990: Part 9. Add correlator for ICE candidates. r=ekr
authorByron Campen [:bwc] <docfaraday@gmail.com>
Fri, 25 Oct 2013 16:47:14 -0700
changeset 169516 eb08b1c4e656922739e5eaebb209a75adc1dfd15
parent 169515 5e1ebc80c9173a7acfba2ed50f6b8f55bce9d894
child 169517 4a68f748d2406d6e7528387917235fbe2df4aa97
push id3224
push userlsblakk@mozilla.com
push dateTue, 04 Feb 2014 01:06:49 +0000
treeherdermozilla-beta@60c04d0987f1 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersekr
bugs906990
milestone28.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 906990: Part 9. Add correlator for ICE candidates. r=ekr
media/mtransport/nricemediastream.cpp
media/mtransport/nricemediastream.h
media/mtransport/test/ice_unittest.cpp
media/mtransport/third_party/nICEr/src/ice/ice_candidate.c
media/mtransport/third_party/nICEr/src/ice/ice_candidate.h
media/mtransport/third_party/nICEr/src/ice/ice_candidate_pair.c
media/mtransport/third_party/nICEr/src/ice/ice_parser.c
--- a/media/mtransport/nricemediastream.cpp
+++ b/media/mtransport/nricemediastream.cpp
@@ -107,16 +107,17 @@ static bool ToNrIceCandidate(const nr_ic
       break;
     default:
       return false;
   }
 
   out->host = addr;
   out->port = port;
   out->type = type;
+  out->codeword = candc.codeword;
   return true;
 }
 
 // Make an NrIceCandidate from the candidate |cand|.
 // This is not a member fxn because we want to hide the
 // defn of nr_ice_candidate but we pass by reference.
 static NrIceCandidate* MakeNrIceCandidate(const nr_ice_candidate& candc) {
   ScopedDeletePtr<NrIceCandidate> out(new NrIceCandidate());
--- a/media/mtransport/nricemediastream.h
+++ b/media/mtransport/nricemediastream.h
@@ -72,16 +72,17 @@ struct NrIceCandidate {
     ICE_SERVER_REFLEXIVE,
     ICE_PEER_REFLEXIVE,
     ICE_RELAYED
   };
 
   std::string host;
   uint16_t port;
   Type type;
+  std::string codeword;
 };
 
 struct NrIceCandidatePair {
 
   enum State {
     STATE_FROZEN,
     STATE_WAITING,
     STATE_IN_PROGRESS,
--- a/media/mtransport/test/ice_unittest.cpp
+++ b/media/mtransport/test/ice_unittest.cpp
@@ -82,28 +82,32 @@ bool ContainsSucceededPair(const std::ve
 }
 
 // Note: Does not correspond to any notion of prioritization; this is just
 // so we can use stl containers/algorithms that need a comparator
 bool operator<(const NrIceCandidate& lhs,
                const NrIceCandidate& rhs) {
   if (lhs.host == rhs.host) {
     if (lhs.port == rhs.port) {
+      if (lhs.type == rhs.type) {
+        return lhs.codeword < rhs.codeword;
+      }
       return lhs.type < rhs.type;
     }
     return lhs.port < rhs.port;
   }
   return lhs.host < rhs.host;
 }
 
 bool operator==(const NrIceCandidate& lhs,
                 const NrIceCandidate& rhs) {
   return lhs.host == rhs.host &&
          lhs.port == rhs.port &&
-         lhs.type == rhs.type;
+         lhs.type == rhs.type &&
+         lhs.codeword == rhs.codeword;
 }
 
 class IceCandidatePairCompare {
   public:
     bool operator()(const NrIceCandidatePair& lhs,
                     const NrIceCandidatePair& rhs) const {
       if (lhs.priority == rhs.priority) {
         if (lhs.local == rhs.local) {
@@ -366,16 +370,18 @@ class IceTestPeer : public sigslot::has_
 
     std::cerr << which
               << " --> "
               << type
               << " "
               << cand.host
               << ":"
               << cand.port
+              << " codeword="
+              << cand.codeword
               << std::endl;
   }
 
   void DumpAndCheckActiveCandidates() {
     std::cerr << "Active candidates:" << std::endl;
     for (size_t i=0; i < streams_.size(); ++i) {
       for (int j=0; j < streams_[i]->components(); ++j) {
         std::cerr << "Stream " << i << " component " << j+1 << std::endl;
--- a/media/mtransport/third_party/nICEr/src/ice/ice_candidate.c
+++ b/media/mtransport/third_party/nICEr/src/ice/ice_candidate.c
@@ -52,16 +52,17 @@ static char *RCSSTRING __UNUSED__="$Id: 
 #include "nr_socket.h"
 #include "async_timer.h"
 
 #include "stun_client_ctx.h"
 #include "stun_server_ctx.h"
 #include "turn_client_ctx.h"
 #include "ice_ctx.h"
 #include "ice_candidate.h"
+#include "ice_codeword.h"
 #include "ice_reg.h"
 #include "ice_util.h"
 #include "nr_socket_turn.h"
 #include "nr_socket.h"
 
 static int next_automatic_preference = 224;
 
 static int nr_ice_candidate_initialize2(nr_ice_candidate *cand);
@@ -69,16 +70,29 @@ static int nr_ice_get_foundation(nr_ice_
 static int nr_ice_srvrflx_start_stun(nr_ice_candidate *cand);
 static void nr_ice_srvrflx_stun_finished_cb(NR_SOCKET sock, int how, void *cb_arg);
 #ifdef USE_TURN
 static int nr_ice_start_relay_turn(nr_ice_candidate *cand);
 static void nr_ice_turn_allocated_cb(NR_SOCKET sock, int how, void *cb_arg);
 static int nr_ice_candidate_resolved_cb(void *cb_arg, nr_transport_addr *addr);
 #endif /* USE_TURN */
 
+void nr_ice_candidate_compute_codeword(nr_ice_candidate *cand)
+  {
+    char as_string[1024];
+
+    snprintf(as_string,
+             sizeof(as_string),
+             "%s(%s)",
+             cand->addr.as_string,
+             cand->label);
+
+    nr_ice_compute_codeword(as_string,strlen(as_string),cand->codeword);
+  }
+
 char *nr_ice_candidate_type_names[]={0,"host","srflx","prflx","relay",0};
 
 static const char *nr_ctype_name(nr_ice_candidate_type ctype) {
   assert(ctype<CTYPE_MAX && ctype>0);
   if (ctype <= 0 || ctype >= CTYPE_MAX) {
     return "ERROR";
   }
   return nr_ice_candidate_type_names[ctype];
@@ -171,16 +185,18 @@ int nr_ice_candidate_create(nr_ice_ctx *
 
     if(ctype==RELAYED)
       cand->u.relayed.turn_sock=osock;
 
 
     /* Add the candidate to the isock list*/
     TAILQ_INSERT_TAIL(&isock->candidates,cand,entry_sock);
 
+    nr_ice_candidate_compute_codeword(cand);
+
     r_log(LOG_ICE,LOG_DEBUG,"ICE(%s): created candidate %s with type %s",
       ctx->label,cand->label,nr_ctype_name(ctype));
 
     *candp=cand;
 
     _status=0;
   abort:
     if (_status){
@@ -217,16 +233,18 @@ int nr_ice_peer_peer_rflx_candidate_crea
     if(r=nr_transport_addr_copy(&cand->base,addr))
       ABORT(r);
     if(r=nr_transport_addr_copy(&cand->addr,addr))
       ABORT(r);
     /* Bogus foundation */
     if(!(cand->foundation=r_strdup(cand->addr.as_string)))
       ABORT(r);
 
+    nr_ice_candidate_compute_codeword(cand);
+
     *candp=cand;
 
     _status=0;
   abort:
     if (_status){
       nr_ice_candidate_destroy(&cand);
     }
     return(_status);
@@ -479,16 +497,18 @@ int nr_ice_candidate_initialize(nr_ice_c
             ABORT(r);
           }
         }
         break;
       default:
         ABORT(R_INTERNAL);
     }
 
+    nr_ice_candidate_compute_codeword(cand);
+
     _status=0;
   abort:
     if(_status && _status!=R_WOULDBLOCK)
       cand->state=NR_ICE_CAND_STATE_FAILED;
     return(_status);
   }
 
 
--- a/media/mtransport/third_party/nICEr/src/ice/ice_candidate.h
+++ b/media/mtransport/third_party/nICEr/src/ice/ice_candidate.h
@@ -38,16 +38,17 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 using namespace std;
 extern "C" {
 #endif /* __cplusplus */
 
 typedef enum {HOST=1, SERVER_REFLEXIVE, PEER_REFLEXIVE, RELAYED, CTYPE_MAX} nr_ice_candidate_type;
 
 struct nr_ice_candidate_ {
   char *label;
+  char codeword[5];
   int state;
 #define NR_ICE_CAND_STATE_CREATED          1
 #define NR_ICE_CAND_STATE_INITIALIZING     2
 #define NR_ICE_CAND_STATE_INITIALIZED      3
 #define NR_ICE_CAND_STATE_FAILED           4
 #define NR_ICE_CAND_PEER_CANDIDATE_UNPAIRED 9
 #define NR_ICE_CAND_PEER_CANDIDATE_PAIRED   10
   struct nr_ice_ctx_ *ctx;
@@ -95,16 +96,17 @@ struct nr_ice_candidate_ {
   TAILQ_ENTRY(nr_ice_candidate_) entry_comp;
 };
 
 extern char *nr_ice_candidate_type_names[];
 
 
 int nr_ice_candidate_create(struct nr_ice_ctx_ *ctx,nr_ice_component *component, nr_ice_socket *isock, nr_socket *osock, nr_ice_candidate_type ctype, nr_ice_stun_server *stun_server, UCHAR component_id, nr_ice_candidate **candp);
 int nr_ice_candidate_initialize(nr_ice_candidate *cand, NR_async_cb ready_cb, void *cb_arg);
+void nr_ice_candidate_compute_codeword(nr_ice_candidate *cand);
 int nr_ice_candidate_process_stun(nr_ice_candidate *cand, UCHAR *msg, int len, nr_transport_addr *faddr);
 int nr_ice_candidate_destroy(nr_ice_candidate **candp);
 void nr_ice_candidate_destroy_cb(NR_SOCKET s, int h, void *cb_arg);
 int nr_ice_format_candidate_attribute(nr_ice_candidate *cand, char *attr, int maxlen);
 int nr_ice_peer_candidate_from_attribute(nr_ice_ctx *ctx,char *attr,nr_ice_media_stream *stream,nr_ice_candidate **candp);
 int nr_ice_peer_peer_rflx_candidate_create(nr_ice_ctx *ctx,char *label, nr_ice_component *comp,nr_transport_addr *addr, nr_ice_candidate **candp);
 int nr_ice_candidate_compute_priority(nr_ice_candidate *cand);
 
--- a/media/mtransport/third_party/nICEr/src/ice/ice_candidate_pair.c
+++ b/media/mtransport/third_party/nICEr/src/ice/ice_candidate_pair.c
@@ -571,23 +571,21 @@ static void nr_ice_candidate_pair_restar
     return;
   }
 
 
 
 static void nr_ice_candidate_pair_compute_codeword(nr_ice_cand_pair *pair,
   nr_ice_candidate *lcand, nr_ice_candidate *rcand)
   {
-    int r,_status;
-    char *as_string=0;
+    char as_string[2048];
 
-    if(r=nr_concat_strings(&as_string,lcand->addr.as_string,"|",
-      rcand->addr.as_string,"(",lcand->label,"|",rcand->label,")",NULL))
-      ABORT(r);
+    snprintf(as_string,
+             sizeof(as_string),
+             "%s|%s(%s|%s)",
+             lcand->addr.as_string,
+             rcand->addr.as_string,
+             lcand->label,
+             rcand->label);
 
     nr_ice_compute_codeword(as_string,strlen(as_string),pair->codeword);
-
-    _status=0;
-      abort:
-    RFREE(as_string);
-return;
   }
 
--- a/media/mtransport/third_party/nICEr/src/ice/ice_parser.c
+++ b/media/mtransport/third_party/nICEr/src/ice/ice_parser.c
@@ -327,16 +327,18 @@ nr_ice_peer_candidate_from_attribute(nr_
 #if 0
     /* This used to be an assert, but we don't want to exit on invalid
        remote data */
     if (strlen(str) != 0) {
       ABORT(R_BAD_DATA);
     }
 #endif
 
+    nr_ice_candidate_compute_codeword(cand);
+
     *candp=cand;
 
     _status=0;
   abort:
     if (_status){
         r_log(LOG_ICE,LOG_WARNING,"ICE(%s): Error parsing attribute: %s",ctx->label,orig);
         nr_ice_candidate_destroy(&cand);
     }