147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/* 247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org * Copyright 2004 The WebRTC Project Authors. All rights reserved. 347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org * 447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org * Use of this source code is governed by a BSD-style license 547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org * that can be found in the LICENSE file in the root of the source 647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org * tree. An additional intellectual property rights grant can be found 747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org * in the file PATENTS. All contributing project authors may 847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org * be found in the AUTHORS file in the root of the source tree. 947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org */ 1047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 1147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#ifndef WEBRTC_BASE_TESTUTILS_H__ 1247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define WEBRTC_BASE_TESTUTILS_H__ 1347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 1447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// Utilities for testing rtc infrastructure in unittests 1547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 1647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#if defined(WEBRTC_LINUX) && !defined(WEBRTC_ANDROID) 1747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#include <X11/Xlib.h> 1847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#include <X11/extensions/Xrandr.h> 1947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 2047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// X defines a few macros that stomp on types that gunit.h uses. 2147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#undef None 2247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#undef Bool 2347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#endif 2447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 2547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#include <map> 2647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#include <vector> 2747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#include "webrtc/base/asyncsocket.h" 2847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#include "webrtc/base/common.h" 2947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#include "webrtc/base/gunit.h" 3047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#include "webrtc/base/nethelpers.h" 31698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org#include "webrtc/base/pathutils.h" 3247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#include "webrtc/base/stream.h" 3347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#include "webrtc/base/stringencode.h" 3447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#include "webrtc/base/stringutils.h" 3547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#include "webrtc/base/thread.h" 3647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 3747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orgnamespace testing { 3847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 3947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orgusing namespace rtc; 4047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 4147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 4247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// StreamSink - Monitor asynchronously signalled events from StreamInterface 4347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// or AsyncSocket (which should probably be a StreamInterface. 4447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 4547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 4647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// Note: Any event that is an error is treaded as SSE_ERROR instead of that 4747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// event. 4847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 4947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orgenum StreamSinkEvent { 5047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SSE_OPEN = SE_OPEN, 5147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SSE_READ = SE_READ, 5247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SSE_WRITE = SE_WRITE, 5347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SSE_CLOSE = SE_CLOSE, 5447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SSE_ERROR = 16 5547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org}; 5647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 5747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orgclass StreamSink : public sigslot::has_slots<> { 5847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org public: 5947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void Monitor(StreamInterface* stream) { 6047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org stream->SignalEvent.connect(this, &StreamSink::OnEvent); 6147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org events_.erase(stream); 6247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 6347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void Unmonitor(StreamInterface* stream) { 6447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org stream->SignalEvent.disconnect(this); 6547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org // In case you forgot to unmonitor a previous object with this address 6647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org events_.erase(stream); 6747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 6847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org bool Check(StreamInterface* stream, StreamSinkEvent event, bool reset = true) { 6947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return DoCheck(stream, event, reset); 7047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 7147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org int Events(StreamInterface* stream, bool reset = true) { 7247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return DoEvents(stream, reset); 7347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 7447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 7547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void Monitor(AsyncSocket* socket) { 7647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket->SignalConnectEvent.connect(this, &StreamSink::OnConnectEvent); 7747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket->SignalReadEvent.connect(this, &StreamSink::OnReadEvent); 7847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket->SignalWriteEvent.connect(this, &StreamSink::OnWriteEvent); 7947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket->SignalCloseEvent.connect(this, &StreamSink::OnCloseEvent); 8047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org // In case you forgot to unmonitor a previous object with this address 8147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org events_.erase(socket); 8247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 8347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void Unmonitor(AsyncSocket* socket) { 8447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket->SignalConnectEvent.disconnect(this); 8547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket->SignalReadEvent.disconnect(this); 8647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket->SignalWriteEvent.disconnect(this); 8747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket->SignalCloseEvent.disconnect(this); 8847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org events_.erase(socket); 8947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 9047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org bool Check(AsyncSocket* socket, StreamSinkEvent event, bool reset = true) { 9147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return DoCheck(socket, event, reset); 9247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 9347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org int Events(AsyncSocket* socket, bool reset = true) { 9447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return DoEvents(socket, reset); 9547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 9647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 9747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org private: 9847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org typedef std::map<void*,int> EventMap; 9947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 10047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void OnEvent(StreamInterface* stream, int events, int error) { 10147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (error) { 10247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org events = SSE_ERROR; 10347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 10447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org AddEvents(stream, events); 10547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 10647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void OnConnectEvent(AsyncSocket* socket) { 10747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org AddEvents(socket, SSE_OPEN); 10847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 10947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void OnReadEvent(AsyncSocket* socket) { 11047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org AddEvents(socket, SSE_READ); 11147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 11247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void OnWriteEvent(AsyncSocket* socket) { 11347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org AddEvents(socket, SSE_WRITE); 11447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 11547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void OnCloseEvent(AsyncSocket* socket, int error) { 11647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org AddEvents(socket, (0 == error) ? SSE_CLOSE : SSE_ERROR); 11747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 11847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 11947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void AddEvents(void* obj, int events) { 12047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org EventMap::iterator it = events_.find(obj); 12147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (events_.end() == it) { 12247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org events_.insert(EventMap::value_type(obj, events)); 12347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } else { 12447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org it->second |= events; 12547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 12647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 12747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org bool DoCheck(void* obj, StreamSinkEvent event, bool reset) { 12847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org EventMap::iterator it = events_.find(obj); 12947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if ((events_.end() == it) || (0 == (it->second & event))) { 13047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return false; 13147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 13247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (reset) { 13347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org it->second &= ~event; 13447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 13547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return true; 13647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 13747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org int DoEvents(void* obj, bool reset) { 13847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org EventMap::iterator it = events_.find(obj); 13947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (events_.end() == it) 14047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return 0; 14147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org int events = it->second; 14247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (reset) { 14347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org it->second = 0; 14447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 14547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return events; 14647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 14747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 14847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org EventMap events_; 14947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org}; 15047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 15147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 15247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// StreamSource - Implements stream interface and simulates asynchronous 15347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// events on the stream, without a network. Also buffers written data. 15447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 15547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 15647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orgclass StreamSource : public StreamInterface { 15747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orgpublic: 15847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org StreamSource() { 15947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org Clear(); 16047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 16147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 16247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void Clear() { 16347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org readable_data_.clear(); 16447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org written_data_.clear(); 16547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org state_ = SS_CLOSED; 16647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org read_block_ = 0; 16747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org write_block_ = SIZE_UNKNOWN; 16847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 16947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void QueueString(const char* data) { 17047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org QueueData(data, strlen(data)); 17147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 17247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void QueueStringF(const char* format, ...) { 17347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org va_list args; 17447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org va_start(args, format); 17547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org char buffer[1024]; 17647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t len = vsprintfn(buffer, sizeof(buffer), format, args); 17747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org ASSERT(len < sizeof(buffer) - 1); 17847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org va_end(args); 17947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org QueueData(buffer, len); 18047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 18147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void QueueData(const char* data, size_t len) { 18247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org readable_data_.insert(readable_data_.end(), data, data + len); 18347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if ((SS_OPEN == state_) && (readable_data_.size() == len)) { 18447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SignalEvent(this, SE_READ, 0); 18547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 18647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 18747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org std::string ReadData() { 18847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org std::string data; 18947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org // avoid accessing written_data_[0] if it is undefined 19047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (written_data_.size() > 0) { 19147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org data.insert(0, &written_data_[0], written_data_.size()); 19247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 19347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org written_data_.clear(); 19447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return data; 19547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 19647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void SetState(StreamState state) { 19747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org int events = 0; 19847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if ((SS_OPENING == state_) && (SS_OPEN == state)) { 19947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org events |= SE_OPEN; 20047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (!readable_data_.empty()) { 20147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org events |= SE_READ; 20247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 20347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } else if ((SS_CLOSED != state_) && (SS_CLOSED == state)) { 20447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org events |= SE_CLOSE; 20547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 20647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org state_ = state; 20747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (events) { 20847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SignalEvent(this, events, 0); 20947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 21047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 21147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org // Will cause Read to block when there are pos bytes in the read queue. 21247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void SetReadBlock(size_t pos) { read_block_ = pos; } 21347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org // Will cause Write to block when there are pos bytes in the write queue. 21447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void SetWriteBlock(size_t pos) { write_block_ = pos; } 21547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 21647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org virtual StreamState GetState() const { return state_; } 21747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org virtual StreamResult Read(void* buffer, size_t buffer_len, 21847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t* read, int* error) { 21947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (SS_CLOSED == state_) { 22047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (error) *error = -1; 22147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return SR_ERROR; 22247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 22347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if ((SS_OPENING == state_) || (readable_data_.size() <= read_block_)) { 22447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return SR_BLOCK; 22547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 22647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t count = _min(buffer_len, readable_data_.size() - read_block_); 22747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org memcpy(buffer, &readable_data_[0], count); 22847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t new_size = readable_data_.size() - count; 22947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org // Avoid undefined access beyond the last element of the vector. 23047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org // This only happens when new_size is 0. 23147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (count < readable_data_.size()) { 23247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org memmove(&readable_data_[0], &readable_data_[count], new_size); 23347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 23447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org readable_data_.resize(new_size); 23547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (read) *read = count; 23647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return SR_SUCCESS; 23747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 23847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org virtual StreamResult Write(const void* data, size_t data_len, 23947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t* written, int* error) { 24047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (SS_CLOSED == state_) { 24147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (error) *error = -1; 24247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return SR_ERROR; 24347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 24447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (SS_OPENING == state_) { 24547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return SR_BLOCK; 24647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 24747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (SIZE_UNKNOWN != write_block_) { 24847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (written_data_.size() >= write_block_) { 24947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return SR_BLOCK; 25047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 25147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (data_len > (write_block_ - written_data_.size())) { 25247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org data_len = write_block_ - written_data_.size(); 25347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 25447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 25547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (written) *written = data_len; 25647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org const char* cdata = static_cast<const char*>(data); 25747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org written_data_.insert(written_data_.end(), cdata, cdata + data_len); 25847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return SR_SUCCESS; 25947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 26047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org virtual void Close() { state_ = SS_CLOSED; } 26147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 26247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orgprivate: 26347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org typedef std::vector<char> Buffer; 26447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org Buffer readable_data_, written_data_; 26547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org StreamState state_; 26647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t read_block_, write_block_; 26747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org}; 26847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 26947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 27047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// SocketTestClient 27147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// Creates a simulated client for testing. Works on real and virtual networks. 27247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 27347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 27447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orgclass SocketTestClient : public sigslot::has_slots<> { 27547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orgpublic: 27647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SocketTestClient() { 27747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org Init(NULL, AF_INET); 27847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 27947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SocketTestClient(AsyncSocket* socket) { 28047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org Init(socket, socket->GetLocalAddress().family()); 28147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 28247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SocketTestClient(const SocketAddress& address) { 28347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org Init(NULL, address.family()); 28447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket_->Connect(address); 28547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 28647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 28747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org AsyncSocket* socket() { return socket_.get(); } 28847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 28947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void QueueString(const char* data) { 29047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org QueueData(data, strlen(data)); 29147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 29247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void QueueStringF(const char* format, ...) { 29347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org va_list args; 29447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org va_start(args, format); 29547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org char buffer[1024]; 29647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t len = vsprintfn(buffer, sizeof(buffer), format, args); 29747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org ASSERT(len < sizeof(buffer) - 1); 29847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org va_end(args); 29947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org QueueData(buffer, len); 30047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 30147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void QueueData(const char* data, size_t len) { 30247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org send_buffer_.insert(send_buffer_.end(), data, data + len); 30347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (Socket::CS_CONNECTED == socket_->GetState()) { 30447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org Flush(); 30547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 30647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 30747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org std::string ReadData() { 30847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org std::string data(&recv_buffer_[0], recv_buffer_.size()); 30947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org recv_buffer_.clear(); 31047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return data; 31147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 31247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 31347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org bool IsConnected() const { 31447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return (Socket::CS_CONNECTED == socket_->GetState()); 31547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 31647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org bool IsClosed() const { 31747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return (Socket::CS_CLOSED == socket_->GetState()); 31847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 31947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 32047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orgprivate: 32147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org typedef std::vector<char> Buffer; 32247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 32347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void Init(AsyncSocket* socket, int family) { 32447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (!socket) { 32547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket = Thread::Current()->socketserver() 32647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org ->CreateAsyncSocket(family, SOCK_STREAM); 32747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 32847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket_.reset(socket); 32947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket_->SignalConnectEvent.connect(this, 33047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org &SocketTestClient::OnConnectEvent); 33147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket_->SignalReadEvent.connect(this, &SocketTestClient::OnReadEvent); 33247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket_->SignalWriteEvent.connect(this, &SocketTestClient::OnWriteEvent); 33347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket_->SignalCloseEvent.connect(this, &SocketTestClient::OnCloseEvent); 33447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 33547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 33647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void Flush() { 33747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t sent = 0; 33847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org while (sent < send_buffer_.size()) { 33947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org int result = socket_->Send(&send_buffer_[sent], 34047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org send_buffer_.size() - sent); 34147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (result > 0) { 34247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org sent += result; 34347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } else { 34447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org break; 34547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 34647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 34747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t new_size = send_buffer_.size() - sent; 34847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org memmove(&send_buffer_[0], &send_buffer_[sent], new_size); 34947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org send_buffer_.resize(new_size); 35047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 35147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 35247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void OnConnectEvent(AsyncSocket* socket) { 35347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (!send_buffer_.empty()) { 35447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org Flush(); 35547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 35647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 35747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void OnReadEvent(AsyncSocket* socket) { 35847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org char data[64 * 1024]; 35947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org int result = socket_->Recv(data, ARRAY_SIZE(data)); 36047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (result > 0) { 36147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org recv_buffer_.insert(recv_buffer_.end(), data, data + result); 36247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 36347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 36447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void OnWriteEvent(AsyncSocket* socket) { 36547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (!send_buffer_.empty()) { 36647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org Flush(); 36747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 36847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 36947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void OnCloseEvent(AsyncSocket* socket, int error) { 37047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 37147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 37247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org scoped_ptr<AsyncSocket> socket_; 37347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org Buffer send_buffer_, recv_buffer_; 37447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org}; 37547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 37647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 37747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// SocketTestServer 37847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// Creates a simulated server for testing. Works on real and virtual networks. 37947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 38047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 38147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orgclass SocketTestServer : public sigslot::has_slots<> { 38247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org public: 38347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SocketTestServer(const SocketAddress& address) 38447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org : socket_(Thread::Current()->socketserver() 38547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org ->CreateAsyncSocket(address.family(), SOCK_STREAM)) 38647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org { 38747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket_->SignalReadEvent.connect(this, &SocketTestServer::OnReadEvent); 38847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket_->Bind(address); 38947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org socket_->Listen(5); 39047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 39147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org virtual ~SocketTestServer() { 39247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org clear(); 39347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 39447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 39547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t size() const { return clients_.size(); } 39647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SocketTestClient* client(size_t index) const { return clients_[index]; } 39747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org SocketTestClient* operator[](size_t index) const { return client(index); } 39847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 39947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void clear() { 40047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org for (size_t i=0; i<clients_.size(); ++i) { 40147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org delete clients_[i]; 40247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 40347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org clients_.clear(); 40447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 40547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 40647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org private: 40747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org void OnReadEvent(AsyncSocket* socket) { 40847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org AsyncSocket* accepted = 40947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org static_cast<AsyncSocket*>(socket_->Accept(NULL)); 41047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (!accepted) 41147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return; 41247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org clients_.push_back(new SocketTestClient(accepted)); 41347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 41447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 41547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org scoped_ptr<AsyncSocket> socket_; 41647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org std::vector<SocketTestClient*> clients_; 41747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org}; 41847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 41947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 42047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// Generic Utilities 42147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 42247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 42347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orginline bool ReadFile(const char* filename, std::string* contents) { 42447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org FILE* fp = fopen(filename, "rb"); 42547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (!fp) 42647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return false; 42747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org char buffer[1024*64]; 42847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t read; 42947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org contents->clear(); 43047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org while ((read = fread(buffer, 1, sizeof(buffer), fp))) { 43147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org contents->append(buffer, read); 43247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 43347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org bool success = (0 != feof(fp)); 43447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org fclose(fp); 43547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return success; 43647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org} 43747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 438698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org// Look in parent dir for parallel directory. 439698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.orginline rtc::Pathname GetSiblingDirectory( 440698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org const std::string& parallel_dir) { 441698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org rtc::Pathname path = rtc::Filesystem::GetCurrentDirectory(); 442698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org while (!path.empty()) { 443698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org rtc::Pathname potential_parallel_dir = path; 444698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org potential_parallel_dir.AppendFolder(parallel_dir); 445698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org if (rtc::Filesystem::IsFolder(potential_parallel_dir)) { 446698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org return potential_parallel_dir; 447698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org } 448698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org 449698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org path.SetFolder(path.parent_folder()); 450698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org } 451698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org return path; 452698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org} 453698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org 454698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.orginline rtc::Pathname GetGoogle3Directory() { 455698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org return GetSiblingDirectory("google3"); 456698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org} 457698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org 458698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.orginline rtc::Pathname GetTalkDirectory() { 459698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org return GetSiblingDirectory("talk"); 460698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org} 461698ee5a2400b47f6ce38a4d4700165b6ea5a2931henrike@webrtc.org 46247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 46347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// Unittest predicates which are similar to STREQ, but for raw memory 46447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 46547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 46647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orginline AssertionResult CmpHelperMemEq(const char* expected_expression, 46747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org const char* expected_length_expression, 46847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org const char* actual_expression, 46947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org const char* actual_length_expression, 47047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org const void* expected, 47147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t expected_length, 47247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org const void* actual, 47347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t actual_length) 47447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org{ 47547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if ((expected_length == actual_length) 47647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org && (0 == memcmp(expected, actual, expected_length))) { 47747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return AssertionSuccess(); 47847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 47947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 48047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org Message msg; 48147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org msg << "Value of: " << actual_expression 48247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org << " [" << actual_length_expression << "]"; 48347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (true) { //!actual_value.Equals(actual_expression)) { 48447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t buffer_size = actual_length * 2 + 1; 48547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org char* buffer = STACK_ARRAY(char, buffer_size); 48647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org hex_encode(buffer, buffer_size, 48747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org reinterpret_cast<const char*>(actual), actual_length); 48847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org msg << "\n Actual: " << buffer << " [" << actual_length << "]"; 48947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 49047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 49147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org msg << "\nExpected: " << expected_expression 49247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org << " [" << expected_length_expression << "]"; 49347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (true) { //!expected_value.Equals(expected_expression)) { 49447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t buffer_size = expected_length * 2 + 1; 49547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org char* buffer = STACK_ARRAY(char, buffer_size); 49647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org hex_encode(buffer, buffer_size, 49747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org reinterpret_cast<const char*>(expected), expected_length); 49847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org msg << "\nWhich is: " << buffer << " [" << expected_length << "]"; 49947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 50047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 50147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return AssertionFailure(msg); 50247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org} 50347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 50447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orginline AssertionResult CmpHelperFileEq(const char* expected_expression, 50547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org const char* expected_length_expression, 50647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org const char* actual_filename, 50747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org const void* expected, 50847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org size_t expected_length, 50947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org const char* filename) 51047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org{ 51147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org std::string contents; 51247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (!ReadFile(filename, &contents)) { 51347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org Message msg; 51447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org msg << "File '" << filename << "' could not be read."; 51547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return AssertionFailure(msg); 51647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 51747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return CmpHelperMemEq(expected_expression, expected_length_expression, 51847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org actual_filename, "", 51947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org expected, expected_length, 52047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org contents.c_str(), contents.size()); 52147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org} 52247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 52347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define EXPECT_MEMEQ(expected, expected_length, actual, actual_length) \ 52447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org EXPECT_PRED_FORMAT4(::testing::CmpHelperMemEq, expected, expected_length, \ 52547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org actual, actual_length) 52647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 52747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define ASSERT_MEMEQ(expected, expected_length, actual, actual_length) \ 52847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org ASSERT_PRED_FORMAT4(::testing::CmpHelperMemEq, expected, expected_length, \ 52947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org actual, actual_length) 53047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 53147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define EXPECT_FILEEQ(expected, expected_length, filename) \ 53247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org EXPECT_PRED_FORMAT3(::testing::CmpHelperFileEq, expected, expected_length, \ 53347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org filename) 53447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 53547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define ASSERT_FILEEQ(expected, expected_length, filename) \ 53647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org ASSERT_PRED_FORMAT3(::testing::CmpHelperFileEq, expected, expected_length, \ 53747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org filename) 53847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 53947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 54047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// Helpers for initializing constant memory with integers in a particular byte 54147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// order 54247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 54347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 54447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define BYTE_CAST(x) static_cast<uint8>((x) & 0xFF) 54547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 54647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// Declare a N-bit integer as a little-endian sequence of bytes 54747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define LE16(x) BYTE_CAST(((uint16)x) >> 0), BYTE_CAST(((uint16)x) >> 8) 54847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 54947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define LE32(x) BYTE_CAST(((uint32)x) >> 0), BYTE_CAST(((uint32)x) >> 8), \ 55047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org BYTE_CAST(((uint32)x) >> 16), BYTE_CAST(((uint32)x) >> 24) 55147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 55247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define LE64(x) BYTE_CAST(((uint64)x) >> 0), BYTE_CAST(((uint64)x) >> 8), \ 55347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org BYTE_CAST(((uint64)x) >> 16), BYTE_CAST(((uint64)x) >> 24), \ 55447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org BYTE_CAST(((uint64)x) >> 32), BYTE_CAST(((uint64)x) >> 40), \ 55547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org BYTE_CAST(((uint64)x) >> 48), BYTE_CAST(((uint64)x) >> 56) 55647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 55747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// Declare a N-bit integer as a big-endian (Internet) sequence of bytes 55847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define BE16(x) BYTE_CAST(((uint16)x) >> 8), BYTE_CAST(((uint16)x) >> 0) 55947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 56047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define BE32(x) BYTE_CAST(((uint32)x) >> 24), BYTE_CAST(((uint32)x) >> 16), \ 56147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org BYTE_CAST(((uint32)x) >> 8), BYTE_CAST(((uint32)x) >> 0) 56247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 56347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define BE64(x) BYTE_CAST(((uint64)x) >> 56), BYTE_CAST(((uint64)x) >> 48), \ 56447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org BYTE_CAST(((uint64)x) >> 40), BYTE_CAST(((uint64)x) >> 32), \ 56547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org BYTE_CAST(((uint64)x) >> 24), BYTE_CAST(((uint64)x) >> 16), \ 56647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org BYTE_CAST(((uint64)x) >> 8), BYTE_CAST(((uint64)x) >> 0) 56747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 56847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// Declare a N-bit integer as a this-endian (local machine) sequence of bytes 56947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#ifndef BIG_ENDIAN 57047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define BIG_ENDIAN 1 57147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#endif // BIG_ENDIAN 57247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 57347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#if BIG_ENDIAN 57447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define TE16 BE16 57547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define TE32 BE32 57647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define TE64 BE64 57747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#else // !BIG_ENDIAN 57847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define TE16 LE16 57947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define TE32 LE32 58047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define TE64 LE64 58147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#endif // !BIG_ENDIAN 58247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 58347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org/////////////////////////////////////////////////////////////////////////////// 58447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 58547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// Helpers for determining if X/screencasting is available (on linux). 58647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 58747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#define MAYBE_SKIP_SCREENCAST_TEST() \ 58847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (!testing::IsScreencastingAvailable()) { \ 58947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org LOG(LS_WARNING) << "Skipping test, since it doesn't have the requisite " \ 59047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org << "X environment for screen capture."; \ 59147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return; \ 59247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } \ 59347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 59447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#if defined(WEBRTC_LINUX) && !defined(WEBRTC_ANDROID) 59547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orgstruct XDisplay { 59647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org XDisplay() : display_(XOpenDisplay(NULL)) { } 59747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org ~XDisplay() { if (display_) XCloseDisplay(display_); } 59847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org bool IsValid() const { return display_ != NULL; } 59947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org operator Display*() { return display_; } 60047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org private: 60147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org Display* display_; 60247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org}; 60347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#endif 60447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 60547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// Returns true if screencasting is available. When false, anything that uses 60647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org// screencasting features may fail. 60747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.orginline bool IsScreencastingAvailable() { 60847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#if defined(WEBRTC_LINUX) && !defined(WEBRTC_ANDROID) 60947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org XDisplay display; 61047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (!display.IsValid()) { 61147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org LOG(LS_WARNING) << "No X Display available."; 61247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return false; 61347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 61447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org int ignored_int, major_version, minor_version; 61547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org if (!XRRQueryExtension(display, &ignored_int, &ignored_int) || 61647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org !XRRQueryVersion(display, &major_version, &minor_version) || 61747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org major_version < 1 || 61847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org (major_version < 2 && minor_version < 3)) { 61947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org LOG(LS_WARNING) << "XRandr version: " << major_version << "." 62047be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org << minor_version; 62147be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org LOG(LS_WARNING) << "XRandr is not supported or is too old (pre 1.3)."; 62247be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return false; 62347be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org } 62447be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#endif 62547be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org return true; 62647be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org} 62747be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org} // namespace testing 62847be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org 62947be73b8629244d6bb63a28198f97f040ce53d21henrike@webrtc.org#endif // WEBRTC_BASE_TESTUTILS_H__ 630