C++ boost::async_写入导致错误现有连接被远程主机强制关闭
我想使用C++ boost::async_写入导致错误现有连接被远程主机强制关闭,c++,boost,boost-asio,C++,Boost,Boost Asio,我想使用boost::asio将结构从客户端发送到服务器。我遵循了boost教程链接。我稍微修改了server.cpp和client.cpp中的代码。使用新代码,在建立连接后,client.cpp将结构stock写入服务器并读取服务器端的stock信息。(在教程版本中,建立连接后,服务器将stock struct写入客户端,客户端读取它们。此版本适用于我。) 我的问题是,建立连接后,client.cpp中的async\u write会导致错误 写入错误:远程主机强制关闭了现有连接 而server
boost::asio
将结构从客户端发送到服务器。我遵循了boost教程链接。我稍微修改了server.cpp
和client.cpp
中的代码。使用新代码,在建立连接后,client.cpp
将结构stock写入服务器并读取服务器端的stock信息。(在教程版本中,建立连接后,服务器将stock struct写入客户端,客户端读取它们。此版本适用于我。)
我的问题是,建立连接后,client.cpp
中的async\u write
会导致错误
写入错误:远程主机强制关闭了现有连接
而server.cpp
中的async\u read
会导致错误
读取错误:本地系统中止了网络连接
正如一些论坛答案所建议的,我将async_write和async_read函数处理程序中的this
指针从this更改为shared_。问题仍然存在
我无法确定是客户端还是服务器端导致了问题。请帮忙
server.cpp
#include <boost/asio.hpp>
#include <boost/bind.hpp>
#include <boost/lexical_cast.hpp>
#include <iostream>
#include <vector>
#include "connection.h" // Must come before boost/serialization headers.
#include <boost/serialization/vector.hpp>
#include <boost/enable_shared_from_this.hpp>
#include "stock.h"
namespace s11n_example
{
/// Serves stock quote information to any client that connects to it.
class server : public boost::enable_shared_from_this<server>
{
private:
/// The acceptor object used to accept incoming socket connections.
boost::asio::ip::tcp::acceptor acceptor_;
/// The data to be sent to each client.
std::vector<stock> stocks_;
public:
/// Constructor opens the acceptor and starts waiting for the first incoming
/// connection.
server(boost::asio::io_service& io_service, unsigned short port):
acceptor_(io_service, boost::asio::ip::tcp::endpoint(boost::asio::ip::tcp::v4(), port))
{
// Start an accept operation for a new connection.
connection_ptr new_conn(new connection(acceptor_.get_io_service()));
acceptor_.async_accept(new_conn->socket(),
boost::bind(&server::handle_accept, this,boost::asio::placeholders::error, new_conn));
}
/// Handle completion of a accept operation.
void handle_accept(const boost::system::error_code& e, connection_ptr conn)
{
if (!e)
{
std::cout << "Received a connection" <<std::endl;
conn->async_read(stocks_,
boost::bind(&server::handle_read, shared_from_this(),boost::asio::placeholders::error));
}
// Start an accept operation for a new connection.
connection_ptr new_conn(new connection(acceptor_.get_io_service()));
acceptor_.async_accept(new_conn->socket(),
boost::bind(&server::handle_accept, this,boost::asio::placeholders::error, new_conn));
}
/// Handle completion of a read operation.
void handle_read(const boost::system::error_code& e)
{
if (!e)
{
// Print out the data that was received.
for (std::size_t i = 0; i < stocks_.size(); ++i)
{
std::cout << "Stock number " << i << "\n";
std::cout << " code: " << stocks_[i].code << "\n";
std::cout << " name: " << stocks_[i].name << "\n";
std::cout << " open_price: " << stocks_[i].open_price << "\n";
std::cout << " high_price: " << stocks_[i].high_price << "\n";
std::cout << " low_price: " << stocks_[i].low_price << "\n";
std::cout << " last_price: " << stocks_[i].last_price << "\n";
std::cout << " buy_price: " << stocks_[i].buy_price << "\n";
std::cout << " buy_quantity: " << stocks_[i].buy_quantity << "\n";
std::cout << " sell_price: " << stocks_[i].sell_price << "\n";
std::cout << " sell_quantity: " << stocks_[i].sell_quantity << "\n";
}
}
else
{
// An error occurred.
std::cerr << "Error in read:" << e.message() << std::endl;
}
}
};
} // namespace s11n_example
int main(int argc, char* argv[])
{
try
{
// Check command line arguments.
if (argc != 2)
{
std::cerr << "Usage: server <port>" << std::endl;
return 1;
}
unsigned short port = boost::lexical_cast<unsigned short>(argv[1]);
boost::asio::io_service io_service;
boost::shared_ptr<s11n_example::server> server(new s11n_example::server(io_service, port));
io_service.run();
}
catch (std::exception& e)
{
std::cerr << e.what() << std::endl;
}
return 0;
}
#包括
#包括
#包括
#包括
#包括
#包括“connection.h”//必须在boost/serialization头之前。
#包括
#包括
#包括“stock.h”
名称空间s11n_示例
{
///将股票报价信息提供给任何连接到它的客户端。
类服务器:public boost::从\u启用\u共享\u
{
私人:
///用于接受传入套接字连接的接受器对象。
boost::asio::ip::tcp::acceptor-acceptor;
///要发送到每个客户端的数据。
std::病媒股票;
公众:
///构造函数打开接受程序并开始等待第一个传入的
///连接。
服务器(boost::asio::io_服务和io_服务,未签名短端口):
接受者(io_服务,boost::asio::ip::tcp::endpoint(boost::asio::ip::tcp::v4(),端口))
{
//启动新连接的接受操作。
连接(新连接(接受器获取io服务());
acceptor_u.async_uAccept(新连接->套接字(),
boost::bind(&server::handle_accept,this,boost::asio::placeholders::error,new_conn));
}
///处理接受操作的完成。
无效句柄\u接受(常量boost::系统::错误\u代码和e,连接\u ptr conn)
{
如果(!e)
{
std::cout您需要传递conn
来处理读取,否则它将在handle\u accept
方法的末尾被破坏。当它被破坏时,它包含的套接字也将被破坏,连接将关闭
conn->async_read(stocks_,
boost::bind(&server::handle_read, shared_from_this(), conn, boost::asio::placeholders::error));
lambda比使用bind更易于阅读:
auto self = shared_from_this();
conn->async_read(stocks_,
[self, this, conn] (boost::system::error_code ec) { handle_read(ec); });
将复制捕获列表中列出的变量,以使共享指针保持活动状态
auto self = shared_from_this();
conn->async_read(stocks_,
[self, this, conn] (boost::system::error_code ec) { handle_read(ec); });