author | EKR <ekr@rtfm.com> |
Sat, 05 Jan 2013 11:40:34 -0800 | |
changeset 119726 | 0eda7bbdfedf848d425d4aebaf256c4a443fda25 |
parent 119725 | 09ebdefa8c78f17189d2e3fb26ec44a55989c619 |
child 119727 | 6b5016ab9ebbb2ec884c4d865266446adebbc162 |
push id | 24219 |
push user | ryanvm@gmail.com |
push date | Thu, 24 Jan 2013 17:36:06 +0000 |
treeherder | mozilla-central@fa969919b1bb [default view] [failures only] |
perfherder | [talos] [build metrics] [platform microbench] (compared to previous push) |
reviewers | abr |
bugs | 786236 |
milestone | 21.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
|
--- a/media/mtransport/nr_socket_prsock.cpp +++ b/media/mtransport/nr_socket_prsock.cpp @@ -234,17 +234,17 @@ static int nr_transport_addr_to_praddr(n ABORT(R_BAD_ARGS); } _status = 0; abort: return(_status); } -static int nr_praddr_to_transport_addr(PRNetAddr *praddr, +int nr_praddr_to_transport_addr(const PRNetAddr *praddr, nr_transport_addr *addr, int keep) { int _status; int r; struct sockaddr_in ip4; switch(praddr->raw.family) { case PR_AF_INET:
--- a/media/mtransport/nr_socket_prsock.h +++ b/media/mtransport/nr_socket_prsock.h @@ -104,10 +104,13 @@ private: PRFileDesc *fd_; nr_transport_addr my_addr_; NR_async_cb cbs_[NR_ASYNC_WAIT_WRITE + 1]; void *cb_args_[NR_ASYNC_WAIT_WRITE + 1]; nsCOMPtr<nsISocketTransportService> stservice_; }; +int nr_praddr_to_transport_addr(const PRNetAddr *praddr, + nr_transport_addr *addr, int keep); + } // close namespace #endif
--- a/media/mtransport/nricectx.cpp +++ b/media/mtransport/nricectx.cpp @@ -76,16 +76,17 @@ extern "C" { #include "ice_candidate.h" #include "ice_handler.h" } // Local includes #include "logging.h" #include "nricectx.h" #include "nricemediastream.h" +#include "nr_socket_prsock.h" namespace mozilla { MOZ_MTLOG_MODULE("mtransport") static bool initialized = false; // Implement NSPR-based crypto algorithms @@ -226,18 +227,18 @@ int NrIceCtx::msg_recvd(void *obj, nr_ic s->SignalPacketReceived(s, component_id, msg, len); return 0; } RefPtr<NrIceCtx> NrIceCtx::Create(const std::string& name, - bool offerer, - bool set_interface_priorities) { + bool offerer, + bool set_interface_priorities) { RefPtr<NrIceCtx> ctx = new NrIceCtx(name, offerer); // Initialize the crypto callbacks if (!initialized) { NR_reg_init(NR_REG_MODE_LOCAL); nr_crypto_vtbl = &nr_ice_crypto_nss_vtbl; initialized = true; @@ -270,18 +271,16 @@ RefPtr<NrIceCtx> NrIceCtx::Create(const NR_reg_set_uchar((char *)"ice.pref.interface.vmnet5", 237); NR_reg_set_uchar((char *)"ice.pref.interface.vmnet6", 236); NR_reg_set_uchar((char *)"ice.pref.interface.vmnet7", 235); NR_reg_set_uchar((char *)"ice.pref.interface.vmnet8", 234); NR_reg_set_uchar((char *)"ice.pref.interface.virbr0", 233); NR_reg_set_uchar((char *)"ice.pref.interface.wlan0", 232); } - NR_reg_set_string((char *)"ice.stun.server.0.addr", (char *)"23.21.150.121"); - NR_reg_set_uint2((char *)"ice.stun.server.0.port",3478); NR_reg_set_uint4((char *)"stun.client.maximum_transmits",4); } // Create the ICE context int r; UINT4 flags = offerer ? NR_ICE_CTX_FLAGS_OFFERER: NR_ICE_CTX_FLAGS_ANSWERER; @@ -352,16 +351,43 @@ void NrIceCtx::destroy_peer_ctx() { nsresult NrIceCtx::SetControlling(Controlling controlling) { peer_->controlling = (controlling == ICE_CONTROLLING)? 1 : 0; MOZ_MTLOG(PR_LOG_DEBUG, "ICE ctx " << name_ << " setting controlling to" << controlling); return NS_OK; } +nsresult NrIceCtx::SetStunServers(const std::vector<NrIceStunServer>& + stun_servers) { + if (stun_servers.empty()) + return NS_OK; + + ScopedDeleteArray<nr_ice_stun_server> servers( + new nr_ice_stun_server[stun_servers.size()]); + + int r; + for (size_t i=0; i < stun_servers.size(); ++i) { + r = nr_praddr_to_transport_addr(&stun_servers[i].addr(), + &servers[i].addr, 0); + if (r) { + MOZ_MTLOG(PR_LOG_ERROR, "Couldn't set STUN server for '" << name_ << "'"); + return NS_ERROR_FAILURE; + } + } + + r = nr_ice_ctx_set_stun_servers(ctx_, servers, stun_servers.size()); + if (r) { + MOZ_MTLOG(PR_LOG_ERROR, "Couldn't set STUN server for '" << name_ << "'"); + return NS_ERROR_FAILURE; + } + + return NS_OK; +} + nsresult NrIceCtx::StartGathering() { this->AddRef(); int r = nr_ice_initialize(ctx_, &NrIceCtx::initialized_cb, this); if (r && r != R_WOULDBLOCK) { MOZ_MTLOG(PR_LOG_ERROR, "Couldn't gather ICE candidates for '" << name_ << "'");
--- a/media/mtransport/nricectx.h +++ b/media/mtransport/nricectx.h @@ -49,16 +49,18 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE // This is a wrapper around the nICEr ICE stack #ifndef nricectx_h__ #define nricectx_h__ #include <vector> #include "sigslot.h" +#include "prnetdb.h" + #include "mozilla/RefPtr.h" #include "mozilla/Scoped.h" #include "nsAutoPtr.h" #include "nsIEventTarget.h" #include "nsITimer.h" #include "m_cpp_utils.h" @@ -69,33 +71,77 @@ typedef struct nr_ice_ctx_ nr_ice_ctx; typedef struct nr_ice_peer_ctx_ nr_ice_peer_ctx; typedef struct nr_ice_media_stream_ nr_ice_media_stream; typedef struct nr_ice_handler_ nr_ice_handler; typedef struct nr_ice_handler_vtbl_ nr_ice_handler_vtbl; typedef struct nr_ice_cand_pair_ nr_ice_cand_pair; class NrIceMediaStream; + +struct NrIceStunServer { + public: + NrIceStunServer(const PRNetAddr& addr) { + memcpy(&addr_, &addr, sizeof(addr)); + } + + // Convenience function to allow you to pass an IP addr as a string + static NrIceStunServer* Create(const std::string& addr, uint16_t port) { + ScopedDeletePtr<NrIceStunServer> server( + new NrIceStunServer()); + + nsresult rv = server->Init(addr, port); + if (NS_FAILED(rv)) + return nullptr; + + return server.forget(); + } + + + const PRNetAddr& addr() const { return addr_; } + + private: + NrIceStunServer() : addr_() {} + + nsresult Init(const std::string& addr, uint16_t port) { + PRStatus status = PR_StringToNetAddr(addr.c_str(), &addr_); + if (status != PR_SUCCESS) + return NS_ERROR_INVALID_ARG; + + addr_.inet.port = PR_htons(port); + + return NS_OK; + } + + PRNetAddr addr_; +}; + +struct NrIceTurnServer { + PRNetAddr addr; + std::string username; + std::string password; +}; + class NrIceCtx { public: enum State { ICE_CTX_INIT, ICE_CTX_GATHERING, ICE_CTX_GATHERED, ICE_CTX_CHECKING, ICE_CTX_OPEN, ICE_CTX_FAILED }; enum Controlling { ICE_CONTROLLING, ICE_CONTROLLED }; static RefPtr<NrIceCtx> Create(const std::string& name, - bool offerer, - bool set_interface_priorities = true); + bool offerer, + bool set_interface_priorities = true); virtual ~NrIceCtx(); nr_ice_ctx *ctx() { return ctx_; } nr_ice_peer_ctx *peer() { return peer_; } // Testing only. void destroy_peer_ctx(); @@ -113,16 +159,20 @@ class NrIceCtx { std::vector<std::string> GetGlobalAttributes(); // Set the other side's global attributes nsresult ParseGlobalAttributes(std::vector<std::string> attrs); // Set whether we are controlling or not. nsresult SetControlling(Controlling controlling); + // Set the STUN servers. Must be called before StartGathering + // (if at all). + nsresult SetStunServers(const std::vector<NrIceStunServer>& stun_servers); + // Start ICE gathering nsresult StartGathering(); // Start checking nsresult StartChecks(); // Finalize the ICE negotiation. I.e., there will be no // more forking. @@ -134,25 +184,26 @@ class NrIceCtx { sigslot::signal1<NrIceCtx *> SignalCompleted; // Done handshaking // The thread to direct method calls to nsCOMPtr<nsIEventTarget> thread() { return sts_target_; } NS_INLINE_DECL_THREADSAFE_REFCOUNTING(NrIceCtx) private: - NrIceCtx(const std::string& name, bool offerer) - : state_(ICE_CTX_INIT), - name_(name), - offerer_(offerer), - streams_(), - ctx_(nullptr), - peer_(nullptr), - ice_handler_vtbl_(nullptr), - ice_handler_(nullptr) {} + NrIceCtx(const std::string& name, + bool offerer) + : state_(ICE_CTX_INIT), + name_(name), + offerer_(offerer), + streams_(), + ctx_(nullptr), + peer_(nullptr), + ice_handler_vtbl_(nullptr), + ice_handler_(nullptr) {} DISALLOW_COPY_ASSIGN(NrIceCtx); // Callbacks for nICEr static void initialized_cb(NR_SOCKET s, int h, void *arg); // ICE initialized // Handler implementation static int select_pair(void *obj,nr_ice_media_stream *stream,
--- a/media/mtransport/test/ice_unittest.cpp +++ b/media/mtransport/test/ice_unittest.cpp @@ -12,16 +12,17 @@ #include <vector> #include "sigslot.h" #include "nspr.h" #include "nss.h" #include "ssl.h" +#include "mozilla/Scoped.h" #include "nsThreadUtils.h" #include "nsXPCOM.h" #include "logging.h" #include "nricectx.h" #include "nricemediastream.h" #include "mtransport_test_utils.h" #include "runnable_utils.h" @@ -70,16 +71,22 @@ class IceTestPeer : public sigslot::has_ stream->SignalCandidate.connect(this, &IceTestPeer::GotCandidate); stream->SignalReady.connect(this, &IceTestPeer::StreamReady); stream->SignalPacketReceived.connect(this, &IceTestPeer::PacketReceived); } void Gather() { nsresult res; + std::vector<NrIceStunServer> stun_servers; + ScopedDeletePtr<NrIceStunServer> server(NrIceStunServer::Create( + std::string((char *)"216.93.246.14"), 3478)); + stun_servers.push_back(*server); + ASSERT_TRUE(NS_SUCCEEDED(ice_ctx_->SetStunServers(stun_servers))); + test_utils->sts_target()->Dispatch( WrapRunnableRet(ice_ctx_, &NrIceCtx::StartGathering, &res), NS_DISPATCH_SYNC); ASSERT_TRUE(NS_SUCCEEDED(res)); } // Get various pieces of state
--- a/media/mtransport/test/transport_unittests.cpp +++ b/media/mtransport/test/transport_unittests.cpp @@ -107,16 +107,22 @@ class TransportTestPeer : public sigslot ice_ctx_(NrIceCtx::Create(name, name == "P2" ? TransportLayerDtls::CLIENT : TransportLayerDtls::SERVER)), streams_(), candidates_(), peer_(nullptr), gathering_complete_(false) { + std::vector<NrIceStunServer> stun_servers; + ScopedDeletePtr<NrIceStunServer> server(NrIceStunServer::Create( + std::string((char *)"216.93.246.14"), 3478)); + stun_servers.push_back(*server); + EXPECT_TRUE(NS_SUCCEEDED(ice_ctx_->SetStunServers(stun_servers))); + dtls_->SetIdentity(identity_); dtls_->SetRole(name == "P2" ? TransportLayerDtls::CLIENT : TransportLayerDtls::SERVER); nsresult res = identity_->ComputeFingerprint("sha-1", fingerprint_, sizeof(fingerprint_),
--- a/media/mtransport/third_party/nICEr/src/ice/ice_ctx.c +++ b/media/mtransport/third_party/nICEr/src/ice/ice_ctx.c @@ -107,16 +107,60 @@ int nr_ice_fetch_stun_servers(int ct, nr _status=0; abort: RFREE(addr); if (_status) RFREE(servers); return(_status); } +int nr_ice_ctx_set_stun_servers(nr_ice_ctx *ctx,nr_ice_stun_server *servers,int ct) + { + int _status; + + if(ctx->stun_servers){ + RFREE(ctx->stun_servers); + ctx->stun_server_ct=0; + } + + if (ct) { + if(!(ctx->stun_servers=RCALLOC(sizeof(nr_ice_stun_server)*ct))) + ABORT(R_NO_MEMORY); + + memcpy(ctx->stun_servers,servers,sizeof(nr_ice_stun_server)*ct); + ctx->stun_server_ct = ct; + } + + _status=0; + abort: + return(_status); + } + +int nr_ice_ctx_set_turn_servers(nr_ice_ctx *ctx,nr_ice_turn_server *servers,int ct) + { + int _status; + + if(ctx->turn_servers){ + RFREE(ctx->turn_servers); + ctx->turn_server_ct=0; + } + + if(ct) { + if(!(ctx->turn_servers=RCALLOC(sizeof(nr_ice_turn_server)*ct))) + ABORT(R_NO_MEMORY); + + memcpy(ctx->turn_servers,servers,sizeof(nr_ice_turn_server)*ct); + ctx->turn_server_ct = ct; + } + + _status=0; + abort: + return(_status); + } + #ifdef USE_TURN int nr_ice_fetch_turn_servers(int ct, nr_ice_turn_server **out) { int r,_status; nr_ice_turn_server *servers = 0; int i; NR_registry child; char *addr=0; @@ -209,34 +253,36 @@ int nr_ice_ctx_create(char *label, UINT4 if(r=nr_ice_random_string(buf,8)) ABORT(r); if(!(ctx->ufrag=r_strdup(buf))) ABORT(r); if(r=nr_ice_random_string(buf,32)) ABORT(r); if(!(ctx->pwd=r_strdup(buf))) ABORT(r); - + /* Get the STUN servers */ if(r=NR_reg_get_child_count(NR_ICE_REG_STUN_SRV_PRFX, (unsigned int *)&ctx->stun_server_ct)||ctx->stun_server_ct==0) { r_log(LOG_ICE,LOG_NOTICE,"No STUN servers specified"); ctx->stun_server_ct=0; } /* 255 is the max for our priority algorithm */ if(ctx->stun_server_ct>255){ r_log(LOG_ICE,LOG_WARNING,"Too many STUN servers specified: max=255"); ctx->stun_server_ct=255; } - if(r=nr_ice_fetch_stun_servers(ctx->stun_server_ct,&ctx->stun_servers)){ - r_log(LOG_ICE,LOG_ERR,"Couldn't load STUN servers from registry"); - ctx->turn_server_ct=0; - ABORT(r); + if(ctx->stun_server_ct>0){ + if(r=nr_ice_fetch_stun_servers(ctx->stun_server_ct,&ctx->stun_servers)){ + r_log(LOG_ICE,LOG_ERR,"Couldn't load STUN servers from registry"); + ctx->stun_server_ct=0; + ABORT(r); + } } #ifdef USE_TURN /* Get the TURN servers */ if(r=NR_reg_get_child_count(NR_ICE_REG_TURN_SRV_PRFX, (unsigned int *)&ctx->turn_server_ct)||ctx->turn_server_ct==0) { r_log(LOG_ICE,LOG_NOTICE,"No TURN servers specified"); ctx->turn_server_ct=0; @@ -247,20 +293,22 @@ int nr_ice_ctx_create(char *label, UINT4 /* 255 is the max for our priority algorithm */ if((ctx->stun_server_ct+ctx->turn_server_ct)>255){ r_log(LOG_ICE,LOG_WARNING,"Too many STUN/TURN servers specified: max=255"); ctx->turn_server_ct=255-ctx->stun_server_ct; } #ifdef USE_TURN - if(r=nr_ice_fetch_turn_servers(ctx->turn_server_ct,&ctx->turn_servers)){ - ctx->turn_server_ct=0; - r_log(LOG_ICE,LOG_ERR,"Couldn't load TURN servers from registry"); - ABORT(r); + if(ctx->turn_server_ct>0){ + if(r=nr_ice_fetch_turn_servers(ctx->turn_server_ct,&ctx->turn_servers)){ + ctx->turn_server_ct=0; + r_log(LOG_ICE,LOG_ERR,"Couldn't load TURN servers from registry"); + ABORT(r); + } } #endif /* USE_TURN */ ctx->Ta = 20; STAILQ_INIT(&ctx->streams); STAILQ_INIT(&ctx->sockets);
--- a/media/mtransport/third_party/nICEr/src/ice/ice_ctx.h +++ b/media/mtransport/third_party/nICEr/src/ice/ice_ctx.h @@ -142,16 +142,18 @@ int nr_ice_initialize(nr_ice_ctx *ctx, N int nr_ice_add_candidate(nr_ice_ctx *ctx, nr_ice_candidate *cand); void nr_ice_initialize_finished_cb(NR_SOCKET s, int h, void *cb_arg); int nr_ice_add_media_stream(nr_ice_ctx *ctx,char *label,int components, nr_ice_media_stream **streamp); int nr_ice_get_global_attributes(nr_ice_ctx *ctx,char ***attrsp, int *attrctp); int nr_ice_ctx_deliver_packet(nr_ice_ctx *ctx, nr_ice_component *comp, nr_transport_addr *source_addr, UCHAR *data, int len); int nr_ice_ctx_is_known_id(nr_ice_ctx *ctx, UCHAR id[12]); int nr_ice_ctx_remember_id(nr_ice_ctx *ctx, nr_stun_message *msg); int nr_ice_ctx_finalize(nr_ice_ctx *ctx, nr_ice_peer_ctx *pctx); +int nr_ice_ctx_set_stun_servers(nr_ice_ctx *ctx,nr_ice_stun_server *servers, int ct); +int nr_ice_ctx_set_turn_servers(nr_ice_ctx *ctx,nr_ice_turn_server *servers, int ct); extern int LOG_ICE; #ifdef __cplusplus } #endif /* __cplusplus */ #endif
--- a/media/webrtc/signaling/src/peerconnection/PeerConnectionMedia.cpp +++ b/media/webrtc/signaling/src/peerconnection/PeerConnectionMedia.cpp @@ -73,16 +73,33 @@ nsresult PeerConnectionMedia::Init() // TODO(ekr@rtfm.com): need some way to set not offerer later // Looks like a bug in the NrIceCtx API. mIceCtx = NrIceCtx::Create("PC:" + mParent->GetHandle(), true); if(!mIceCtx) { CSFLogErrorS(logTag, __FUNCTION__ << ": Failed to create Ice Context"); return NS_ERROR_FAILURE; } + // Temporarily hardwire the ICE server. + // TODO(ekr@rtfm.com): Remove this when we have ICE configuration + // settings. + std::vector<NrIceStunServer> stun_servers; + ScopedDeletePtr<NrIceStunServer> server(NrIceStunServer::Create( + std::string((char *)"216.93.246.14"), 3478)); + MOZ_ASSERT(server); + if (!server) { + CSFLogErrorS(logTag, __FUNCTION__ << ": Could not parse STUN server string"); + return NS_ERROR_FAILURE; + } + + stun_servers.push_back(*server); + nsresult rv = mIceCtx->SetStunServers(stun_servers); + if (NS_FAILED(rv)) + return rv; + mIceCtx->SignalGatheringCompleted.connect(this, &PeerConnectionMedia::IceGatheringCompleted); mIceCtx->SignalCompleted.connect(this, &PeerConnectionMedia::IceCompleted); // Create three streams to start with. // One each for audio, video and DataChannel // TODO: this will be re-visited