diff --git a/rtc_tools/rtcbot/OWNERS b/rtc_tools/rtcbot/OWNERS
deleted file mode 100644
index 296f71f..0000000
--- a/rtc_tools/rtcbot/OWNERS
+++ /dev/null
@@ -1 +0,0 @@
-andresp@webrtc.org
diff --git a/rtc_tools/rtcbot/README b/rtc_tools/rtcbot/README
deleted file mode 100644
index 1f4d7c1..0000000
--- a/rtc_tools/rtcbot/README
+++ /dev/null
@@ -1,59 +0,0 @@
-=== RTCBot ===
-RTCBot is a framework to write tests that need to spawn multiple webrtc
-endpoints.
-
-== Description ==
-RTCBot is a framework that allows to write tests where logic runs on a single
-host that controls multiple endpoints ("bots"). It allows creating complex
-scenarios that would otherwise require non-trival signalling between multiple
-parties.
-
-The host runs in node.js, but the test code is run in an isolated context with
-no access to node.js specifics other than the exposed api via a test variable.
-
-Part of the exposed api (test.spawnBot) allows a test to spawn a bot and
-access its exposed API. Details are in botmanager.js.
-
-== How to run the test ==
- $ cd trunk/webrtc/tool/rtcbot
- $ npm install express browserify ws websocket-stream dnode
- $ mkdir configurations
- $ cd configurations
- $ openssl genrsa -out priv.pem 1024
- $ openssl req -x509 -new -key priv.pem -days 3650 -out cert.crt
- $ cd trunk/webrtc/tool/rtcbot
- $ node main.js "<test_name>"
-
-* Note:
-    In first time you will use rtcBot you will receive a warning telling
-  you that your connection is not private. Just avoid this warning and
-  click Proceed to localhost (unsafe).
-
-== How can I see the list of available tests? ==
- $ node main.js
-
-== Example on how to install nodejs ==
- $ cd /work/tools/
- $ git clone https://github.com/creationix/nvm.git
- $ export NVM_DIR=/work/tools/nvm; source $NVM_DIR/nvm.sh
- $ nvm install 0.10
- $ nvm use 0.10
-
-== Why generating the private key and self signed certificate? ==
-  - Private key and certificate are used for creating HTTPs server in
-    rtcBot for loading the required files on the different types of the bots.
-
-== Supported Bot Types ==
-  - "chrome": chrome on host machine.
-  - "android-chrome": chrome on android device. Details in "Android" Section.
-
- * Bot type is specified directly by the test.
-
-== Android ==
-Before running test with Android one MUST forward the device port 8080 to the
-host machine. That is easy to achieve with chrome port forwarding tools.
- - Visit chrome://inspect/devices on the host machine.
- - Configure and enable port forwarding 8080 -> localhost:8080
- - Open chrome on you Android device before running test, and leave it
-   running until the end of test.
- - Run your test.
diff --git a/rtc_tools/rtcbot/bot/api.js b/rtc_tools/rtcbot/bot/api.js
deleted file mode 100644
index 7e1a436..0000000
--- a/rtc_tools/rtcbot/bot/api.js
+++ /dev/null
@@ -1,37 +0,0 @@
-// Copyright (c) 2014 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.
-//
-// This file exposes the api for the bot to connect to the host script
-// waiting a websocket connection and using dnode for javascript rpc.
-//
-// This file is served to the browser via browserify to resolve the
-// dnode requires.
-var WebSocketStream = require('websocket-stream');
-var Dnode = require('dnode');
-
-function connectToServer(api) {
-  var stream = new WebSocketStream("wss://localhost:8080/");
-  var dnode = new Dnode(api);
-  dnode.on('error', function (error) { console.log(error); });
-  dnode.pipe(stream).pipe(dnode);
-}
-
-// Dnode loses certain method calls when exposing native browser objects such as
-// peer connections. This methods helps work around that by allowing one to
-// redefine a non-native method in a target "obj" from "src" that applies a list
-// of casts to the arguments (types are lost in dnode).
-function expose(obj, src, method, casts) {
-  obj[method] = function () {
-    for (index in casts)
-      arguments[index] = new (casts[index])(arguments[index]);
-    src[method].apply(src, arguments);
-  }
-}
-
-window.expose = expose;
-window.connectToServer = connectToServer;
diff --git a/rtc_tools/rtcbot/bot/browser/bot.js b/rtc_tools/rtcbot/bot/browser/bot.js
deleted file mode 100644
index a5785df..0000000
--- a/rtc_tools/rtcbot/bot/browser/bot.js
+++ /dev/null
@@ -1,140 +0,0 @@
-// Copyright (c) 2014 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.
-//
-var localStreams = [];
-var remoteStreams = [];
-
-function ping(callback) {
-  callback("pong");
-}
-
-function getUserMedia(constraints, onSuccessCallback, onFailCallback){
-  console.log("Getting user media.");
-  navigator.webkitGetUserMedia(constraints,
-      onSuccessCallbackWraper, onFailCallback);
-
-  function onSuccessCallbackWraper(stream) {
-    console.log("GetUserMedia success.");
-    localStreams[stream.id] = stream;
-    onSuccessCallback(stream);
-  }
-}
-
-function createPeerConnection(config, doneCallback, failCallback) {
-  console.log("Creating peer connection");
-  var obj = {};
-  var pc = new webkitRTCPeerConnection(config);
-
-  expose(obj, pc, "close");
-  expose(obj, pc, "createOffer");
-  expose(obj, pc, "createAnswer");
-  expose(obj, pc, "addEventListener");
-  expose(obj, pc, "addIceCandidate", { 0: RTCIceCandidate});
-  expose(obj, pc, "setRemoteDescription", { 0: RTCSessionDescription });
-  expose(obj, pc, "setLocalDescription", { 0: RTCSessionDescription });
-
-  obj.addStream = function(stream) {
-    console.log("Adding local stream.");
-    var tempStream = localStreams[stream.id];
-    if (!tempStream) {
-      console.log("Undefined stream!");
-      return;
-    }
-    pc.addStream(tempStream);
-  };
-
-  // Return an array of Objects, each Object is a copy of RTCStateReport
-  // and has the following attributes (id, type, names, and stats).
-  // names: array originaly returned by calling RTCStateReport.names().
-  // stats: dictionary of stat name as key and stat value as dictionary
-  // value.
-  obj.getStats = function(callback, mediaTrack) {
-    pc.getStats(onStatsReady, mediaTrack);
-
-    function onStatsReady(stateResponse) {
-      var outputReports = [];
-      var reports = stateResponse.result();
-      for (index in reports) {
-        var report = {};
-        report.id = reports[index].id;
-        report.type = reports[index].type;
-        report.names = reports[index].names();
-        report.stats = [];
-        populateStats(reports[index], report.stats);
-
-        outputReports.push(report);
-      }
-
-      callback(outputReports);
-    }
-
-    function populateStats(report, stats) {
-      var names = report.names();
-      for (index in names) {
-        stats.push({
-           name: names[index],
-           stat: report.stat(names[index]),
-          });
-      }
-
-    }
-  };
-
-  pc.addEventListener('addstream', function(event) {
-    remoteStreams[event.stream.id] = event.stream;
-  });
-
-  doneCallback(obj);
-};
-
-function showStream(streamId, autoplay, muted) {
-  var stream = getStreamFromIdentifier_(streamId);
-  var video = document.createElement('video');
-  video.autoplay = autoplay;
-  video.muted = muted;
-  document.body.appendChild(video);
-  video.src = URL.createObjectURL(stream);
-  console.log("Stream " + stream.id + " attached to video element");
-};
-
-function getStreamFromIdentifier_(id) {
-  var tempStream = localStreams[id];
-  if (tempStream)
-    return tempStream;
-  tempStream = remoteStreams[id];
-  if (tempStream)
-    return tempStream;
-  console.log(id + " is not id for stream.");
-  return null;
-};
-
-function downloadFile(path, onSuccess, onError) {
-  var xhr = new XMLHttpRequest();
-  function onResult() {
-    if (xhr.readyState != 4)
-      return;
-
-    if (xhr.status != 200) {
-      onError("Download request failed!");
-      return;
-    }
-    onSuccess(xhr.responseText);
-  }
-
-  xhr.onreadystatechange = onResult;
-  xhr.open('GET', path, true);
-  xhr.send();
-};
-
-connectToServer({
-  ping: ping,
-  getUserMedia: getUserMedia,
-  createPeerConnection: createPeerConnection,
-  showStream: showStream,
-  downloadFile: downloadFile,
-});
diff --git a/rtc_tools/rtcbot/bot/browser/index.html b/rtc_tools/rtcbot/bot/browser/index.html
deleted file mode 100644
index 57bf5961..0000000
--- a/rtc_tools/rtcbot/bot/browser/index.html
+++ /dev/null
@@ -1,11 +0,0 @@
-<!--
-// Copyright (c) 2014 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.
--->
-<script src="../api.js"></script>
-<script src="bot.js"></script>
diff --git a/rtc_tools/rtcbot/botmanager.js b/rtc_tools/rtcbot/botmanager.js
deleted file mode 100644
index 5b325bd..0000000
--- a/rtc_tools/rtcbot/botmanager.js
+++ /dev/null
@@ -1,216 +0,0 @@
-// Copyright (c) 2014 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.
-//
-// botmanager.js module allows a test to spawn bots that expose an RPC API
-// to be controlled by tests.
-var https = require('https');
-var fs = require('fs');
-var child = require('child_process');
-var Browserify = require('browserify');
-var Dnode = require('dnode');
-var Express = require('express');
-var WebSocketServer = require('ws').Server;
-var WebSocketStream = require('websocket-stream');
-
-// BotManager runs a HttpsServer that serves bots assets and and WebSocketServer
-// that listens to incoming connections. Once a connection is available it
-// connects it to bots pending endpoints.
-//
-// TODO(andresp): There should be a way to control which bot was spawned
-// and what bot instance it gets connected to.
-BotManager = function () {
-  this.webSocketServer_ = null;
-  this.bots_ = [];
-  this.pendingConnections_ = [];
-  this.androidDeviceManager_ = new AndroidDeviceManager();
-}
-
-BotManager.BotTypes = {
-  CHROME : 'chrome',
-  ANDROID_CHROME : 'android-chrome',
-};
-
-BotManager.prototype = {
-  createBot_: function (name, botType, callback) {
-    switch(botType) {
-      case BotManager.BotTypes.CHROME:
-        return new BrowserBot(name, callback);
-      case BotManager.BotTypes.ANDROID_CHROME:
-        return new AndroidChromeBot(name, this.androidDeviceManager_,
-            callback);
-      default:
-        console.log('Error: Type ' + botType + ' not supported by rtc-Bot!');
-        process.exit(1);
-    }
-  },
-
-  spawnNewBot: function (name, botType, callback) {
-    this.startWebSocketServer_();
-    var bot = this.createBot_(name, botType, callback);
-    this.bots_.push(bot);
-    this.pendingConnections_.push(bot.onBotConnected.bind(bot));
-  },
-
-  startWebSocketServer_: function () {
-    if (this.webSocketServer_) return;
-
-    this.app_ = new Express();
-
-    this.app_.use('/bot/api.js',
-        this.serveBrowserifyFile_.bind(this,
-          __dirname + '/bot/api.js'));
-
-    this.app_.use('/bot/', Express.static(__dirname + '/bot'));
-
-    var options = options = {
-      key: fs.readFileSync('configurations/priv.pem', 'utf8'),
-      cert: fs.readFileSync('configurations/cert.crt', 'utf8')
-    };
-    this.server_ = https.createServer(options, this.app_);
-
-    this.webSocketServer_ = new WebSocketServer({ server: this.server_ });
-    this.webSocketServer_.on('connection', this.onConnection_.bind(this));
-
-    this.server_.listen(8080);
-  },
-
-  onConnection_: function (ws) {
-    var callback = this.pendingConnections_.shift();
-    callback(new WebSocketStream(ws));
-  },
-
-  serveBrowserifyFile_: function (file, request, result) {
-    // TODO(andresp): Cache browserify result for future serves.
-    var browserify = new Browserify();
-    browserify.add(file);
-    browserify.bundle().pipe(result);
-  }
-}
-
-// A basic bot waits for onBotConnected to be called with a stream to the actual
-// endpoint with the bot. Once that stream is available it establishes a dnode
-// connection and calls the callback with the other endpoint interface so the
-// test can interact with it.
-Bot = function (name, callback) {
-  this.name_ = name;
-  this.onbotready_ = callback;
-}
-
-Bot.prototype = {
-  log: function (msg) {
-    console.log("bot:" + this.name_ + " > " + msg);
-  },
-
-  name: function () { return this.name_; },
-
-  onBotConnected: function (stream) {
-    this.log('Connected');
-    this.stream_ = stream;
-    this.dnode_ = new Dnode();
-    this.dnode_.on('remote', this.onRemoteFromDnode_.bind(this));
-    this.dnode_.pipe(this.stream_).pipe(this.dnode_);
-  },
-
-  onRemoteFromDnode_: function (remote) {
-    this.onbotready_(remote);
-  }
-}
-
-// BrowserBot spawns a process to open "https://localhost:8080/bot/browser".
-//
-// That page once loaded, connects to the websocket server run by BotManager
-// and exposes the bot api.
-BrowserBot = function (name, callback) {
-  Bot.call(this, name, callback);
-  this.spawnBotProcess_();
-}
-
-BrowserBot.prototype = {
-  spawnBotProcess_: function () {
-    this.log('Spawning browser');
-    child.exec('google-chrome "https://localhost:8080/bot/browser/"');
-  },
-
-  __proto__: Bot.prototype
-}
-
-// AndroidChromeBot spawns a process to open
-// "https://localhost:8080/bot/browser/" on chrome for Android.
-AndroidChromeBot = function (name, androidDeviceManager, callback) {
-  Bot.call(this, name, callback);
-  androidDeviceManager.getNewDevice(function (serialNumber) {
-    this.serialNumber_ = serialNumber;
-    this.spawnBotProcess_();
-  }.bind(this));
-}
-
-AndroidChromeBot.prototype = {
-  spawnBotProcess_: function () {
-    this.log('Spawning Android device with serial ' + this.serialNumber_);
-    var runChrome = 'adb -s ' + this.serialNumber_ + ' shell am start ' +
-    '-n com.android.chrome/com.google.android.apps.chrome.Main ' +
-    '-d https://localhost:8080/bot/browser/';
-    child.exec(runChrome, function (error, stdout, stderr) {
-      if (error) {
-        this.log(error);
-        process.exit(1);
-      }
-      this.log('Opening Chrome for Android...');
-      this.log(stdout);
-    }.bind(this));
-  },
-
-  __proto__: Bot.prototype
-}
-
-AndroidDeviceManager = function () {
-  this.connectedDevices_ = [];
-}
-
-AndroidDeviceManager.prototype = {
-  getNewDevice: function (callback) {
-    this.listDevices_(function (devices) {
-      for (var i = 0; i < devices.length; i++) {
-        if (!this.connectedDevices_[devices[i]]) {
-          this.connectedDevices_[devices[i]] = devices[i];
-          callback(this.connectedDevices_[devices[i]]);
-          return;
-        }
-      }
-      if (devices.length == 0) {
-        console.log('Error: No connected devices!');
-      } else {
-        console.log('Error: There is no enough connected devices.');
-      }
-      process.exit(1);
-    }.bind(this));
-  },
-
-  listDevices_: function (callback) {
-    child.exec('adb devices' , function (error, stdout, stderr) {
-      var devices = [];
-      if (error || stderr) {
-        console.log(error || stderr);
-      }
-      if (stdout) {
-        // The first line is "List of devices attached"
-        // and the following lines:
-        // <serial number>  <device/emulator>
-        var tempList = stdout.split("\n").slice(1);
-        for (var i = 0; i < tempList.length; i++) {
-          if (tempList[i] == "") {
-            continue;
-          }
-          devices.push(tempList[i].split("\t")[0]);
-        }
-      }
-      callback(devices);
-    });
-  },
-}
-module.exports = BotManager;
diff --git a/rtc_tools/rtcbot/main.js b/rtc_tools/rtcbot/main.js
deleted file mode 100644
index 665f6e8..0000000
--- a/rtc_tools/rtcbot/main.js
+++ /dev/null
@@ -1,102 +0,0 @@
-// Copyright (c) 2014 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.
-//
-// This script loads all the test/* files into a very small context that
-// only exposes a minimal set of functions that allows to register tests.
-//
-// Once all files are loaded it runs the specific test on the command line.
-// If no arguments are given it lists all the registered tests.
-//
-// Note: the small context where the scripts are loaded is intended to keep
-// nodejs-isms away from the test code and isolate implementation details away
-// from them.
-var fs = require('fs');
-var vm = require('vm');
-var Test = require('./test.js');
-
-var testSuites = {};
-
-function registerTest(name, func) {
-  testSuites[name] = func;
-}
-
-function registerBotTest(name, func, bots) {
-  registerTest(name, bootstrap);
-
-  function bootstrap(test) {
-    var callbacks = [];
-    for (var i = 0; i != bots.length; ++i)
-      callbacks.push(test.spawnBot.bind(test, "", bots[i]));
-
-    test.wait(callbacks, func.bind(test, test));
-  }
-}
-
-function loadTestFile(filename, doneCallback) {
-  var loadTestContext = {
-    setTimeout: setTimeout,
-    registerTest: registerTest,
-    registerBotTest: registerBotTest
-  };
-  var script = vm.createScript(fs.readFileSync(filename), filename);
-  script.runInNewContext(loadTestContext);
-  doneCallback();
-}
-
-function iterateOverTestFiles(foreachCallback, doneCallback) {
-  fs.readdir('test', function (error, list) {
-    function iterateNextFile() {
-      if (list.length === 0) {
-        doneCallback();
-      } else {
-        var filename = list.pop();
-        if (filename[0] === '.' || filename.slice(-3) !== '.js') {
-          // Skip hidden and non .js files on that directory.
-          iterateNextFile();
-        } else {
-          foreachCallback('test/' + filename, iterateNextFile);
-        }
-      }
-    }
-
-    if (error !== null) {
-      throw error;
-    }
-    iterateNextFile();
-  });
-}
-
-function runTest(testname) {
-  if (testname in testSuites) {
-    console.log("Running test: " + testname);
-    var test = new Test();
-    testSuites[testname](test);
-  } else {
-    console.log("Unknown test: " + testname);
-  }
-}
-
-function printUsage() {
-  console.log('Run as:\n $ '
-      + process.argv[0] + ' ' + process.argv[1]
-      + ' <testname>');
-  console.log('These are the existent ones:');
-  for (var testname in testSuites)
-    console.log('  ' + testname);
-}
-
-function main() {
-  // TODO(andresp): support multiple tests.
-  var testList = process.argv.slice(2);
-  if (testList.length === 1)
-    runTest(testList[0]);
-  else
-    printUsage();
-}
-
-iterateOverTestFiles(loadTestFile, main);
diff --git a/rtc_tools/rtcbot/rtcBotReportVisualizer/index.html b/rtc_tools/rtcbot/rtcBotReportVisualizer/index.html
deleted file mode 100644
index 7ff59fc..0000000
--- a/rtc_tools/rtcbot/rtcBotReportVisualizer/index.html
+++ /dev/null
@@ -1,14 +0,0 @@
-<!--
-// Copyright (c) 2014 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.
--->
-<html>
-  <script src="https://www.google.com/jsapi"></script>
-  <script type="text/javascript" src="main.js"></script>
-  <input type="file" onchange="openFiles(event)" multiple>
-</html>
\ No newline at end of file
diff --git a/rtc_tools/rtcbot/rtcBotReportVisualizer/main.js b/rtc_tools/rtcbot/rtcBotReportVisualizer/main.js
deleted file mode 100644
index 91b0eec..0000000
--- a/rtc_tools/rtcbot/rtcBotReportVisualizer/main.js
+++ /dev/null
@@ -1,191 +0,0 @@
-// Copyright (c) 2014 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.
-//
-google.load("visualization", "1", {packages:["corechart"]});
-
-function openFiles(event) {
-  var files = event.target.files;
-  readAndAnalyzeFiles(files)
-}
-
-function readAndAnalyzeFiles(files) {
-  if(!files) {
-    alert("No files have been selected!");
-    return;
-  }
-
-  var reports = [];
-  var filesNames = [];
-  missingFiles = files.length;
-
-  for(var i = 0; i < files.length; i++) {
-    var reader = new FileReader();
-    reader.onload = onReaderLoad.bind(reader, files[i].name);
-    reader.readAsText(files[i]);
-  }
-
-  function onReaderLoad(fileName) {
-    reports.push(JSON.parse(this.result));
-    filesNames.push(fileName);
-
-    missingFiles--;
-    if(missingFiles == 0) {
-      analyzeReports_(reports, filesNames);
-    }
-  }
-}
-
-// TODO(houssainy) take the input stats from the select list or
-// drop down menu in html.
-function analyzeReports_(reports, filesNames) {
-  filesNames.unshift(""); // ned
-
-  // Rtt
-  analyzeRttData(reports, filesNames, "bot1");
-  analyzeRttData(reports, filesNames, "bot2");
-
-  // Send Packets Lost
-  analyzePacketsLostData(reports, filesNames, "bot1");
-  analyzePacketsLostData(reports, filesNames, "bot2");
-
-  // Send bandwidth
-  analyzeData(reports, filesNames, "Available Send Bandwidth-bot1", "bot1",
-      "bweforvideo", "googAvailableSendBandwidth");
-  analyzeData(reports, filesNames, "Available Send Bandwidth-bot2", "bot2",
-      "bweforvideo", "googAvailableSendBandwidth");
-
-   // Receive bandwidth
-   analyzeData(reports, filesNames, "Available Receive Bandwidth-bot1", "bot1",
-       "bweforvideo", "googAvailableReceiveBandwidth");
-   analyzeData(reports, filesNames, "Available Receive Bandwidth-bot2", "bot2",
-     "bweforvideo", "googAvailableReceiveBandwidth");
-
-  drawSeparatorLine();
-}
-
-function analyzeRttData(reports, filesNames, botName) {
-  var outPut = [];
-  outPut.push(filesNames);
-
-  var avergaData = ['Average Rtt x10'];
-  var maxData = ['Max Rtt'];
-
-  var average;
-  var max;
-  for(var index in reports) {
-    average = getStateAverage(reports[index], botName, "Conn-audio-1-0",
-      "googRtt");
-    avergaData.push(average*10);
-
-    max = getStateMax(reports[index], botName, "Conn-audio-1-0",
-      "googRtt");
-    maxData.push(max);
-  }
-  outPut.push(avergaData);
-  outPut.push(maxData);
-
-  drawChart("Rtt-" + botName, outPut);
-}
-
-function analyzePacketsLostData(reports, filesNames, botName) {
-  var outPut = [];
-  outPut.push(filesNames);
-
-  var maxData = ['Max Send PacketsLost'];
-  var max;
-  for(var index in reports) {
-    max = getStateMax(reports[index], botName, "ssrc_[0-9]+_send",
-        "packetsLost");
-    maxData.push(max);
-  }
-  outPut.push(maxData);
-
-  drawChart("Send PacketsLost-" + botName, outPut);
-}
-
-function analyzeData(reports, filesNames, chartName, botName, reportId,
-    statName) {
-  var outPut = [];
-  outPut.push(filesNames);
-
-  var avergaData = ['Average ' + statName];
-  var maxData = ['Max ' + statName];
-
-  var average;
-  var max;
-  for(var index in reports) {
-    average = getStateAverage(reports[index], botName, reportId, statName);
-    avergaData.push(average);
-
-    max = getStateMax(reports[index], botName, reportId, statName);
-    maxData.push(max);
-  }
-  outPut.push(avergaData);
-  outPut.push(maxData);
-
-  drawChart(chartName, outPut);
-}
-
-function getStateAverage(reports, botName, reportId, statName) {
-  var sum = 0;
-  var count = 0;
-
-  for (var index in reports) {
-    var data = reports[index].data;
-    if(index == 0 || !data.hasOwnProperty(botName))
-      continue;
-
-    var stats = data[botName];
-    for (var key in stats) {
-      if(key.search(reportId) != -1) {
-        var value = parseInt(stats[key][statName]);
-        sum += value;
-        count++;
-      }
-    }
-  }
-  return Math.round(sum/count);
-}
-
-function getStateMax(reports, botName, reportId, statName) {
-  var max = -1;
-
-  for (var index in reports) {
-    var data = reports[index].data;
-    if(index == 0 || !data.hasOwnProperty(botName))
-      continue;
-
-    var stats = data[botName];
-    for (var key in stats) {
-      if(key.search(reportId) != -1) {
-        var value = parseInt(stats[key][statName]);
-        max = Math.max(value, max);
-      }
-    }
-  }
-  return max;
-}
-
-function drawChart(title, data) {
-  var dataTable = google.visualization.arrayToDataTable(data);
-
-  var options = {
-    title: title,
-  };
-
-  var div = document.createElement('div');
-  document.body.appendChild(div);
-
-  var chart = new google.visualization.ColumnChart(div);
-  chart.draw(dataTable, options);
-}
-
-function drawSeparatorLine()  {
-  var hr = document.createElement('hr');
-  document.body.appendChild(hr);
-}
diff --git a/rtc_tools/rtcbot/test.js b/rtc_tools/rtcbot/test.js
deleted file mode 100644
index 33ef960..0000000
--- a/rtc_tools/rtcbot/test.js
+++ /dev/null
@@ -1,155 +0,0 @@
-// Copyright (c) 2014 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.
-//
-// Provides a Test class that exposes api to the tests.
-// Read test.prototype to see what methods are exposed.
-var fs = require('fs');
-var request = require('request');
-var BotManager = require('./botmanager.js');
-
-function Test() {
-  this.timeout_ = setTimeout(
-      this.fail.bind(this, "Test timeout!"),
-      100000);
-}
-
-Test.prototype = {
-  log: function () {
-    console.log.apply(console.log, arguments);
-  },
-
-  abort: function (error) {
-    var error = new Error(error || "Test aborted");
-    console.log(error.stack);
-    process.exit(1);
-  },
-
-  assert: function (value, message) {
-    if (value !== true) {
-      this.abort(message || "Assert failed.");
-    }
-  },
-
-  fail: function () {
-    this.assert(false, "Test failed.");
-  },
-
-  done: function () {
-    clearTimeout(this.timeout_);
-    console.log("Test succeeded");
-    process.exit(0);
-  },
-
-  // Utility method to wait for multiple callbacks to be executed.
-  //  functions - array of functions to call with a callback.
-  //  doneCallback - called when all callbacks on the array have completed.
-  wait: function (functions, doneCallback) {
-    var result = new Array(functions.length);
-    var missingResult = functions.length;
-    for (var i = 0; i != functions.length; ++i)
-      functions[i](complete.bind(this, i));
-
-    function complete(index, value) {
-      missingResult--;
-      result[index] = value;
-      if (missingResult == 0)
-        doneCallback.apply(null, result);
-    }
-  },
-
-  spawnBot: function (name, botType, doneCallback) {
-    // Lazy initialization of botmanager.
-    if (!this.botManager_)
-      this.botManager_ = new BotManager();
-    this.botManager_.spawnNewBot(name, botType, doneCallback);
-  },
-
-  createStatisticsReport: function (outputFileName) {
-    return new StatisticsReport(outputFileName);
-  },
-
-  // Ask computeengineondemand to give us TURN server credentials and URIs.
-  createTurnConfig: function (onSuccess, onError) {
-    request('https://computeengineondemand.appspot.com/turn?username=1234&key=5678',
-        function (error, response, body) {
-          if (error || response.statusCode != 200) {
-            onError('TURN request failed');
-            return;
-          }
-
-          var response = JSON.parse(body);
-          var iceServer = {
-            'username': response.username,
-            'credential': response.password,
-            'urls': response.uris
-          };
-          onSuccess({ 'iceServers': [ iceServer ] });
-        }
-      );
-  },
-}
-
-StatisticsReport = function (outputFileName) {
-  this.output_ = [];
-  this.output_.push("Version: 1");
-  this.outputFileName_ = outputFileName;
-}
-
-StatisticsReport.prototype = {
-  collectStatsFromPeerConnection: function (prefix, pc) {
-    setInterval(this.addPeerConnectionStats.bind(this, prefix, pc), 100);
-  },
-
-  addPeerConnectionStats: function (prefix, pc) {
-    pc.getStats(onStatsReady.bind(this));
-
-    function onStatsReady(reports) {
-      for (index in reports) {
-        var stats = {};
-        stats[reports[index].id] = collectStats(reports[index].stats);
-
-        var data = {};
-        data[prefix] = stats;
-
-        this.output_.push({
-            type: "UpdateCounters",
-            startTime: (new Date()).getTime(),
-            data: data,
-          });
-      }
-    };
-
-    function collectStats(stats) {
-      var outputStats = {};
-      for (index in stats) {
-        var statValue = parseFloat(stats[index].stat);
-        outputStats[stats[index].name] = isNaN(statValue)?
-            stats[index].stat : statValue;
-      }
-      return outputStats;
-    };
-  },
-
-  finish: function (doneCallback) {
-    fs.exists("test/reports/", function (exists) {
-      if(exists) {
-        writeFile.bind(this)();
-      } else {
-        fs.mkdir("test/reports/", 0777, writeFile.bind(this));
-      }
-    }.bind(this));
-
-    function writeFile () {
-      fs.writeFile("test/reports/" + this.outputFileName_ + "_" +
-        (new Date()).getTime() +".json", JSON.stringify(this.output_),
-        doneCallback);
-    }
-  },
-};
-
-module.exports = Test;
diff --git a/rtc_tools/rtcbot/test/oneWayVideoStreamingWithDownloadingFile.js b/rtc_tools/rtcbot/test/oneWayVideoStreamingWithDownloadingFile.js
deleted file mode 100644
index 857d838..0000000
--- a/rtc_tools/rtcbot/test/oneWayVideoStreamingWithDownloadingFile.js
+++ /dev/null
@@ -1,122 +0,0 @@
-// Copyright (c) 2014 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.
-//
-// A unidirectional video and audio flowing test from bot 1 to bot 2,
-// and download a file from a server after 2 seconds of establishing
-// the call.
-//
-// The test succeeds after collecting stats for 10 seconds from both bots
-// and then write these stats to a file.
-//
-// Note: the source of the video and audio stream is getUserMedia().
-//
-function testOneWayVideoWithDownloading(test, bot1, bot2) {
-  var report = test.createStatisticsReport("testOneWayVideoWithDownloading");
-
-  test.wait([
-      createPeerConnection.bind(bot1),
-      createPeerConnection.bind(bot2) ],
-    onPeerConnectionCreated);
-
-  function createPeerConnection(done) {
-    test.createTurnConfig(onTurnConfig.bind(this), test.fail);
-
-    function onTurnConfig(config) {
-      this.createPeerConnection(config, done, test.fail);
-    };
-  }
-
-  function onPeerConnectionCreated(pc1, pc2) {
-    test.log("RTC Peers created.");
-    pc1.addEventListener('addstream', test.fail);
-    pc2.addEventListener('addstream', onAddStream);
-    pc1.addEventListener('icecandidate', onIceCandidate.bind(pc2));
-    pc2.addEventListener('icecandidate', onIceCandidate.bind(pc1));
-
-    bot1.getUserMedia({video:true, audio:true}, onUserMediaSuccess, test.fail);
-
-    function onUserMediaSuccess(stream) {
-      test.log("User has granted access to local media.");
-      pc1.addStream(stream);
-      bot1.showStream(stream.id, true, true);
-
-      createOfferAndAnswer(pc1, pc2);
-    }
-  }
-
-  function onAddStream(event) {
-    test.log("On Add stream.");
-    bot2.showStream(event.stream.id, true, false);
-  }
-
-  function onIceCandidate(event) {
-    if(event.candidate) {
-      test.log(event.candidate.candidate);
-      this.addIceCandidate(event.candidate,
-         onAddIceCandidateSuccess, test.fail);
-    }
-
-    function onAddIceCandidateSuccess() {
-      test.log("Candidate added successfully");
-    }
-  }
-
-  function createOfferAndAnswer(pc1, pc2) {
-    test.log("Creating offer.");
-    pc1.createOffer(gotOffer, test.fail);
-
-    function gotOffer(offer) {
-      test.log("Got offer");
-      pc1.setLocalDescription(offer, onSetSessionDescriptionSuccess, test.fail);
-      pc2.setRemoteDescription(offer, onSetSessionDescriptionSuccess,
-          test.fail);
-      test.log("Creating answer");
-      pc2.createAnswer(gotAnswer, test.fail);
-    }
-
-    function gotAnswer(answer) {
-      test.log("Got answer");
-      pc2.setLocalDescription(answer, onSetSessionDescriptionSuccess,
-          test.fail);
-      pc1.setRemoteDescription(answer, onSetSessionDescriptionSuccess,
-          test.fail);
-      collectStats();
-
-      setTimeout(function() {
-        downloadFile(bot1, "bot1");
-        downloadFile(bot2, "bot2");
-      }, 2000);
-    }
-
-    function onSetSessionDescriptionSuccess() {
-      test.log("Set session description success.");
-    }
-
-    function collectStats() {
-      report.collectStatsFromPeerConnection("bot1", pc1);
-      report.collectStatsFromPeerConnection("bot2", pc2);
-
-      setTimeout(function() {
-        report.finish(test.done);
-        }, 10000);
-    }
-
-    function downloadFile(bot, name) {
-      bot.downloadFile("https://test.webrtc.org/test-download-file/9000KB.data",
-          onDownloadSuccess.bind(null, name), test.fail);
-
-      function onDownloadSuccess(name, data) {
-        test.log( name + " downloaded " +
-            Math.round(data.length/(1024*1024)) + "MB.");
-      }
-    }
-  }
-}
-
-registerBotTest('testOneWayVideoWithDownloading/chrome-chrome',
-                testOneWayVideoWithDownloading, ['chrome', 'chrome']);
diff --git a/rtc_tools/rtcbot/test/ping_pong.js b/rtc_tools/rtcbot/test/ping_pong.js
deleted file mode 100644
index 1d9886e..0000000
--- a/rtc_tools/rtcbot/test/ping_pong.js
+++ /dev/null
@@ -1,20 +0,0 @@
-// Copyright (c) 2014 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.
-//
-function testPingPong(test, bot) {
-  test.assert(typeof bot.ping === 'function', 'Bot does not exposes ping.');
-
-  bot.ping(gotAnswer);
-
-  function gotAnswer(answer) {
-    test.log('bot > ' + answer);
-    test.done();
-  }
-}
-
-registerBotTest('testPingPong/chrome', testPingPong, ['chrome']);
diff --git a/rtc_tools/rtcbot/test/simple_offer_answer.js b/rtc_tools/rtcbot/test/simple_offer_answer.js
deleted file mode 100644
index 888662a..0000000
--- a/rtc_tools/rtcbot/test/simple_offer_answer.js
+++ /dev/null
@@ -1,48 +0,0 @@
-// Copyright (c) 2014 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.
-//
-// Test that offer/answer between 2 peers completes successfully.
-//
-// Note: This test does not performs ice candidate exchange and
-// does not verifies that media can flow between the peers.
-function testOfferAnswer(test, bot1, bot2) {
-  test.wait( [ bot1.createPeerConnection.bind(bot1, null),
-               bot2.createPeerConnection.bind(bot2, null) ],
-            run);
-
-  function run(pc1, pc2) {
-    test.log("Establishing call.");
-    pc1.createOffer(gotOffer);
-
-    function gotOffer(offer) {
-      test.log("Got offer");
-      expectedCall();
-      pc1.setLocalDescription(offer, expectedCall, test.fail);
-      pc2.setRemoteDescription(offer, expectedCall, test.fail);
-      pc2.createAnswer(gotAnswer, test.fail);
-    }
-
-    function gotAnswer(answer) {
-      test.log("Got answer");
-      expectedCall();
-      pc2.setLocalDescription(answer, expectedCall, test.fail);
-      pc1.setRemoteDescription(answer, expectedCall, test.fail);
-    }
-
-    // TODO(andresp): Implement utilities in test to write expectations
-    // that certain methods must be called.
-    var expectedCalls = 0;
-    function expectedCall() {
-      if (++expectedCalls == 6)
-        test.done();
-    }
-  }
-}
-
-registerBotTest('testOfferAnswer/chrome-chrome',
-                testOfferAnswer, ['chrome', 'chrome']);
diff --git a/rtc_tools/rtcbot/test/three_bots_video_conference.js b/rtc_tools/rtcbot/test/three_bots_video_conference.js
deleted file mode 100644
index 65c3e99..0000000
--- a/rtc_tools/rtcbot/test/three_bots_video_conference.js
+++ /dev/null
@@ -1,135 +0,0 @@
-// Copyright (c) 2014 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.
-//
-// A video conference between 3 bots streaming video and audio between
-// each other.
-// The test succeeds after establishing the call between the three
-// devices.
-//
-// Note: the source of the video and audio stream is getUserMedia().
-function testTwoWayVideoStreaming(test, bot1, bot2, bot3) {
-  var answersCount = 0;
-  var statsCollector;
-
-  test.wait([
-      createBotPeerConnectionsWithLocalStream.bind(bot1),
-      createBotPeerConnectionsWithLocalStream.bind(bot2),
-      createBotPeerConnectionsWithLocalStream.bind(bot3)],
-    onPeerConnectionCreated);
-
-  // done() callback is called with list of peers as argument.
-  function createBotPeerConnectionsWithLocalStream(done) {
-    var peerConnections = [];
-
-    this.getUserMedia({video:true, audio:true},
-        onUserMediaSuccess.bind(this), test.fail);
-
-    function onUserMediaSuccess(stream) {
-      test.log("User has granted access to local media.");
-      this.showStream(stream.id, true, true);
-
-      test.createTurnConfig(onTurnConfig.bind(this), test.fail);
-
-      function onTurnConfig(config) {
-        this.createPeerConnection(config, addStream.bind(this),
-            test.fail);
-        this.createPeerConnection(config, addStream.bind(this),
-            test.fail);
-      }
-
-      function addStream(pc) {
-        pc.addStream(stream);
-        pc.addEventListener('addstream', onAddStream.bind(this));
-
-        peerConnections.push(pc);
-        if(peerConnections.length == 2)
-          done(peerConnections);
-      }
-    }
-  }
-
-  function onPeerConnectionCreated(peerConnections1,
-      peerConnections2, peerConnections3) {
-    test.log("RTC Peers created.");
-
-    // Bot1 and Bot2
-    establichCall(peerConnections1[0], peerConnections2[1]);
-    // Bot2 and Bot3
-    establichCall(peerConnections2[0], peerConnections3[1]);
-    // Bot3 and Bot1
-    establichCall(peerConnections3[0], peerConnections1[1]);
-  }
-
-  function establichCall(pc1, pc2) {
-    pc1.addEventListener('icecandidate', onIceCandidate.bind(pc2));
-    pc2.addEventListener('icecandidate', onIceCandidate.bind(pc1));
-
-    createOfferAndAnswer(pc1, pc2);
-  }
-
-  function onAddStream(event) {
-    test.log("On Add stream.");
-    this.showStream(event.stream.id, true, false);
-  }
-
-  function onIceCandidate(event) {
-    if(event.candidate) {
-      this.addIceCandidate(event.candidate,
-         onAddIceCandidateSuccess, test.fail);
-    };
-
-    function onAddIceCandidateSuccess() {
-      test.log("Candidate added successfully");
-    };
-  }
-
-  function createOfferAndAnswer(pc1, pc2) {
-    test.log("Creating offer.");
-    pc1.createOffer(gotOffer, test.fail);
-
-    function gotOffer(offer) {
-      test.log("Got offer");
-      pc1.setLocalDescription(offer, onSetSessionDescriptionSuccess, test.fail);
-      pc2.setRemoteDescription(offer, onSetSessionDescriptionSuccess,
-          test.fail);
-      test.log("Creating answer");
-      pc2.createAnswer(gotAnswer, test.fail);
-    }
-
-    function gotAnswer(answer) {
-      test.log("Got answer");
-      pc2.setLocalDescription(answer, onSetSessionDescriptionSuccess,
-          test.fail);
-      pc1.setRemoteDescription(answer, onSetSessionDescriptionSuccess,
-          test.fail);
-
-      answersCount++;
-      if(answersCount == 3) {
-        // SetTimeout used because creating the three answers will very fast
-        // and test will success and the vm will be closed before establishing
-        // the calls.
-        setTimeout(function() {
-            test.done();
-          }, 5000);
-      }
-    }
-
-    function onSetSessionDescriptionSuccess() {
-      test.log("Set session description success.");
-    }
-  }
-}
-
-registerBotTest('threeBotsVideoConference/android+android+chrome',
-                testTwoWayVideoStreaming, ['android-chrome', 'android-chrome',
-                'chrome']);
-registerBotTest('threeBotsVideoConference/chrome-chrome-chrome',
-                testTwoWayVideoStreaming, ['chrome', 'chrome', 'chrome']);
-registerBotTest('threeBotsVideoConference/android-android-android',
-                testTwoWayVideoStreaming, ['android-chrome', 'android-chrome',
-                'android-chrome']);
\ No newline at end of file
diff --git a/rtc_tools/rtcbot/test/two_way_video_streaming.js b/rtc_tools/rtcbot/test/two_way_video_streaming.js
deleted file mode 100644
index 7b02dce..0000000
--- a/rtc_tools/rtcbot/test/two_way_video_streaming.js
+++ /dev/null
@@ -1,112 +0,0 @@
-// Copyright (c) 2014 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.
-//
-// A two way video and audio flowing test between bot 1 and bot 2.
-// The test succeeds after collecting stats for 10 seconds from both bots
-// and then write these stats to a file.
-//
-// Note: the source of the video and audio stream is getUserMedia().
-function testTwoWayVideoStreaming(test, bot1, bot2) {
-  var report = test.createStatisticsReport("two_way_video_streaming");
-  var statsCollector;
-
-  test.wait([
-      createPeerConnectionWithLocalStream.bind(bot1),
-      createPeerConnectionWithLocalStream.bind(bot2)],
-    onPeerConnectionCreated);
-
-  function createPeerConnectionWithLocalStream(done) {
-    this.getUserMedia({video:true, audio:true},
-        onUserMediaSuccess.bind(this), test.fail);
-
-    function onUserMediaSuccess(stream) {
-      test.log("User has granted access to local media.");
-      test.createTurnConfig(onTurnConfig.bind(this), test.fail);
-
-      function onTurnConfig(config) {
-        this.createPeerConnection(config, addAndShowStream.bind(this),
-            test.fail);
-      };
-
-      function addAndShowStream(pc) {
-        pc.addStream(stream);
-        this.showStream(stream.id, true, true);
-
-        done(pc);
-      }
-    }
-  }
-
-  function onPeerConnectionCreated(pc1, pc2) {
-    test.log("RTC Peers created.");
-    pc1.addEventListener('addstream', onAddStream.bind(bot1));
-    pc2.addEventListener('addstream', onAddStream.bind(bot2));
-    pc1.addEventListener('icecandidate', onIceCandidate.bind(pc2));
-    pc2.addEventListener('icecandidate', onIceCandidate.bind(pc1));
-
-    createOfferAndAnswer(pc1, pc2);
-  }
-
-  function onAddStream(event) {
-    test.log("On Add stream.");
-    this.showStream(event.stream.id, true, false);
-  }
-
-  function onIceCandidate(event) {
-    if(event.candidate) {
-      test.log(event.candidate.candidate);
-      this.addIceCandidate(event.candidate,
-         onAddIceCandidateSuccess, test.fail);
-    };
-
-    function onAddIceCandidateSuccess() {
-      test.log("Candidate added successfully");
-    };
-  }
-
-  function createOfferAndAnswer(pc1, pc2) {
-    test.log("Creating offer.");
-    pc1.createOffer(gotOffer, test.fail);
-
-    function gotOffer(offer) {
-      test.log("Got offer");
-      pc1.setLocalDescription(offer, onSetSessionDescriptionSuccess, test.fail);
-      pc2.setRemoteDescription(offer, onSetSessionDescriptionSuccess,
-          test.fail);
-      test.log("Creating answer");
-      pc2.createAnswer(gotAnswer, test.fail);
-    }
-
-    function gotAnswer(answer) {
-      test.log("Got answer");
-      pc2.setLocalDescription(answer, onSetSessionDescriptionSuccess,
-          test.fail);
-      pc1.setRemoteDescription(answer, onSetSessionDescriptionSuccess,
-          test.fail);
-      collectStats();
-    }
-
-    function onSetSessionDescriptionSuccess() {
-      test.log("Set session description success.");
-    }
-
-    function collectStats() {
-      report.collectStatsFromPeerConnection("bot1", pc1);
-      report.collectStatsFromPeerConnection("bot2", pc2);
-
-      setTimeout(function() {
-        report.finish(test.done);
-        }, 10000);
-    }
-  }
-}
-
-registerBotTest('testTwoWayVideo/android-android',
-                testTwoWayVideoStreaming, ['android-chrome', 'android-chrome']);
-registerBotTest('testTwoWayVideo/chrome-chrome',
-                testTwoWayVideoStreaming, ['chrome', 'chrome']);
\ No newline at end of file
diff --git a/rtc_tools/rtcbot/test/webrtc_video_streaming.js b/rtc_tools/rtcbot/test/webrtc_video_streaming.js
deleted file mode 100644
index 6518c20..0000000
--- a/rtc_tools/rtcbot/test/webrtc_video_streaming.js
+++ /dev/null
@@ -1,103 +0,0 @@
-// Copyright (c) 2014 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.
-//
-// A unidirectional video and audio flowing test from bot 1 to bot 2.
-// The test succeeds after collecting stats for 10 seconds from both bots
-// and then write these stats to a file.
-//
-// Note: the source of the video and audio stream is getUserMedia().
-function testOneWayVideo(test, bot1, bot2) {
-  var report = test.createStatisticsReport("webrtc_video_streaming");
-
-  test.wait([
-      createPeerConnection.bind(bot1),
-      createPeerConnection.bind(bot2) ],
-    onPeerConnectionCreated);
-
-  function createPeerConnection(done) {
-    test.createTurnConfig(onTurnConfig.bind(this), test.fail);
-
-    function onTurnConfig(config) {
-      this.createPeerConnection(config, done, test.fail);
-    };
-  }
-
-  function onPeerConnectionCreated(pc1, pc2) {
-    test.log("RTC Peers created.");
-    pc1.addEventListener('addstream', test.fail);
-    pc2.addEventListener('addstream', onAddStream);
-    pc1.addEventListener('icecandidate', onIceCandidate.bind(pc2));
-    pc2.addEventListener('icecandidate', onIceCandidate.bind(pc1));
-
-    bot1.getUserMedia({video:true, audio:true}, onUserMediaSuccess, test.fail);
-
-    function onUserMediaSuccess(stream) {
-      test.log("User has granted access to local media.");
-      pc1.addStream(stream);
-      bot1.showStream(stream.id, true, true);
-
-      createOfferAndAnswer(pc1, pc2);
-    }
-  }
-
-  function onAddStream(event) {
-    test.log("On Add stream.");
-    bot2.showStream(event.stream.id, true, false);
-  }
-
-  function onIceCandidate(event) {
-    if(event.candidate) {
-      test.log(event.candidate.candidate);
-      this.addIceCandidate(event.candidate,
-         onAddIceCandidateSuccess, test.fail);
-    }
-
-    function onAddIceCandidateSuccess() {
-      test.log("Candidate added successfully");
-    }
-  }
-
-  function createOfferAndAnswer(pc1, pc2) {
-    test.log("Creating offer.");
-    pc1.createOffer(gotOffer, test.fail);
-
-    function gotOffer(offer) {
-      test.log("Got offer");
-      pc1.setLocalDescription(offer, onSetSessionDescriptionSuccess, test.fail);
-      pc2.setRemoteDescription(offer, onSetSessionDescriptionSuccess,
-          test.fail);
-      test.log("Creating answer");
-      pc2.createAnswer(gotAnswer, test.fail);
-    }
-
-    function gotAnswer(answer) {
-      test.log("Got answer");
-      pc2.setLocalDescription(answer, onSetSessionDescriptionSuccess,
-          test.fail);
-      pc1.setRemoteDescription(answer, onSetSessionDescriptionSuccess,
-          test.fail);
-      collectStats();
-    }
-
-    function onSetSessionDescriptionSuccess() {
-      test.log("Set session description success.");
-    }
-
-    function collectStats() {
-      report.collectStatsFromPeerConnection("bot1", pc1);
-      report.collectStatsFromPeerConnection("bot2", pc2);
-
-      setTimeout(function() {
-        report.finish(test.done);
-        }, 10000);
-    }
-  }
-}
-
-registerBotTest('testOneWayVideo/chrome-chrome',
-                testOneWayVideo, ['chrome', 'chrome']);
