unix_domain_server_socket_posix_unittest.cc 5.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151
  1. // Copyright 2014 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #include "net/socket/unix_domain_server_socket_posix.h"
  5. #include <memory>
  6. #include <vector>
  7. #include "base/bind.h"
  8. #include "base/files/file_path.h"
  9. #include "base/files/scoped_temp_dir.h"
  10. #include "base/run_loop.h"
  11. #include "base/test/task_environment.h"
  12. #include "build/build_config.h"
  13. #include "net/base/io_buffer.h"
  14. #include "net/base/ip_endpoint.h"
  15. #include "net/base/net_errors.h"
  16. #include "net/base/test_completion_callback.h"
  17. #include "net/socket/unix_domain_client_socket_posix.h"
  18. #include "net/test/gtest_util.h"
  19. #include "testing/gmock/include/gmock/gmock.h"
  20. #include "testing/gtest/include/gtest/gtest.h"
  21. using net::test::IsError;
  22. using net::test::IsOk;
  23. namespace net {
  24. namespace {
  25. const char kSocketFilename[] = "socket_for_testing";
  26. const char kInvalidSocketPath[] = "/invalid/path";
  27. bool UserCanConnectCallback(bool allow_user,
  28. const UnixDomainServerSocket::Credentials& credentials) {
  29. // Here peers are running in same process.
  30. #if BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_ANDROID)
  31. EXPECT_EQ(getpid(), credentials.process_id);
  32. #endif
  33. EXPECT_EQ(getuid(), credentials.user_id);
  34. EXPECT_EQ(getgid(), credentials.group_id);
  35. return allow_user;
  36. }
  37. UnixDomainServerSocket::AuthCallback CreateAuthCallback(bool allow_user) {
  38. return base::BindRepeating(&UserCanConnectCallback, allow_user);
  39. }
  40. class UnixDomainServerSocketTest : public testing::Test {
  41. protected:
  42. UnixDomainServerSocketTest() {
  43. EXPECT_TRUE(temp_dir_.CreateUniqueTempDir());
  44. socket_path_ = temp_dir_.GetPath().Append(kSocketFilename).value();
  45. }
  46. base::ScopedTempDir temp_dir_;
  47. std::string socket_path_;
  48. };
  49. TEST_F(UnixDomainServerSocketTest, ListenWithInvalidPath) {
  50. const bool kUseAbstractNamespace = false;
  51. UnixDomainServerSocket server_socket(CreateAuthCallback(true),
  52. kUseAbstractNamespace);
  53. EXPECT_EQ(ERR_FILE_NOT_FOUND,
  54. server_socket.BindAndListen(kInvalidSocketPath, /*backlog=*/1));
  55. }
  56. TEST_F(UnixDomainServerSocketTest, ListenWithInvalidPathWithAbstractNamespace) {
  57. const bool kUseAbstractNamespace = true;
  58. UnixDomainServerSocket server_socket(CreateAuthCallback(true),
  59. kUseAbstractNamespace);
  60. #if BUILDFLAG(IS_ANDROID) || BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS)
  61. EXPECT_THAT(server_socket.BindAndListen(kInvalidSocketPath, /*backlog=*/1),
  62. IsOk());
  63. #else
  64. EXPECT_EQ(ERR_ADDRESS_INVALID,
  65. server_socket.BindAndListen(kInvalidSocketPath, /*backlog=*/1));
  66. #endif
  67. }
  68. TEST_F(UnixDomainServerSocketTest, ListenAgainAfterFailureWithInvalidPath) {
  69. const bool kUseAbstractNamespace = false;
  70. UnixDomainServerSocket server_socket(CreateAuthCallback(true),
  71. kUseAbstractNamespace);
  72. EXPECT_EQ(ERR_FILE_NOT_FOUND,
  73. server_socket.BindAndListen(kInvalidSocketPath, /*backlog=*/1));
  74. EXPECT_THAT(server_socket.BindAndListen(socket_path_, /*backlog=*/1), IsOk());
  75. }
  76. TEST_F(UnixDomainServerSocketTest, AcceptWithForbiddenUser) {
  77. base::test::TaskEnvironment task_environment(
  78. base::test::TaskEnvironment::MainThreadType::IO);
  79. const bool kUseAbstractNamespace = false;
  80. UnixDomainServerSocket server_socket(CreateAuthCallback(false),
  81. kUseAbstractNamespace);
  82. EXPECT_THAT(server_socket.BindAndListen(socket_path_, /*backlog=*/1), IsOk());
  83. std::unique_ptr<StreamSocket> accepted_socket;
  84. TestCompletionCallback accept_callback;
  85. EXPECT_EQ(ERR_IO_PENDING,
  86. server_socket.Accept(&accepted_socket, accept_callback.callback()));
  87. EXPECT_FALSE(accepted_socket);
  88. UnixDomainClientSocket client_socket(socket_path_, kUseAbstractNamespace);
  89. EXPECT_FALSE(client_socket.IsConnected());
  90. // Connect() will return OK before the server rejects the connection.
  91. TestCompletionCallback connect_callback;
  92. int rv = connect_callback.GetResult(
  93. client_socket.Connect(connect_callback.callback()));
  94. ASSERT_THAT(rv, IsOk());
  95. // Try to read from the socket.
  96. const int read_buffer_size = 10;
  97. scoped_refptr<IOBuffer> read_buffer =
  98. base::MakeRefCounted<IOBuffer>(read_buffer_size);
  99. TestCompletionCallback read_callback;
  100. rv = read_callback.GetResult(client_socket.Read(
  101. read_buffer.get(), read_buffer_size, read_callback.callback()));
  102. // The server should have disconnected gracefully, without sending any data.
  103. ASSERT_EQ(0, rv);
  104. EXPECT_FALSE(client_socket.IsConnected());
  105. // The server socket should not have called |accept_callback| or modified
  106. // |accepted_socket|.
  107. EXPECT_FALSE(accept_callback.have_result());
  108. EXPECT_FALSE(accepted_socket);
  109. }
  110. TEST_F(UnixDomainServerSocketTest, UnimplementedMethodsFail) {
  111. const bool kUseAbstractNamespace = false;
  112. UnixDomainServerSocket server_socket(CreateAuthCallback(true),
  113. kUseAbstractNamespace);
  114. IPEndPoint ep;
  115. EXPECT_THAT(server_socket.Listen(ep, 0), IsError(ERR_NOT_IMPLEMENTED));
  116. EXPECT_EQ(ERR_NOT_IMPLEMENTED,
  117. server_socket.ListenWithAddressAndPort(kInvalidSocketPath,
  118. 0,
  119. /*backlog=*/1));
  120. EXPECT_THAT(server_socket.GetLocalAddress(&ep), IsError(ERR_ADDRESS_INVALID));
  121. }
  122. // Normal cases including read/write are tested by UnixDomainClientSocketTest.
  123. } // namespace
  124. } // namespace net