소켓 요청이 들어오면 등록한 콜백함수를 호출하게 하는 형식으로 작성하였다. 사용시 참고바람
<사용방법>
0. handler 함수 구현 (형태는 void (string, socket) 이지만 socketmanager를 변경하면 다른 타입도 가능)
1. io_service obj 선언
(예) boost::asio::io_service io_service;
2. endpoint object 선언
(예) boost::asio::ip::tcp::endpoint endpoint(boost::asio::ip::tcp::v4(), PortNo);
3. SocketManager object 선언
(예) SocketManager socketManager(io_service, endpoint, handler)
4. accept() 함수 실행
(예) socketManager.accept();
5. io_service 구동
(예) io_service.run();
<사용방법>
0. handler 함수 구현 (형태는 void (string, socket) 이지만 socketmanager를 변경하면 다른 타입도 가능)
1. io_service obj 선언
(예) boost::asio::io_service io_service;
2. endpoint object 선언
(예) boost::asio::ip::tcp::endpoint endpoint(boost::asio::ip::tcp::v4(), PortNo);
3. SocketManager object 선언
(예) SocketManager socketManager(io_service, endpoint, handler)
4. accept() 함수 실행
(예) socketManager.accept();
5. io_service 구동
(예) io_service.run();
///
/// @file SocketManager.h
/// @brief header file of SocketManager class
/// @author Dohyun Yun
/// @date 2008-10-01
/// @details
/// - Log
///
#ifndef _SOCKET_MANAGER_H_
#define _SOCKET_MANAGER_H_
#include <string>
#include <boost/bind.hpp>
#include <boost/asio.hpp>
#include <boost/shared_ptr.hpp>
#include <boost/enable_shared_from_this.hpp>
//#define DEBUG
class SocketObject : public boost::enable_shared_from_this<SocketObject>
{
public:
SocketObject(boost::asio::io_service& io_service)
: socket_(io_service), data_(NULL)
{
}
~SocketObject()
{
if (data_ != NULL)
{
delete[] data_;
}
}
boost::asio::ip::tcp::socket& socket() { return socket_; };
void run(void func1(std::string, boost::asio::ip::tcp::socket&))
{
#ifdef DEBUG
std::cout << "run() start" << std::endl;
#endif // DEBUG
handlerFromOutside_ = func1;
if (data_ != NULL)
{
delete[] data_;
}
data_ = new char[HEADER_LENGTH];
boost::asio::async_read(socket_,
boost::asio::buffer(data_, HEADER_LENGTH),
boost::bind(&SocketObject::readData, shared_from_this(),
boost::asio::placeholders::error));
}
void readData(const boost::system::error_code& error)
{
#ifdef DEBUG
std::cout << "readData() start" << std::endl;
#endif // DEBUG
if (!error)
{
dataLength_ = *(reinterpret_cast<unsigned int*>(data_));
if (data_ != NULL)
{
delete[] data_;
data_ = NULL;
}
data_ = new char[dataLength_ + 1];
boost::asio::async_read(socket_,
boost::asio::buffer(data_, dataLength_),
boost::bind(&SocketObject::runHandlerFromOutside, shared_from_this(),
boost::asio::placeholders::error));
}
}
void runHandlerFromOutside(const boost::system::error_code& error)
{
#ifdef DEBUG
std::cout << "runHandlerFromOutside() start" << std::endl;
#endif // DEBUG
if (!error)
{
data_[dataLength_] = '\0';
std::string queryXML(data_);
handlerFromOutside_(queryXML, socket_);
}
#ifdef DEBUG
std::cout << "runHandlerFromOutside() OK" << std::endl;
#endif // DEBUG
}
public:
void (*handlerFromOutside_)(std::string, boost::asio::ip::tcp::socket&);
static const size_t HEADER_LENGTH = sizeof(int);
boost::asio::ip::tcp::socket socket_;
private:
int dataLength_;
char* data_;
};
typedef boost::shared_ptr<SocketObject> SocketPointer;
///
/// @brief SocketManager controls socket communications between outside and main process.
/// @details
/// SocketManager gets queryXML from outside and sends the resultXML to the outside.\n
/// It supports:
/// - Async reading from outside.
/// - Async writing to outside.
///
class SocketManager
{
public:
SocketManager(boost::asio::io_service& io_service,
const boost::asio::ip::tcp::endpoint& endpoint,
void func(std::string, boost::asio::ip::tcp::socket&))
: io_service_(io_service),
acceptor_(io_service, endpoint),
handlerFromOutside_(boost::ref(func)) {};
~SocketManager() {};
void accept()
{
#ifdef DEBUG
std::cout << "accept() start" << std::endl;
#endif // DEBUG
SocketPointer newSocketPointerObject(new SocketObject(io_service_));
acceptor_.async_accept(newSocketPointerObject->socket(),
boost::bind(&SocketManager::handler, this, newSocketPointerObject, boost::asio::placeholders::error));
} // end - accept()
void handler(SocketPointer socketPointerObject, const boost::system::error_code& error)
{
#ifdef DEBUG
std::cout << "handler() start" << std::endl;
#endif // DEBUG
if (!error)
{
socketPointerObject->run(handlerFromOutside_);
// Make new socket which gets the next connection request.
SocketPointer newSocketPointerObject(new SocketObject(io_service_));
acceptor_.async_accept(newSocketPointerObject->socket(),
boost::bind(&SocketManager::handler, this, newSocketPointerObject, boost::asio::placeholders::error));
} // end - if
} // end - handler
private:
boost::asio::io_service& io_service_;
boost::asio::ip::tcp::acceptor acceptor_;
public:
void (*handlerFromOutside_)(std::string, boost::asio::ip::tcp::socket&);
}; // end - class
#endif // _SOCKET_MANAGER_H_
/// @file SocketManager.h
/// @brief header file of SocketManager class
/// @author Dohyun Yun
/// @date 2008-10-01
/// @details
/// - Log
///
#ifndef _SOCKET_MANAGER_H_
#define _SOCKET_MANAGER_H_
#include <string>
#include <boost/bind.hpp>
#include <boost/asio.hpp>
#include <boost/shared_ptr.hpp>
#include <boost/enable_shared_from_this.hpp>
//#define DEBUG
class SocketObject : public boost::enable_shared_from_this<SocketObject>
{
public:
SocketObject(boost::asio::io_service& io_service)
: socket_(io_service), data_(NULL)
{
}
~SocketObject()
{
if (data_ != NULL)
{
delete[] data_;
}
}
boost::asio::ip::tcp::socket& socket() { return socket_; };
void run(void func1(std::string, boost::asio::ip::tcp::socket&))
{
#ifdef DEBUG
std::cout << "run() start" << std::endl;
#endif // DEBUG
handlerFromOutside_ = func1;
if (data_ != NULL)
{
delete[] data_;
}
data_ = new char[HEADER_LENGTH];
boost::asio::async_read(socket_,
boost::asio::buffer(data_, HEADER_LENGTH),
boost::bind(&SocketObject::readData, shared_from_this(),
boost::asio::placeholders::error));
}
void readData(const boost::system::error_code& error)
{
#ifdef DEBUG
std::cout << "readData() start" << std::endl;
#endif // DEBUG
if (!error)
{
dataLength_ = *(reinterpret_cast<unsigned int*>(data_));
if (data_ != NULL)
{
delete[] data_;
data_ = NULL;
}
data_ = new char[dataLength_ + 1];
boost::asio::async_read(socket_,
boost::asio::buffer(data_, dataLength_),
boost::bind(&SocketObject::runHandlerFromOutside, shared_from_this(),
boost::asio::placeholders::error));
}
}
void runHandlerFromOutside(const boost::system::error_code& error)
{
#ifdef DEBUG
std::cout << "runHandlerFromOutside() start" << std::endl;
#endif // DEBUG
if (!error)
{
data_[dataLength_] = '\0';
std::string queryXML(data_);
handlerFromOutside_(queryXML, socket_);
}
#ifdef DEBUG
std::cout << "runHandlerFromOutside() OK" << std::endl;
#endif // DEBUG
}
public:
void (*handlerFromOutside_)(std::string, boost::asio::ip::tcp::socket&);
static const size_t HEADER_LENGTH = sizeof(int);
boost::asio::ip::tcp::socket socket_;
private:
int dataLength_;
char* data_;
};
typedef boost::shared_ptr<SocketObject> SocketPointer;
///
/// @brief SocketManager controls socket communications between outside and main process.
/// @details
/// SocketManager gets queryXML from outside and sends the resultXML to the outside.\n
/// It supports:
/// - Async reading from outside.
/// - Async writing to outside.
///
class SocketManager
{
public:
SocketManager(boost::asio::io_service& io_service,
const boost::asio::ip::tcp::endpoint& endpoint,
void func(std::string, boost::asio::ip::tcp::socket&))
: io_service_(io_service),
acceptor_(io_service, endpoint),
handlerFromOutside_(boost::ref(func)) {};
~SocketManager() {};
void accept()
{
#ifdef DEBUG
std::cout << "accept() start" << std::endl;
#endif // DEBUG
SocketPointer newSocketPointerObject(new SocketObject(io_service_));
acceptor_.async_accept(newSocketPointerObject->socket(),
boost::bind(&SocketManager::handler, this, newSocketPointerObject, boost::asio::placeholders::error));
} // end - accept()
void handler(SocketPointer socketPointerObject, const boost::system::error_code& error)
{
#ifdef DEBUG
std::cout << "handler() start" << std::endl;
#endif // DEBUG
if (!error)
{
socketPointerObject->run(handlerFromOutside_);
// Make new socket which gets the next connection request.
SocketPointer newSocketPointerObject(new SocketObject(io_service_));
acceptor_.async_accept(newSocketPointerObject->socket(),
boost::bind(&SocketManager::handler, this, newSocketPointerObject, boost::asio::placeholders::error));
} // end - if
} // end - handler
private:
boost::asio::io_service& io_service_;
boost::asio::ip::tcp::acceptor acceptor_;
public:
void (*handlerFromOutside_)(std::string, boost::asio::ip::tcp::socket&);
}; // end - class
#endif // _SOCKET_MANAGER_H_
'Tools for Dev' 카테고리의 다른 글
GIT - Fast Version Control System (9) | 2008.11.13 |
---|---|
boost::shared_ptr (0) | 2008.10.08 |
boost asio - 수정중 (0) | 2008.10.01 |
boost::enable_shared_from_this (0) | 2008.10.01 |
boost test (0) | 2008.09.12 |
댓글