commit f91ea0d4fbf8c776b73dda345d60239b353abd25 Author: Chang Lan changlan9@gmail.com Date: Sun Apr 6 01:27:40 2014 -0700
Fix lots of bugs. --- chrome/app/background.js | 33 ++++++++--- chrome/extension/background.js | 122 +++++++++++++++++++++++++++------------- 2 files changed, 109 insertions(+), 46 deletions(-)
diff --git a/chrome/app/background.js b/chrome/app/background.js index 4355266..1ce4d32 100644 --- a/chrome/app/background.js +++ b/chrome/app/background.js @@ -36,6 +36,13 @@ function onListenCallback(socketId, resultCode) { } serverSocketId = socketId; chrome.sockets.tcpServer.onAccept.addListener(onAccept); + chrome.sockets.tcpServer.onAcceptError.addListener(function(info) { + console.log("onAcceptError " + JSON.stringify(info)); + }); + chrome.sockets.tcp.onReceive.addListener(onReceive); + chrome.sockets.tcp.onReceiveError.addListener(function(info) { + console.log("onReceiveError " + JSON.stringify(info)); + }); }
function onAccept(info) { @@ -43,19 +50,19 @@ function onAccept(info) { if (info.socketId != serverSocketId) return;
- chrome.sockets.tcp.onReceive.addListener(onReceive); chrome.sockets.tcp.setPaused(info.clientSocketId, false); }
function readIntoBuf(data) { + console.log("readIntoBuf " + "bytesToRead: " + bytesToRead + ", datalen: " + data.byteLength + ", buflen: " + buf.length); var n = Math.min(data.byteLength, bytesToRead); - buf.subarray(buf.length - bytesToRead, n).set(new Uint8Array(data.slice(0, n))); + buf.set(new Uint8Array(data.slice(0, n)), buf.length - bytesToRead); bytesToRead -= n; return data.slice(n); }
function onReceive(info) { - console.log("onReceive " + JSON.stringify(info)); + console.log("onReceive " + JSON.stringify(info) + " len: " + info.data.byteLength); var data = info.data; switch (state) { case STATE_READING_LENGTH: @@ -85,13 +92,22 @@ function onReceive(info) { } }
-function makeRequest(request, client_socket) { - chrome.runtime.sendMessage(EXTENSION_ID, request, function(response) { - returnResponse(response, client_socket); +function makeRequest(request, socketId) { + console.log("makeRequest " + JSON.stringify(request)); + + port = chrome.runtime.connect(EXTENSION_ID); + port.onMessage.addListener(function(response) { + returnResponse(response, socketId); + port.disconnect(); + }); + port.onDisconnect.addListener(function() { + console.log("onDisconnect"); }); + port.postMessage(request); }
-function returnResponse(response, client_socket) { +function returnResponse(response, socketId) { + console.log("returnResponse " + JSON.stringify(response)); var str = JSON.stringify(response); var b = str2ab(str);
@@ -103,7 +119,8 @@ function returnResponse(response, client_socket) { buf[3] = len & 0xff; buf.set(new Uint8Array(b), 4);
- chrome.sockets.tcp.send(client_socket, buf.buffer, function(info) { + chrome.sockets.tcp.send(socketId, buf.buffer, function(info) { + console.log("send " + socketId); if (info.resultCode != 0) console.log("Send failed " + info.resultCode); }); diff --git a/chrome/extension/background.js b/chrome/extension/background.js index edb99ee..ecadac5 100644 --- a/chrome/extension/background.js +++ b/chrome/extension/background.js @@ -22,48 +22,94 @@ function onBeforeSendHeadersCallback(details) { return { requestHeaders: details.requestHeaders }; }
-chrome.runtime.onMessageExternal.addListener(function(request, header, sendResponse) { - var timeout = 2000; - var xhr = new XMLHttpRequest(); - xhr.ontimeout = function() { - console.error(url + "timed out."); - chrome.webRequest.onBeforeSendHeaders.removeListener(onBeforeSendHeadersCallback); - }; - xhr.onerror = function() { - chrome.webRequest.onBeforeSendHeaders.removeListener(onBeforeSendHeadersCallback); - var response = { error: xhr.statusText }; - sendResponse(response); - }; - xhr.onreadystatechange = function() { - if (xhr.readyState == 4) { +chrome.runtime.onConnectExternal.addListener(function(port) { + console.log("onConnectExternal"); + port.onMessage.addListener(function(request) { + console.log("onMessage"); + var timeout = 2000; + var xhr = new XMLHttpRequest(); + xhr.responseType = "arraybuffer"; + xhr.ontimeout = function() { + console.error(url + "timed out."); chrome.webRequest.onBeforeSendHeaders.removeListener(onBeforeSendHeadersCallback); - var response = {status: xhr.status, body: btoa(xhr.responseText) }; + }; + xhr.onerror = function() { + chrome.webRequest.onBeforeSendHeaders.removeListener(onBeforeSendHeadersCallback); + var response = { error: xhr.statusText }; sendResponse(response); - } - }; - var requestMethod = request.method; - var url = request.url; - xhr.open(requestMethod, url); - if (request.header != undefined) { - for (var key in request.header) { - if (key != "Host") { // TODO: Add more restricted header fields - xhr.setRequestHeader(key, request.header[key]); - } else { - host = request.header[key]; + }; + xhr.onload = function() { + console.log("onload " + xhr.response.byteLength); + chrome.webRequest.onBeforeSendHeaders.removeListener(onBeforeSendHeadersCallback); + var response = { + status: xhr.status, + body: _arrayBufferToBase64(xhr.response) + }; + port.postMessage(response); + console.log("postMessage " + JSON.stringify(response)); + }; + var requestMethod = request.method; + var url = request.url; + xhr.open(requestMethod, url); + if (request.header != undefined) { + for (var key in request.header) { + if (key != "Host") { // TODO: Add more restricted header fields + xhr.setRequestHeader(key, request.header[key]); + } else { + host = request.header[key]; + } } } - } - var body = null; - if (request.body != undefined) { - body = atob(request.body); - xhr.setRequestHeader("Content-Type", "application/octet-stream"); - console.log(body); - } + var body = null; + if (request.body != undefined) { + body = _base64ToArrayBuffer(request.body); + xhr.overrideMimeType("Content-Type", "application/octet-stream"); + console.log(body); + }
- chrome.webRequest.onBeforeSendHeaders.addListener(onBeforeSendHeadersCallback, { - urls: [url], - types: ['xmlhttprequest'] - }, ['requestHeaders', 'blocking']); + chrome.webRequest.onBeforeSendHeaders.addListener(onBeforeSendHeadersCallback, { + urls: [url], + types: ['xmlhttprequest'] + }, ['requestHeaders', 'blocking']);
- xhr.send(body); + xhr.send(body); + }); }); + +function _base64ToArrayBuffer(base64) { + var binary_string = atob(base64); + var len = binary_string.length; + var bytes = new Uint8Array(len); + for (var i = 0; i < len; i++) { + bytes[i] = binary_string.charCodeAt(i); + } + return bytes; +} + +function _arrayBufferToBase64(buf) { + var bytes = new Uint8Array(buf); + console.log(JSON.stringify(buf)); + var base64 = ''; + var encodings = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/='; + var chr1, chr2, chr3, enc1, enc2, enc3, enc4; + var i = 0; + while (i < bytes.length) { + chr1 = bytes[i++]; + chr2 = i < bytes.length ? bytes[i++] : Number.NaN; + chr3 = i < bytes.length ? bytes[i++] : Number.NaN; + + enc1 = chr1 >> 2; + enc2 = ((chr1 & 3) << 4) | (chr2 >> 4); + enc3 = ((chr2 & 15) << 2) | (chr3 >> 6); + enc4 = chr3 & 63; + + if (isNaN(chr2)) { + enc3 = enc4 = 64; + } else if (isNaN(chr3)) { + enc4 = 64; + } + base64 += encodings.charAt(enc1) + encodings.charAt(enc2) + + encodings.charAt(enc3) + encodings.charAt(enc4); + } + return base64; +}
tor-commits@lists.torproject.org