void AsyncMcClientImpl::attemptConnection() { assert(connectionState_ == ConnectionState::DOWN); connectionState_ = ConnectionState::CONNECTING; if (connectionOptions_.noNetwork) { socket_.reset(new MockMcClientTransport(eventBase_)); connectSuccess(); return; } if (connectionOptions_.sslContextProvider) { auto sslContext = connectionOptions_.sslContextProvider(); if (!sslContext) { LOG_FAILURE("AsyncMcClient", failure::Category::kBadEnvironment, "SSLContext provider returned nullptr, check SSL certificates. Any " "further request to {} will fail.", connectionOptions_.accessPoint.toHostPortString()); connectErr(folly::AsyncSocketException( folly::AsyncSocketException::SSL_ERROR, "")); return; } socket_.reset(new folly::AsyncSSLSocket( sslContext, &eventBase_)); } else { socket_.reset(new folly::AsyncSocket(&eventBase_)); } auto& socket = dynamic_cast<folly::AsyncSocket&>(*socket_); folly::SocketAddress address; try { address = folly::SocketAddress( connectionOptions_.accessPoint.getHost(), connectionOptions_.accessPoint.getPort(), /* allowNameLookup */ true); } catch (const std::system_error& e) { LOG_FAILURE("AsyncMcClient", failure::Category::kBadEnvironment, "{}", e.what()); connectErr(folly::AsyncSocketException( folly::AsyncSocketException::NOT_OPEN, "")); return; } auto socketOptions = createSocketOptions(address, connectionOptions_); socket.setSendTimeout(connectionOptions_.writeTimeout.count()); socket.connect(this, address, connectionOptions_.writeTimeout.count(), socketOptions); // If AsyncSocket::connect() fails, socket_ may have been reset if (socket_ && connectionOptions_.enableQoS) { checkWhetherQoSIsApplied(address, socket.getFd(), connectionOptions_); } }
void ClientThread::run() { memset(&client, 0, sizeof(struct sockaddr)); client.sin_family = AF_INET; client.sin_addr.s_addr = INADDR_ANY; client.sin_port = 0; sock = socket(PF_INET, SOCK_DGRAM, 0); setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &optval, sizeof(optval)); if(gethostbyname_r(addr.toStdString().c_str(), &he, buf, sizeof(buf), &ip_addr, &status) || !ip_addr || sock < 0 || bind(sock, (struct sockaddr*)&client, sizeof(struct sockaddr)) < 0) { emit connectError(); ::close(sock); } else { memset(&server, 0, sizeof(struct sockaddr)); memcpy(&server.sin_addr.s_addr, ip_addr->h_addr, ip_addr->h_length); server.sin_family = AF_INET; server.sin_port = htons(port.toInt()); sendto(sock, "new0"+name.toUtf8(), name.toUtf8().length()+4, 0, (struct sockaddr*)&server, sizeof(struct sockaddr)); buf_size = recvfrom(sock, buf, 2048, 0, (struct sockaddr*)&server, &size); id = QString::fromUtf8(buf, buf_size); emit connectSuccess(id); while (true) { buf_size = recvfrom(sock, buf, 2048, 0, (struct sockaddr*)&consultant, &size); if(QString::fromUtf8(buf, 4) == "exit") { talk = false; emit newSysMessage("Rozmowa została zakończona."); sendto(sock, "exit"+id.toUtf8(), id.toUtf8().length()+4, 0, (struct sockaddr*)&server, sizeof(struct sockaddr)); emit exitTalk(); break; } else if(!talk && QString::fromUtf8(buf, 3) == "con") { talk = true; emit newSysMessage("Właśnie połączył się z Tobą konsultant "+QString::fromUtf8(buf, buf_size).mid(3,buf_size-3)+"."); emit startTalk(); } else if(talk && QString::fromUtf8(buf, 1) == ";") { emit newMessage(QString::fromUtf8(buf, buf_size).mid(1,buf_size-1)); } } } }
void NetHandler::start() { m_bRunning = true; // first let's increase the limit of open files int maxconn = 100000; struct rlimit srl; srl.rlim_cur = maxconn + 10; srl.rlim_max = maxconn + 10; if (setrlimit(RLIMIT_NOFILE, &srl) < 0) { LOG4CXX_FATAL(logger_, "Cannot set RLimit!"); exit(1); } epfd = epoll_create(maxconn); if (epfd < 0) { LOG4CXX_FATAL(logger_, "epoll_create error!"); exit(1); } // Now let's ignore broken pipes struct sigaction sa; memset(&sa, 0, sizeof (sa)); sa.sa_handler = SIG_IGN; if (sigaction(SIGPIPE, &sa, NULL) < 0) { LOG4CXX_WARN(logger_, "Error ignoring SIGPIPE!"); } if (initSockets() < 0) { exit(1); } struct epoll_event ev, evs[MAX_EVENTS]; LOG4CXX_INFO(logger_, "Nethandler started."); for (; ; ) { if (!m_bRunning) { break; } int count = epoll_wait(epfd, evs, MAX_EVENTS, 1000); if (count < 0) { LOG4CXX_FATAL(logger_, "epoll_wait error!"); } time_t now = Clock::getCurrentSystemTime(); if (!preNetEvent(now)) { LOG4CXX_ERROR(logger_, "PreNetEvent returned false, terminating..."); break; } for (int i = 0; i < count; i++) { int fd = evs[i].data.fd; if (isListenSocket(fd)) { struct sockaddr_in sa; socklen_t slen = sizeof (sa); int nfd = 0; nfd = accept(fd, (struct sockaddr*) &sa, &slen); if (nfd > 0) { ev.events = EPOLLIN | EPOLLHUP; //| EPOLLRDHUP; ev.data.fd = nfd; if (epoll_ctl(epfd, EPOLL_CTL_ADD, nfd, &ev) < 0) { LOG4CXX_ERROR(logger_, "epoll_ctl error, cannot add client!"); } else { size_t rsize = readCacheSize(fd); //size_t rsize = (fd==wsfd ? NetCache::WEBSERVER_READ_SIZE : NetCache::DEFAULT_READ_SIZE); NetCache *cache = addConnection(nfd, sa, rsize); createProtocolHandler(cache, fd); } } } else // data { NetCache *cache = getCacheFromFd(fd); if (cache != NULL) { __uint32_t events = evs[i].events; bool readError = false; if ((events & EPOLLIN) > 0) { int64 uid = cache->uid; readError = !cache->read(); if (!readError) { string req; while (cache->assemble(req) && !cache->remove) { //LOG4CXX_DEBUG(logger_, "Command Received: \"" << req.c_str() << "\" from uid:" << uid << " fd:" << fd); if (cache->ph != NULL) { cache->ph->handle(uid, req); } else { LOG4CXX_ERROR(logger_, "Protocol handler is NULL for fd:" << fd); } } } } if ((events & EPOLLOUT) > 0) { if ( isConnecting( fd )) { connectSuccess( fd ); } else if (cache->write()) { ev.events = EPOLLIN | EPOLLHUP; // | EPOLLRDHUP; ev.data.fd = fd; epoll_ctl(epfd, EPOLL_CTL_MOD, fd, &ev); } } if ((cache->remove && !cache->waitToWrite()) || readError || (events & EPOLLHUP) > 0 || //(events&EPOLLRDHUP)>0 || (events & EPOLLERR) > 0) { int64 uid = cache->uid; if (uid >= 0 && cache->ph != NULL) { cache->ph->leave(uid); } LOG4CXX_DEBUG(logger_, "Client disconnected of fd:" << fd << ", remove: " << cache->remove << ", read error: " << readError << ", hup: " << (events & EPOLLHUP) //<< //", rdhup: " << (events & EPOLLRDHUP) << ", epoll error: " << (events & EPOLLERR)); doCloseConnection(fd); if (isConnectSocket(fd)) { connectFailed(fd); } } } else { LOG4CXX_ERROR(logger_, "Cannot find cache for fd:" << fd); } } } } }