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

Unified Diff: net/tools/gdig/gdig.cc

Issue 10386120: Utility to resolve an hostname using Chromium's code in net/dns (Closed) Base URL: http://git.chromium.org/chromium/src.git@master
Patch Set: Created 8 years, 7 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 side-by-side diff with in-line comments
Download patch
« net/base/host_resolver_impl.cc ('K') | « net/net.gyp ('k') | no next file » | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: net/tools/gdig/gdig.cc
diff --git a/net/tools/gdig/gdig.cc b/net/tools/gdig/gdig.cc
new file mode 100644
index 0000000000000000000000000000000000000000..b729ae39997860e63af7e817f1489332ded9365d
--- /dev/null
+++ b/net/tools/gdig/gdig.cc
@@ -0,0 +1,208 @@
+#include <stdio.h>
+#include <iostream>
+
+#include "base/memory/scoped_ptr.h"
+#include "base/at_exit.h"
+#include "base/message_loop.h"
+#include "base/command_line.h"
+#include "base/string_number_conversions.h"
+
+#include "net/base/host_resolver_impl.h"
+#include "net/base/net_util.h"
+#include "net/base/sys_addrinfo.h"
+
+#include "net/base/net_errors.h"
szym 2012/05/14 18:48:32 The lint tool will automatically point most style
+
+#if defined(OS_MACOSX)
+#include "base/mac/scoped_nsautorelease_pool.h"
+#endif
+
+namespace net {
+
+namespace {
+
+void usage(const char* program_name) {
szym 2012/05/14 18:48:32 Suggested function name: PrintUsage, probably shou
Daniele 2012/05/17 23:04:34 Ok, even if I don't really see the necessity to ma
+ std::cout << "usage: " << program_name <<
+ " [--max_retry=<retry>] [--concurrent_resolves=<n>] domain_name" <<
+ std::endl;
+}
+
+// This class is used to mock the DnsConfigService when an HostResolverImpl
+// is created and to set to it a custom dns_config.
+class DnsConfigServiceMock : public DnsConfigService {
+ public:
+ DnsConfigServiceMock(const DnsConfig& dns_config) :
+ dns_config_(dns_config) {};
+
+ virtual ~DnsConfigServiceMock() {};
+
+ virtual void Watch(const CallbackType& callback) OVERRIDE{
+ DCHECK(CalledOnValidThread());
+ DCHECK(!callback.is_null());
+ set_callback(callback);
+ callback.Run(dns_config_);
szym 2012/05/14 18:48:32 This is strongly discouraged. Rule-of-thumb: avoid
Daniele 2012/05/17 23:04:34 Quite clear, it solved other problems I had to wor
+ }
+ private:
+ const DnsConfig& dns_config_;
+};
+
+class GDig {
+
+ public:
+ GDig() :
+ resolve_name_ret_(ERR_TIMED_OUT),
+ max_retry_(1),
+ concurrent_resolves_(1){ }
+
+ int Main(int argc, const char* argv[]) {
+
+ if( !ParseCommandLine(argc, argv) ){
+ usage(argv[0]);
+ return -1;
szym 2012/05/14 18:48:32 I suggest defining in GDig: enum { RESULT_NO_RES
Daniele 2012/05/17 23:04:34 Done, but the name you used seems ok to me, so I k
+ }
+
+#if defined(OS_MACOSX)
+ //without this there will be a mem leak on osx
+ base::mac::ScopedNSAutoreleasePool scoped_pool;
+#endif
+
+ base::AtExitManager exit_manager;
+ MessageLoop loop(MessageLoop::TYPE_IO);
+
+ LoadDnsConfig();
szym 2012/05/14 18:48:32 I suggest: void Start() { resolver_ = new HostR
Daniele 2012/05/17 23:04:34 That's definitely nicer than what I did. On 2012/
+
+ MessageLoop::current()->Run();
+
+ if (!dns_config_.IsValid()){
+ std::cout << "Dns configuration is not valid." << std::endl;
+ return -2;
+ }
+ if (resolve_name_ret_ < 0){
+ std::cout << "Error trying to resolve hostname " << domain_name_ <<
+ ":" << ErrorToString(resolve_name_ret_) << std::endl;
+ return -3;
+ }
+
+ return 0;
+ }
+
+private:
+ void ResolverCallback(int val){
szym 2012/05/14 18:48:32 better name: OnResolveComplete(int rv)
Daniele 2012/05/17 23:04:34 Done.
+ timeout_.Cancel();
+ resolve_name_ret_ = val;
+
+ if (resolve_name_ret_ < 0 ){
+ MessageLoop::current()->Quit();
+ }
+
+ const struct addrinfo* addrinf = addrlist_.head();
+ while (addrinf){
+ std::string ip = NetAddressToStringWithPort(addrinf);
+ std::cout << ip << std::endl;
+ addrinf = addrinf->ai_next;
+ }
+
+ MessageLoop::current()->Quit();
+ }
+
+ void ReleaseDnsConfigService(){
+ config_service_.reset();
+ }
+
+ void ResolveName(const std::string& domain_name){
+
+ scoped_ptr<DnsConfigService>
+ dns_config_service(new DnsConfigServiceMock(dns_config_));
+
+ resolver_.reset(CreateHostResolver(concurrent_resolves_,
+ max_retry_,
+ HostCache::CreateDefaultCache(),
+ dns_config_service.Pass(),
+ NULL));
+
+ HostResolver::RequestInfo info(HostPortPair(domain_name.c_str(), 80));
+
+ CompletionCallback callback = base::Bind(&GDig::ResolverCallback,
+ base::Unretained(this));
+ int ret = resolver_->Resolve(info, &addrlist_, callback, NULL,
+ BoundNetLog());
+ DCHECK(ret == ERR_IO_PENDING);
+
+ timeout_.Reset(MessageLoop::QuitClosure());
+ MessageLoop::current()->PostDelayedTask(FROM_HERE,
+ timeout_.callback(),
+ base::TimeDelta::FromSeconds(5));
szym 2012/05/14 18:48:32 Ideally, make timeout value a command-line argumen
Daniele 2012/05/17 23:04:34 Done.
+ }
+
+ void OnDnsConfigChanged(const DnsConfig& dns_config) {
+ timeout_.Cancel();
+ dns_config_ = dns_config;
+ MessageLoop::current()->PostTask(FROM_HERE,
szym 2012/05/14 18:48:32 No need to post it on MessageLoop. Just let go of
Daniele 2012/05/17 23:04:34 Releasing the pointer here, caused a DCHECK to com
+ base::Bind(&GDig::ReleaseDnsConfigService,
+ base::Unretained(this)));
+
+ ResolveName(domain_name_);
+ }
+
+ bool ParseCommandLine(int argc, const char* argv[]){
+ CommandLine::Init(argc, argv);
+ const CommandLine& parsed_command_line = *CommandLine::ForCurrentProcess();
+
+ if (parsed_command_line.GetArgs().size() != 1){
+ return false;
+ }
+ domain_name_ = parsed_command_line.GetArgs().at(0);
+
+ if (parsed_command_line.HasSwitch("max_retry")) {
szym 2012/05/14 18:48:32 These values are not going to be used with DnsConf
Daniele 2012/05/17 23:04:34 Done.
+ base::StringToInt(parsed_command_line.GetSwitchValueASCII("max_retry"),
+ &max_retry_);
+ }
+
+ if (parsed_command_line.HasSwitch("concurrent_resolves")) {
+ base::StringToInt(parsed_command_line.
+ GetSwitchValueASCII("concurrent_resolves"),
+ &concurrent_resolves_);
+ }
+
+ return true;
+ }
+
+ void LoadDnsConfig(){
+
+ timeout_.Reset(MessageLoop::QuitClosure());
+
+ // Is there a better way of doing this?
+ config_service_.reset(DnsConfigService::CreateSystemService().release());
szym 2012/05/14 18:48:32 scoped_ptr::operator= has the semantics you want:
+ config_service_->Watch(base::Bind(&GDig::OnDnsConfigChanged,
+ base::Unretained(this)));
+
+ MessageLoop::current()->PostDelayedTask(FROM_HERE,
+ timeout_.callback(),
+ base::TimeDelta::FromSeconds(5));
+
+ }
+
+ int resolve_name_ret_;
+ AddressList addrlist_;
+
+ base::CancelableClosure timeout_;
+ DnsConfig dns_config_;
+
+ int max_retry_;
+ int concurrent_resolves_;
+
+ std::string domain_name_;
+
+ scoped_ptr<DnsConfigService> config_service_;
+ scoped_ptr<HostResolver> resolver_;
+
+};
+
+} // empty namespace
+
+} // namespace net
+
+int main(int argc, const char* argv[]) {
+ net::GDig dig;
+ return dig.Main(argc, argv);
+}
« net/base/host_resolver_impl.cc ('K') | « net/net.gyp ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698