diff options
Diffstat (limited to 'linden/indra/llmessage/lliosocket.cpp')
-rw-r--r-- | linden/indra/llmessage/lliosocket.cpp | 99 |
1 files changed, 36 insertions, 63 deletions
diff --git a/linden/indra/llmessage/lliosocket.cpp b/linden/indra/llmessage/lliosocket.cpp index 7ec577c..686c037 100644 --- a/linden/indra/llmessage/lliosocket.cpp +++ b/linden/indra/llmessage/lliosocket.cpp | |||
@@ -41,6 +41,7 @@ | |||
41 | #include "llhost.h" | 41 | #include "llhost.h" |
42 | #include "llmemtype.h" | 42 | #include "llmemtype.h" |
43 | #include "llpumpio.h" | 43 | #include "llpumpio.h" |
44 | #include "llthread.h" | ||
44 | 45 | ||
45 | // | 46 | // |
46 | // constants | 47 | // constants |
@@ -104,51 +105,31 @@ void ll_debug_socket(const char* msg, apr_socket_t* apr_sock) | |||
104 | /// | 105 | /// |
105 | 106 | ||
106 | // static | 107 | // static |
107 | LLSocket::ptr_t LLSocket::create(apr_pool_t* pool, EType type, U16 port) | 108 | LLSocket::ptr_t LLSocket::create(EType type, U16 port) |
108 | { | 109 | { |
109 | LLMemType m1(LLMemType::MTYPE_IO_TCP); | 110 | LLMemType m1(LLMemType::MTYPE_IO_TCP); |
110 | LLSocket::ptr_t rv; | ||
111 | apr_socket_t* socket = NULL; | ||
112 | apr_pool_t* new_pool = NULL; | ||
113 | apr_status_t status = APR_EGENERAL; | 111 | apr_status_t status = APR_EGENERAL; |
114 | 112 | LLSocket::ptr_t rv(new LLSocket); | |
115 | // create a pool for the socket | ||
116 | status = apr_pool_create(&new_pool, pool); | ||
117 | if(ll_apr_warn_status(status)) | ||
118 | { | ||
119 | if(new_pool) apr_pool_destroy(new_pool); | ||
120 | return rv; | ||
121 | } | ||
122 | 113 | ||
123 | if(STREAM_TCP == type) | 114 | if(STREAM_TCP == type) |
124 | { | 115 | { |
125 | status = apr_socket_create( | 116 | status = apr_socket_create(&rv->mSocket, APR_INET, SOCK_STREAM, APR_PROTO_TCP, rv->mPool()); |
126 | &socket, | ||
127 | APR_INET, | ||
128 | SOCK_STREAM, | ||
129 | APR_PROTO_TCP, | ||
130 | new_pool); | ||
131 | } | 117 | } |
132 | else if(DATAGRAM_UDP == type) | 118 | else if(DATAGRAM_UDP == type) |
133 | { | 119 | { |
134 | status = apr_socket_create( | 120 | status = apr_socket_create(&rv->mSocket, APR_INET, SOCK_DGRAM, APR_PROTO_UDP, rv->mPool()); |
135 | &socket, | ||
136 | APR_INET, | ||
137 | SOCK_DGRAM, | ||
138 | APR_PROTO_UDP, | ||
139 | new_pool); | ||
140 | } | 121 | } |
141 | else | 122 | else |
142 | { | 123 | { |
143 | if(new_pool) apr_pool_destroy(new_pool); | 124 | rv.reset(); |
144 | return rv; | 125 | return rv; |
145 | } | 126 | } |
146 | if(ll_apr_warn_status(status)) | 127 | if(ll_apr_warn_status(status)) |
147 | { | 128 | { |
148 | if(new_pool) apr_pool_destroy(new_pool); | 129 | rv->mSocket = NULL; |
130 | rv.reset(); | ||
149 | return rv; | 131 | return rv; |
150 | } | 132 | } |
151 | rv = ptr_t(new LLSocket(socket, new_pool)); | ||
152 | if(port > 0) | 133 | if(port > 0) |
153 | { | 134 | { |
154 | apr_sockaddr_t* sa = NULL; | 135 | apr_sockaddr_t* sa = NULL; |
@@ -158,7 +139,7 @@ LLSocket::ptr_t LLSocket::create(apr_pool_t* pool, EType type, U16 port) | |||
158 | APR_UNSPEC, | 139 | APR_UNSPEC, |
159 | port, | 140 | port, |
160 | 0, | 141 | 0, |
161 | new_pool); | 142 | rv->mPool()); |
162 | if(ll_apr_warn_status(status)) | 143 | if(ll_apr_warn_status(status)) |
163 | { | 144 | { |
164 | rv.reset(); | 145 | rv.reset(); |
@@ -166,8 +147,8 @@ LLSocket::ptr_t LLSocket::create(apr_pool_t* pool, EType type, U16 port) | |||
166 | } | 147 | } |
167 | // This allows us to reuse the address on quick down/up. This | 148 | // This allows us to reuse the address on quick down/up. This |
168 | // is unlikely to create problems. | 149 | // is unlikely to create problems. |
169 | ll_apr_warn_status(apr_socket_opt_set(socket, APR_SO_REUSEADDR, 1)); | 150 | ll_apr_warn_status(apr_socket_opt_set(rv->mSocket, APR_SO_REUSEADDR, 1)); |
170 | status = apr_socket_bind(socket, sa); | 151 | status = apr_socket_bind(rv->mSocket, sa); |
171 | if(ll_apr_warn_status(status)) | 152 | if(ll_apr_warn_status(status)) |
172 | { | 153 | { |
173 | rv.reset(); | 154 | rv.reset(); |
@@ -181,7 +162,7 @@ LLSocket::ptr_t LLSocket::create(apr_pool_t* pool, EType type, U16 port) | |||
181 | // to keep a queue of incoming connections for ACCEPT. | 162 | // to keep a queue of incoming connections for ACCEPT. |
182 | lldebugs << "Setting listen state for socket." << llendl; | 163 | lldebugs << "Setting listen state for socket." << llendl; |
183 | status = apr_socket_listen( | 164 | status = apr_socket_listen( |
184 | socket, | 165 | rv->mSocket, |
185 | LL_DEFAULT_LISTEN_BACKLOG); | 166 | LL_DEFAULT_LISTEN_BACKLOG); |
186 | if(ll_apr_warn_status(status)) | 167 | if(ll_apr_warn_status(status)) |
187 | { | 168 | { |
@@ -202,21 +183,28 @@ LLSocket::ptr_t LLSocket::create(apr_pool_t* pool, EType type, U16 port) | |||
202 | } | 183 | } |
203 | 184 | ||
204 | // static | 185 | // static |
205 | LLSocket::ptr_t LLSocket::create(apr_socket_t* socket, apr_pool_t* pool) | 186 | LLSocket::ptr_t LLSocket::create(apr_status_t& status, LLSocket::ptr_t& listen_socket) |
206 | { | 187 | { |
207 | LLMemType m1(LLMemType::MTYPE_IO_TCP); | 188 | LLMemType m1(LLMemType::MTYPE_IO_TCP); |
208 | LLSocket::ptr_t rv; | 189 | if (!listen_socket->getSocket()) |
209 | if(!socket) | 190 | { |
191 | status = APR_ENOSOCKET; | ||
192 | return LLSocket::ptr_t(); | ||
193 | } | ||
194 | LLSocket::ptr_t rv(new LLSocket); | ||
195 | lldebugs << "accepting socket" << llendl; | ||
196 | status = apr_socket_accept(&rv->mSocket, listen_socket->getSocket(), rv->mPool()); | ||
197 | if (status != APR_SUCCESS) | ||
210 | { | 198 | { |
199 | rv->mSocket = NULL; | ||
200 | rv.reset(); | ||
211 | return rv; | 201 | return rv; |
212 | } | 202 | } |
213 | rv = ptr_t(new LLSocket(socket, pool)); | ||
214 | rv->mPort = PORT_EPHEMERAL; | 203 | rv->mPort = PORT_EPHEMERAL; |
215 | rv->setOptions(); | 204 | rv->setOptions(); |
216 | return rv; | 205 | return rv; |
217 | } | 206 | } |
218 | 207 | ||
219 | |||
220 | bool LLSocket::blockingConnect(const LLHost& host) | 208 | bool LLSocket::blockingConnect(const LLHost& host) |
221 | { | 209 | { |
222 | if(!mSocket) return false; | 210 | if(!mSocket) return false; |
@@ -229,7 +217,7 @@ bool LLSocket::blockingConnect(const LLHost& host) | |||
229 | APR_UNSPEC, | 217 | APR_UNSPEC, |
230 | host.getPort(), | 218 | host.getPort(), |
231 | 0, | 219 | 0, |
232 | mPool))) | 220 | mPool()))) |
233 | { | 221 | { |
234 | return false; | 222 | return false; |
235 | } | 223 | } |
@@ -240,13 +228,11 @@ bool LLSocket::blockingConnect(const LLHost& host) | |||
240 | return true; | 228 | return true; |
241 | } | 229 | } |
242 | 230 | ||
243 | LLSocket::LLSocket(apr_socket_t* socket, apr_pool_t* pool) : | 231 | LLSocket::LLSocket() : |
244 | mSocket(socket), | 232 | mSocket(NULL), |
245 | mPool(pool), | 233 | mPool(LLThread::tldata().mRootPool), |
246 | mPort(PORT_INVALID) | 234 | mPort(PORT_INVALID) |
247 | { | 235 | { |
248 | ll_debug_socket("Constructing wholely formed socket", mSocket); | ||
249 | LLMemType m1(LLMemType::MTYPE_IO_TCP); | ||
250 | } | 236 | } |
251 | 237 | ||
252 | LLSocket::~LLSocket() | 238 | LLSocket::~LLSocket() |
@@ -258,10 +244,6 @@ LLSocket::~LLSocket() | |||
258 | ll_debug_socket("Destroying socket", mSocket); | 244 | ll_debug_socket("Destroying socket", mSocket); |
259 | apr_socket_close(mSocket); | 245 | apr_socket_close(mSocket); |
260 | } | 246 | } |
261 | if(mPool) | ||
262 | { | ||
263 | apr_pool_destroy(mPool); | ||
264 | } | ||
265 | } | 247 | } |
266 | 248 | ||
267 | void LLSocket::setOptions() | 249 | void LLSocket::setOptions() |
@@ -522,10 +504,8 @@ LLIOPipe::EStatus LLIOSocketWriter::process_impl( | |||
522 | /// | 504 | /// |
523 | 505 | ||
524 | LLIOServerSocket::LLIOServerSocket( | 506 | LLIOServerSocket::LLIOServerSocket( |
525 | apr_pool_t* pool, | ||
526 | LLIOServerSocket::socket_t listener, | 507 | LLIOServerSocket::socket_t listener, |
527 | factory_t factory) : | 508 | factory_t factory) : |
528 | mPool(pool), | ||
529 | mListenSocket(listener), | 509 | mListenSocket(listener), |
530 | mReactor(factory), | 510 | mReactor(factory), |
531 | mInitialized(false), | 511 | mInitialized(false), |
@@ -585,21 +565,15 @@ LLIOPipe::EStatus LLIOServerSocket::process_impl( | |||
585 | lldebugs << "accepting socket" << llendl; | 565 | lldebugs << "accepting socket" << llendl; |
586 | 566 | ||
587 | PUMP_DEBUG; | 567 | PUMP_DEBUG; |
588 | apr_pool_t* new_pool = NULL; | 568 | apr_status_t status; |
589 | apr_status_t status = apr_pool_create(&new_pool, mPool); | 569 | LLSocket::ptr_t llsocket(LLSocket::create(status, mListenSocket)); |
590 | apr_socket_t* socket = NULL; | ||
591 | status = apr_socket_accept( | ||
592 | &socket, | ||
593 | mListenSocket->getSocket(), | ||
594 | new_pool); | ||
595 | LLSocket::ptr_t llsocket(LLSocket::create(socket, new_pool)); | ||
596 | //EStatus rv = STATUS_ERROR; | 570 | //EStatus rv = STATUS_ERROR; |
597 | if(llsocket) | 571 | if(llsocket && status == APR_SUCCESS) |
598 | { | 572 | { |
599 | PUMP_DEBUG; | 573 | PUMP_DEBUG; |
600 | 574 | ||
601 | apr_sockaddr_t* remote_addr; | 575 | apr_sockaddr_t* remote_addr; |
602 | apr_socket_addr_get(&remote_addr, APR_REMOTE, socket); | 576 | apr_socket_addr_get(&remote_addr, APR_REMOTE, llsocket->getSocket()); |
603 | 577 | ||
604 | char* remote_host_string; | 578 | char* remote_host_string; |
605 | apr_sockaddr_ip_get(&remote_host_string, remote_addr); | 579 | apr_sockaddr_ip_get(&remote_host_string, remote_addr); |
@@ -614,7 +588,6 @@ LLIOPipe::EStatus LLIOServerSocket::process_impl( | |||
614 | { | 588 | { |
615 | chain.push_back(LLIOPipe::ptr_t(new LLIOSocketWriter(llsocket))); | 589 | chain.push_back(LLIOPipe::ptr_t(new LLIOSocketWriter(llsocket))); |
616 | pump->addChain(chain, mResponseTimeout); | 590 | pump->addChain(chain, mResponseTimeout); |
617 | status = STATUS_OK; | ||
618 | } | 591 | } |
619 | else | 592 | else |
620 | { | 593 | { |
@@ -623,7 +596,8 @@ LLIOPipe::EStatus LLIOServerSocket::process_impl( | |||
623 | } | 596 | } |
624 | else | 597 | else |
625 | { | 598 | { |
626 | llwarns << "Unable to create linden socket." << llendl; | 599 | char buf[256]; |
600 | llwarns << "Unable to accept linden socket: " << apr_strerror(status, buf, sizeof(buf)) << llendl; | ||
627 | } | 601 | } |
628 | 602 | ||
629 | PUMP_DEBUG; | 603 | PUMP_DEBUG; |
@@ -636,11 +610,10 @@ LLIOPipe::EStatus LLIOServerSocket::process_impl( | |||
636 | #if 0 | 610 | #if 0 |
637 | LLIODataSocket::LLIODataSocket( | 611 | LLIODataSocket::LLIODataSocket( |
638 | U16 suggested_port, | 612 | U16 suggested_port, |
639 | U16 start_discovery_port, | 613 | U16 start_discovery_port) : |
640 | apr_pool_t* pool) : | ||
641 | mSocket(NULL) | 614 | mSocket(NULL) |
642 | { | 615 | { |
643 | if(!pool || (PORT_INVALID == suggested_port)) return; | 616 | if(PORT_INVALID == suggested_port) return; |
644 | if(ll_apr_warn_status(apr_socket_create(&mSocket, APR_INET, SOCK_DGRAM, APR_PROTO_UDP, pool))) return; | 617 | if(ll_apr_warn_status(apr_socket_create(&mSocket, APR_INET, SOCK_DGRAM, APR_PROTO_UDP, pool))) return; |
645 | apr_sockaddr_t* sa = NULL; | 618 | apr_sockaddr_t* sa = NULL; |
646 | if(ll_apr_warn_status(apr_sockaddr_info_get(&sa, APR_ANYADDR, APR_UNSPEC, suggested_port, 0, pool))) return; | 619 | if(ll_apr_warn_status(apr_sockaddr_info_get(&sa, APR_ANYADDR, APR_UNSPEC, suggested_port, 0, pool))) return; |