libcouchbase 0.2.0 → 0.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (129) hide show
  1. checksums.yaml +4 -4
  2. data/.travis.yml +1 -1
  3. data/README.md +1 -1
  4. data/ext/libcouchbase/CMakeLists.txt +8 -6
  5. data/ext/libcouchbase/README.markdown +2 -2
  6. data/ext/libcouchbase/RELEASE_NOTES.markdown +0 -86
  7. data/ext/libcouchbase/cmake/Modules/ConfigureDtrace.cmake +0 -11
  8. data/ext/libcouchbase/cmake/Modules/GenerateConfigDotH.cmake +0 -2
  9. data/ext/libcouchbase/cmake/Modules/GetLibcouchbaseFlags.cmake +1 -2
  10. data/ext/libcouchbase/cmake/Modules/GetVersionInfo.cmake +3 -3
  11. data/ext/libcouchbase/cmake/config-cmake.h.in +0 -2
  12. data/ext/libcouchbase/cmake/defs.mk.in +2 -0
  13. data/ext/libcouchbase/cmake/source_files.cmake +5 -21
  14. data/ext/libcouchbase/include/libcouchbase/auth.h +0 -10
  15. data/ext/libcouchbase/include/libcouchbase/cntl.h +1 -27
  16. data/ext/libcouchbase/include/libcouchbase/error.h +1 -15
  17. data/ext/libcouchbase/include/libcouchbase/n1ql.h +1 -13
  18. data/ext/libcouchbase/include/libcouchbase/plugins/io/bsdio-inl.c +1 -1
  19. data/ext/libcouchbase/include/libcouchbase/subdoc.h +0 -9
  20. data/ext/libcouchbase/include/libcouchbase/views.h +1 -7
  21. data/ext/libcouchbase/include/libcouchbase/visibility.h +0 -1
  22. data/ext/libcouchbase/include/memcached/protocol_binary.h +1131 -29
  23. data/ext/libcouchbase/include/memcached/vbucket.h +42 -0
  24. data/ext/libcouchbase/packaging/parse-git-describe.pl +1 -1
  25. data/ext/libcouchbase/plugins/io/libev/libev_io_opts.h +2 -3
  26. data/ext/libcouchbase/src/README.md +2 -0
  27. data/ext/libcouchbase/src/auth-priv.h +0 -1
  28. data/ext/libcouchbase/src/auth.cc +4 -10
  29. data/ext/libcouchbase/src/bootstrap.c +269 -0
  30. data/ext/libcouchbase/src/bootstrap.h +39 -50
  31. data/ext/libcouchbase/src/bucketconfig/bc_cccp.cc +117 -84
  32. data/ext/libcouchbase/src/bucketconfig/bc_file.c +347 -0
  33. data/ext/libcouchbase/src/bucketconfig/bc_http.c +630 -0
  34. data/ext/libcouchbase/src/bucketconfig/bc_http.h +25 -50
  35. data/ext/libcouchbase/src/bucketconfig/bc_mcraw.c +150 -0
  36. data/ext/libcouchbase/src/bucketconfig/clconfig.h +386 -407
  37. data/ext/libcouchbase/src/bucketconfig/confmon.c +474 -0
  38. data/ext/libcouchbase/src/cbft.cc +27 -22
  39. data/ext/libcouchbase/src/cntl.cc +19 -30
  40. data/ext/libcouchbase/src/connspec.cc +1 -48
  41. data/ext/libcouchbase/src/connspec.h +0 -27
  42. data/ext/libcouchbase/src/dump.cc +2 -2
  43. data/ext/libcouchbase/src/getconfig.cc +33 -7
  44. data/ext/libcouchbase/src/handler.cc +2 -0
  45. data/ext/libcouchbase/src/hostlist.cc +36 -0
  46. data/ext/libcouchbase/src/hostlist.h +62 -41
  47. data/ext/libcouchbase/src/http/http-priv.h +112 -125
  48. data/ext/libcouchbase/src/http/http.cc +30 -15
  49. data/ext/libcouchbase/src/http/http.h +34 -1
  50. data/ext/libcouchbase/src/http/http_io.cc +26 -22
  51. data/ext/libcouchbase/src/instance.cc +23 -94
  52. data/ext/libcouchbase/src/internal.h +26 -52
  53. data/ext/libcouchbase/src/jsparse/parser.cc +202 -146
  54. data/ext/libcouchbase/src/jsparse/parser.h +98 -91
  55. data/ext/libcouchbase/src/lcbht/lcbht.c +282 -0
  56. data/ext/libcouchbase/src/lcbht/lcbht.h +163 -174
  57. data/ext/libcouchbase/src/lcbio/connect.c +557 -0
  58. data/ext/libcouchbase/src/lcbio/connect.h +2 -9
  59. data/ext/libcouchbase/src/lcbio/ctx.c +1 -1
  60. data/ext/libcouchbase/src/lcbio/iotable.h +16 -61
  61. data/ext/libcouchbase/src/lcbio/ioutils.h +1 -1
  62. data/ext/libcouchbase/src/lcbio/manager.c +2 -2
  63. data/ext/libcouchbase/src/mc/mcreq.h +2 -9
  64. data/ext/libcouchbase/src/mcserver/mcserver.cc +34 -143
  65. data/ext/libcouchbase/src/mcserver/mcserver.h +12 -7
  66. data/ext/libcouchbase/src/mcserver/negotiate.cc +38 -132
  67. data/ext/libcouchbase/src/n1ql/ixmgmt.cc +2 -1
  68. data/ext/libcouchbase/src/n1ql/n1ql.cc +32 -56
  69. data/ext/libcouchbase/src/newconfig.cc +6 -6
  70. data/ext/libcouchbase/src/nodeinfo.cc +2 -2
  71. data/ext/libcouchbase/src/operations/{cbflush.cc → cbflush.c} +15 -7
  72. data/ext/libcouchbase/src/operations/{counter.cc → counter.c} +0 -0
  73. data/ext/libcouchbase/src/operations/durability.cc +26 -6
  74. data/ext/libcouchbase/src/operations/durability_internal.h +3 -6
  75. data/ext/libcouchbase/src/operations/{get.cc → get.c} +26 -24
  76. data/ext/libcouchbase/src/operations/{observe.cc → observe.c} +93 -68
  77. data/ext/libcouchbase/src/operations/{pktfwd.cc → pktfwd.c} +0 -0
  78. data/ext/libcouchbase/src/operations/{remove.cc → remove.c} +0 -0
  79. data/ext/libcouchbase/src/operations/stats.cc +8 -3
  80. data/ext/libcouchbase/src/operations/{store.cc → store.c} +32 -27
  81. data/ext/libcouchbase/src/operations/subdoc.cc +18 -38
  82. data/ext/libcouchbase/src/operations/{touch.cc → touch.c} +0 -0
  83. data/ext/libcouchbase/src/packetutils.c +37 -0
  84. data/ext/libcouchbase/src/packetutils.h +2 -2
  85. data/ext/libcouchbase/src/probes.d +1 -1
  86. data/ext/libcouchbase/src/{retrychk.cc → retrychk.c} +3 -2
  87. data/ext/libcouchbase/src/retryq.cc +4 -4
  88. data/ext/libcouchbase/src/settings.c +0 -3
  89. data/ext/libcouchbase/src/settings.h +0 -5
  90. data/ext/libcouchbase/src/simplestring.c +211 -0
  91. data/ext/libcouchbase/src/simplestring.h +228 -0
  92. data/ext/libcouchbase/src/ssl/ssl_c.c +0 -1
  93. data/ext/libcouchbase/src/ssl/ssl_common.c +0 -2
  94. data/ext/libcouchbase/src/ssl/ssl_e.c +1 -0
  95. data/ext/libcouchbase/src/ssobuf.h +82 -0
  96. data/ext/libcouchbase/src/trace.h +4 -4
  97. data/ext/libcouchbase/src/vbucket/vbucket.c +1 -0
  98. data/ext/libcouchbase/src/views/{docreq.cc → docreq.c} +54 -48
  99. data/ext/libcouchbase/src/views/docreq.h +30 -24
  100. data/ext/libcouchbase/src/views/viewreq.c +358 -0
  101. data/ext/libcouchbase/src/views/viewreq.h +13 -43
  102. data/ext/libcouchbase/tests/basic/t_connstr.cc +50 -89
  103. data/ext/libcouchbase/tests/basic/t_host.cc +75 -67
  104. data/ext/libcouchbase/tests/basic/t_jsparse.cc +78 -27
  105. data/ext/libcouchbase/tests/basic/t_string.cc +112 -0
  106. data/ext/libcouchbase/tests/htparse/t_basic.cc +78 -58
  107. data/ext/libcouchbase/tests/iotests/mock-environment.h +1 -2
  108. data/ext/libcouchbase/tests/iotests/t_confmon.cc +114 -96
  109. data/ext/libcouchbase/tests/mc/t_alloc.cc +9 -9
  110. data/ext/libcouchbase/tools/cbc-pillowfight.cc +1 -1
  111. data/lib/libcouchbase/ext/tasks.rb +6 -2
  112. data/lib/libcouchbase/query_view.rb +1 -1
  113. data/lib/libcouchbase/results_fiber.rb +6 -6
  114. data/lib/libcouchbase/version.rb +1 -1
  115. metadata +26 -26
  116. data/ext/libcouchbase/src/bootstrap.cc +0 -216
  117. data/ext/libcouchbase/src/bucketconfig/bc_file.cc +0 -281
  118. data/ext/libcouchbase/src/bucketconfig/bc_http.cc +0 -528
  119. data/ext/libcouchbase/src/bucketconfig/bc_mcraw.cc +0 -115
  120. data/ext/libcouchbase/src/bucketconfig/confmon.cc +0 -378
  121. data/ext/libcouchbase/src/dns-srv.cc +0 -142
  122. data/ext/libcouchbase/src/errmap.cc +0 -107
  123. data/ext/libcouchbase/src/errmap.h +0 -113
  124. data/ext/libcouchbase/src/lcbht/lcbht.cc +0 -177
  125. data/ext/libcouchbase/src/lcbio/connect.cc +0 -562
  126. data/ext/libcouchbase/src/lcbio/timer-cxx.h +0 -87
  127. data/ext/libcouchbase/src/mctx-helper.h +0 -51
  128. data/ext/libcouchbase/src/views/viewreq.cc +0 -318
  129. data/ext/libcouchbase/tests/iotests/t_errmap.cc +0 -97
