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

Side by Side Diff: net/tools/quic/quic_socket_utils.cc

Issue 300683008: Land Recent QUIC Changes. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 6 years, 6 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
« no previous file with comments | « net/tools/quic/quic_socket_utils.h ('k') | net/tools/quic/test_tools/quic_test_utils.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
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/tools/quic/quic_socket_utils.h" 5 #include "net/tools/quic/quic_socket_utils.h"
6 6
7 #include <errno.h> 7 #include <errno.h>
8 #include <netinet/in.h> 8 #include <netinet/in.h>
9 #include <string.h> 9 #include <string.h>
10 #include <sys/socket.h> 10 #include <sys/socket.h>
(...skipping 136 matching lines...) Expand 10 before | Expand all | Expand 10 after
147 sizeof(struct sockaddr_in))); 147 sizeof(struct sockaddr_in)));
148 } else if (raw_address.ss_family == AF_INET6) { 148 } else if (raw_address.ss_family == AF_INET6) {
149 CHECK(peer_address->FromSockAddr( 149 CHECK(peer_address->FromSockAddr(
150 reinterpret_cast<const sockaddr*>(&raw_address), 150 reinterpret_cast<const sockaddr*>(&raw_address),
151 sizeof(struct sockaddr_in6))); 151 sizeof(struct sockaddr_in6)));
152 } 152 }
153 153
154 return bytes_read; 154 return bytes_read;
155 } 155 }
156 156
157 void QuicSocketUtils::SetIpInfoInCmsg(const IPAddressNumber& self_address,
158 cmsghdr* cmsg) {
159 if (GetAddressFamily(self_address) == ADDRESS_FAMILY_IPV4) {
160 cmsg->cmsg_len = CMSG_LEN(sizeof(in_pktinfo));
161 cmsg->cmsg_level = IPPROTO_IP;
162 cmsg->cmsg_type = IP_PKTINFO;
163 in_pktinfo* pktinfo = reinterpret_cast<in_pktinfo*>(CMSG_DATA(cmsg));
164 memset(pktinfo, 0, sizeof(in_pktinfo));
165 pktinfo->ipi_ifindex = 0;
166 memcpy(&pktinfo->ipi_spec_dst, &self_address[0], self_address.size());
167 } else {
168 cmsg->cmsg_len = CMSG_LEN(sizeof(in6_pktinfo));
169 cmsg->cmsg_level = IPPROTO_IPV6;
170 cmsg->cmsg_type = IPV6_PKTINFO;
171 in6_pktinfo* pktinfo = reinterpret_cast<in6_pktinfo*>(CMSG_DATA(cmsg));
172 memset(pktinfo, 0, sizeof(in6_pktinfo));
173 memcpy(&pktinfo->ipi6_addr, &self_address[0], self_address.size());
174 }
175 }
176
157 // static 177 // static
158 WriteResult QuicSocketUtils::WritePacket(int fd, 178 WriteResult QuicSocketUtils::WritePacket(int fd,
159 const char* buffer, 179 const char* buffer,
160 size_t buf_len, 180 size_t buf_len,
161 const IPAddressNumber& self_address, 181 const IPAddressNumber& self_address,
162 const IPEndPoint& peer_address) { 182 const IPEndPoint& peer_address) {
163 sockaddr_storage raw_address; 183 sockaddr_storage raw_address;
164 socklen_t address_len = sizeof(raw_address); 184 socklen_t address_len = sizeof(raw_address);
165 CHECK(peer_address.ToSockAddr( 185 CHECK(peer_address.ToSockAddr(
166 reinterpret_cast<struct sockaddr*>(&raw_address), 186 reinterpret_cast<struct sockaddr*>(&raw_address),
167 &address_len)); 187 &address_len));
168 iovec iov = {const_cast<char*>(buffer), buf_len}; 188 iovec iov = {const_cast<char*>(buffer), buf_len};
169 189
170 msghdr hdr; 190 msghdr hdr;
171 hdr.msg_name = &raw_address; 191 hdr.msg_name = &raw_address;
172 hdr.msg_namelen = address_len; 192 hdr.msg_namelen = address_len;
173 hdr.msg_iov = &iov; 193 hdr.msg_iov = &iov;
174 hdr.msg_iovlen = 1; 194 hdr.msg_iovlen = 1;
175 hdr.msg_flags = 0; 195 hdr.msg_flags = 0;
176 196
177 const int kSpaceForIpv4 = CMSG_SPACE(sizeof(in_pktinfo)); 197 const int kSpaceForIpv4 = CMSG_SPACE(sizeof(in_pktinfo));
178 const int kSpaceForIpv6 = CMSG_SPACE(sizeof(in6_pktinfo)); 198 const int kSpaceForIpv6 = CMSG_SPACE(sizeof(in6_pktinfo));
179 // kSpaceForIp should be big enough to hold both IPv4 and IPv6 packet info. 199 // kSpaceForIp should be big enough to hold both IPv4 and IPv6 packet info.
180 const int kSpaceForIp = 200 const int kSpaceForIp =
181 (kSpaceForIpv4 < kSpaceForIpv6) ? kSpaceForIpv6 : kSpaceForIpv4; 201 (kSpaceForIpv4 < kSpaceForIpv6) ? kSpaceForIpv6 : kSpaceForIpv4;
182 char cbuf[kSpaceForIp]; 202 char cbuf[kSpaceForIp];
183 if (self_address.empty()) { 203 if (self_address.empty()) {
184 hdr.msg_control = 0; 204 hdr.msg_control = 0;
185 hdr.msg_controllen = 0; 205 hdr.msg_controllen = 0;
186 } else if (GetAddressFamily(self_address) == ADDRESS_FAMILY_IPV4) {
187 hdr.msg_control = cbuf;
188 hdr.msg_controllen = kSpaceForIp;
189 cmsghdr* cmsg = CMSG_FIRSTHDR(&hdr);
190
191 cmsg->cmsg_len = CMSG_LEN(sizeof(in_pktinfo));
192 cmsg->cmsg_level = IPPROTO_IP;
193 cmsg->cmsg_type = IP_PKTINFO;
194 in_pktinfo* pktinfo = reinterpret_cast<in_pktinfo*>(CMSG_DATA(cmsg));
195 memset(pktinfo, 0, sizeof(in_pktinfo));
196 pktinfo->ipi_ifindex = 0;
197 memcpy(&pktinfo->ipi_spec_dst, &self_address[0], self_address.size());
198 hdr.msg_controllen = cmsg->cmsg_len;
199 } else { 206 } else {
200 hdr.msg_control = cbuf; 207 hdr.msg_control = cbuf;
201 hdr.msg_controllen = kSpaceForIp; 208 hdr.msg_controllen = kSpaceForIp;
202 cmsghdr* cmsg = CMSG_FIRSTHDR(&hdr); 209 cmsghdr *cmsg = CMSG_FIRSTHDR(&hdr);
203 210 SetIpInfoInCmsg(self_address, cmsg);
204 cmsg->cmsg_len = CMSG_LEN(sizeof(in6_pktinfo));
205 cmsg->cmsg_level = IPPROTO_IPV6;
206 cmsg->cmsg_type = IPV6_PKTINFO;
207 in6_pktinfo* pktinfo = reinterpret_cast<in6_pktinfo*>(CMSG_DATA(cmsg));
208 memset(pktinfo, 0, sizeof(in6_pktinfo));
209 memcpy(&pktinfo->ipi6_addr, &self_address[0], self_address.size());
210 hdr.msg_controllen = cmsg->cmsg_len; 211 hdr.msg_controllen = cmsg->cmsg_len;
211 } 212 }
212 213
213 int rc = sendmsg(fd, &hdr, 0); 214 int rc = sendmsg(fd, &hdr, 0);
214 if (rc >= 0) { 215 if (rc >= 0) {
215 return WriteResult(WRITE_STATUS_OK, rc); 216 return WriteResult(WRITE_STATUS_OK, rc);
216 } 217 }
217 return WriteResult((errno == EAGAIN || errno == EWOULDBLOCK) ? 218 return WriteResult((errno == EAGAIN || errno == EWOULDBLOCK) ?
218 WRITE_STATUS_BLOCKED : WRITE_STATUS_ERROR, errno); 219 WRITE_STATUS_BLOCKED : WRITE_STATUS_ERROR, errno);
219 } 220 }
220 221
221 } // namespace tools 222 } // namespace tools
222 } // namespace net 223 } // namespace net
OLDNEW
« no previous file with comments | « net/tools/quic/quic_socket_utils.h ('k') | net/tools/quic/test_tools/quic_test_utils.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698