[core] Add support for vsock transport (#32847)

This is another attempt to add support for vsock in grpc since previous
PRs(#24551, #21745) all closed without merging.

The VSOCK address family facilitates communication between
virtual machines and the host they are running on.
This patch will introduce new scheme: [vsock:cid:port] to
support VSOCK address family.

Fixes #32738.

---------

Signed-off-by: Yadong Qi <yadong.qi@intel.com>
Co-authored-by: AJ Heller <hork@google.com>
Co-authored-by: YadongQi <YadongQi@users.noreply.github.com>
pull/33277/head
Yadong 2 years ago committed by GitHub
parent 272a89ad2b
commit 9d765860ef
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
  1. 2
      BUILD
  2. 4
      CMakeLists.txt
  3. 2
      Makefile
  4. 8
      build_autogenerated.yaml
  5. 1
      config.m4
  6. 1
      config.w32
  7. 6
      doc/naming.md
  8. 2
      gRPC-C++.podspec
  9. 3
      gRPC-Core.podspec
  10. 2
      grpc.gemspec
  11. 3
      grpc.gyp
  12. 2
      package.xml
  13. 5
      src/core/ext/filters/client_channel/http_proxy.cc
  14. 2
      src/core/ext/filters/client_channel/resolver/sockaddr/README.md
  15. 24
      src/core/ext/filters/client_channel/resolver/sockaddr/sockaddr_resolver.cc
  16. 4
      src/core/ext/transport/chttp2/server/chttp2_server.cc
  17. 64
      src/core/lib/address_utils/parse_address.cc
  18. 8
      src/core/lib/address_utils/parse_address.h
  19. 47
      src/core/lib/address_utils/sockaddr_utils.cc
  20. 6
      src/core/lib/event_engine/posix_engine/posix_engine_listener_utils.cc
  21. 4
      src/core/lib/event_engine/posix_engine/tcp_socket_utils.cc
  22. 61
      src/core/lib/event_engine/tcp_socket_utils.cc
  23. 3
      src/core/lib/event_engine/tcp_socket_utils.h
  24. 8
      src/core/lib/iomgr/port.h
  25. 7
      src/core/lib/iomgr/sockaddr_posix.h
  26. 3
      src/core/lib/iomgr/tcp_client_posix.cc
  27. 3
      src/core/lib/iomgr/tcp_server_posix.cc
  28. 5
      src/core/lib/iomgr/tcp_server_utils_posix_common.cc
  29. 59
      src/core/lib/iomgr/vsock.cc
  30. 38
      src/core/lib/iomgr/vsock.h
  31. 1
      src/python/grpcio/grpc_core_dependencies.py
  32. 31
      test/core/address_utils/parse_address_test.cc
  33. 20
      test/core/address_utils/sockaddr_utils_test.cc
  34. 35
      test/core/event_engine/tcp_socket_utils_test.cc
  35. 2
      tools/doxygen/Doxyfile.c++.internal
  36. 2
      tools/doxygen/Doxyfile.core.internal

@ -1330,6 +1330,7 @@ grpc_cc_library(
"//src/core:lib/iomgr/tcp_windows.cc",
"//src/core:lib/iomgr/unix_sockets_posix.cc",
"//src/core:lib/iomgr/unix_sockets_posix_noop.cc",
"//src/core:lib/iomgr/vsock.cc",
"//src/core:lib/iomgr/wakeup_fd_eventfd.cc",
"//src/core:lib/iomgr/wakeup_fd_nospecial.cc",
"//src/core:lib/iomgr/wakeup_fd_pipe.cc",
@ -1426,6 +1427,7 @@ grpc_cc_library(
"//src/core:lib/iomgr/tcp_server_utils_posix.h",
"//src/core:lib/iomgr/tcp_windows.h",
"//src/core:lib/iomgr/unix_sockets_posix.h",
"//src/core:lib/iomgr/vsock.h",
"//src/core:lib/iomgr/wakeup_fd_pipe.h",
"//src/core:lib/iomgr/wakeup_fd_posix.h",
"//src/core:lib/resource_quota/api.h",

4
CMakeLists.txt generated

@ -2181,6 +2181,7 @@ add_library(grpc
src/core/lib/iomgr/timer_manager.cc
src/core/lib/iomgr/unix_sockets_posix.cc
src/core/lib/iomgr/unix_sockets_posix_noop.cc
src/core/lib/iomgr/vsock.cc
src/core/lib/iomgr/wakeup_fd_eventfd.cc
src/core/lib/iomgr/wakeup_fd_nospecial.cc
src/core/lib/iomgr/wakeup_fd_pipe.cc
@ -2882,6 +2883,7 @@ add_library(grpc_unsecure
src/core/lib/iomgr/timer_manager.cc
src/core/lib/iomgr/unix_sockets_posix.cc
src/core/lib/iomgr/unix_sockets_posix_noop.cc
src/core/lib/iomgr/vsock.cc
src/core/lib/iomgr/wakeup_fd_eventfd.cc
src/core/lib/iomgr/wakeup_fd_nospecial.cc
src/core/lib/iomgr/wakeup_fd_pipe.cc
@ -4413,6 +4415,7 @@ add_library(grpc_authorization_provider
src/core/lib/iomgr/timer_manager.cc
src/core/lib/iomgr/unix_sockets_posix.cc
src/core/lib/iomgr/unix_sockets_posix_noop.cc
src/core/lib/iomgr/vsock.cc
src/core/lib/iomgr/wakeup_fd_eventfd.cc
src/core/lib/iomgr/wakeup_fd_nospecial.cc
src/core/lib/iomgr/wakeup_fd_pipe.cc
@ -11648,6 +11651,7 @@ add_executable(frame_test
src/core/lib/iomgr/timer_manager.cc
src/core/lib/iomgr/unix_sockets_posix.cc
src/core/lib/iomgr/unix_sockets_posix_noop.cc
src/core/lib/iomgr/vsock.cc
src/core/lib/iomgr/wakeup_fd_eventfd.cc
src/core/lib/iomgr/wakeup_fd_nospecial.cc
src/core/lib/iomgr/wakeup_fd_pipe.cc

2
Makefile generated

@ -1562,6 +1562,7 @@ LIBGRPC_SRC = \
src/core/lib/iomgr/timer_manager.cc \
src/core/lib/iomgr/unix_sockets_posix.cc \
src/core/lib/iomgr/unix_sockets_posix_noop.cc \
src/core/lib/iomgr/vsock.cc \
src/core/lib/iomgr/wakeup_fd_eventfd.cc \
src/core/lib/iomgr/wakeup_fd_nospecial.cc \
src/core/lib/iomgr/wakeup_fd_pipe.cc \
@ -2117,6 +2118,7 @@ LIBGRPC_UNSECURE_SRC = \
src/core/lib/iomgr/timer_manager.cc \
src/core/lib/iomgr/unix_sockets_posix.cc \
src/core/lib/iomgr/unix_sockets_posix_noop.cc \
src/core/lib/iomgr/vsock.cc \
src/core/lib/iomgr/wakeup_fd_eventfd.cc \
src/core/lib/iomgr/wakeup_fd_nospecial.cc \
src/core/lib/iomgr/wakeup_fd_pipe.cc \

@ -821,6 +821,7 @@ libs:
- src/core/lib/iomgr/timer_heap.h
- src/core/lib/iomgr/timer_manager.h
- src/core/lib/iomgr/unix_sockets_posix.h
- src/core/lib/iomgr/vsock.h
- src/core/lib/iomgr/wakeup_fd_pipe.h
- src/core/lib/iomgr/wakeup_fd_posix.h
- src/core/lib/json/json.h
@ -1611,6 +1612,7 @@ libs:
- src/core/lib/iomgr/timer_manager.cc
- src/core/lib/iomgr/unix_sockets_posix.cc
- src/core/lib/iomgr/unix_sockets_posix_noop.cc
- src/core/lib/iomgr/vsock.cc
- src/core/lib/iomgr/wakeup_fd_eventfd.cc
- src/core/lib/iomgr/wakeup_fd_nospecial.cc
- src/core/lib/iomgr/wakeup_fd_pipe.cc
@ -2199,6 +2201,7 @@ libs:
- src/core/lib/iomgr/timer_heap.h
- src/core/lib/iomgr/timer_manager.h
- src/core/lib/iomgr/unix_sockets_posix.h
- src/core/lib/iomgr/vsock.h
- src/core/lib/iomgr/wakeup_fd_pipe.h
- src/core/lib/iomgr/wakeup_fd_posix.h
- src/core/lib/json/json.h
@ -2598,6 +2601,7 @@ libs:
- src/core/lib/iomgr/timer_manager.cc
- src/core/lib/iomgr/unix_sockets_posix.cc
- src/core/lib/iomgr/unix_sockets_posix_noop.cc
- src/core/lib/iomgr/vsock.cc
- src/core/lib/iomgr/wakeup_fd_eventfd.cc
- src/core/lib/iomgr/wakeup_fd_nospecial.cc
- src/core/lib/iomgr/wakeup_fd_pipe.cc
@ -3691,6 +3695,7 @@ libs:
- src/core/lib/iomgr/timer_heap.h
- src/core/lib/iomgr/timer_manager.h
- src/core/lib/iomgr/unix_sockets_posix.h
- src/core/lib/iomgr/vsock.h
- src/core/lib/iomgr/wakeup_fd_pipe.h
- src/core/lib/iomgr/wakeup_fd_posix.h
- src/core/lib/json/json.h
@ -3974,6 +3979,7 @@ libs:
- src/core/lib/iomgr/timer_manager.cc
- src/core/lib/iomgr/unix_sockets_posix.cc
- src/core/lib/iomgr/unix_sockets_posix_noop.cc
- src/core/lib/iomgr/vsock.cc
- src/core/lib/iomgr/wakeup_fd_eventfd.cc
- src/core/lib/iomgr/wakeup_fd_nospecial.cc
- src/core/lib/iomgr/wakeup_fd_pipe.cc
@ -7635,6 +7641,7 @@ targets:
- src/core/lib/iomgr/timer_heap.h
- src/core/lib/iomgr/timer_manager.h
- src/core/lib/iomgr/unix_sockets_posix.h
- src/core/lib/iomgr/vsock.h
- src/core/lib/iomgr/wakeup_fd_pipe.h
- src/core/lib/iomgr/wakeup_fd_posix.h
- src/core/lib/json/json.h
@ -7899,6 +7906,7 @@ targets:
- src/core/lib/iomgr/timer_manager.cc
- src/core/lib/iomgr/unix_sockets_posix.cc
- src/core/lib/iomgr/unix_sockets_posix_noop.cc
- src/core/lib/iomgr/vsock.cc
- src/core/lib/iomgr/wakeup_fd_eventfd.cc
- src/core/lib/iomgr/wakeup_fd_nospecial.cc
- src/core/lib/iomgr/wakeup_fd_pipe.cc

1
config.m4 generated

@ -687,6 +687,7 @@ if test "$PHP_GRPC" != "no"; then
src/core/lib/iomgr/timer_manager.cc \
src/core/lib/iomgr/unix_sockets_posix.cc \
src/core/lib/iomgr/unix_sockets_posix_noop.cc \
src/core/lib/iomgr/vsock.cc \
src/core/lib/iomgr/wakeup_fd_eventfd.cc \
src/core/lib/iomgr/wakeup_fd_nospecial.cc \
src/core/lib/iomgr/wakeup_fd_pipe.cc \

1
config.w32 generated

@ -652,6 +652,7 @@ if (PHP_GRPC != "no") {
"src\\core\\lib\\iomgr\\timer_manager.cc " +
"src\\core\\lib\\iomgr\\unix_sockets_posix.cc " +
"src\\core\\lib\\iomgr\\unix_sockets_posix_noop.cc " +
"src\\core\\lib\\iomgr\\vsock.cc " +
"src\\core\\lib\\iomgr\\wakeup_fd_eventfd.cc " +
"src\\core\\lib\\iomgr\\wakeup_fd_nospecial.cc " +
"src\\core\\lib\\iomgr\\wakeup_fd_pipe.cc " +

@ -49,6 +49,12 @@ Most gRPC implementations support the following URI schemes:
as the first character; the implementation will prepend this null. Do not include
the null in `abstract_path`.
- `vsock:cid:port` -- VSOCK (Linux systems only)
- `cid` is 32-bit Context Identifier (CID). It indicates the source or
destination, which is either a virtual machine or the host.
- `port` is a 32-bit port number. It differentiates between multiple
services running on a single machine.
The following schemes are supported by the gRPC C-core implementation,
but may not be supported in other languages:

2
gRPC-C++.podspec generated

@ -915,6 +915,7 @@ Pod::Spec.new do |s|
'src/core/lib/iomgr/timer_heap.h',
'src/core/lib/iomgr/timer_manager.h',
'src/core/lib/iomgr/unix_sockets_posix.h',
'src/core/lib/iomgr/vsock.h',
'src/core/lib/iomgr/wakeup_fd_pipe.h',
'src/core/lib/iomgr/wakeup_fd_posix.h',
'src/core/lib/json/json.h',
@ -1953,6 +1954,7 @@ Pod::Spec.new do |s|
'src/core/lib/iomgr/timer_heap.h',
'src/core/lib/iomgr/timer_manager.h',
'src/core/lib/iomgr/unix_sockets_posix.h',
'src/core/lib/iomgr/vsock.h',
'src/core/lib/iomgr/wakeup_fd_pipe.h',
'src/core/lib/iomgr/wakeup_fd_posix.h',
'src/core/lib/json/json.h',

3
gRPC-Core.podspec generated

@ -1491,6 +1491,8 @@ Pod::Spec.new do |s|
'src/core/lib/iomgr/unix_sockets_posix.cc',
'src/core/lib/iomgr/unix_sockets_posix.h',
'src/core/lib/iomgr/unix_sockets_posix_noop.cc',
'src/core/lib/iomgr/vsock.cc',
'src/core/lib/iomgr/vsock.h',
'src/core/lib/iomgr/wakeup_fd_eventfd.cc',
'src/core/lib/iomgr/wakeup_fd_nospecial.cc',
'src/core/lib/iomgr/wakeup_fd_pipe.cc',
@ -2680,6 +2682,7 @@ Pod::Spec.new do |s|
'src/core/lib/iomgr/timer_heap.h',
'src/core/lib/iomgr/timer_manager.h',
'src/core/lib/iomgr/unix_sockets_posix.h',
'src/core/lib/iomgr/vsock.h',
'src/core/lib/iomgr/wakeup_fd_pipe.h',
'src/core/lib/iomgr/wakeup_fd_posix.h',
'src/core/lib/json/json.h',

2
grpc.gemspec generated

@ -1397,6 +1397,8 @@ Gem::Specification.new do |s|
s.files += %w( src/core/lib/iomgr/unix_sockets_posix.cc )
s.files += %w( src/core/lib/iomgr/unix_sockets_posix.h )
s.files += %w( src/core/lib/iomgr/unix_sockets_posix_noop.cc )
s.files += %w( src/core/lib/iomgr/vsock.cc )
s.files += %w( src/core/lib/iomgr/vsock.h )
s.files += %w( src/core/lib/iomgr/wakeup_fd_eventfd.cc )
s.files += %w( src/core/lib/iomgr/wakeup_fd_nospecial.cc )
s.files += %w( src/core/lib/iomgr/wakeup_fd_pipe.cc )

3
grpc.gyp generated

@ -865,6 +865,7 @@
'src/core/lib/iomgr/timer_manager.cc',
'src/core/lib/iomgr/unix_sockets_posix.cc',
'src/core/lib/iomgr/unix_sockets_posix_noop.cc',
'src/core/lib/iomgr/vsock.cc',
'src/core/lib/iomgr/wakeup_fd_eventfd.cc',
'src/core/lib/iomgr/wakeup_fd_nospecial.cc',
'src/core/lib/iomgr/wakeup_fd_pipe.cc',
@ -1359,6 +1360,7 @@
'src/core/lib/iomgr/timer_manager.cc',
'src/core/lib/iomgr/unix_sockets_posix.cc',
'src/core/lib/iomgr/unix_sockets_posix_noop.cc',
'src/core/lib/iomgr/vsock.cc',
'src/core/lib/iomgr/wakeup_fd_eventfd.cc',
'src/core/lib/iomgr/wakeup_fd_nospecial.cc',
'src/core/lib/iomgr/wakeup_fd_pipe.cc',
@ -1875,6 +1877,7 @@
'src/core/lib/iomgr/timer_manager.cc',
'src/core/lib/iomgr/unix_sockets_posix.cc',
'src/core/lib/iomgr/unix_sockets_posix_noop.cc',
'src/core/lib/iomgr/vsock.cc',
'src/core/lib/iomgr/wakeup_fd_eventfd.cc',
'src/core/lib/iomgr/wakeup_fd_nospecial.cc',
'src/core/lib/iomgr/wakeup_fd_pipe.cc',

2
package.xml generated

@ -1379,6 +1379,8 @@
<file baseinstalldir="/" name="src/core/lib/iomgr/unix_sockets_posix.cc" role="src" />
<file baseinstalldir="/" name="src/core/lib/iomgr/unix_sockets_posix.h" role="src" />
<file baseinstalldir="/" name="src/core/lib/iomgr/unix_sockets_posix_noop.cc" role="src" />
<file baseinstalldir="/" name="src/core/lib/iomgr/vsock.cc" role="src" />
<file baseinstalldir="/" name="src/core/lib/iomgr/vsock.h" role="src" />
<file baseinstalldir="/" name="src/core/lib/iomgr/wakeup_fd_eventfd.cc" role="src" />
<file baseinstalldir="/" name="src/core/lib/iomgr/wakeup_fd_nospecial.cc" role="src" />
<file baseinstalldir="/" name="src/core/lib/iomgr/wakeup_fd_pipe.cc" role="src" />

@ -180,6 +180,11 @@ absl::optional<std::string> HttpProxyMapper::MapName(
std::string(server_uri).c_str());
return absl::nullopt;
}
if (uri->scheme() == "vsock") {
gpr_log(GPR_INFO, "not using proxy for VSock '%s'",
std::string(server_uri).c_str());
return absl::nullopt;
}
// Prefer using 'no_grpc_proxy'. Fallback on 'no_proxy' if it is not set.
auto no_proxy_str = GetEnv("no_grpc_proxy");
if (!no_proxy_str.has_value()) {

@ -1 +1 @@
Support for resolving ipv4:, ipv6:, unix: schemes
Support for resolving ipv4:, ipv6:, unix:, vsock: schemes

@ -172,6 +172,26 @@ class UnixAbstractResolverFactory : public ResolverFactory {
};
#endif // GRPC_HAVE_UNIX_SOCKET
#ifdef GRPC_HAVE_VSOCK
class VSockResolverFactory : public ResolverFactory {
public:
bool IsValidUri(const URI& uri) const override {
return ParseUri(uri, grpc_parse_vsock, nullptr);
}
OrphanablePtr<Resolver> CreateResolver(ResolverArgs args) const override {
return CreateSockaddrResolver(std::move(args), grpc_parse_vsock);
}
std::string GetDefaultAuthority(const URI& /*uri*/) const override {
return "localhost";
}
absl::string_view scheme() const override { return "vsock"; }
};
#endif // GRPC_HAVE_VSOCK
} // namespace
void RegisterSockaddrResolver(CoreConfiguration::Builder* builder) {
@ -185,6 +205,10 @@ void RegisterSockaddrResolver(CoreConfiguration::Builder* builder) {
builder->resolver_registry()->RegisterResolverFactory(
std::make_unique<UnixAbstractResolverFactory>());
#endif
#ifdef GRPC_HAVE_VSOCK
builder->resolver_registry()->RegisterResolverFactory(
std::make_unique<VSockResolverFactory>());
#endif
}
} // namespace grpc_core

@ -71,6 +71,7 @@
#include "src/core/lib/iomgr/resolved_address.h"
#include "src/core/lib/iomgr/tcp_server.h"
#include "src/core/lib/iomgr/unix_sockets_posix.h"
#include "src/core/lib/iomgr/vsock.h"
#include "src/core/lib/resource_quota/memory_quota.h"
#include "src/core/lib/resource_quota/resource_quota.h"
#include "src/core/lib/security/credentials/credentials.h"
@ -98,6 +99,7 @@ using ::grpc_event_engine::experimental::EventEngine;
const char kUnixUriPrefix[] = "unix:";
const char kUnixAbstractUriPrefix[] = "unix-abstract:";
const char kVSockUriPrefix[] = "vsock:";
class Chttp2ServerListener : public Server::ListenerInterface {
public:
@ -941,6 +943,8 @@ grpc_error_handle Chttp2ServerAddPort(Server* server, const char* addr,
kUnixAbstractUriPrefix)) {
resolved_or =
grpc_resolve_unix_abstract_domain_address(parsed_addr_unprefixed);
} else if (absl::ConsumePrefix(&parsed_addr_unprefixed, kVSockUriPrefix)) {
resolved_or = grpc_resolve_vsock_address(parsed_addr_unprefixed);
} else {
resolved_or =
GetDNSResolver()->LookupHostnameBlocking(parsed_addr, "https");

@ -20,6 +20,12 @@
#include "src/core/lib/address_utils/parse_address.h"
#include "src/core/lib/iomgr/port.h" // IWYU pragma: keep
#ifdef GRPC_HAVE_VSOCK
#include <linux/vm_sockets.h>
#endif
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
@ -38,7 +44,6 @@
#include "src/core/lib/gprpp/host_port.h"
#include "src/core/lib/gprpp/status_helper.h"
#include "src/core/lib/iomgr/grpc_if_nametoindex.h"
#include "src/core/lib/iomgr/port.h"
#include "src/core/lib/iomgr/sockaddr.h"
#include "src/core/lib/iomgr/socket_utils.h"
@ -144,6 +149,60 @@ grpc_error_handle UnixAbstractSockaddrPopulate(
} // namespace grpc_core
#endif // GRPC_HAVE_UNIX_SOCKET
#ifdef GRPC_HAVE_VSOCK
bool grpc_parse_vsock(const grpc_core::URI& uri,
grpc_resolved_address* resolved_addr) {
if (uri.scheme() != "vsock") {
gpr_log(GPR_ERROR, "Expected 'vsock' scheme, got '%s'",
uri.scheme().c_str());
return false;
}
grpc_error_handle error =
grpc_core::VSockaddrPopulate(uri.path(), resolved_addr);
if (!error.ok()) {
gpr_log(GPR_ERROR, "%s", grpc_core::StatusToString(error).c_str());
return false;
}
return true;
}
namespace grpc_core {
grpc_error_handle VSockaddrPopulate(absl::string_view path,
grpc_resolved_address* resolved_addr) {
memset(resolved_addr, 0, sizeof(*resolved_addr));
struct sockaddr_vm* vm =
reinterpret_cast<struct sockaddr_vm*>(resolved_addr->addr);
vm->svm_family = AF_VSOCK;
std::string s = std::string(path);
if (sscanf(s.c_str(), "%u:%u", &vm->svm_cid, &vm->svm_port) != 2) {
return GRPC_ERROR_CREATE(
absl::StrCat("Failed to parse vsock cid/port: ", s));
}
resolved_addr->len = static_cast<socklen_t>(sizeof(*vm));
return absl::OkStatus();
}
} // namespace grpc_core
#else // GRPC_HAVE_VSOCK
bool grpc_parse_vsock(const grpc_core::URI& /* uri */,
grpc_resolved_address* /* resolved_addr */) {
GPR_UNREACHABLE_CODE(return false);
}
namespace grpc_core {
grpc_error_handle VSockaddrPopulate(
absl::string_view /* path */, grpc_resolved_address* /* resolved_addr */) {
GPR_UNREACHABLE_CODE(return absl::InvalidArgumentError("vsock unsupported."));
}
} // namespace grpc_core
#endif // GRPC_HAVE_VSOCK
bool grpc_parse_ipv4_hostport(absl::string_view hostport,
grpc_resolved_address* addr, bool log_errors) {
bool success = false;
@ -299,6 +358,9 @@ bool grpc_parse_uri(const grpc_core::URI& uri,
if (uri.scheme() == "unix-abstract") {
return grpc_parse_unix_abstract(uri, resolved_addr);
}
if (uri.scheme() == "vsock") {
return grpc_parse_vsock(uri, resolved_addr);
}
if (uri.scheme() == "ipv4") {
return grpc_parse_ipv4(uri, resolved_addr);
}

@ -40,6 +40,11 @@ bool grpc_parse_unix(const grpc_core::URI& uri,
bool grpc_parse_unix_abstract(const grpc_core::URI& uri,
grpc_resolved_address* resolved_addr);
/// Populate \a resolved_addr from \a uri, whose path is expected to contain a
/// vsock cid:port pair. Returns true upon success.
bool grpc_parse_vsock(const grpc_core::URI& uri,
grpc_resolved_address* resolved_addr);
/// Populate \a resolved_addr from \a uri, whose path is expected to contain an
/// IPv4 host:port pair. Returns true upon success.
bool grpc_parse_ipv4(const grpc_core::URI& uri,
@ -81,6 +86,9 @@ grpc_error_handle UnixSockaddrPopulate(absl::string_view path,
grpc_error_handle UnixAbstractSockaddrPopulate(
absl::string_view path, grpc_resolved_address* resolved_addr);
/// Populate \a resolved_addr to be a vsock at \a path
grpc_error_handle VSockaddrPopulate(absl::string_view path,
grpc_resolved_address* resolved_addr);
} // namespace grpc_core
#endif // GRPC_SRC_CORE_LIB_ADDRESS_UTILS_PARSE_ADDRESS_H

@ -22,6 +22,9 @@
#include <errno.h>
#include <inttypes.h>
#ifdef GRPC_HAVE_VSOCK
#include <linux/vm_sockets.h>
#endif
#include <string.h>
#include <initializer_list>
@ -77,6 +80,25 @@ static absl::StatusOr<std::string> grpc_sockaddr_to_uri_unix_if_possible(
}
#endif
#ifdef GRPC_HAVE_VSOCK
static absl::StatusOr<std::string> grpc_sockaddr_to_uri_vsock_if_possible(
const grpc_resolved_address* resolved_addr) {
const grpc_sockaddr* addr =
reinterpret_cast<const grpc_sockaddr*>(resolved_addr->addr);
if (addr->sa_family != AF_VSOCK) {
return absl::InvalidArgumentError(
absl::StrCat("Socket family is not AF_VSOCK: ", addr->sa_family));
}
const auto* vsock_addr = reinterpret_cast<const struct sockaddr_vm*>(addr);
return absl::StrCat("vsock:", vsock_addr->svm_cid, ":", vsock_addr->svm_port);
}
#else
static absl::StatusOr<std::string> grpc_sockaddr_to_uri_vsock_if_possible(
const grpc_resolved_address* /* addr */) {
return absl::InvalidArgumentError("VSOCK is not supported.");
}
#endif
static const uint8_t kV4MappedPrefix[] = {0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0xff, 0xff};
@ -224,6 +246,14 @@ absl::StatusOr<std::string> grpc_sockaddr_to_string(
}
#endif
#ifdef GRPC_HAVE_VSOCK
if (addr->sa_family == GRPC_AF_VSOCK) {
const sockaddr_vm* addr_vm = reinterpret_cast<const sockaddr_vm*>(addr);
out = absl::StrCat(addr_vm->svm_cid, ":", addr_vm->svm_port);
return out;
}
#endif
const void* ip = nullptr;
int port = 0;
uint32_t sin6_scope_id = 0;
@ -269,9 +299,16 @@ absl::StatusOr<std::string> grpc_sockaddr_to_uri(
resolved_addr = &addr_normalized;
}
const char* scheme = grpc_sockaddr_get_uri_scheme(resolved_addr);
if (scheme == nullptr || strcmp("unix", scheme) == 0) {
if (scheme == nullptr) {
return absl::InvalidArgumentError("Unknown address type");
}
if (strcmp("unix", scheme) == 0) {
return grpc_sockaddr_to_uri_unix_if_possible(resolved_addr);
}
if (strcmp("vsock", scheme) == 0) {
return grpc_sockaddr_to_uri_vsock_if_possible(resolved_addr);
}
auto path = grpc_sockaddr_to_string(resolved_addr, false /* normalize */);
if (!path.ok()) return path;
absl::StatusOr<grpc_core::URI> uri =
@ -292,6 +329,10 @@ const char* grpc_sockaddr_get_uri_scheme(
return "ipv6";
case GRPC_AF_UNIX:
return "unix";
#ifdef GRPC_HAVE_VSOCK
case GRPC_AF_VSOCK:
return "vsock";
#endif
}
return nullptr;
}
@ -315,6 +356,10 @@ int grpc_sockaddr_get_port(const grpc_resolved_address* resolved_addr) {
#ifdef GRPC_HAVE_UNIX_SOCKET
case AF_UNIX:
return 1;
#endif
#ifdef GRPC_HAVE_VSOCK
case AF_VSOCK:
return 1;
#endif
default:
gpr_log(GPR_ERROR, "Unknown socket family %d in grpc_sockaddr_get_port",

@ -148,7 +148,8 @@ absl::Status PrepareSocket(const PosixTcpOptions& options,
}
});
if (PosixSocketWrapper::IsSocketReusePortSupported() &&
options.allow_reuse_port && socket.addr.address()->sa_family != AF_UNIX) {
options.allow_reuse_port && socket.addr.address()->sa_family != AF_UNIX &&
!ResolvedAddressIsVSock(socket.addr)) {
GRPC_RETURN_IF_ERROR(socket.sock.SetSocketReusePort(1));
}
@ -164,7 +165,8 @@ absl::Status PrepareSocket(const PosixTcpOptions& options,
GRPC_RETURN_IF_ERROR(socket.sock.SetSocketNonBlocking(1));
GRPC_RETURN_IF_ERROR(socket.sock.SetSocketCloexec(1));
if (socket.addr.address()->sa_family != AF_UNIX) {
if (socket.addr.address()->sa_family != AF_UNIX &&
!ResolvedAddressIsVSock(socket.addr)) {
GRPC_RETURN_IF_ERROR(socket.sock.SetSocketLowLatency(1));
GRPC_RETURN_IF_ERROR(socket.sock.SetSocketReuseAddr(1));
socket.sock.TrySetSocketTcpUserTimeout(options, false);

@ -128,8 +128,8 @@ absl::Status PrepareTcpClientSocket(PosixSocketWrapper sock,
if (options.tcp_receive_buffer_size != options.kReadBufferSizeUnset) {
GRPC_RETURN_IF_ERROR(sock.SetSocketRcvBuf(options.tcp_receive_buffer_size));
}
if (reinterpret_cast<const sockaddr*>(addr.address())->sa_family != AF_UNIX) {
// If its not a unix socket address.
if (addr.address()->sa_family != AF_UNIX && !ResolvedAddressIsVSock(addr)) {
// If its not a unix socket or vsock address.
GRPC_RETURN_IF_ERROR(sock.SetSocketLowLatency(1));
GRPC_RETURN_IF_ERROR(sock.SetSocketReuseAddr(1));
sock.TrySetSocketTcpUserTimeout(options, true);

@ -36,6 +36,10 @@
#include <sys/un.h>
#endif
#ifdef GRPC_HAVE_VSOCK
#include <linux/vm_sockets.h>
#endif
#include <errno.h>
#include <inttypes.h>
#include <stdlib.h>
@ -70,6 +74,10 @@ absl::StatusOr<std::string> GetScheme(
return "ipv6";
case AF_UNIX:
return "unix";
#ifdef GRPC_HAVE_VSOCK
case AF_VSOCK:
return "vsock";
#endif
default:
return absl::InvalidArgumentError(
absl::StrFormat("Unknown sockaddr family: %d",
@ -142,6 +150,39 @@ absl::StatusOr<std::string> ResolvedAddrToUriUnixIfPossible(
}
#endif
#ifdef GRPC_HAVE_VSOCK
absl::StatusOr<std::string> ResolvedAddrToVsockPathIfPossible(
const EventEngine::ResolvedAddress* resolved_addr) {
const sockaddr* addr = resolved_addr->address();
if (addr->sa_family != AF_VSOCK) {
return absl::InvalidArgumentError(
absl::StrCat("Socket family is not AF_VSOCK: ", addr->sa_family));
}
const sockaddr_vm* vm_addr = reinterpret_cast<const sockaddr_vm*>(addr);
return absl::StrCat(vm_addr->svm_cid, ":", vm_addr->svm_port);
}
absl::StatusOr<std::string> ResolvedAddrToUriVsockIfPossible(
const EventEngine::ResolvedAddress* resolved_addr) {
auto path = ResolvedAddrToVsockPathIfPossible(resolved_addr);
absl::StatusOr<grpc_core::URI> uri =
grpc_core::URI::Create("vsock", /*authority=*/"", std::move(*path),
/*query_parameter_pairs=*/{}, /*fragment=*/"");
if (!uri.ok()) return uri.status();
return uri->ToString();
}
#else
absl::StatusOr<std::string> ResolvedAddrToVsockPathIfPossible(
const EventEngine::ResolvedAddress* /*resolved_addr*/) {
return absl::InvalidArgumentError("VSOCK is not supported.");
}
absl::StatusOr<std::string> ResolvedAddrToUriVsockIfPossible(
const EventEngine::ResolvedAddress* /*resolved_addr*/) {
return absl::InvalidArgumentError("VSOCK is not supported.");
}
#endif
} // namespace
bool ResolvedAddressIsV4Mapped(
@ -232,6 +273,10 @@ int ResolvedAddressGetPort(const EventEngine::ResolvedAddress& resolved_addr) {
#ifdef GRPC_HAVE_UNIX_SOCKET
case AF_UNIX:
return 1;
#endif
#ifdef GRPC_HAVE_VSOCK
case AF_VSOCK:
return 1;
#endif
default:
gpr_log(GPR_ERROR, "Unknown socket family %d in ResolvedAddressGetPort",
@ -292,6 +337,15 @@ absl::optional<int> ResolvedAddressIsWildcard(
}
}
bool ResolvedAddressIsVSock(const EventEngine::ResolvedAddress& resolved_addr) {
#ifdef GRPC_HAVE_VSOCK
return resolved_addr.address()->sa_family == AF_VSOCK;
#else
(void)resolved_addr;
return false;
#endif
}
absl::StatusOr<std::string> ResolvedAddressToNormalizedString(
const EventEngine::ResolvedAddress& resolved_addr) {
EventEngine::ResolvedAddress addr_normalized;
@ -312,6 +366,10 @@ absl::StatusOr<std::string> ResolvedAddressToString(
}
#endif // GRPC_HAVE_UNIX_SOCKET
if (ResolvedAddressIsVSock(resolved_addr)) {
return ResolvedAddrToVsockPathIfPossible(&resolved_addr);
}
const void* ip = nullptr;
int port = 0;
uint32_t sin6_scope_id = 0;
@ -362,6 +420,9 @@ absl::StatusOr<std::string> ResolvedAddressToURI(
if (*scheme == "unix") {
return ResolvedAddrToUriUnixIfPossible(&addr);
}
if (*scheme == "vsock") {
return ResolvedAddrToUriVsockIfPossible(&addr);
}
auto path = ResolvedAddressToString(addr);
GRPC_RETURN_IF_ERROR(path.status());
absl::StatusOr<grpc_core::URI> uri =

@ -61,6 +61,9 @@ void ResolvedAddressSetPort(EventEngine::ResolvedAddress& resolved_addr,
absl::optional<int> ResolvedAddressIsWildcard(
const EventEngine::ResolvedAddress& addr);
// Returns true if resolved_addr is an VSOCK address. Otherwise returns false.
bool ResolvedAddressIsVSock(const EventEngine::ResolvedAddress& resolved_addr);
// Converts a EventEngine::ResolvedAddress into a newly-allocated
// human-readable string.
// Currently, only the AF_INET, AF_INET6, and AF_UNIX families are

@ -37,6 +37,11 @@
#define GRPC_HAVE_IP_PKTINFO 1
#define GRPC_HAVE_MSG_NOSIGNAL 1
#define GRPC_HAVE_UNIX_SOCKET 1
#ifdef LINUX_VERSION_CODE
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 9, 0)
#define GRPC_HAVE_VSOCK 1
#endif // LINUX_VERSION_CODE >= KERNEL_VERSION(3, 9, 0)
#endif // LINUX_VERSION_CODE
#define GRPC_LINUX_EVENTFD 1
#define GRPC_POSIX_SOCKET 1
#define GRPC_POSIX_SOCKETUTILS 1
@ -55,6 +60,9 @@
#if LINUX_VERSION_CODE >= KERNEL_VERSION(4, 0, 0)
#define GRPC_LINUX_ERRQUEUE 1
#endif // LINUX_VERSION_CODE >= KERNEL_VERSION(4, 0, 0)
#if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 9, 0)
#define GRPC_HAVE_VSOCK 1
#endif // LINUX_VERSION_CODE >= KERNEL_VERSION(3, 9, 0)
#endif // LINUX_VERSION_CODE
#define GRPC_LINUX_MULTIPOLL_WITH_EPOLL 1
#define GRPC_POSIX_FORK 1

@ -33,6 +33,10 @@
#include <sys/types.h>
#include <unistd.h>
#ifdef GRPC_HAVE_VSOCK
#include <linux/vm_sockets.h>
#endif
typedef struct sockaddr grpc_sockaddr;
typedef struct sockaddr_in grpc_sockaddr_in;
typedef struct in_addr grpc_in_addr;
@ -47,6 +51,9 @@ typedef struct in6_addr grpc_in6_addr;
#define GRPC_AF_UNSPEC AF_UNSPEC
#define GRPC_AF_UNIX AF_UNIX
#ifdef GRPC_HAVE_VSOCK
#define GRPC_AF_VSOCK AF_VSOCK
#endif
#define GRPC_AF_INET AF_INET
#define GRPC_AF_INET6 AF_INET6

@ -51,6 +51,7 @@
#include "src/core/lib/iomgr/tcp_posix.h"
#include "src/core/lib/iomgr/timer.h"
#include "src/core/lib/iomgr/unix_sockets_posix.h"
#include "src/core/lib/iomgr/vsock.h"
#include "src/core/lib/slice/slice_internal.h"
extern grpc_core::TraceFlag grpc_tcp_trace;
@ -111,7 +112,7 @@ static grpc_error_handle prepare_socket(
err = grpc_set_socket_rcvbuf(fd, options.tcp_receive_buffer_size);
if (!err.ok()) goto error;
}
if (!grpc_is_unix_socket(addr)) {
if (!grpc_is_unix_socket(addr) && !grpc_is_vsock(addr)) {
err = grpc_set_socket_low_latency(fd, 1);
if (!err.ok()) goto error;
err = grpc_set_socket_reuse_addr(fd, 1);

@ -74,6 +74,7 @@
#include "src/core/lib/iomgr/tcp_server.h"
#include "src/core/lib/iomgr/tcp_server_utils_posix.h"
#include "src/core/lib/iomgr/unix_sockets_posix.h"
#include "src/core/lib/iomgr/vsock.h"
#include "src/core/lib/resource_quota/api.h"
#include "src/core/lib/transport/error_utils.h"
@ -755,7 +756,7 @@ static void tcp_server_start(grpc_tcp_server* s,
sp = s->head;
while (sp != nullptr) {
if (s->so_reuseport && !grpc_is_unix_socket(&sp->addr) &&
pollsets->size() > 1) {
!grpc_is_vsock(&sp->addr) && pollsets->size() > 1) {
GPR_ASSERT(GRPC_LOG_IF_ERROR(
"clone_port", clone_port(sp, (unsigned)(pollsets->size() - 1))));
for (i = 0; i < pollsets->size(); i++) {

@ -42,6 +42,7 @@
#include "src/core/lib/iomgr/sockaddr.h"
#include "src/core/lib/iomgr/tcp_server_utils_posix.h"
#include "src/core/lib/iomgr/unix_sockets_posix.h"
#include "src/core/lib/iomgr/vsock.h"
#define MIN_SAFE_ACCEPT_QUEUE_SIZE 100
@ -190,7 +191,7 @@ grpc_error_handle grpc_tcp_server_prepare_socket(
GPR_ASSERT(fd >= 0);
if (so_reuseport && !grpc_is_unix_socket(addr)) {
if (so_reuseport && !grpc_is_unix_socket(addr) && !grpc_is_vsock(addr)) {
err = grpc_set_socket_reuse_port(fd, 1);
if (!err.ok()) goto error;
}
@ -206,7 +207,7 @@ grpc_error_handle grpc_tcp_server_prepare_socket(
if (!err.ok()) goto error;
err = grpc_set_socket_cloexec(fd, 1);
if (!err.ok()) goto error;
if (!grpc_is_unix_socket(addr)) {
if (!grpc_is_unix_socket(addr) && !grpc_is_vsock(addr)) {
err = grpc_set_socket_low_latency(fd, 1);
if (!err.ok()) goto error;
err = grpc_set_socket_reuse_addr(fd, 1);

@ -0,0 +1,59 @@
//
//
// Copyright 2023 gRPC authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
//
#include <grpc/support/port_platform.h>
#include "src/core/lib/iomgr/vsock.h"
#ifdef GRPC_HAVE_VSOCK
#include <string.h>
#include <sys/stat.h>
#include <sys/types.h>
#include "absl/strings/str_cat.h"
#include <grpc/support/alloc.h>
#include <grpc/support/log.h>
#include "src/core/lib/address_utils/parse_address.h"
#include "src/core/lib/gpr/useful.h"
#include "src/core/lib/gprpp/crash.h"
#include "src/core/lib/iomgr/sockaddr.h"
#include "src/core/lib/transport/error_utils.h"
absl::StatusOr<std::vector<grpc_resolved_address>> grpc_resolve_vsock_address(
absl::string_view name) {
grpc_resolved_address addr;
grpc_error_handle error = grpc_core::VSockaddrPopulate(name, &addr);
GRPC_RETURN_IF_ERROR(error);
return std::vector<grpc_resolved_address>({addr});
}
int grpc_is_vsock(const grpc_resolved_address* resolved_addr) {
const grpc_sockaddr* addr =
reinterpret_cast<const grpc_sockaddr*>(resolved_addr->addr);
return addr->sa_family == AF_VSOCK;
}
#else
absl::StatusOr<std::vector<grpc_resolved_address>> grpc_resolve_vsock_address(
absl::string_view /*name*/) {
return absl::InvalidArgumentError("VSOCK is not supported.");
}
int grpc_is_vsock(const grpc_resolved_address* /*resolved_addr*/) { return 0; }
#endif

@ -0,0 +1,38 @@
//
//
// Copyright 2023 gRPC authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
//
#ifndef GRPC_SRC_CORE_LIB_IOMGR_VSOCK_H
#define GRPC_SRC_CORE_LIB_IOMGR_VSOCK_H
#include <grpc/support/port_platform.h>
#include <string>
#include "absl/strings/string_view.h"
#include <grpc/support/string_util.h>
#include "src/core/lib/iomgr/port.h"
#include "src/core/lib/iomgr/resolve_address.h"
absl::StatusOr<std::vector<grpc_resolved_address>> grpc_resolve_vsock_address(
absl::string_view name);
int grpc_is_vsock(const grpc_resolved_address* resolved_addr);
#endif /* GRPC_SRC_CORE_LIB_IOMGR_VSOCK_H */

@ -661,6 +661,7 @@ CORE_SOURCE_FILES = [
'src/core/lib/iomgr/timer_manager.cc',
'src/core/lib/iomgr/unix_sockets_posix.cc',
'src/core/lib/iomgr/unix_sockets_posix_noop.cc',
'src/core/lib/iomgr/vsock.cc',
'src/core/lib/iomgr/wakeup_fd_eventfd.cc',
'src/core/lib/iomgr/wakeup_fd_nospecial.cc',
'src/core/lib/iomgr/wakeup_fd_pipe.cc',

@ -21,6 +21,10 @@
#include <sys/un.h>
#endif
#ifdef GRPC_HAVE_VSOCK
#include <linux/vm_sockets.h>
#endif
#include <string>
#include "absl/status/status.h"
@ -80,6 +84,32 @@ static void test_grpc_parse_unix_abstract(const char* uri_text,
#endif // GRPC_HAVE_UNIX_SOCKET
#ifdef GRPC_HAVE_VSOCK
static void test_grpc_parse_vsock(const char* uri_text, uint32_t cid,
uint32_t port) {
grpc_core::ExecCtx exec_ctx;
absl::StatusOr<grpc_core::URI> uri = grpc_core::URI::Parse(uri_text);
if (!uri.ok()) {
gpr_log(GPR_ERROR, "%s", uri.status().ToString().c_str());
ASSERT_TRUE(uri.ok());
}
grpc_resolved_address addr;
ASSERT_TRUE(grpc_parse_uri(*uri, &addr));
struct sockaddr_vm* addr_vm =
reinterpret_cast<struct sockaddr_vm*>(addr.addr);
ASSERT_EQ(AF_VSOCK, addr_vm->svm_family);
ASSERT_EQ(grpc_ntohl(addr_vm->svm_cid), cid);
ASSERT_EQ(addr_vm->svm_port, port);
}
#else // GRPC_HAVE_VSOCK
static void test_grpc_parse_vsock(const char* /* uri_text */, ...) {}
#endif // GRPC_HAVE_VSOCK
static void test_grpc_parse_ipv4(const char* uri_text, const char* host,
unsigned short port) {
grpc_core::ExecCtx exec_ctx;
@ -137,6 +167,7 @@ TEST(ParseAddressTest, MainTest) {
test_grpc_parse_unix("unix:/path/name", "/path/name");
test_grpc_parse_unix_abstract("unix-abstract:foobar", "foobar");
test_grpc_parse_vsock("vsock:-1:12345", -1, 12345);
test_grpc_parse_ipv4("ipv4:192.0.2.1:12345", "192.0.2.1", 12345);
test_grpc_parse_ipv6("ipv6:[2001:db8::1]:12345", "2001:db8::1", 12345, 0);
test_grpc_parse_ipv6("ipv6:[2001:db8::1%252]:12345", "2001:db8::1", 12345, 2);

@ -262,6 +262,14 @@ TEST(SockAddrUtilsTest, SockAddrToString) {
EXPECT_EQ(grpc_sockaddr_to_string(&inputun, true).status(),
absl::InvalidArgumentError("empty UDS abstract path"));
#endif
#ifdef GRPC_HAVE_VSOCK
grpc_resolved_address inputvm;
ASSERT_EQ(grpc_core::VSockaddrPopulate("-1:12345", &inputvm),
absl::OkStatus());
EXPECT_EQ(grpc_sockaddr_to_string(&inputvm, true).value(),
absl::StrCat((uint32_t)-1, ":12345"));
#endif
}
#ifdef GRPC_HAVE_UNIX_SOCKET
@ -285,6 +293,18 @@ TEST(SockAddrUtilsTest, UnixSockAddrToUri) {
#endif // GRPC_HAVE_UNIX_SOCKET
#ifdef GRPC_HAVE_VSOCK
TEST(SockAddrUtilsTest, VSockAddrToUri) {
grpc_resolved_address addr;
ASSERT_TRUE(absl::OkStatus() ==
grpc_core::VSockaddrPopulate("-1:12345", &addr));
EXPECT_EQ(grpc_sockaddr_to_uri(&addr).value(),
absl::StrCat("vsock:", (uint32_t)-1, ":12345"));
}
#endif // GRPC_HAVE_VSOCK
TEST(SockAddrUtilsTest, SockAddrSetGetPort) {
grpc_resolved_address input4 = MakeAddr4(kIPv4, sizeof(kIPv4));
ASSERT_EQ(grpc_sockaddr_get_port(&input4), 12345);

@ -16,7 +16,15 @@
#include "src/core/lib/event_engine/tcp_socket_utils.h"
#include <errno.h>
#include "src/core/lib/iomgr/port.h" // IWYU pragma: keep
#ifdef GRPC_HAVE_VSOCK
#include <linux/vm_sockets.h>
#endif
#include <stdint.h>
#include <stdio.h>
#include <string.h>
#include "absl/strings/str_cat.h"
@ -26,8 +34,6 @@
#include <string>
#include "src/core/lib/iomgr/port.h"
#ifdef GRPC_HAVE_UNIX_SOCKET
#include <sys/un.h>
#endif
@ -134,6 +140,25 @@ absl::StatusOr<EventEngine::ResolvedAddress> UnixAbstractSockaddrPopulate(
}
#endif // GRPC_HAVE_UNIX_SOCKET
#ifdef GRPC_HAVE_VSOCK
absl::StatusOr<EventEngine::ResolvedAddress> VSockaddrPopulate(
absl::string_view path) {
EventEngine::ResolvedAddress resolved_addr;
memset(const_cast<sockaddr*>(resolved_addr.address()), 0,
resolved_addr.size());
struct sockaddr_vm* vm = reinterpret_cast<struct sockaddr_vm*>(
const_cast<sockaddr*>(resolved_addr.address()));
vm->svm_family = AF_VSOCK;
std::string s = std::string(path);
if (sscanf(s.c_str(), "%u:%u", &vm->svm_cid, &vm->svm_port) != 2) {
return absl::InternalError(
absl::StrCat("Failed to parse vsock cid/port: ", s));
}
return EventEngine::ResolvedAddress(reinterpret_cast<sockaddr*>(vm),
static_cast<socklen_t>(sizeof(*vm)));
}
#endif // GRPC_HAVE_VSOCK
} // namespace
TEST(TcpSocketUtilsTest, ResolvedAddressIsV4MappedTest) {
@ -255,6 +280,12 @@ TEST(TcpSocketUtilsTest, ResolvedAddressToNormalizedStringTest) {
EXPECT_EQ(ResolvedAddressToNormalizedString(inputun3).value(),
absl::StrCat(std::string(1, '\0'), max_abspath));
#endif
#ifdef GRPC_HAVE_VSOCK
EventEngine::ResolvedAddress inputvm = *VSockaddrPopulate("-1:12345");
EXPECT_EQ(ResolvedAddressToNormalizedString(inputvm).value(),
absl::StrCat((uint32_t)-1, ":12345"));
#endif
}
TEST(TcpSocketUtilsTest, SockAddrPortTest) {

@ -2393,6 +2393,8 @@ src/core/lib/iomgr/timer_manager.h \
src/core/lib/iomgr/unix_sockets_posix.cc \
src/core/lib/iomgr/unix_sockets_posix.h \
src/core/lib/iomgr/unix_sockets_posix_noop.cc \
src/core/lib/iomgr/vsock.cc \
src/core/lib/iomgr/vsock.h \
src/core/lib/iomgr/wakeup_fd_eventfd.cc \
src/core/lib/iomgr/wakeup_fd_nospecial.cc \
src/core/lib/iomgr/wakeup_fd_pipe.cc \

@ -2174,6 +2174,8 @@ src/core/lib/iomgr/timer_manager.h \
src/core/lib/iomgr/unix_sockets_posix.cc \
src/core/lib/iomgr/unix_sockets_posix.h \
src/core/lib/iomgr/unix_sockets_posix_noop.cc \
src/core/lib/iomgr/vsock.cc \
src/core/lib/iomgr/vsock.h \
src/core/lib/iomgr/wakeup_fd_eventfd.cc \
src/core/lib/iomgr/wakeup_fd_nospecial.cc \
src/core/lib/iomgr/wakeup_fd_pipe.cc \

Loading…
Cancel
Save