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

Unified Diff: net/base/address_list.cc

Issue 10309002: Reimplements net::AddressList without struct addrinfo. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: get_canonical_name -> canonical_name. iterator to indexing 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
« no previous file with comments | « net/base/address_list.h ('k') | net/base/address_list_net_log_param.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: net/base/address_list.cc
diff --git a/net/base/address_list.cc b/net/base/address_list.cc
index 4aee12c0f156acab26d33db4de4122dc15e933d5..e5935c7ba59ff029ea12a66072663329d5bc61a3 100644
--- a/net/base/address_list.cc
+++ b/net/base/address_list.cc
@@ -4,283 +4,66 @@
#include "net/base/address_list.h"
-#include <stdlib.h>
-
#include "base/logging.h"
-#include "base/string_util.h"
#include "net/base/net_util.h"
#include "net/base/sys_addrinfo.h"
namespace net {
-namespace {
-
-struct addrinfo* CreateAddrInfo(const IPAddressNumber& address,
- bool canonicalize_name) {
- struct addrinfo* ai = new addrinfo;
- memset(ai, 0, sizeof(addrinfo));
- ai->ai_socktype = SOCK_STREAM;
-
- switch (address.size()) {
- case kIPv4AddressSize: {
- ai->ai_family = AF_INET;
- const size_t sockaddr_in_size = sizeof(struct sockaddr_in);
- ai->ai_addrlen = sockaddr_in_size;
-
- struct sockaddr_in* addr = reinterpret_cast<struct sockaddr_in*>(
- new char[sockaddr_in_size]);
- memset(addr, 0, sockaddr_in_size);
- addr->sin_family = AF_INET;
-#if defined(SIN6_LEN)
- addr->sin_len = sockaddr_in_size;
-#endif
- memcpy(&addr->sin_addr, &address[0], kIPv4AddressSize);
- ai->ai_addr = reinterpret_cast<struct sockaddr*>(addr);
- break;
- }
- case kIPv6AddressSize: {
- ai->ai_family = AF_INET6;
- const size_t sockaddr_in6_size = sizeof(struct sockaddr_in6);
- ai->ai_addrlen = sockaddr_in6_size;
-
- struct sockaddr_in6* addr6 = reinterpret_cast<struct sockaddr_in6*>(
- new char[sockaddr_in6_size]);
- memset(addr6, 0, sockaddr_in6_size);
- addr6->sin6_family = AF_INET6;
-#if defined(SIN6_LEN)
- addr6->sin6_len = sockaddr_in6_size;
-#endif
- memcpy(&addr6->sin6_addr, &address[0], kIPv6AddressSize);
- ai->ai_addr = reinterpret_cast<struct sockaddr*>(addr6);
- break;
- }
- default: {
- NOTREACHED() << "Bad IP address";
- break;
- }
- }
-
- if (canonicalize_name) {
- std::string name = NetAddressToString(ai);
- ai->ai_canonname = base::strdup(name.c_str());
- }
- return ai;
-}
-
-} // namespace
-
-struct AddressList::Data : public base::RefCountedThreadSafe<Data> {
- Data(struct addrinfo* ai, bool is_system_created);
-
- // This variable is const since it should NOT be mutated. Since
- // Data is reference counted, this |head| could be shared by multiple
- // instances of AddressList, hence we need to be careful not to mutate
- // it from any one instance.
- const struct addrinfo * const head;
-
- // Indicates which free function to use for |head|.
- bool is_system_created;
-
- private:
- friend class base::RefCountedThreadSafe<Data>;
-
- ~Data();
-};
+AddressList::AddressList() {}
-AddressList::AddressList() {
-}
-
-AddressList::AddressList(const AddressList& addresslist)
- : data_(addresslist.data_) {
-}
+AddressList::~AddressList() {}
-AddressList::~AddressList() {
+AddressList::AddressList(const IPEndPoint& endpoint) {
+ push_back(endpoint);
}
-AddressList& AddressList::operator=(const AddressList& addresslist) {
- data_ = addresslist.data_;
- return *this;
+// static
+AddressList AddressList::CreateFromIPAddress(const IPAddressNumber& address,
+ uint16 port) {
+ return AddressList(IPEndPoint(address, port));
}
// static
AddressList AddressList::CreateFromIPAddressList(
const IPAddressList& addresses,
const std::string& canonical_name) {
- DCHECK(!addresses.empty());
- struct addrinfo* head = NULL;
- struct addrinfo* next = NULL;
-
- for (IPAddressList::const_iterator it = addresses.begin();
- it != addresses.end(); ++it) {
- if (head == NULL) {
- head = next = CreateAddrInfo(*it, false);
- if (!canonical_name.empty()) {
- head->ai_canonname = base::strdup(canonical_name.c_str());
- }
- } else {
- next->ai_next = CreateAddrInfo(*it, false);
- next = next->ai_next;
- }
+ AddressList list;
+ list.set_canonical_name(canonical_name);
+ for (IPAddressList::const_iterator iter = addresses.begin();
+ iter != addresses.end(); ++iter) {
+ list.push_back(IPEndPoint(*iter, 0));
}
-
- return AddressList(new Data(head, false));
+ return list;
}
// static
-AddressList AddressList::CreateFromIPAddress(
- const IPAddressNumber& address,
- uint16 port) {
- return CreateFromIPAddressWithCname(address, port, false);
-}
-
-// static
-AddressList AddressList::CreateFromIPAddressWithCname(
- const IPAddressNumber& address,
- uint16 port,
- bool canonicalize_name) {
- struct addrinfo* ai = CreateAddrInfo(address, canonicalize_name);
-
- SetPortForAllAddrinfos(ai, port);
- return AddressList(new Data(ai, false /*is_system_created*/));
-}
-
-
-// static
-AddressList AddressList::CreateByAdoptingFromSystem(struct addrinfo* head) {
- return AddressList(new Data(head, true /*is_system_created*/));
-}
-
-// static
-AddressList AddressList::CreateByCopying(const struct addrinfo* head) {
- return AddressList(new Data(CreateCopyOfAddrinfo(head, true /*recursive*/),
- false /*is_system_created*/));
-}
-
-// static
-AddressList AddressList::CreateByCopyingFirstAddress(
- const struct addrinfo* head) {
- return AddressList(new Data(CreateCopyOfAddrinfo(head, false /*recursive*/),
- false /*is_system_created*/));
-}
-
-// static
-AddressList AddressList::CreateFromSockaddr(
- const struct sockaddr* address,
- socklen_t address_length,
- int socket_type,
- int protocol) {
- // Do sanity checking on socket_type and protocol.
- DCHECK(socket_type == SOCK_DGRAM || socket_type == SOCK_STREAM);
- DCHECK(protocol == IPPROTO_TCP || protocol == IPPROTO_UDP);
-
- struct addrinfo* ai = new addrinfo;
- memset(ai, 0, sizeof(addrinfo));
- switch (address_length) {
- case sizeof(struct sockaddr_in):
- {
- const struct sockaddr_in* sin =
- reinterpret_cast<const struct sockaddr_in*>(address);
- ai->ai_family = sin->sin_family;
- DCHECK_EQ(AF_INET, ai->ai_family);
- }
- break;
- case sizeof(struct sockaddr_in6):
- {
- const struct sockaddr_in6* sin6 =
- reinterpret_cast<const struct sockaddr_in6*>(address);
- ai->ai_family = sin6->sin6_family;
- DCHECK_EQ(AF_INET6, ai->ai_family);
- }
- break;
- default:
- NOTREACHED() << "Bad IP address";
- break;
- }
- ai->ai_socktype = socket_type;
- ai->ai_protocol = protocol;
- ai->ai_addrlen = address_length;
- ai->ai_addr = reinterpret_cast<struct sockaddr*>(new char[address_length]);
- memcpy(ai->ai_addr, address, address_length);
- return AddressList(new Data(ai, false /*is_system_created*/));
-}
-
-void AddressList::Append(const struct addrinfo* head) {
+AddressList AddressList::CreateFromAddrinfo(const struct addrinfo* head) {
DCHECK(head);
- // Always create a copy, since the Data might be shared across instances.
- struct addrinfo* new_head = CreateCopyOfAddrinfo(data_->head, true);
- data_ = new Data(new_head, false /*is_system_created*/);
-
- // Find the end of current linked list and append new data there.
- struct addrinfo* copy_ptr = new_head;
- while (copy_ptr->ai_next)
- copy_ptr = copy_ptr->ai_next;
- copy_ptr->ai_next = CreateCopyOfAddrinfo(head, true);
-
- // Only the head of the list should have a canonname. Strip any
- // canonical name in the appended data.
- copy_ptr = copy_ptr->ai_next;
- while (copy_ptr) {
- if (copy_ptr->ai_canonname) {
- free(copy_ptr->ai_canonname);
- copy_ptr->ai_canonname = NULL;
- }
- copy_ptr = copy_ptr->ai_next;
+ AddressList list;
+ if (head->ai_canonname)
+ list.set_canonical_name(std::string(head->ai_canonname));
+ for (const struct addrinfo* ai = head; ai; ai = ai->ai_next) {
+ IPEndPoint ipe;
+ // NOTE: Ignoring non-INET* families.
+ if (ipe.FromSockAddr(ai->ai_addr, ai->ai_addrlen))
+ list.push_back(ipe);
+ else
+ DLOG(WARNING) << "Unknown family found in addrinfo: " << ai->ai_family;
}
+ return list;
}
-void AddressList::SetPort(uint16 port) {
- // NOTE: we need to be careful not to mutate the reference-counted data,
- // since it might be shared by other AddressLists.
- struct addrinfo* head = CreateCopyOfAddrinfo(data_->head, true);
- SetPortForAllAddrinfos(head, port);
- data_ = new Data(head, false /*is_system_created*/);
+void AddressList::SetDefaultCanonicalName() {
+ DCHECK(!empty());
+ set_canonical_name(front().ToStringWithoutPort());
}
-uint16 AddressList::GetPort() const {
- return GetPortFromAddrinfo(data_->head);
-}
-
-bool AddressList::GetCanonicalName(std::string* canonical_name) const {
- DCHECK(canonical_name);
- if (!data_ || !data_->head->ai_canonname)
- return false;
- canonical_name->assign(data_->head->ai_canonname);
- return true;
-}
-
-const struct addrinfo* AddressList::head() const {
- if (!data_)
- return NULL;
- return data_->head;
-}
-
-AddressList::AddressList(Data* data) : data_(data) {}
-
-AddressList::Data::Data(struct addrinfo* ai, bool is_system_created)
- : head(ai), is_system_created(is_system_created) {
- DCHECK(head);
-}
-
-AddressList::Data::~Data() {
- // Casting away the const is safe, since upon destruction we know that
- // no one holds a reference to the data any more.
- struct addrinfo* mutable_head = const_cast<struct addrinfo*>(head);
-
- // Call either freeaddrinfo(head), or FreeMyAddrinfo(head), depending who
- // created the data.
- if (is_system_created)
- freeaddrinfo(mutable_head);
- else
- FreeCopyOfAddrinfo(mutable_head);
-}
-
-AddressList CreateAddressListUsingPort(const AddressList& src, int port) {
- if (src.GetPort() == port)
- return src;
-
- AddressList out = src;
- out.SetPort(port);
- return out;
+void SetPortOnAddressList(uint16 port, AddressList* list) {
+ DCHECK(list);
+ for (AddressList::iterator it = list->begin(); it != list->end(); ++it) {
+ *it = IPEndPoint(it->address(), port);
+ }
}
} // namespace net
« no previous file with comments | « net/base/address_list.h ('k') | net/base/address_list_net_log_param.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698