Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(237)

Side by Side Diff: net/base/host_resolver_impl.cc

Issue 11065052: [net] Add AsyncDNS.TTL histogram. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: remove obsolete code Created 8 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "net/base/host_resolver_impl.h" 5 #include "net/base/host_resolver_impl.h"
6 6
7 #if defined(OS_WIN) 7 #if defined(OS_WIN)
8 #include <Winsock2.h> 8 #include <Winsock2.h>
9 #elif defined(OS_POSIX) 9 #elif defined(OS_POSIX)
10 #include <netdb.h> 10 #include <netdb.h>
(...skipping 187 matching lines...) Expand 10 before | Expand all | Expand 10 after
198 } 198 }
199 } else { 199 } else {
200 if (speculative) { 200 if (speculative) {
201 DNS_HISTOGRAM("DNS.TotalTime_speculative", duration); 201 DNS_HISTOGRAM("DNS.TotalTime_speculative", duration);
202 } else { 202 } else {
203 DNS_HISTOGRAM("DNS.TotalTime", duration); 203 DNS_HISTOGRAM("DNS.TotalTime", duration);
204 } 204 }
205 } 205 }
206 } 206 }
207 207
208 void RecordTTL(base::TimeDelta ttl) {
209 UMA_HISTOGRAM_CUSTOM_COUNTS("AsyncDNS.TTL", ttl.InSeconds(), 1, 86400, 100);
cbentzel 2012/10/13 10:50:45 Should be UMA_HISTOGRAM_CUSTOM_TIMES?
szym 2012/10/15 19:45:36 I initially used _TIMES, but then I looked at the
210 }
211
208 //----------------------------------------------------------------------------- 212 //-----------------------------------------------------------------------------
209 213
210 // Wraps call to SystemHostResolverProc as an instance of HostResolverProc. 214 // Wraps call to SystemHostResolverProc as an instance of HostResolverProc.
211 // TODO(szym): This should probably be declared in host_resolver_proc.h. 215 // TODO(szym): This should probably be declared in host_resolver_proc.h.
212 class CallSystemHostResolverProc : public HostResolverProc { 216 class CallSystemHostResolverProc : public HostResolverProc {
213 public: 217 public:
214 CallSystemHostResolverProc() : HostResolverProc(NULL) {} 218 CallSystemHostResolverProc() : HostResolverProc(NULL) {}
215 virtual int Resolve(const std::string& hostname, 219 virtual int Resolve(const std::string& hostname,
216 AddressFamily address_family, 220 AddressFamily address_family,
217 HostResolverFlags host_resolver_flags, 221 HostResolverFlags host_resolver_flags,
(...skipping 1106 matching lines...) Expand 10 before | Expand all | Expand 10 after
1324 base::Bind(&NetLogJobAttachCallback, 1328 base::Bind(&NetLogJobAttachCallback,
1325 req->request_net_log().source(), 1329 req->request_net_log().source(),
1326 priority())); 1330 priority()));
1327 1331
1328 if (num_active_requests() > 0) { 1332 if (num_active_requests() > 0) {
1329 UpdatePriority(); 1333 UpdatePriority();
1330 } else { 1334 } else {
1331 // If we were called from a Request's callback within CompleteRequests, 1335 // If we were called from a Request's callback within CompleteRequests,
1332 // that Request could not have been cancelled, so num_active_requests() 1336 // that Request could not have been cancelled, so num_active_requests()
1333 // could not be 0. Therefore, we are not in CompleteRequests(). 1337 // could not be 0. Therefore, we are not in CompleteRequests().
1334 CompleteRequests(OK, AddressList(), base::TimeDelta()); 1338 CompleteRequestsWithError(OK /* cancelled */);
1335 } 1339 }
1336 } 1340 }
1337 1341
1338 // Called from AbortAllInProgressJobs. Completes all requests as aborted 1342 // Called from AbortAllInProgressJobs. Completes all requests as aborted
1339 // and destroys the job. 1343 // and destroys the job.
1340 void Abort() { 1344 void Abort() {
1341 DCHECK(is_running()); 1345 DCHECK(is_running());
1342 CompleteRequests(ERR_ABORTED, AddressList(), base::TimeDelta()); 1346 CompleteRequestsWithError(ERR_ABORTED);
1343 } 1347 }
1344 1348
1345 // Called by HostResolverImpl when this job is evicted due to queue overflow. 1349 // Called by HostResolverImpl when this job is evicted due to queue overflow.
1346 // Completes all requests and destroys the job. 1350 // Completes all requests and destroys the job.
1347 void OnEvicted() { 1351 void OnEvicted() {
1348 DCHECK(!is_running()); 1352 DCHECK(!is_running());
1349 DCHECK(is_queued()); 1353 DCHECK(is_queued());
1350 handle_.Reset(); 1354 handle_.Reset();
1351 1355
1352 net_log_.AddEvent(NetLog::TYPE_HOST_RESOLVER_IMPL_JOB_EVICTED); 1356 net_log_.AddEvent(NetLog::TYPE_HOST_RESOLVER_IMPL_JOB_EVICTED);
1353 1357
1354 // This signals to CompleteRequests that this job never ran. 1358 // This signals to CompleteRequests that this job never ran.
1355 CompleteRequests(ERR_HOST_RESOLVER_QUEUE_TOO_LARGE, 1359 CompleteRequestsWithError(ERR_HOST_RESOLVER_QUEUE_TOO_LARGE);
1356 AddressList(),
1357 base::TimeDelta());
1358 } 1360 }
1359 1361
1360 // Attempts to serve the job from HOSTS. Returns true if succeeded and 1362 // Attempts to serve the job from HOSTS. Returns true if succeeded and
1361 // this Job was destroyed. 1363 // this Job was destroyed.
1362 bool ServeFromHosts() { 1364 bool ServeFromHosts() {
1363 DCHECK_GT(num_active_requests(), 0u); 1365 DCHECK_GT(num_active_requests(), 0u);
1364 AddressList addr_list; 1366 AddressList addr_list;
1365 if (resolver_->ServeFromHosts(key(), 1367 if (resolver_->ServeFromHosts(key(),
1366 requests_.front()->info(), 1368 requests_.front()->info(),
1367 &addr_list)) { 1369 &addr_list)) {
1368 // This will destroy the Job. 1370 // This will destroy the Job.
1369 CompleteRequests(OK, addr_list, base::TimeDelta()); 1371 CompleteRequests(OK, addr_list, base::TimeDelta(), false /* true_ttl */);
cbentzel 2012/10/13 10:50:45 Would it make sense to change to CompleteRequests(
szym 2012/10/15 19:45:36 I don't see the benefit. Wouldn't this be the only
1370 return true; 1372 return true;
1371 } 1373 }
1372 return false; 1374 return false;
1373 } 1375 }
1374 1376
1375 const Key key() const { 1377 const Key key() const {
1376 return key_; 1378 return key_;
1377 } 1379 }
1378 1380
1379 bool is_queued() const { 1381 bool is_queued() const {
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after
1457 UmaAsyncDnsResolveStatus(RESOLVE_STATUS_PROC_SUCCESS); 1459 UmaAsyncDnsResolveStatus(RESOLVE_STATUS_PROC_SUCCESS);
1458 } 1460 }
1459 UMA_HISTOGRAM_CUSTOM_ENUMERATION("AsyncDNS.ResolveError", 1461 UMA_HISTOGRAM_CUSTOM_ENUMERATION("AsyncDNS.ResolveError",
1460 std::abs(dns_task_error_), 1462 std::abs(dns_task_error_),
1461 GetAllErrorCodesForUma()); 1463 GetAllErrorCodesForUma());
1462 } else { 1464 } else {
1463 UmaAsyncDnsResolveStatus(RESOLVE_STATUS_FAIL); 1465 UmaAsyncDnsResolveStatus(RESOLVE_STATUS_FAIL);
1464 } 1466 }
1465 } 1467 }
1466 1468
1467 base::TimeDelta ttl = base::TimeDelta::FromSeconds( 1469 base::TimeDelta ttl =
1468 kNegativeCacheEntryTTLSeconds); 1470 base::TimeDelta::FromSeconds(kNegativeCacheEntryTTLSeconds);
1469 if (net_error == OK) 1471 if (net_error == OK)
1470 ttl = base::TimeDelta::FromSeconds(kCacheEntryTTLSeconds); 1472 ttl = base::TimeDelta::FromSeconds(kCacheEntryTTLSeconds);
1471 1473
1472 CompleteRequests(net_error, addr_list, ttl); 1474 CompleteRequests(net_error, addr_list, ttl, false /* true_ttl */);
1473 } 1475 }
1474 1476
1475 void StartDnsTask() { 1477 void StartDnsTask() {
1476 DCHECK(resolver_->HaveDnsConfig()); 1478 DCHECK(resolver_->HaveDnsConfig());
1477 dns_task_.reset(new DnsTask( 1479 dns_task_.reset(new DnsTask(
1478 resolver_->dns_client_.get(), 1480 resolver_->dns_client_.get(),
1479 key_, 1481 key_,
1480 base::Bind(&Job::OnDnsTaskComplete, base::Unretained(this)), 1482 base::Bind(&Job::OnDnsTaskComplete, base::Unretained(this)),
1481 net_log_)); 1483 net_log_));
1482 1484
(...skipping 19 matching lines...) Expand all
1502 // TODO(szym): Run ServeFromHosts now if nsswitch.conf says so. 1504 // TODO(szym): Run ServeFromHosts now if nsswitch.conf says so.
1503 // http://crbug.com/117655 1505 // http://crbug.com/117655
1504 1506
1505 // TODO(szym): Some net errors indicate lack of connectivity. Starting 1507 // TODO(szym): Some net errors indicate lack of connectivity. Starting
1506 // ProcTask in that case is a waste of time. 1508 // ProcTask in that case is a waste of time.
1507 StartProcTask(); 1509 StartProcTask();
1508 return; 1510 return;
1509 } 1511 }
1510 1512
1511 UmaAsyncDnsResolveStatus(RESOLVE_STATUS_DNS_SUCCESS); 1513 UmaAsyncDnsResolveStatus(RESOLVE_STATUS_DNS_SUCCESS);
1514 RecordTTL(ttl);
1512 1515
1513 CompleteRequests(net_error, addr_list, ttl); 1516 CompleteRequests(net_error, addr_list, ttl, true /* true_ttl */);
1514 } 1517 }
1515 1518
1516 // Performs Job's last rites. Completes all Requests. Deletes this. 1519 // Performs Job's last rites. Completes all Requests. Deletes this.
1517 void CompleteRequests(int net_error, 1520 void CompleteRequests(int net_error,
1518 const AddressList& addr_list, 1521 const AddressList& addr_list,
1519 base::TimeDelta ttl) { 1522 base::TimeDelta ttl,
1523 bool true_ttl) {
1520 CHECK(resolver_); 1524 CHECK(resolver_);
1521 1525
1522 // This job must be removed from resolver's |jobs_| now to make room for a 1526 // This job must be removed from resolver's |jobs_| now to make room for a
1523 // new job with the same key in case one of the OnComplete callbacks decides 1527 // new job with the same key in case one of the OnComplete callbacks decides
1524 // to spawn one. Consequently, the job deletes itself when CompleteRequests 1528 // to spawn one. Consequently, the job deletes itself when CompleteRequests
1525 // is done. 1529 // is done.
1526 scoped_ptr<Job> self_deleter(this); 1530 scoped_ptr<Job> self_deleter(this);
1527 1531
1528 resolver_->RemoveJob(this); 1532 resolver_->RemoveJob(this);
1529 1533
1530 // |addr_list| will be destroyed once we destroy |proc_task_| and 1534 // |addr_list| will be destroyed with |proc_task_| and |dns_task_|.
1531 // |dns_task_|.
1532 AddressList list = addr_list; 1535 AddressList list = addr_list;
1533 1536
1534 if (is_running()) { 1537 if (is_running()) {
1535 DCHECK(!is_queued()); 1538 DCHECK(!is_queued());
1536 if (is_proc_running()) { 1539 if (is_proc_running()) {
1537 proc_task_->Cancel(); 1540 proc_task_->Cancel();
1538 proc_task_ = NULL; 1541 proc_task_ = NULL;
1539 } 1542 }
1540 dns_task_.reset(); 1543 dns_task_.reset();
1541 1544
(...skipping 19 matching lines...) Expand all
1561 if (net_error == OK) { 1564 if (net_error == OK) {
1562 SetPortOnAddressList(requests_.front()->info().port(), &list); 1565 SetPortOnAddressList(requests_.front()->info().port(), &list);
1563 // Record this histogram here, when we know the system has a valid DNS 1566 // Record this histogram here, when we know the system has a valid DNS
1564 // configuration. 1567 // configuration.
1565 UMA_HISTOGRAM_BOOLEAN("AsyncDNS.HaveDnsConfig", 1568 UMA_HISTOGRAM_BOOLEAN("AsyncDNS.HaveDnsConfig",
1566 resolver_->received_dns_config_); 1569 resolver_->received_dns_config_);
1567 } 1570 }
1568 1571
1569 bool did_complete = (net_error != ERR_ABORTED) && 1572 bool did_complete = (net_error != ERR_ABORTED) &&
1570 (net_error != ERR_HOST_RESOLVER_QUEUE_TOO_LARGE); 1573 (net_error != ERR_HOST_RESOLVER_QUEUE_TOO_LARGE);
1571 if (did_complete) 1574 if (did_complete) {
1572 resolver_->CacheResult(key_, net_error, list, ttl); 1575 HostCache::Entry entry = true_ttl ?
1576 HostCache::Entry(net_error, list, ttl) :
1577 HostCache::Entry(net_error, list);
1578 resolver_->CacheResult(key_, entry, ttl);
1579 }
1573 1580
1574 // Complete all of the requests that were attached to the job. 1581 // Complete all of the requests that were attached to the job.
1575 for (RequestsList::const_iterator it = requests_.begin(); 1582 for (RequestsList::const_iterator it = requests_.begin();
1576 it != requests_.end(); ++it) { 1583 it != requests_.end(); ++it) {
1577 Request* req = *it; 1584 Request* req = *it;
1578 1585
1579 if (req->was_canceled()) 1586 if (req->was_canceled())
1580 continue; 1587 continue;
1581 1588
1582 DCHECK_EQ(this, req->job()); 1589 DCHECK_EQ(this, req->job());
1583 // Update the net log and notify registered observers. 1590 // Update the net log and notify registered observers.
1584 LogFinishRequest(req->source_net_log(), req->request_net_log(), 1591 LogFinishRequest(req->source_net_log(), req->request_net_log(),
1585 req->info(), net_error); 1592 req->info(), net_error);
1586 if (did_complete) { 1593 if (did_complete) {
1587 // Record effective total time from creation to completion. 1594 // Record effective total time from creation to completion.
1588 RecordTotalTime(had_dns_config_, req->info().is_speculative(), 1595 RecordTotalTime(had_dns_config_, req->info().is_speculative(),
1589 base::TimeTicks::Now() - req->request_time()); 1596 base::TimeTicks::Now() - req->request_time());
1590 } 1597 }
1591 req->OnComplete(net_error, list); 1598 req->OnComplete(net_error, list);
1592 1599
1593 // Check if the resolver was destroyed as a result of running the 1600 // Check if the resolver was destroyed as a result of running the
1594 // callback. If it was, we could continue, but we choose to bail. 1601 // callback. If it was, we could continue, but we choose to bail.
1595 if (!resolver_) 1602 if (!resolver_)
1596 return; 1603 return;
1597 } 1604 }
1598 } 1605 }
1599 1606
1607 // Convenience wrapper for CompleteRequests in case of failure.
1608 void CompleteRequestsWithError(int net_error) {
1609 CompleteRequests(net_error, AddressList(), base::TimeDelta(), false);
1610 }
1611
1600 RequestPriority priority() const { 1612 RequestPriority priority() const {
1601 return priority_tracker_.highest_priority(); 1613 return priority_tracker_.highest_priority();
1602 } 1614 }
1603 1615
1604 // Number of non-canceled requests in |requests_|. 1616 // Number of non-canceled requests in |requests_|.
1605 size_t num_active_requests() const { 1617 size_t num_active_requests() const {
1606 return priority_tracker_.total_count(); 1618 return priority_tracker_.total_count();
1607 } 1619 }
1608 1620
1609 bool is_dns_running() const { 1621 bool is_dns_running() const {
(...skipping 341 matching lines...) Expand 10 before | Expand all | Expand 10 after
1951 if (!info.allow_cached_response() || !cache_.get()) 1963 if (!info.allow_cached_response() || !cache_.get())
1952 return false; 1964 return false;
1953 1965
1954 const HostCache::Entry* cache_entry = cache_->Lookup( 1966 const HostCache::Entry* cache_entry = cache_->Lookup(
1955 key, base::TimeTicks::Now()); 1967 key, base::TimeTicks::Now());
1956 if (!cache_entry) 1968 if (!cache_entry)
1957 return false; 1969 return false;
1958 1970
1959 *net_error = cache_entry->error; 1971 *net_error = cache_entry->error;
1960 if (*net_error == OK) { 1972 if (*net_error == OK) {
1973 if (cache_entry->has_ttl())
1974 RecordTTL(cache_entry->ttl);
1961 *addresses = cache_entry->addrlist; 1975 *addresses = cache_entry->addrlist;
1962 EnsurePortOnAddressList(info.port(), addresses); 1976 EnsurePortOnAddressList(info.port(), addresses);
1963 } 1977 }
1964 return true; 1978 return true;
1965 } 1979 }
1966 1980
1967 bool HostResolverImpl::ServeFromHosts(const Key& key, 1981 bool HostResolverImpl::ServeFromHosts(const Key& key,
1968 const RequestInfo& info, 1982 const RequestInfo& info,
1969 AddressList* addresses) { 1983 AddressList* addresses) {
1970 DCHECK(addresses); 1984 DCHECK(addresses);
(...skipping 20 matching lines...) Expand all
1991 it = hosts.find(DnsHostsKey(hostname, ADDRESS_FAMILY_IPV6)); 2005 it = hosts.find(DnsHostsKey(hostname, ADDRESS_FAMILY_IPV6));
1992 if (it == hosts.end()) 2006 if (it == hosts.end())
1993 return false; 2007 return false;
1994 } 2008 }
1995 2009
1996 *addresses = AddressList::CreateFromIPAddress(it->second, info.port()); 2010 *addresses = AddressList::CreateFromIPAddress(it->second, info.port());
1997 return true; 2011 return true;
1998 } 2012 }
1999 2013
2000 void HostResolverImpl::CacheResult(const Key& key, 2014 void HostResolverImpl::CacheResult(const Key& key,
2001 int net_error, 2015 const HostCache::Entry& entry,
2002 const AddressList& addr_list,
2003 base::TimeDelta ttl) { 2016 base::TimeDelta ttl) {
2004 if (cache_.get()) 2017 if (cache_.get())
2005 cache_->Set(key, net_error, addr_list, base::TimeTicks::Now(), ttl); 2018 cache_->Set(key, entry, base::TimeTicks::Now(), ttl);
2006 } 2019 }
2007 2020
2008 void HostResolverImpl::RemoveJob(Job* job) { 2021 void HostResolverImpl::RemoveJob(Job* job) {
2009 DCHECK(job); 2022 DCHECK(job);
2010 JobMap::iterator it = jobs_.find(job->key()); 2023 JobMap::iterator it = jobs_.find(job->key());
2011 if (it != jobs_.end() && it->second == job) 2024 if (it != jobs_.end() && it->second == job)
2012 jobs_.erase(it); 2025 jobs_.erase(it);
2013 } 2026 }
2014 2027
2015 void HostResolverImpl::DiscardIPv6ProbeJob() { 2028 void HostResolverImpl::DiscardIPv6ProbeJob() {
(...skipping 130 matching lines...) Expand 10 before | Expand all | Expand 10 after
2146 // |this| may be deleted inside AbortAllInProgressJobs(). 2159 // |this| may be deleted inside AbortAllInProgressJobs().
2147 if (self) 2160 if (self)
2148 TryServingAllJobsFromHosts(); 2161 TryServingAllJobsFromHosts();
2149 } 2162 }
2150 2163
2151 bool HostResolverImpl::HaveDnsConfig() const { 2164 bool HostResolverImpl::HaveDnsConfig() const {
2152 return (dns_client_.get() != NULL) && (dns_client_->GetConfig() != NULL); 2165 return (dns_client_.get() != NULL) && (dns_client_->GetConfig() != NULL);
2153 } 2166 }
2154 2167
2155 } // namespace net 2168 } // namespace net
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698