gvisor.dev/gvisor@v0.0.0-20240520182842-f9d4d51c7e0f/test/syscalls/linux/readv_socket.cc (about)

     1  // Copyright 2018 The gVisor Authors.
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //     http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  #include <errno.h>
    16  #include <fcntl.h>
    17  #include <sys/socket.h>
    18  #include <sys/types.h>
    19  #include <unistd.h>
    20  
    21  #include "gtest/gtest.h"
    22  #include "test/syscalls/linux/readv_common.h"
    23  #include "test/util/test_util.h"
    24  
    25  namespace gvisor {
    26  namespace testing {
    27  
    28  namespace {
    29  
    30  class ReadvSocketTest : public ::testing::Test {
    31   public:
    32    void SetUp() override {
    33      test_unix_stream_socket_[0] = -1;
    34      test_unix_stream_socket_[1] = -1;
    35      test_unix_dgram_socket_[0] = -1;
    36      test_unix_dgram_socket_[1] = -1;
    37      test_unix_seqpacket_socket_[0] = -1;
    38      test_unix_seqpacket_socket_[1] = -1;
    39  
    40      ASSERT_THAT(socketpair(AF_UNIX, SOCK_STREAM, 0, test_unix_stream_socket_),
    41                  SyscallSucceeds());
    42      ASSERT_THAT(fcntl(test_unix_stream_socket_[0], F_SETFL, O_NONBLOCK),
    43                  SyscallSucceeds());
    44      ASSERT_THAT(socketpair(AF_UNIX, SOCK_DGRAM, 0, test_unix_dgram_socket_),
    45                  SyscallSucceeds());
    46      ASSERT_THAT(fcntl(test_unix_dgram_socket_[0], F_SETFL, O_NONBLOCK),
    47                  SyscallSucceeds());
    48      ASSERT_THAT(
    49          socketpair(AF_UNIX, SOCK_SEQPACKET, 0, test_unix_seqpacket_socket_),
    50          SyscallSucceeds());
    51      ASSERT_THAT(fcntl(test_unix_seqpacket_socket_[0], F_SETFL, O_NONBLOCK),
    52                  SyscallSucceeds());
    53  
    54      ASSERT_THAT(
    55          write(test_unix_stream_socket_[1], kReadvTestData, kReadvTestDataSize),
    56          SyscallSucceedsWithValue(kReadvTestDataSize));
    57      ASSERT_THAT(
    58          write(test_unix_dgram_socket_[1], kReadvTestData, kReadvTestDataSize),
    59          SyscallSucceedsWithValue(kReadvTestDataSize));
    60      ASSERT_THAT(write(test_unix_seqpacket_socket_[1], kReadvTestData,
    61                        kReadvTestDataSize),
    62                  SyscallSucceedsWithValue(kReadvTestDataSize));
    63    }
    64  
    65    void TearDown() override {
    66      close(test_unix_stream_socket_[0]);
    67      close(test_unix_stream_socket_[1]);
    68  
    69      close(test_unix_dgram_socket_[0]);
    70      close(test_unix_dgram_socket_[1]);
    71  
    72      close(test_unix_seqpacket_socket_[0]);
    73      close(test_unix_seqpacket_socket_[1]);
    74    }
    75  
    76    int test_unix_stream_socket_[2];
    77    int test_unix_dgram_socket_[2];
    78    int test_unix_seqpacket_socket_[2];
    79  };
    80  
    81  TEST_F(ReadvSocketTest, ReadOneBufferPerByte_StreamSocket) {
    82    ReadOneBufferPerByte(test_unix_stream_socket_[0]);
    83  }
    84  
    85  TEST_F(ReadvSocketTest, ReadOneBufferPerByte_DgramSocket) {
    86    ReadOneBufferPerByte(test_unix_dgram_socket_[0]);
    87  }
    88  
    89  TEST_F(ReadvSocketTest, ReadOneBufferPerByte_SeqPacketSocket) {
    90    ReadOneBufferPerByte(test_unix_seqpacket_socket_[0]);
    91  }
    92  
    93  TEST_F(ReadvSocketTest, ReadOneHalfAtATime_StreamSocket) {
    94    ReadOneHalfAtATime(test_unix_stream_socket_[0]);
    95  }
    96  
    97  TEST_F(ReadvSocketTest, ReadOneHalfAtATime_DgramSocket) {
    98    ReadOneHalfAtATime(test_unix_dgram_socket_[0]);
    99  }
   100  
   101  TEST_F(ReadvSocketTest, ReadAllOneBuffer_StreamSocket) {
   102    ReadAllOneBuffer(test_unix_stream_socket_[0]);
   103  }
   104  
   105  TEST_F(ReadvSocketTest, ReadAllOneBuffer_DgramSocket) {
   106    ReadAllOneBuffer(test_unix_dgram_socket_[0]);
   107  }
   108  
   109  TEST_F(ReadvSocketTest, ReadAllOneLargeBuffer_StreamSocket) {
   110    ReadAllOneLargeBuffer(test_unix_stream_socket_[0]);
   111  }
   112  
   113  TEST_F(ReadvSocketTest, ReadAllOneLargeBuffer_DgramSocket) {
   114    ReadAllOneLargeBuffer(test_unix_dgram_socket_[0]);
   115  }
   116  
   117  TEST_F(ReadvSocketTest, ReadBuffersOverlapping_StreamSocket) {
   118    ReadBuffersOverlapping(test_unix_stream_socket_[0]);
   119  }
   120  
   121  TEST_F(ReadvSocketTest, ReadBuffersOverlapping_DgramSocket) {
   122    ReadBuffersOverlapping(test_unix_dgram_socket_[0]);
   123  }
   124  
   125  TEST_F(ReadvSocketTest, ReadBuffersDiscontinuous_StreamSocket) {
   126    ReadBuffersDiscontinuous(test_unix_stream_socket_[0]);
   127  }
   128  
   129  TEST_F(ReadvSocketTest, ReadBuffersDiscontinuous_DgramSocket) {
   130    ReadBuffersDiscontinuous(test_unix_dgram_socket_[0]);
   131  }
   132  
   133  TEST_F(ReadvSocketTest, ReadIovecsCompletelyFilled_StreamSocket) {
   134    ReadIovecsCompletelyFilled(test_unix_stream_socket_[0]);
   135  }
   136  
   137  TEST_F(ReadvSocketTest, ReadIovecsCompletelyFilled_DgramSocket) {
   138    ReadIovecsCompletelyFilled(test_unix_dgram_socket_[0]);
   139  }
   140  
   141  TEST_F(ReadvSocketTest, BadIovecsPointer_StreamSocket) {
   142  #pragma GCC diagnostic push
   143  #pragma GCC diagnostic ignored "-Wnonnull"
   144    ASSERT_THAT(readv(test_unix_stream_socket_[0], nullptr, 1),
   145                SyscallFailsWithErrno(EFAULT));
   146  #pragma GCC diagnostic pop
   147  }
   148  
   149  TEST_F(ReadvSocketTest, BadIovecsPointer_DgramSocket) {
   150  #pragma GCC diagnostic push
   151  #pragma GCC diagnostic ignored "-Wnonnull"
   152    ASSERT_THAT(readv(test_unix_dgram_socket_[0], nullptr, 1),
   153                SyscallFailsWithErrno(EFAULT));
   154  #pragma GCC diagnostic pop
   155  }
   156  
   157  TEST_F(ReadvSocketTest, BadIovecBase_StreamSocket) {
   158    struct iovec iov[1];
   159    iov[0].iov_base = nullptr;
   160    iov[0].iov_len = 1024;
   161    ASSERT_THAT(readv(test_unix_stream_socket_[0], iov, 1),
   162                SyscallFailsWithErrno(EFAULT));
   163  }
   164  
   165  TEST_F(ReadvSocketTest, BadIovecBase_DgramSocket) {
   166    struct iovec iov[1];
   167    iov[0].iov_base = nullptr;
   168    iov[0].iov_len = 1024;
   169    ASSERT_THAT(readv(test_unix_dgram_socket_[0], iov, 1),
   170                SyscallFailsWithErrno(EFAULT));
   171  }
   172  
   173  TEST_F(ReadvSocketTest, ZeroIovecs_StreamSocket) {
   174    struct iovec iov[1];
   175    iov[0].iov_base = 0;
   176    iov[0].iov_len = 0;
   177    ASSERT_THAT(readv(test_unix_stream_socket_[0], iov, 1), SyscallSucceeds());
   178  }
   179  
   180  TEST_F(ReadvSocketTest, ZeroIovecs_DgramSocket) {
   181    struct iovec iov[1];
   182    iov[0].iov_base = 0;
   183    iov[0].iov_len = 0;
   184    ASSERT_THAT(readv(test_unix_dgram_socket_[0], iov, 1), SyscallSucceeds());
   185  }
   186  
   187  TEST_F(ReadvSocketTest, WouldBlock_StreamSocket) {
   188    struct iovec iov[1];
   189    iov[0].iov_base = reinterpret_cast<char*>(malloc(kReadvTestDataSize));
   190    iov[0].iov_len = kReadvTestDataSize;
   191    ASSERT_THAT(readv(test_unix_stream_socket_[0], iov, 1),
   192                SyscallSucceedsWithValue(kReadvTestDataSize));
   193    free(iov[0].iov_base);
   194  
   195    iov[0].iov_base = reinterpret_cast<char*>(malloc(kReadvTestDataSize));
   196    ASSERT_THAT(readv(test_unix_stream_socket_[0], iov, 1),
   197                SyscallFailsWithErrno(EAGAIN));
   198    free(iov[0].iov_base);
   199  }
   200  
   201  TEST_F(ReadvSocketTest, WouldBlock_DgramSocket) {
   202    struct iovec iov[1];
   203    iov[0].iov_base = reinterpret_cast<char*>(malloc(kReadvTestDataSize));
   204    iov[0].iov_len = kReadvTestDataSize;
   205    ASSERT_THAT(readv(test_unix_dgram_socket_[0], iov, 1),
   206                SyscallSucceedsWithValue(kReadvTestDataSize));
   207    free(iov[0].iov_base);
   208  
   209    iov[0].iov_base = reinterpret_cast<char*>(malloc(kReadvTestDataSize));
   210    ASSERT_THAT(readv(test_unix_dgram_socket_[0], iov, 1),
   211                SyscallFailsWithErrno(EAGAIN));
   212    free(iov[0].iov_base);
   213  }
   214  
   215  }  // namespace
   216  
   217  }  // namespace testing
   218  }  // namespace gvisor