libuv-svace-build

Форк
0
/
test-udp-connect.c 
196 строк · 5.7 Кб
1
/* Copyright libuv project and contributors. All rights reserved.
2
 *
3
 * Permission is hereby granted, free of charge, to any person obtaining a copy
4
 * of this software and associated documentation files (the "Software"), to
5
 * deal in the Software without restriction, including without limitation the
6
 * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
7
 * sell copies of the Software, and to permit persons to whom the Software is
8
 * furnished to do so, subject to the following conditions:
9
 *
10
 * The above copyright notice and this permission notice shall be included in
11
 * all copies or substantial portions of the Software.
12
 *
13
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
18
 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
19
 * IN THE SOFTWARE.
20
 */
21

22
#include "uv.h"
23
#include "task.h"
24

25
#include <stdio.h>
26
#include <stdlib.h>
27
#include <string.h>
28

29
#define CHECK_HANDLE(handle) \
30
  ASSERT_NE((uv_udp_t*)(handle) == &server || (uv_udp_t*)(handle) == &client, 0)
31

32
static uv_udp_t server;
33
static uv_udp_t client;
34
static uv_buf_t buf;
35
static struct sockaddr_in lo_addr;
36

37
static int cl_send_cb_called;
38
static int sv_recv_cb_called;
39

40
static int close_cb_called;
41

42

43
static void alloc_cb(uv_handle_t* handle,
44
                     size_t suggested_size,
45
                     uv_buf_t* buf) {
46
  static char slab[65536];
47
  CHECK_HANDLE(handle);
48
  ASSERT_LE(suggested_size, sizeof(slab));
49
  buf->base = slab;
50
  buf->len = sizeof(slab);
51
}
52

53

54
static void close_cb(uv_handle_t* handle) {
55
  CHECK_HANDLE(handle);
56
  ASSERT(uv_is_closing(handle));
57
  close_cb_called++;
58
}
59

60

61
static void cl_send_cb(uv_udp_send_t* req, int status) {
62
  int r;
63

64
  ASSERT_NOT_NULL(req);
65
  ASSERT_OK(status);
66
  CHECK_HANDLE(req->handle);
67
  if (++cl_send_cb_called == 1) {
68
    uv_udp_connect(&client, NULL);
69
    r = uv_udp_send(req, &client, &buf, 1, NULL, cl_send_cb);
70
    ASSERT_EQ(r, UV_EDESTADDRREQ);
71
    r = uv_udp_send(req,
72
                    &client,
73
                    &buf,
74
                    1,
75
                    (const struct sockaddr*) &lo_addr,
76
                    cl_send_cb);
77
    ASSERT_OK(r);
78
  }
79

80
}
81

82

83
static void sv_recv_cb(uv_udp_t* handle,
84
                       ssize_t nread,
85
                       const uv_buf_t* rcvbuf,
86
                       const struct sockaddr* addr,
87
                       unsigned flags) {
88
  if (nread > 0) {
89
    ASSERT_EQ(4, nread);
90
    ASSERT_NOT_NULL(addr);
91
    ASSERT_OK(memcmp("EXIT", rcvbuf->base, nread));
92
    if (++sv_recv_cb_called == 4) {
93
      uv_close((uv_handle_t*) &server, close_cb);
94
      uv_close((uv_handle_t*) &client, close_cb);
95
    }
96
  }
97
}
98

99

