| /* |
| * Copyright 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 |
| * tree. An additional intellectual property rights grant can be found |
| * in the file PATENTS. All contributing project authors may |
| * be found in the AUTHORS file in the root of the source tree. |
| */ |
| |
| #include <gtk/gtk.h> |
| |
| #include <cstdio> |
| #include <memory> |
| #include <string> |
| |
| #include "absl/flags/flag.h" |
| #include "absl/flags/parse.h" |
| #include "api/environment/environment.h" |
| #include "api/environment/environment_factory.h" |
| #include "api/field_trials.h" |
| #include "api/make_ref_counted.h" |
| #include "api/scoped_refptr.h" |
| #include "api/units/time_delta.h" |
| #include "examples/peerconnection/client/conductor.h" |
| #include "examples/peerconnection/client/flag_defs.h" |
| #include "examples/peerconnection/client/linux/main_wnd.h" |
| #include "examples/peerconnection/client/peer_connection_client.h" |
| #include "rtc_base/physical_socket_server.h" |
| #include "rtc_base/ssl_adapter.h" |
| #include "rtc_base/thread.h" |
| |
| class CustomSocketServer : public webrtc::PhysicalSocketServer { |
| public: |
| explicit CustomSocketServer(GtkMainWnd* wnd) |
| : wnd_(wnd), conductor_(nullptr), client_(nullptr) {} |
| ~CustomSocketServer() override {} |
| |
| void SetMessageQueue(webrtc::Thread* queue) override { |
| message_queue_ = queue; |
| } |
| |
| void set_client(PeerConnectionClient* client) { client_ = client; } |
| void set_conductor(Conductor* conductor) { conductor_ = conductor; } |
| |
| // Override so that we can also pump the GTK message loop. |
| // This function never waits. |
| bool Wait(webrtc::TimeDelta max_wait_duration, bool process_io) override { |
| // Pump GTK events. |
| // TODO(henrike): We really should move either the socket server or UI to a |
| // different thread. Alternatively we could look at merging the two loops |
| // by implementing a dispatcher for the socket server and/or use |
| // g_main_context_set_poll_func. |
| while (gtk_events_pending()) |
| gtk_main_iteration(); |
| |
| if (!wnd_->IsWindow() && !conductor_->connection_active() && |
| client_ != nullptr && !client_->is_connected()) { |
| message_queue_->Quit(); |
| } |
| return webrtc::PhysicalSocketServer::Wait(webrtc::TimeDelta::Zero(), |
| process_io); |
| } |
| |
| protected: |
| webrtc::Thread* message_queue_; |
| GtkMainWnd* wnd_; |
| Conductor* conductor_; |
| PeerConnectionClient* client_; |
| }; |
| |
| int main(int argc, char* argv[]) { |
| gtk_init(&argc, &argv); |
| |
| absl::ParseCommandLine(argc, argv); |
| |
| webrtc::Environment env = |
| webrtc::CreateEnvironment(std::make_unique<webrtc::FieldTrials>( |
| absl::GetFlag(FLAGS_force_fieldtrials))); |
| |
| // Abort if the user specifies a port that is outside the allowed |
| // range [1, 65535]. |
| if ((absl::GetFlag(FLAGS_port) < 1) || (absl::GetFlag(FLAGS_port) > 65535)) { |
| printf("Error: %i is not a valid port.\n", absl::GetFlag(FLAGS_port)); |
| return -1; |
| } |
| |
| const std::string server = absl::GetFlag(FLAGS_server); |
| GtkMainWnd wnd(server.c_str(), absl::GetFlag(FLAGS_port), |
| absl::GetFlag(FLAGS_autoconnect), |
| absl::GetFlag(FLAGS_autocall)); |
| wnd.Create(); |
| |
| CustomSocketServer socket_server(&wnd); |
| webrtc::AutoSocketServerThread thread(&socket_server); |
| |
| webrtc::InitializeSSL(); |
| // Must be constructed after we set the socketserver. |
| PeerConnectionClient client; |
| auto conductor = webrtc::make_ref_counted<Conductor>(env, &client, &wnd); |
| socket_server.set_client(&client); |
| socket_server.set_conductor(conductor.get()); |
| |
| thread.Run(); |
| |
| // gtk_main(); |
| wnd.Destroy(); |
| |
| // TODO(henrike): Run the Gtk main loop to tear down the connection. |
| /* |
| while (gtk_events_pending()) { |
| gtk_main_iteration(); |
| } |
| */ |
| webrtc::CleanupSSL(); |
| return 0; |
| } |