support.cpp revision 078cfcf7cce9185ec7559910d08b0bc02bfc88a3
11156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber/*
21156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber * Copyright (C) 2011 The Android Open Source Project
31156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber *
41156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber * Licensed under the Apache License, Version 2.0 (the "License");
51156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber * you may not use this file except in compliance with the License.
61156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber * You may obtain a copy of the License at
71156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber *
81156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber *      http://www.apache.org/licenses/LICENSE-2.0
91156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber *
101156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber * Unless required by applicable law or agreed to in writing, software
111156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber * distributed under the License is distributed on an "AS IS" BASIS,
121156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
131156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber * See the License for the specific language governing permissions and
141156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber * limitations under the License.
151156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber */
161156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
171156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber//#define LOG_NDEBUG 0
181156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#define LOG_TAG "ChromiumHTTPDataSourceSupport"
191156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#include <utils/Log.h>
201156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
211156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#include <media/stagefright/foundation/AString.h>
221156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
231156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#include "support.h"
241156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
251156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#include "android/net/android_network_library_impl.h"
26a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma#include "base/logging.h"
27a533975a8e3bb741948750a68a2c962a48777fe0Kristian Monsen#include "base/threading/thread.h"
28cd45ccddb00662f2af8409b895fbcdd0434da8b1Kristian Monsen#include "net/base/cert_verifier.h"
29deaba1c70b8ebdd1fffb40665a40e0593bd9cf3eKristian Monsen#include "net/base/cookie_monster.h"
301156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#include "net/base/host_resolver.h"
311156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#include "net/base/ssl_config_service.h"
3270fcf534d3fb6faa3aaa8061fc87f720c396e7aeAndreas Huber#include "net/http/http_auth_handler_factory.h"
331156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#include "net/http/http_cache.h"
3472fee698602ede6f6b64b77c0f1f28d96ff673d3Andreas Huber#include "net/proxy/proxy_config_service_android.h"
351156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
361156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#include "include/ChromiumHTTPDataSource.h"
371156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
38a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma#include <cutils/log.h>
391156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#include <cutils/properties.h>
401156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#include <media/stagefright/MediaErrors.h>
41a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma#include <string>
421156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
431156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubernamespace android {
441156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
451156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huberstatic Mutex gNetworkThreadLock;
461156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huberstatic base::Thread *gNetworkThread = NULL;
4764125da2f3b76f2d88bb757cb6bf5bd5e29a0639Kristian Monsenstatic scoped_refptr<net::URLRequestContext> gReqContext;
48553f66e21be6e11120460830fc78793a4d11b465Andreas Huberstatic scoped_ptr<net::NetworkChangeNotifier> gNetworkChangeNotifier;
491156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
50a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharmabool logMessageHandler(
51a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        int severity,
52a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        const char* file,
53a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        int line,
54a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        size_t message_start,
55a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        const std::string& str) {
56a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma    int androidSeverity = ANDROID_LOG_VERBOSE;
57a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma    switch(severity) {
58a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma    case logging::LOG_FATAL:
59a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        androidSeverity = ANDROID_LOG_FATAL;
60a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        break;
61a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma    case logging::LOG_ERROR_REPORT:
62a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma    case logging::LOG_ERROR:
63a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        androidSeverity = ANDROID_LOG_ERROR;
64a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        break;
65a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma    case logging::LOG_WARNING:
66a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        androidSeverity = ANDROID_LOG_WARN;
67a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        break;
68a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma    default:
69a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        androidSeverity = ANDROID_LOG_VERBOSE;
70a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        break;
71a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma    }
72a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma    android_printLog(androidSeverity, "chromium-libstagefright",
73a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma                    "%s:%d: %s", file, line, str.c_str());
74a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma    return false;
75a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma}
76a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma
77078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huberstruct AutoPrioritySaver {
78078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber    AutoPrioritySaver()
79078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber        : mTID(androidGetTid()),
80078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber          mPrevPriority(androidGetThreadPriority(mTID)) {
81078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber        androidSetThreadPriority(mTID, ANDROID_PRIORITY_NORMAL);
82078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber    }
83078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber
84078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber    ~AutoPrioritySaver() {
85078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber        androidSetThreadPriority(mTID, mPrevPriority);
86078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber    }
87078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber
88078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huberprivate:
89078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber    pid_t mTID;
90078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber    int mPrevPriority;
91078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber
92078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber    DISALLOW_EVIL_CONSTRUCTORS(AutoPrioritySaver);
93078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber};
94a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma
951156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huberstatic void InitializeNetworkThreadIfNecessary() {
961156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    Mutex::Autolock autoLock(gNetworkThreadLock);
97078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber
981156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    if (gNetworkThread == NULL) {
99078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber        // Make sure any threads spawned by the chromium framework are
100078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber        // running at normal priority instead of inheriting this thread's.
101078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber        AutoPrioritySaver saver;
102078cfcf7cce9185ec7559910d08b0bc02bfc88a3Andreas Huber
1031156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        gNetworkThread = new base::Thread("network");
1041156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        base::Thread::Options options;
1051156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        options.message_loop_type = MessageLoop::TYPE_IO;
1061156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        CHECK(gNetworkThread->StartWithOptions(options));
1071156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
1081156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        gReqContext = new SfRequestContext;
1091156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
110553f66e21be6e11120460830fc78793a4d11b465Andreas Huber        gNetworkChangeNotifier.reset(net::NetworkChangeNotifier::Create());
111553f66e21be6e11120460830fc78793a4d11b465Andreas Huber
1121156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        net::AndroidNetworkLibrary::RegisterSharedInstance(
1131156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                new SfNetworkLibrary);
114a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma        logging::SetLogMessageHandler(logMessageHandler);
1151156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    }
1161156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
1171156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
1181156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huberstatic void MY_LOGI(const char *s) {
1191156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    LOG_PRI(ANDROID_LOG_INFO, LOG_TAG, "%s", s);
1201156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
1211156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
1221156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huberstatic void MY_LOGV(const char *s) {
1231156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#if !defined(LOG_NDEBUG) || LOG_NDEBUG == 0
1241156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    LOG_PRI(ANDROID_LOG_VERBOSE, LOG_TAG, "%s", s);
1251156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#endif
1261156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
1271156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
1281156dc913a5ba7b2bc86489468d4914430f03d14Andreas HuberSfNetLog::SfNetLog()
1291156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    : mNextID(1) {
1301156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
1311156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
1321156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfNetLog::AddEntry(
1331156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        EventType type,
1341156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        const base::TimeTicks &time,
1351156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        const Source &source,
1361156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        EventPhase phase,
1371156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        EventParameters *params) {
1381156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#if 0
1391156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    MY_LOGI(StringPrintf(
1401156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                "AddEntry time=%s type=%s source=%s phase=%s\n",
1411156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                TickCountToString(time).c_str(),
1421156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                EventTypeToString(type),
1431156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                SourceTypeToString(source.type),
1441156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                EventPhaseToString(phase)).c_str());
1451156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#endif
1461156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
1471156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
1481156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huberuint32 SfNetLog::NextID() {
1491156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    return mNextID++;
1501156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
1511156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
1521156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubernet::NetLog::LogLevel SfNetLog::GetLogLevel() const {
1531156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    return LOG_ALL;
1541156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
1551156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
1561156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber////////////////////////////////////////////////////////////////////////////////
1571156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
1581156dc913a5ba7b2bc86489468d4914430f03d14Andreas HuberSfRequestContext::SfRequestContext() {
1591156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    AString ua;
1601156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    ua.append("stagefright/1.2 (Linux;Android ");
1611156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
1621156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#if (PROPERTY_VALUE_MAX < 8)
1631156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#error "PROPERTY_VALUE_MAX must be at least 8"
1641156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber#endif
1651156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
1661156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    char value[PROPERTY_VALUE_MAX];
1671156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    property_get("ro.build.version.release", value, "Unknown");
1681156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    ua.append(value);
1691156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    ua.append(")");
1701156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
1711156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mUserAgent = ua.c_str();
1721156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
17363d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen    set_net_log(new SfNetLog());
1741156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
17563d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen    set_host_resolver(
1761156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        net::CreateSystemHostResolver(
1771156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                net::HostResolver::kDefaultParallelism,
1781156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                NULL /* resolver_proc */,
17963d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen                net_log()));
1801156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
18163d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen    set_ssl_config_service(
18263d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen        net::SSLConfigService::CreateSystemSSLConfigService());
1831156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
18463d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen    set_proxy_service(net::ProxyService::CreateWithoutProxyResolver(
18563d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen        new net::ProxyConfigServiceAndroid, net_log()));
1861156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
18763d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen    set_http_transaction_factory(new net::HttpCache(
18863d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen            host_resolver(),
189cd45ccddb00662f2af8409b895fbcdd0434da8b1Kristian Monsen            new net::CertVerifier(),
19063d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen            dnsrr_resolver(),
19163d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen            dns_cert_checker(),
19263d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen            proxy_service(),
19363d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen            ssl_config_service(),
19463d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen            net::HttpAuthHandlerFactory::CreateDefault(host_resolver()),
19563d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen            network_delegate(),
19663d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen            net_log(),
19763d794763a680c29edccce3a6fac3d6d9c13c8e3Kristian Monsen            NULL));  // backend_factory
198deaba1c70b8ebdd1fffb40665a40e0593bd9cf3eKristian Monsen
199deaba1c70b8ebdd1fffb40665a40e0593bd9cf3eKristian Monsen    set_cookie_store(new net::CookieMonster(NULL, NULL));
2001156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
2011156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2021156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huberconst std::string &SfRequestContext::GetUserAgent(const GURL &url) const {
2031156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    return mUserAgent;
2041156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
2051156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2061156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber////////////////////////////////////////////////////////////////////////////////
2071156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2081156dc913a5ba7b2bc86489468d4914430f03d14Andreas HuberSfNetworkLibrary::SfNetworkLibrary() {}
2091156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2101156dc913a5ba7b2bc86489468d4914430f03d14Andreas HuberSfNetworkLibrary::VerifyResult SfNetworkLibrary::VerifyX509CertChain(
2111156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        const std::vector<std::string>& cert_chain,
2121156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        const std::string& hostname,
2131156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        const std::string& auth_type) {
2141156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    return VERIFY_OK;
2151156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
2161156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2171156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber////////////////////////////////////////////////////////////////////////////////
2181156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2191156dc913a5ba7b2bc86489468d4914430f03d14Andreas HuberSfDelegate::SfDelegate()
2201156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    : mOwner(NULL),
2211156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber      mURLRequest(NULL),
2221156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber      mReadBuffer(new net::IOBufferWithSize(8192)),
2231156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber      mNumBytesRead(0),
2241156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber      mNumBytesTotal(0),
2251156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber      mDataDestination(NULL),
2261156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber      mAtEOS(false) {
2271156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    InitializeNetworkThreadIfNecessary();
2281156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
2291156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2301156dc913a5ba7b2bc86489468d4914430f03d14Andreas HuberSfDelegate::~SfDelegate() {
2311156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    CHECK(mURLRequest == NULL);
2321156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
2331156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2341156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::setOwner(ChromiumHTTPDataSource *owner) {
2351156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mOwner = owner;
2361156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
2371156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
238a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharmavoid SfDelegate::setUID(uid_t uid) {
239a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma    gReqContext->setUID(uid);
240a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma}
241a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma
242a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharmabool SfDelegate::getUID(uid_t *uid) const {
243a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma    return gReqContext->getUID(uid);
244a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma}
245a23456b306f35b9ecf973bf5818ca39295e9e029Ashish Sharma
2461156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::OnReceivedRedirect(
247cd45ccddb00662f2af8409b895fbcdd0434da8b1Kristian Monsen            net::URLRequest *request, const GURL &new_url, bool *defer_redirect) {
2486801b4dbd00b485ecdcd31b517ed885a8fa21c63Andreas Huber    MY_LOGV("OnReceivedRedirect");
2491156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
2501156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2511156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::OnAuthRequired(
252cd45ccddb00662f2af8409b895fbcdd0434da8b1Kristian Monsen            net::URLRequest *request, net::AuthChallengeInfo *auth_info) {
2536801b4dbd00b485ecdcd31b517ed885a8fa21c63Andreas Huber    MY_LOGV("OnAuthRequired");
2541156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2551156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    inherited::OnAuthRequired(request, auth_info);
2561156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
2571156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2581156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::OnCertificateRequested(
259cd45ccddb00662f2af8409b895fbcdd0434da8b1Kristian Monsen            net::URLRequest *request, net::SSLCertRequestInfo *cert_request_info) {
2606801b4dbd00b485ecdcd31b517ed885a8fa21c63Andreas Huber    MY_LOGV("OnCertificateRequested");
2611156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2621156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    inherited::OnCertificateRequested(request, cert_request_info);
2631156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
2641156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2651156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::OnSSLCertificateError(
266cd45ccddb00662f2af8409b895fbcdd0434da8b1Kristian Monsen            net::URLRequest *request, int cert_error, net::X509Certificate *cert) {
2671156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    fprintf(stderr, "OnSSLCertificateError cert_error=%d\n", cert_error);
2681156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2691156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    inherited::OnSSLCertificateError(request, cert_error, cert);
2701156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
2711156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
272cd45ccddb00662f2af8409b895fbcdd0434da8b1Kristian Monsenvoid SfDelegate::OnGetCookies(net::URLRequest *request, bool blocked_by_policy) {
2736801b4dbd00b485ecdcd31b517ed885a8fa21c63Andreas Huber    MY_LOGV("OnGetCookies");
2741156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
2751156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2761156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::OnSetCookie(
277cd45ccddb00662f2af8409b895fbcdd0434da8b1Kristian Monsen        net::URLRequest *request,
2781156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        const std::string &cookie_line,
2791156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        const net::CookieOptions &options,
2801156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        bool blocked_by_policy) {
2816801b4dbd00b485ecdcd31b517ed885a8fa21c63Andreas Huber    MY_LOGV("OnSetCookie");
2821156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
2831156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
284cd45ccddb00662f2af8409b895fbcdd0434da8b1Kristian Monsenvoid SfDelegate::OnResponseStarted(net::URLRequest *request) {
28564125da2f3b76f2d88bb757cb6bf5bd5e29a0639Kristian Monsen    if (request->status().status() != net::URLRequestStatus::SUCCESS) {
2861156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        MY_LOGI(StringPrintf(
2871156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    "Request failed with status %d and os_error %d",
2881156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    request->status().status(),
2891156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    request->status().os_error()).c_str());
2901156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2911156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        delete mURLRequest;
2921156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        mURLRequest = NULL;
2931156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
2941156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        mOwner->onConnectionFailed(ERROR_IO);
2951156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        return;
2961156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    } else if (mRangeRequested && request->GetResponseCode() != 206) {
2971156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        MY_LOGI(StringPrintf(
2981156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    "We requested a content range, but server didn't "
2991156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    "support that. (responded with %d)",
3001156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    request->GetResponseCode()).c_str());
3011156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3021156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        delete mURLRequest;
3031156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        mURLRequest = NULL;
3041156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3051156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        mOwner->onConnectionFailed(-EPIPE);
3061156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        return;
3071156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    } else if ((request->GetResponseCode() / 100) != 2) {
3081156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        MY_LOGI(StringPrintf(
3091156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    "Server responded with http status %d",
3101156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    request->GetResponseCode()).c_str());
3111156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3121156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        delete mURLRequest;
3131156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        mURLRequest = NULL;
3141156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3151156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        mOwner->onConnectionFailed(ERROR_IO);
3161156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        return;
3171156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    }
3181156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3191156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    MY_LOGV("OnResponseStarted");
3201156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3211156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    std::string headers;
3221156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    request->GetAllResponseHeaders(&headers);
3231156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3241156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    MY_LOGV(StringPrintf("response headers: %s", headers.c_str()).c_str());
3251156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3266511c9755c3a3360ba869772600c7aae048a7ffcAndreas Huber    std::string contentType;
3276511c9755c3a3360ba869772600c7aae048a7ffcAndreas Huber    request->GetResponseHeaderByName("Content-Type", &contentType);
3286511c9755c3a3360ba869772600c7aae048a7ffcAndreas Huber
3296511c9755c3a3360ba869772600c7aae048a7ffcAndreas Huber    mOwner->onConnectionEstablished(
3306511c9755c3a3360ba869772600c7aae048a7ffcAndreas Huber            request->GetExpectedContentSize(), contentType.c_str());
3311156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
3321156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
333cd45ccddb00662f2af8409b895fbcdd0434da8b1Kristian Monsenvoid SfDelegate::OnReadCompleted(net::URLRequest *request, int bytes_read) {
3341156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    if (bytes_read == -1) {
3351156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        MY_LOGI(StringPrintf(
3361156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    "OnReadCompleted, read failed, status %d",
3371156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    request->status().status()).c_str());
3381156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3391156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        mOwner->onReadCompleted(ERROR_IO);
3401156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        return;
3411156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    }
3421156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3431156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    MY_LOGV(StringPrintf("OnReadCompleted, read %d bytes", bytes_read).c_str());
3441156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3451156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    if (bytes_read < 0) {
3461156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        MY_LOGI(StringPrintf(
3471156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    "Read failed w/ status %d\n",
3481156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    request->status().status()).c_str());
3491156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3501156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        mOwner->onReadCompleted(ERROR_IO);
3511156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        return;
3521156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    } else if (bytes_read == 0) {
3531156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        mAtEOS = true;
3541156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        mOwner->onReadCompleted(mNumBytesRead);
3551156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        return;
3561156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    }
3571156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3581156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    CHECK_GT(bytes_read, 0);
3591156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    CHECK_LE(mNumBytesRead + bytes_read, mNumBytesTotal);
3601156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3611156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    memcpy((uint8_t *)mDataDestination + mNumBytesRead,
3621156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber           mReadBuffer->data(),
3631156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber           bytes_read);
3641156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3651156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mNumBytesRead += bytes_read;
3661156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3671156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    readMore(request);
3681156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
3691156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
370cd45ccddb00662f2af8409b895fbcdd0434da8b1Kristian Monsenvoid SfDelegate::readMore(net::URLRequest *request) {
3711156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    while (mNumBytesRead < mNumBytesTotal) {
3721156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        size_t copy = mNumBytesTotal - mNumBytesRead;
3731156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        if (copy > mReadBuffer->size()) {
3741156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            copy = mReadBuffer->size();
3751156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        }
3761156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3771156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        int n;
3781156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        if (request->Read(mReadBuffer, copy, &n)) {
3791156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            MY_LOGV(StringPrintf("Read %d bytes directly.", n).c_str());
3801156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3811156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            CHECK_LE((size_t)n, copy);
3821156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3831156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            memcpy((uint8_t *)mDataDestination + mNumBytesRead,
3841156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                   mReadBuffer->data(),
3851156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                   n);
3861156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3871156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            mNumBytesRead += n;
3881156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
3891156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            if (n == 0) {
3901156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                mAtEOS = true;
3911156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                break;
3921156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            }
3931156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        } else {
3941156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            MY_LOGV("readMore pending read");
3951156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
39664125da2f3b76f2d88bb757cb6bf5bd5e29a0639Kristian Monsen            if (request->status().status() != net::URLRequestStatus::IO_PENDING) {
3971156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                MY_LOGI(StringPrintf(
3981156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                            "Direct read failed w/ status %d\n",
3991156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                            request->status().status()).c_str());
4001156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4011156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                mOwner->onReadCompleted(ERROR_IO);
4021156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                return;
4031156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            }
4041156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4051156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            return;
4061156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        }
4071156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    }
4081156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4091156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mOwner->onReadCompleted(mNumBytesRead);
4101156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
4111156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4121156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::initiateConnection(
4131156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        const char *uri,
4141156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        const KeyedVector<String8, String8> *headers,
4151156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        off64_t offset) {
4161156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    GURL url(uri);
4171156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4181156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    MessageLoop *loop = gNetworkThread->message_loop();
4191156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    loop->PostTask(
4201156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            FROM_HERE,
4211156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            NewRunnableFunction(
4221156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                &SfDelegate::OnInitiateConnectionWrapper,
4231156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                this,
4241156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                url,
4251156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                headers,
4261156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                offset));
4271156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4281156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
4291156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4301156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber// static
4311156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::OnInitiateConnectionWrapper(
4321156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        SfDelegate *me, GURL url,
4331156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        const KeyedVector<String8, String8> *headers,
4341156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        off64_t offset) {
4351156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    me->onInitiateConnection(url, headers, offset);
4361156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
4371156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4381156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::onInitiateConnection(
4391156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        const GURL &url,
4401156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        const KeyedVector<String8, String8> *extra,
4411156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        off64_t offset) {
4421156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    CHECK(mURLRequest == NULL);
4431156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
444cd45ccddb00662f2af8409b895fbcdd0434da8b1Kristian Monsen    mURLRequest = new net::URLRequest(url, this);
4451156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mAtEOS = false;
4461156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4471156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mRangeRequested = false;
4481156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4491156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    if (offset != 0 || extra != NULL) {
4501156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        net::HttpRequestHeaders headers =
4511156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            mURLRequest->extra_request_headers();
4521156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4531156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        if (offset != 0) {
4541156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            headers.AddHeaderFromString(
4551156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                    StringPrintf("Range: bytes=%lld-", offset).c_str());
4561156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4571156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            mRangeRequested = true;
4581156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        }
4591156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4601156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        if (extra != NULL) {
4611156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            for (size_t i = 0; i < extra->size(); ++i) {
4621156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                AString s;
4631156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                s.append(extra->keyAt(i).string());
4641156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                s.append(": ");
4651156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                s.append(extra->valueAt(i).string());
4661156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4671156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                headers.AddHeaderFromString(s.c_str());
4681156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            }
4691156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        }
4701156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4711156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        mURLRequest->SetExtraRequestHeaders(headers);
4721156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    }
4731156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4741156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mURLRequest->set_context(gReqContext);
4751156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4761156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mURLRequest->Start();
4771156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
4781156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4791156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::initiateDisconnect() {
4801156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    MessageLoop *loop = gNetworkThread->message_loop();
4811156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    loop->PostTask(
4821156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            FROM_HERE,
4831156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            NewRunnableFunction(
4841156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                &SfDelegate::OnInitiateDisconnectWrapper, this));
4851156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
4861156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4871156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber// static
4881156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::OnInitiateDisconnectWrapper(SfDelegate *me) {
4891156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    me->onInitiateDisconnect();
4901156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
4911156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4921156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::onInitiateDisconnect() {
4931156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mURLRequest->Cancel();
4941156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4951156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    delete mURLRequest;
4961156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mURLRequest = NULL;
4971156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
4981156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mOwner->onDisconnectComplete();
4991156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
5001156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
5011156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::initiateRead(void *data, size_t size) {
5021156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    MessageLoop *loop = gNetworkThread->message_loop();
5031156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    loop->PostTask(
5041156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            FROM_HERE,
5051156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber            NewRunnableFunction(
5061156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber                &SfDelegate::OnInitiateReadWrapper, this, data, size));
5071156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
5081156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
5091156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber// static
5101156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::OnInitiateReadWrapper(
5111156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        SfDelegate *me, void *data, size_t size) {
5121156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    me->onInitiateRead(data, size);
5131156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
5141156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
5151156dc913a5ba7b2bc86489468d4914430f03d14Andreas Hubervoid SfDelegate::onInitiateRead(void *data, size_t size) {
5161156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    CHECK(mURLRequest != NULL);
5171156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
5181156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mNumBytesRead = 0;
5191156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mNumBytesTotal = size;
5201156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    mDataDestination = data;
5211156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
5221156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    if (mAtEOS) {
5231156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        mOwner->onReadCompleted(0);
5241156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber        return;
5251156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    }
5261156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
5271156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber    readMore(mURLRequest);
5281156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}
5291156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
5301156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber}  // namespace android
5311156dc913a5ba7b2bc86489468d4914430f03d14Andreas Huber
532