gpt4 book ai didi

c++ - boost::asio async_read/async_send 正在绕过它的处理程序

转载 作者:行者123 更新时间:2023-11-30 02:08:46 27 4
gpt4 key购买 nike

我做了一个静态库。我在

中创建了这三个类

连接类

#ifndef _CONNECTION_H_
#define _CONNECTION_H_

#include <boost/array.hpp>
#include <boost/bind.hpp>
#include <boost/shared_ptr.hpp>
#include <boost/enable_shared_from_this.hpp>
#include <boost/asio.hpp>
#include <memory>
#include "ByteBuffer.h"

class Connection: public boost::enable_shared_from_this<Connection>
{
public:
typedef boost::shared_ptr<Connection> pointer;

explicit Connection(boost::asio::io_service& io_service);
virtual ~Connection();
boost::asio::ip::tcp::socket& socket();

virtual void OnConnected()=0;
virtual void Send(std::shared_ptr<uint8_t> buffer, int length);
void Receive();
void Disconnect();
bool connected;
protected:
virtual void OnReceived(ByteBuffer &b) = 0;

private:
void handle_Receive(const boost::system::error_code& error, std::size_t bytes_transferred );
void handle_Send(const boost::system::error_code& error, std::size_t bytes_transferred);

boost::asio::ip::tcp::socket socket_;
bool disconnecting;
boost::array<uint8_t, 1000> read_buffer_;
};

#endif


#include "Connection.h"


Connection::Connection(boost::asio::io_service& io_service)
:socket_(io_service),disconnecting(false),connected(false){}

Connection::~Connection(){}


boost::asio::ip::tcp::socket& Connection::socket(){
return socket_;
}

void Connection::Send(std::shared_ptr<uint8_t> buf, int length){
boost::asio::async_write(socket_,boost::asio::buffer(buf.get(),length),
boost::bind(&Connection::handle_Send, shared_from_this(), boost::asio::placeholders::error, boost::asio::placeholders::bytes_transferred));
}

void Connection::handle_Send(const boost::system::error_code& error, std::size_t bytes_transferred){

}

void Connection::Receive(){
boost::asio::async_read(socket_,boost::asio::buffer(this->read_buffer_),
boost::bind(&Connection::handle_Receive, shared_from_this(),boost::asio::placeholders::error,boost::asio::placeholders::bytes_transferred));
}

void Connection::handle_Receive(const boost::system::error_code& error, std::size_t bytes_transferred)
{
if(!error)
{
if(bytes_transferred <=0){
this->Disconnect();
}else{

ByteBuffer b((std::shared_ptr)this->read_buffer_.data(), this->read_buffer_.size()); 这个->OnReceived(b); 这个->接收();}

void Connection::Disconnect()
{
if (!disconnecting) {
boost::system::error_code ec;
socket_.shutdown(boost::asio::ip::tcp::socket::shutdown_send,ec);
socket_.close(ec);
disconnecting = true;
std::cout<<"disconnected"<<std::endl;
}
}

连接工厂类

#pragma once
#include "Connection.h"
class ConnectionFactory
{
public:
ConnectionFactory(void);
virtual ~ConnectionFactory(void);

virtual Connection::pointer create(boost::asio::io_service& io_service) = 0;
};


#include "ConnectionFactory.h"


ConnectionFactory::ConnectionFactory(void)
{
}


ConnectionFactory::~ConnectionFactory(void)
{
}

服务器类

#ifndef _SERVER_H_
#define _SERVER_H_

#include "Connection.h"
#include "ConnectionFactory.h"

class Server
{
public:
Server(boost::asio::io_service& io_service , std::string ip,short port,boost::shared_ptr<ConnectionFactory> factory);
~Server();
private:
void start_accept();
void handle_accept(boost::shared_ptr<Connection> conn,const boost::system::error_code& error);

boost::shared_ptr<ConnectionFactory> m_factory;
boost::asio::io_service &io_service;
boost::asio::ip::tcp::acceptor acceptor_;
};

#endif

#include "Server.h"


Server::Server(boost::asio::io_service& io_service,std::string ip,short port,boost::shared_ptr<ConnectionFactory> factory)
:io_service(io_service), acceptor_(io_service, boost::asio::ip::tcp::endpoint(boost::asio::ip::address_v4::from_string(ip.data()), port)){

m_factory = factory;
start_accept();

std::cout<<"Socket accepting connections..."<<std::endl;
}

Server::~Server()
{
}


void Server::start_accept(){

boost::shared_ptr<Connection> conn = m_factory->create(this->io_service);
acceptor_.async_accept(conn->socket(),
boost::bind(&Server::handle_accept, this,conn,boost::asio::placeholders::error));

}


void Server::handle_accept(boost::shared_ptr<Connection> conn,const boost::system::error_code& error){
if (!error){
std::cout<<"on connected"<<std::endl;
conn->OnConnected();
conn->Receive();
start_accept();
}
//conn->Disconnect();
}

我从静态库中提取并使用了这个类,它工作得很好

在我的 main.cpp 中

#include <iostream>
#include "auth_proto.h"
#include <Server.h>
#include <ConnectionFactory.h>
#include "AuthConnectionFactory.h"

using namespace std;
int main()
{
Auth_Setup();
try
{
boost::asio::io_service io_service;
boost::shared_ptr<ConnectionFactory> fact (new AuthConnectionFactory(io_service));
Server s(io_service,"5.113.195.156",9959,fact);
io_service.run();
}
catch (std::exception& e)
{
std::cerr << e.what() << std::endl;
}

return 0;
}

我真的不明白这里出了什么问题,当涉及到 Receive() 函数时,它从客户端接收数据,但它没有调用 handle_Receive() 方法,所以我可以使用这些数据,行为我正在等待它调用 handle_Receive(),这样我就可以将数据传递给 ByteBuffer 并使用它,但这并没有发生......

最佳答案

boost::asio::async_read 似乎只有在达到传递给它的“数据量”时才调用读取处理程序。

引用 boost 的 1.46.0 引用:

async_read

Start an asynchronous operation to read a certain amount of data from a stream.

作为解决方案,如果您希望收到任意数量的数据接收通知,请使用 socket_.async_read_some 而不是 boost::asio::async_read

另一个解决方案,正如 Sam Miller 在评论中试图说的那样,您可以添加一个固定大小的 header ,其中包含在您应该接收的每个帧之前传入的字节数,读取 header 然后调用 boost: :asio::async_read 与先前提取的数字。

关于c++ - boost::asio async_read/async_send 正在绕过它的处理程序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6221891/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com