100
TEST_IMPL(udp_connect) {
101
#if defined(__OpenBSD__)
102
  RETURN_SKIP("Test does not currently work in OpenBSD");
103
#endif
104
  uv_udp_send_t req;
105
  struct sockaddr_in ext_addr;
106
  struct sockaddr_in tmp_addr;
107
  int r;
108
  int addrlen;
109

110
  ASSERT_OK(uv_ip4_addr("0.0.0.0", TEST_PORT, &lo_addr));
111

112
  r = uv_udp_init(uv_default_loop(), &server);
113
  ASSERT_OK(r);
114

115
  r = uv_udp_bind(&server, (const struct sockaddr*) &lo_addr, 0);
116
  ASSERT_OK(r);
117

118
  r = uv_udp_recv_start(&server, alloc_cb, sv_recv_cb);
119
  ASSERT_OK(r);
120

121
  r = uv_udp_init(uv_default_loop(), &client);
122
  ASSERT_OK(r);
123

124
  buf = uv_buf_init("EXIT", 4);
125

126
  /* connect() to INADDR_ANY fails on Windows with WSAEADDRNOTAVAIL */
127
  ASSERT_OK(uv_ip4_addr("0.0.0.0", TEST_PORT, &tmp_addr));
128
  r = uv_udp_connect(&client, (const struct sockaddr*) &tmp_addr);
129
#ifdef _WIN32
130
  ASSERT_EQ(r, UV_EADDRNOTAVAIL);
131
#else
132
  ASSERT_OK(r);
133
  r = uv_udp_connect(&client, NULL);
134
  ASSERT_OK(r);
135
#endif
136

137
  ASSERT_OK(uv_ip4_addr("8.8.8.8", TEST_PORT, &ext_addr));
138
  ASSERT_OK(uv_ip4_addr("127.0.0.1", TEST_PORT, &lo_addr));
139

140
  r = uv_udp_connect(&client, (const struct sockaddr*) &lo_addr);
141
  ASSERT_OK(r);
142
  r = uv_udp_connect(&client, (const struct sockaddr*) &ext_addr);
143
  ASSERT_EQ(r, UV_EISCONN);
144

145
  addrlen = sizeof(tmp_addr);
146
  r = uv_udp_getpeername(&client, (struct sockaddr*) &tmp_addr, &addrlen);
147
  ASSERT_OK(r);
148

149
  /* To send messages in connected UDP sockets addr must be NULL */
150
  r = uv_udp_try_send(&client, &buf, 1, (const struct sockaddr*) &lo_addr);
151
  ASSERT_EQ(r, UV_EISCONN);
152
  r = uv_udp_try_send(&client, &buf, 1, NULL);
153
  ASSERT_EQ(4, r);
154
  r = uv_udp_try_send(&client, &buf, 1, (const struct sockaddr*) &ext_addr);
155
  ASSERT_EQ(r, UV_EISCONN);
156

157
  r = uv_udp_connect(&client, NULL);
158
  ASSERT_OK(r);
159
  r = uv_udp_connect(&client, NULL);
160
  ASSERT_EQ(r, UV_ENOTCONN);
161

162
  addrlen = sizeof(tmp_addr);
163
  r = uv_udp_getpeername(&client, (struct sockaddr*) &tmp_addr, &addrlen);
164
  ASSERT_EQ(r, UV_ENOTCONN);
165

166
  /* To send messages in disconnected UDP sockets addr must be set */
167
  r = uv_udp_try_send(&client, &buf, 1, (const struct sockaddr*) &lo_addr);
168
  ASSERT_EQ(4, r);
169
  r = uv_udp_try_send(&client, &buf, 1, NULL);
170
  ASSERT_EQ(r, UV_EDESTADDRREQ);
171

172

173
  r = uv_udp_connect(&client, (const struct sockaddr*) &lo_addr);
174
  ASSERT_OK(r);
175
  r = uv_udp_send(&req,
176
                  &client,
177
                  &buf,
178
                  1,
179
                  (const struct sockaddr*) &lo_addr,
180
                  cl_send_cb);
181
  ASSERT_EQ(r, UV_EISCONN);
182
  r = uv_udp_send(&req, &client, &buf, 1, NULL, cl_send_cb);
183
  ASSERT_OK(r);
184

185
  uv_run(uv_default_loop(), UV_RUN_DEFAULT);
186

187
  ASSERT_EQ(2, close_cb_called);
188
  ASSERT_EQ(4, sv_recv_cb_called);
189
  ASSERT_EQ(2, cl_send_cb_called);
190

191
  ASSERT_OK(client.send_queue_size);
192
  ASSERT_OK(server.send_queue_size);
193

194
  MAKE_VALGRIND_HAPPY(uv_default_loop());
195
  return 0;
196
}
197

Использование cookies

Мы используем файлы cookie в соответствии с Политикой конфиденциальности и Политикой использования cookies.

Нажимая кнопку «Принимаю», Вы даете АО «СберТех» согласие на обработку Ваших персональных данных в целях совершенствования нашего веб-сайта и Сервиса GitVerse, а также повышения удобства их использования.

Запретить использование cookies Вы можете самостоятельно в настройках Вашего браузера.