@@ -1,562 +0,0 @@
1
- /* -*- Mode: C; tab-width: 4; c-basic-offset: 4; indent-tabs-mode: nil -*- */
2
- /*
3
- * Copyright 2014 Couchbase, Inc.
4
- *
5
- * Licensed under the Apache License, Version 2.0 (the "License");
6
- * you may not use this file except in compliance with the License.
7
- * You may obtain a copy of the License at
8
- *
9
- * http://www.apache.org/licenses/LICENSE-2.0
10
- *
11
- * Unless required by applicable law or agreed to in writing, software
12
- * distributed under the License is distributed on an "AS IS" BASIS,
13
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
- * See the License for the specific language governing permissions and
15
- * limitations under the License.
16
- */
17
-
18
- #include "config.h"
19
- #include "connect.h"
20
- #include "ioutils.h"
21
- #include "iotable.h"
22
- #include "settings.h"
23
- #include "timer-ng.h"
24
- #include "timer-cxx.h"
25
- #include <errno.h>
26
-
27
- using namespace lcb::io;
28
-
29
- /* win32 lacks EAI_SYSTEM */
30
- #ifndef EAI_SYSTEM
31
- #define EAI_SYSTEM 0
32
- #endif
33
- #define LOGARGS(conn, lvl) conn->settings, "connection", LCB_LOG_##lvl, __FILE__, __LINE__
34
- static const lcb_host_t *get_loghost(lcbio_SOCKET *s) {
35
- static lcb_host_t host = { "NOHOST", "NOPORT" };
36
- if (!s) { return &host; }
37
- if (!s->info) { return &host; }
38
- return &s->info->ep;
39
- }
40
-
41
- /** Format string arguments for %p%s:%s */
42
- #define CSLOGID(sock) get_loghost(sock)->host, get_loghost(sock)->port, (void*)sock
43
- #define CSLOGFMT "<%s:%s> (SOCK=%p) "
44
-
45
- #define LOGARGS_T(lvl) LOGARGS(this->sock, lvl)
46
- #define CSLOGID_T() CSLOGID(this->sock)
47
-
48
- namespace lcb {
49
- namespace io {
50
- struct Connstart {
51
- Connstart(lcbio_TABLE*, lcb_settings*, const lcb_host_t*,
52
- uint32_t, lcbio_CONNDONE_cb, void*);
53
-
54
- ~Connstart();
55
- void unwatch();
56
- void handler();
57
- void cancel();
58
- void C_connect();
59
-
60
- enum State {
61
- CS_PENDING, CS_CANCELLED, CS_CONNECTED, CS_ERROR
62
- };
63
-
64
- void state_signal(State next_state, lcb_error_t status);
65
- void notify_success();
66
- void notify_error(lcb_error_t err);
67
- bool ensure_sock();
68
- void clear_sock();
69
-
70
- lcbio_CONNDONE_cb user_handler;
71
- void *user_arg;
72
-
73
- lcbio_SOCKET *sock;
74
- lcbio_OSERR syserr;
75
- void *event;
76
- bool ev_active; /* whether the event pointer is active (Event only) */
77
- bool in_uhandler; /* Whether we're inside the user-defined handler */
78
- addrinfo *ai_root;
79
- addrinfo *ai;
80
- State state;
81
- lcb_error_t last_error;
82
- Timer<Connstart, &Connstart::handler> timer;
83
- };
84
- }
85
- }
86
-
87
- void Connstart::unwatch() {
88
- if (sock && ev_active) {
89
- lcb_assert(sock->u.fd != INVALID_SOCKET);
90
- sock->io->E_event_cancel(sock->u.fd, event);
91
- ev_active = false;
92
- }
93
- }
94
-
95
- /**
96
- * Handler invoked to deliver final status for a connection. This will invoke
97
- * the user supplied callback with the relevant status (if it has not been
98
- * cancelled) and then free the CONNSTART object.
99
- */
100
- void Connstart::handler() {
101
- lcb_error_t err;
102
-
103
- if (sock && event) {
104
- unwatch();
105
- sock->io->E_event_destroy(event);
106
- }
107
-
108
- if (state == CS_PENDING) {
109
- /* state was not changed since initial scheduling */
110
- err = LCB_ETIMEDOUT;
111
- } else if (state == CS_CONNECTED) {
112
- /* clear pending error */
113
- err = LCB_SUCCESS;
114
- } else {
115
- if (sock != NULL && last_error == LCB_CONNECT_ERROR) {
116
- err = lcbio_mklcberr(syserr, sock->settings);
117
- } else {
118
- err = last_error;
119
- }
120
- }
121
-
122
- if (state == CS_CANCELLED) {
123
- /* ignore everything. Clean up resources */
124
- goto GT_DTOR;
125
- }
126
-
127
- if (sock) {
128
- lcbio__load_socknames(sock);
129
- if (err == LCB_SUCCESS) {
130
- lcb_log(LOGARGS_T(INFO), CSLOGFMT "Connected established", CSLOGID_T());
131
-
132
- if (sock->settings->tcp_nodelay) {
133
- lcb_error_t ndrc = lcbio_disable_nagle(sock);
134
- if (ndrc != LCB_SUCCESS) {
135
- lcb_log(LOGARGS_T(INFO), CSLOGFMT "Couldn't set TCP_NODELAY", CSLOGID_T());
136
- } else {
137
- lcb_log(LOGARGS_T(DEBUG), CSLOGFMT "Successfuly set TCP_NODELAY", CSLOGID_T());
138
- }
139
- }
140
- } else {
141
- lcb_log(LOGARGS_T(ERR), CSLOGFMT "Failed to establish connection: %s, os errno=%u", CSLOGID_T(), lcb_strerror_short(err), syserr);
142
- }
143
- }
144
-
145
- /** Handler section */
146
- in_uhandler = true;
147
- user_handler(err == LCB_SUCCESS ? sock : NULL, user_arg, err, syserr);
148
- in_uhandler = false;
149
-
150
- GT_DTOR:
151
- delete this;
152
- }
153
-
154
- Connstart::~Connstart() {
155
- timer.release();
156
- if (sock) {
157
- lcbio_unref(sock);
158
- }
159
- if (ai_root) {
160
- freeaddrinfo(ai_root);
161
- }
162
- }
163
-
164
- void Connstart::state_signal(State next_state, lcb_error_t err) {
165
- if (state != CS_PENDING) {
166
- /** State already set */
167
- return;
168
- }
169
-
170
-
171
- if (state == CS_CONNECTED) {
172
- /* clear last errors if we're successful */
173
- last_error = LCB_SUCCESS;
174
- } else if (last_error == LCB_SUCCESS) {
175
- /* set error code only if previous code was not a failure */
176
- last_error = err;
177
- }
178
-
179
- state = next_state;
180
- timer.signal();
181
- }
182
-
183
- void Connstart::notify_success() {
184
- state_signal(CS_CONNECTED, LCB_SUCCESS);
185
- }
186
-
187
- void Connstart::notify_error(lcb_error_t err) {
188
- state_signal(CS_ERROR, err);
189
- }
190
-
191
- /** Cancels and mutes any pending event */
192
- void lcbio_connect_cancel(lcbio_pCONNSTART cs) {
193
- cs->cancel();
194
- }
195
-
196
- void Connstart::cancel() {
197
- if (in_uhandler) {
198
- /* already inside user-defined handler */
199
- return;
200
- }
201
- state = CS_CANCELLED;
202
- handler();
203
- }
204
-
205
-
206
- bool Connstart::ensure_sock() {
207
- lcbio_TABLE *io = sock->io;
208
- int errtmp = 0;
209
-
210
- if (ai == NULL) {
211
- return false;
212
- }
213
-
214
- if (io->is_E()) {
215
- if (sock->u.fd != INVALID_SOCKET) {
216
- /* already have one? */
217
- return true;
218
- }
219
-
220
- while (sock->u.fd == INVALID_SOCKET && ai != NULL) {
221
- sock->u.fd = lcbio_E_ai2sock(io, &ai, &errtmp);
222
- if (sock->u.fd != INVALID_SOCKET) {
223
- lcb_log(LOGARGS_T(DEBUG), CSLOGFMT "Created new socket with FD=%d", CSLOGID_T(), sock->u.fd);
224
- return true;
225
- }
226
- }
227
- } else {
228
- if (sock->u.sd) {
229
- return true;
230
- }
231
-
232
- while (sock->u.sd == NULL && ai != NULL) {
233
- sock->u.sd = lcbio_C_ai2sock(io, &ai, &errtmp);
234
- if (sock->u.sd) {
235
- sock->u.sd->lcbconn = const_cast<lcbio_SOCKET*>(sock);
236
- sock->u.sd->parent = IOT_ARG(io);
237
- return true;
238
- }
239
- }
240
- }
241
-
242
- if (ai == NULL) {
243
- lcbio_mksyserr(IOT_ERRNO(io), &syserr);
244
- return false;
245
- }
246
- return true;
247
- }
248
-
249
- void Connstart::clear_sock() {
250
- lcbio_TABLE *iot = sock->io;
251
- if (ai) {
252
- ai = ai->ai_next;
253
- }
254
-
255
- if (!ai) {
256
- return;
257
- }
258
-
259
- if (iot->is_E()) {
260
- unwatch();
261
- iot->E_close(sock->u.fd);
262
- sock->u.fd = INVALID_SOCKET;
263
- } else {
264
- if (sock->u.sd) {
265
- iot->C_close(sock->u.sd);
266
- sock->u.sd = NULL;
267
- }
268
- }
269
- }
270
-
271
- static void
272
- E_conncb(lcb_socket_t, short events, void *arg)
273
- {
274
- Connstart *cs = reinterpret_cast<Connstart*>(arg);
275
- lcbio_SOCKET *s = cs->sock;
276
- lcbio_TABLE *io = s->io;
277
- int retry_once = 0;
278
- lcbio_CSERR connstatus;
279
- int rv = 0;
280
- addrinfo *ai = NULL;
281
-
282
- GT_NEXTSOCK:
283
- if (!cs->ensure_sock()) {
284
- cs->notify_error(LCB_CONNECT_ERROR);
285
- return;
286
- }
287
-
288
- if (events & LCB_ERROR_EVENT) {
289
- socklen_t errlen = sizeof(int);
290
- int sockerr = 0;
291
- lcb_log(LOGARGS(s, TRACE), CSLOGFMT "Received ERROR_EVENT", CSLOGID(s));
292
- getsockopt(s->u.fd, SOL_SOCKET, SO_ERROR, (char *)&sockerr, &errlen);
293
- lcbio_mksyserr(sockerr, &cs->syserr);
294
- cs->clear_sock();
295
- goto GT_NEXTSOCK;
296
-
297
- } else {
298
- rv = 0;
299
- ai = cs->ai;
300
-
301
- GT_CONNECT:
302
- rv = io->E_connect(s->u.fd, ai->ai_addr, ai->ai_addrlen);
303
- if (rv == 0) {
304
- cs->unwatch();
305
- cs->notify_success();
306
- return;
307
- }
308
- }
309
-
310
- connstatus = lcbio_mkcserr(io->get_errno());
311
- lcbio_mksyserr(io->get_errno(), &cs->syserr);
312
-
313
-
314
- switch (connstatus) {
315
-
316
- case LCBIO_CSERR_INTR:
317
- goto GT_CONNECT;
318
-
319
- case LCBIO_CSERR_CONNECTED:
320
- cs->unwatch();
321
- cs->notify_success();
322
- return;
323
-
324
- case LCBIO_CSERR_BUSY:
325
- lcb_log(LOGARGS(s, TRACE), CSLOGFMT "Scheduling I/O watcher for asynchronous connection completion.", CSLOGID(s));
326
- io->E_event_watch(s->u.fd, cs->event, LCB_WRITE_EVENT, cs, E_conncb);
327
- cs->ev_active = 1;
328
- return;
329
-
330
- case LCBIO_CSERR_EINVAL:
331
- if (!retry_once) {
332
- retry_once = 1;
333
- goto GT_CONNECT;
334
- }
335
- /* fallthrough */
336
-
337
- case LCBIO_CSERR_EFAIL:
338
- default:
339
- /* close the current socket and try again */
340
- lcb_log(LOGARGS(s, TRACE), CSLOGFMT "connect() failed. errno=%d [%s]", CSLOGID(s), IOT_ERRNO(io), strerror(IOT_ERRNO(io)));
341
- cs->clear_sock();
342
- goto GT_NEXTSOCK;
343
- }
344
- }
345
-
346
-
347
- static void
348
- C_conncb(lcb_sockdata_t *sock, int status)
349
- {
350
- lcbio_SOCKET *s = reinterpret_cast<lcbio_SOCKET*>(sock->lcbconn);
351
- Connstart *cs = reinterpret_cast<Connstart*>(s->ctx);
352
-
353
- lcb_log(LOGARGS(s, TRACE), CSLOGFMT "Received completion handler. Status=%d. errno=%d", CSLOGID(s), status, IOT_ERRNO(s->io));
354
-
355
- if (!--s->refcount) {
356
- lcbio__destroy(s);
357
- return;
358
- }
359
-
360
- if (!status) {
361
- if (cs->state == Connstart::CS_PENDING) {
362
- cs->state = Connstart::CS_CONNECTED;
363
- }
364
- cs->handler();
365
- } else {
366
- lcbio_mksyserr(s->io->get_errno(), &cs->syserr);
367
- cs->clear_sock();
368
- cs->C_connect();
369
- }
370
- }
371
-
372
- void Connstart::C_connect()
373
- {
374
- int rv;
375
- bool retry_once = 0;
376
- lcbio_CSERR status;
377
- lcbio_TABLE *io = sock->io;
378
-
379
- GT_NEXTSOCK:
380
- if (!ensure_sock()) {
381
- lcbio_mksyserr(IOT_ERRNO(io), &syserr);
382
- notify_error(LCB_CONNECT_ERROR);
383
- return;
384
- }
385
-
386
- GT_CONNECT:
387
- rv = io->C_connect(sock->u.sd, ai->ai_addr, ai->ai_addrlen, C_conncb);
388
- if (rv == 0) {
389
- lcbio_ref(sock);
390
- return;
391
- }
392
-
393
- lcbio_mksyserr(io->get_errno(), &syserr);
394
- status = lcbio_mkcserr(io->get_errno());
395
- switch (status) {
396
-
397
- case LCBIO_CSERR_INTR:
398
- goto GT_CONNECT;
399
-
400
- case LCBIO_CSERR_CONNECTED:
401
- notify_success();
402
- return;
403
-
404
- case LCBIO_CSERR_BUSY:
405
- return;
406
-
407
- case LCBIO_CSERR_EINVAL:
408
- if (!retry_once) {
409
- retry_once = 1;
410
- goto GT_CONNECT;
411
- }
412
- /* fallthrough */
413
-
414
- case LCBIO_CSERR_EFAIL:
415
- default:
416
- clear_sock();
417
- goto GT_NEXTSOCK;
418
- }
419
- }
420
-
421
- Connstart *
422
- lcbio_connect(lcbio_TABLE *iot, lcb_settings *settings, const lcb_host_t *dest,
423
- uint32_t timeout, lcbio_CONNDONE_cb handler, void *arg)
424
- {
425
- return new Connstart(iot, settings, dest, timeout, handler, arg);
426
- }
427
-
428
- Connstart::Connstart(lcbio_TABLE* iot_, lcb_settings* settings_,
429
- const lcb_host_t *dest, uint32_t timeout,
430
- lcbio_CONNDONE_cb handler, void *arg)
431
- : user_handler(handler), user_arg(arg), sock(NULL), syserr(0),
432
- event(NULL), ev_active(false), in_uhandler(false),
433
- ai_root(NULL), ai(NULL), state(CS_PENDING), last_error(LCB_SUCCESS),
434
- timer(iot_, this) {
435
-
436
- addrinfo hints;
437
- int rv;
438
-
439
- sock = reinterpret_cast<lcbio_SOCKET*>(calloc(1, sizeof(*sock)));
440
-
441
- /** Initialize the socket first */
442
- sock->io = iot_;
443
- sock->settings = settings_;
444
- sock->ctx = this;
445
- sock->refcount = 1;
446
- sock->info = reinterpret_cast<lcbio_CONNINFO*>(calloc(1, sizeof(*sock->info)));
447
- sock->info->ep = *dest;
448
- lcbio_table_ref(sock->io);
449
- lcb_settings_ref(sock->settings);
450
- lcb_list_init(&sock->protos);
451
-
452
- if (iot_->is_E()) {
453
- sock->u.fd = INVALID_SOCKET;
454
- event = iot_->E_event_create();
455
- }
456
-
457
- timer.rearm(timeout);
458
- lcb_log(LOGARGS_T(INFO), CSLOGFMT "Starting. Timeout=%uus", CSLOGID_T(), timeout);
459
-
460
- /** Hostname lookup: */
461
- memset(&hints, 0, sizeof(hints));
462
- hints.ai_flags = AI_PASSIVE;
463
- hints.ai_socktype = SOCK_STREAM;
464
- if (settings_->ipv6 == LCB_IPV6_DISABLED) {
465
- hints.ai_family = AF_INET;
466
- } else if (settings_->ipv6 == LCB_IPV6_ONLY) {
467
- hints.ai_family = AF_INET6;
468
- } else {
469
- hints.ai_family = AF_UNSPEC;
470
- }
471
-
472
- if ((rv = getaddrinfo(dest->host, dest->port, &hints, &ai_root))) {
473
- const char *errstr = rv != EAI_SYSTEM ? gai_strerror(rv) : "";
474
- lcb_log(LOGARGS_T(ERR), CSLOGFMT "Couldn't look up %s (%s) [EAI=%d]", CSLOGID_T(), dest->host, errstr, rv);
475
- notify_error(LCB_UNKNOWN_HOST);
476
- } else {
477
- ai = ai_root;
478
-
479
- /** Figure out how to connect */
480
- if (iot_->is_E()) {
481
- E_conncb(-1, LCB_WRITE_EVENT, this);
482
- } else {
483
- C_connect();
484
- }
485
- }
486
- }
487
-
488
- Connstart *
489
- lcbio_connect_hl(lcbio_TABLE *iot, lcb_settings *settings,
490
- lcb::Hostlist* hl, int rollover, uint32_t timeout,
491
- lcbio_CONNDONE_cb handler, void *arg)
492
- {
493
- const lcb_host_t *cur;
494
- unsigned ii = 0, hlmax = hl->size();
495
-
496
- while ( (cur = hl->next(rollover)) && ii++ < hlmax) {
497
- Connstart *ret = lcbio_connect(
498
- iot, settings, cur, timeout, handler, arg);
499
- if (ret) {
500
- return ret;
501
- }
502
- }
503
-
504
- return NULL;
505
- }
506
-
507
- lcbio_SOCKET *
508
- lcbio_wrap_fd(lcbio_pTABLE iot, lcb_settings *settings, lcb_socket_t fd)
509
- {
510
- lcbio_SOCKET *ret = reinterpret_cast<lcbio_SOCKET*>(calloc(1, sizeof(*ret)));
511
- lcbio_CONNDONE_cb *ci = reinterpret_cast<lcbio_CONNDONE_cb*>(calloc(1, sizeof(*ci)));
512
-
513
- if (ret == NULL || ci == NULL) {
514
- free(ret);
515
- free(ci);
516
- return NULL;
517
- }
518
-
519
- assert(iot->model = LCB_IOMODEL_EVENT);
520
-
521
- lcb_list_init(&ret->protos);
522
- ret->settings = settings;
523
- ret->io = iot;
524
- ret->refcount = 1;
525
- ret->u.fd = fd;
526
-
527
- lcbio_table_ref(ret->io);
528
- lcb_settings_ref(ret->settings);
529
- lcbio__load_socknames(ret);
530
- return ret;
531
- }
532
-
533
- void
534
- lcbio_shutdown(lcbio_SOCKET *s)
535
- {
536
- lcbio_TABLE *io = s->io;
537
-
538
- lcbio__protoctx_delall(s);
539
- if (IOT_IS_EVENT(io)) {
540
- if (s->u.fd != INVALID_SOCKET) {
541
- io->E_close(s->u.fd);
542
- s->u.fd = INVALID_SOCKET;
543
- }
544
- } else {
545
- if (s->u.sd) {
546
- io->C_close(s->u.sd);
547
- s->u.sd = NULL;
548
- }
549
- }
550
- }
551
-
552
- void
553
- lcbio__destroy(lcbio_SOCKET *s)
554
- {
555
- lcbio_shutdown(s);
556
- if (s->info) {
557
- free(s->info);
558
- }
559
- lcbio_table_unref(s->io);
560
- lcb_settings_unref(s->settings);
561
- free(s);
562
- }