1c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati/****************************************************************************** 2c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * 35b790feeeb211c42bf78ca3ae9c26aa30e516765Jakub Pawlowski * Copyright 2014 Google, Inc. 4c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * 5c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * Licensed under the Apache License, Version 2.0 (the "License"); 6c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * you may not use this file except in compliance with the License. 7c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * You may obtain a copy of the License at: 8c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * 9c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * http://www.apache.org/licenses/LICENSE-2.0 10c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * 11c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * Unless required by applicable law or agreed to in writing, software 12c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * distributed under the License is distributed on an "AS IS" BASIS, 13c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * See the License for the specific language governing permissions and 15c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * limitations under the License. 16c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati * 17c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati ******************************************************************************/ 18c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 19c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati#define LOG_TAG "bt_osi_socket" 20c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 2149a86709488e5cfd5e23759da18bf9613e15b04dMarie Janssen#include "osi/include/socket.h" 2249a86709488e5cfd5e23759da18bf9613e15b04dMarie Janssen 2398bf85fea392258ba22a252eeeed1153dc3eb16fSharvil Nanavati#include <asm/ioctls.h> 24f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He#include <base/logging.h> 25c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati#include <errno.h> 26c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati#include <netinet/in.h> 27c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati#include <string.h> 2898bf85fea392258ba22a252eeeed1153dc3eb16fSharvil Nanavati#include <sys/ioctl.h> 29c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati#include <sys/socket.h> 30c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati#include <unistd.h> 31c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 320f9b91e150e153229235c163861198e23600e636Sharvil Nanavati#include "osi/include/allocator.h" 3344802768c447ab480d4227b3a852a97d923b816dSharvil Nanavati#include "osi/include/log.h" 3449a86709488e5cfd5e23759da18bf9613e15b04dMarie Janssen#include "osi/include/osi.h" 350f9b91e150e153229235c163861198e23600e636Sharvil Nanavati#include "osi/include/reactor.h" 36c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 37d2199cbb8f361772819402b56e6fa46587a31c56Pavlin Radoslavov// The IPv4 loopback address: 127.0.0.1 38d2199cbb8f361772819402b56e6fa46587a31c56Pavlin Radoslavovstatic const in_addr_t LOCALHOST_ = 0x7f000001; 39d2199cbb8f361772819402b56e6fa46587a31c56Pavlin Radoslavov 40c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavatistruct socket_t { 41fbf89085bf308a98b00da77d1538539f6dd58604Sharvil Nanavati int fd; 42b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson reactor_object_t* reactor_object; 43c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati socket_cb read_ready; 44c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati socket_cb write_ready; 45b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson void* context; // Not owned, do not free. 46c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati}; 47c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 48b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonstatic void internal_read_ready(void* context); 49b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonstatic void internal_write_ready(void* context); 50c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 51b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonsocket_t* socket_new(void) { 52b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson socket_t* ret = (socket_t*)osi_calloc(sizeof(socket_t)); 53b2a292b5d8df2f359c38b0787bc01181225a9bc9Pavlin Radoslavov int enable = 1; 54c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 55fbf89085bf308a98b00da77d1538539f6dd58604Sharvil Nanavati ret->fd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); 56fbf89085bf308a98b00da77d1538539f6dd58604Sharvil Nanavati if (ret->fd == INVALID_FD) { 57b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson LOG_ERROR(LOG_TAG, "%s unable to create socket: %s", __func__, 58b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson strerror(errno)); 59c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati goto error; 60c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati } 61c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 62b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson if (setsockopt(ret->fd, SOL_SOCKET, SO_REUSEADDR, &enable, sizeof(enable)) == 63b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson -1) { 64b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson LOG_ERROR(LOG_TAG, "%s unable to set SO_REUSEADDR: %s", __func__, 65b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson strerror(errno)); 66c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati goto error; 67c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati } 68c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 69c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati return ret; 70c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 71c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavatierror:; 72b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson if (ret) close(ret->fd); 73384f8a948e9837475c4f504a626205334522df2aZach Johnson osi_free(ret); 74c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati return NULL; 75c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati} 76c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 77b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonsocket_t* socket_new_from_fd(int fd) { 78f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(fd != INVALID_FD); 79ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati 80b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson socket_t* ret = (socket_t*)osi_calloc(sizeof(socket_t)); 81ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati 82ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati ret->fd = fd; 83ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati return ret; 84ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati} 85ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati 86b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonvoid socket_free(socket_t* socket) { 87b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson if (!socket) return; 88c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 89c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati socket_unregister(socket); 90fbf89085bf308a98b00da77d1538539f6dd58604Sharvil Nanavati close(socket->fd); 91384f8a948e9837475c4f504a626205334522df2aZach Johnson osi_free(socket); 92c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati} 93c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 94b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonbool socket_listen(const socket_t* socket, port_t port) { 95f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(socket != NULL); 96c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 97c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati struct sockaddr_in addr; 98c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati addr.sin_family = AF_INET; 99d2199cbb8f361772819402b56e6fa46587a31c56Pavlin Radoslavov addr.sin_addr.s_addr = htonl(LOCALHOST_); 100c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati addr.sin_port = htons(port); 101b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson if (bind(socket->fd, (struct sockaddr*)&addr, sizeof(addr)) == -1) { 102b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson LOG_ERROR(LOG_TAG, "%s unable to bind socket to port %u: %s", __func__, 103b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson port, strerror(errno)); 104c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati return false; 105c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati } 106c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 107fbf89085bf308a98b00da77d1538539f6dd58604Sharvil Nanavati if (listen(socket->fd, 10) == -1) { 108b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson LOG_ERROR(LOG_TAG, "%s unable to listen on port %u: %s", __func__, port, 109b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson strerror(errno)); 110c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati return false; 111c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati } 112c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 113c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati return true; 114c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati} 115c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 116b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonsocket_t* socket_accept(const socket_t* socket) { 117f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(socket != NULL); 118c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 119d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov int fd; 120d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov OSI_NO_INTR(fd = accept(socket->fd, NULL, NULL)); 121fbf89085bf308a98b00da77d1538539f6dd58604Sharvil Nanavati if (fd == INVALID_FD) { 122b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson LOG_ERROR(LOG_TAG, "%s unable to accept socket: %s", __func__, 123b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson strerror(errno)); 124c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati return NULL; 125c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati } 126c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 127b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson socket_t* ret = (socket_t*)osi_calloc(sizeof(socket_t)); 128c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 129fbf89085bf308a98b00da77d1538539f6dd58604Sharvil Nanavati ret->fd = fd; 130c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati return ret; 131c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati} 132c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 133b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonssize_t socket_read(const socket_t* socket, void* buf, size_t count) { 134f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(socket != NULL); 135f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(buf != NULL); 136c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 137d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov ssize_t ret; 138d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov OSI_NO_INTR(ret = recv(socket->fd, buf, count, MSG_DONTWAIT)); 139d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov 140d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov return ret; 141c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati} 142c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 143b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonssize_t socket_write(const socket_t* socket, const void* buf, size_t count) { 144f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(socket != NULL); 145f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(buf != NULL); 146c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 147d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov ssize_t ret; 148d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov OSI_NO_INTR(ret = send(socket->fd, buf, count, MSG_DONTWAIT)); 149d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov 150d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov return ret; 151c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati} 152c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 153b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonssize_t socket_write_and_transfer_fd(const socket_t* socket, const void* buf, 154b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson size_t count, int fd) { 155f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(socket != NULL); 156f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(buf != NULL); 157ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati 158b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson if (fd == INVALID_FD) return socket_write(socket, buf, count); 159ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati 160ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati struct msghdr msg; 161ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati struct iovec iov; 162ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati char control_buf[CMSG_SPACE(sizeof(int))]; 163ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati 164b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson iov.iov_base = (void*)buf; 165ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati iov.iov_len = count; 166ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati 167ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati msg.msg_iov = &iov; 168ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati msg.msg_iovlen = 1; 169ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati msg.msg_control = control_buf; 170ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati msg.msg_controllen = sizeof(control_buf); 171ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati msg.msg_name = NULL; 172ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati msg.msg_namelen = 0; 173ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati 174b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson struct cmsghdr* header = CMSG_FIRSTHDR(&msg); 175ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati header->cmsg_level = SOL_SOCKET; 176ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati header->cmsg_type = SCM_RIGHTS; 177ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati header->cmsg_len = CMSG_LEN(sizeof(int)); 178b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson *(int*)CMSG_DATA(header) = fd; 179ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati 180d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov ssize_t ret; 181d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov OSI_NO_INTR(ret = sendmsg(socket->fd, &msg, MSG_DONTWAIT)); 182d6121a37c579731b89348e618a823c53b938449aPavlin Radoslavov 183ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati close(fd); 184ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati return ret; 185ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati} 186ad3067b83e4d309b4027a4e9b44b0a614f267da8Sharvil Nanavati 187b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonssize_t socket_bytes_available(const socket_t* socket) { 188f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(socket != NULL); 18998bf85fea392258ba22a252eeeed1153dc3eb16fSharvil Nanavati 19098bf85fea392258ba22a252eeeed1153dc3eb16fSharvil Nanavati int size = 0; 191b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson if (ioctl(socket->fd, FIONREAD, &size) == -1) return -1; 19298bf85fea392258ba22a252eeeed1153dc3eb16fSharvil Nanavati return size; 19398bf85fea392258ba22a252eeeed1153dc3eb16fSharvil Nanavati} 19498bf85fea392258ba22a252eeeed1153dc3eb16fSharvil Nanavati 195b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonvoid socket_register(socket_t* socket, reactor_t* reactor, void* context, 196b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson socket_cb read_cb, socket_cb write_cb) { 197f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(socket != NULL); 198c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 199c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati // Make sure the socket isn't currently registered. 200c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati socket_unregister(socket); 201c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 202c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati socket->read_ready = read_cb; 203c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati socket->write_ready = write_cb; 204c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati socket->context = context; 205c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 206b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson void (*read_fn)(void*) = (read_cb != NULL) ? internal_read_ready : NULL; 207b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson void (*write_fn)(void*) = (write_cb != NULL) ? internal_write_ready : NULL; 208fbf89085bf308a98b00da77d1538539f6dd58604Sharvil Nanavati 209b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson socket->reactor_object = 210b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson reactor_register(reactor, socket->fd, socket, read_fn, write_fn); 211c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati} 212c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 213b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonvoid socket_unregister(socket_t* socket) { 214f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(socket != NULL); 215c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 216b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson if (socket->reactor_object) reactor_unregister(socket->reactor_object); 217fbf89085bf308a98b00da77d1538539f6dd58604Sharvil Nanavati socket->reactor_object = NULL; 218c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati} 219c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 220b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonstatic void internal_read_ready(void* context) { 221f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(context != NULL); 222c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 223b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson socket_t* socket = static_cast<socket_t*>(context); 224c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati socket->read_ready(socket, socket->context); 225c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati} 226c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 227b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watsonstatic void internal_write_ready(void* context) { 228f2af1c42ccb2f642b241c2261b42d0be61d45438Jack He CHECK(context != NULL); 229c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati 230b55040cc6448a8847490da807d2b6362aa8cb8d9Myles Watson socket_t* socket = static_cast<socket_t*>(context); 231c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati socket->write_ready(socket, socket->context); 232c2031c4fbab9ed2d2e51a0b287a3fab805932ca4Sharvil Nanavati} 233