Sender.h
#pragma once
#include <ace/Asynch_IO.h>
#include <ace/SOCK_Dgram.h>
#include <ace/INET_Addr.h>
#include <ace/Proactor.h>
class Sender:public ACE_Handler
{
public:
Sender(ACE_Proactor* actor, const char* ipstr);
~Sender(void);
int send( const char* data);
private:
virtual void handle_write_dgram (const ACE_Asynch_Write_Dgram::Result &result);
private:
ACE_Asynch_Write_Dgram write_require_;
ACE_SOCK_Dgram socket_;
ACE_INET_Addr addr_;
};
Sender.cpp
#include "Sender.h"
#include <ace/Message_Block.h>
#include <iostream>
Sender::Sender(ACE_Proactor* actor, const char* ipstr)
:ACE_Handler(actor),addr_(ipstr)
{
this->socket_.open( ACE_Addr::sap_any);
this->write_require_.open(*this, this->socket_.get_handle(),0, this->proactor());
}
Sender::~Sender(void)
{
this->write_require_.cancel();
this->socket_.close();
}
int
Sender::send( const char* data){
size_t len =ACE_OS::strlen( data ) +1;
ACE_Message_Block* m;
ACE_NEW_RETURN(m, ACE_Message_Block(len), -1);
m->copy( data );
size_t sendsize(0);
int ret = this->write_require_.send( m, sendsize,0, this->addr_);
if( 0!=ret && 1!=ret){
m->release();
}
return ret;
}
void
Sender::handle_write_dgram (const ACE_Asynch_Write_Dgram::Result &result){
result.message_block()->release();
if(!result.success()){
std::cout<<std::endl<<"Sender fail:"<<result.error();
return;
}
}
Receiver.h
#pragma once
#include <ace/Asynch_IO.h>
#include <ace/SOCK_Dgram.h>
#include <ace/INET_Addr.h>
#include <ace/Message_Block.h>
#include <ace/Proactor.h>
class Receiver:public ACE_Handler
{
public:
Receiver(ACE_Proactor* actor, const char* ipstr);
~Receiver(void);
private:
virtual void handle_read_dgram (const ACE_Asynch_Read_Dgram::Result &result);
private:
ACE_Asynch_Read_Dgram read_require_;
ACE_SOCK_Dgram socket_;
ACE_INET_Addr addr_;
ACE_Message_Block read_msg_;
private:
int recv_();
};
Receiver.cpp
#include "Receiver.h"
#include <iostream>
Receiver::Receiver(ACE_Proactor* actor, const char* ipstr)
:ACE_Handler(actor), addr_(ipstr), read_msg_(4096)
{
this->socket_.open( addr_ );
this->read_require_.open(*this, this->socket_.get_handle(),0, this->proactor());
this->recv_();
}
Receiver::~Receiver(void)
{
this->read_require_.cancel();
this->socket_.close();
}
void
Receiver::handle_read_dgram (const ACE_Asynch_Read_Dgram::Result &result){
if(!result.success()){
this->recv_();
std::cout<<std::endl<<"Receiver fail:"<<result.error();
return;
}
std::cout<<std::endl<<"Receiver Data:"<<(const char*)( result.message_block()->rd_ptr())<<std::endl;
this->recv_();
}
int
Receiver::recv_(){
this->read_msg_.reset();
size_t sendsize(0);
return this->read_require_.recv(&this->read_msg_,sendsize,0, PF_INET);
}
Test_UDP_Proactor.cpp
// Test_UDP_Proactor.cpp : Defines the entry point for the console application.
//
#include "stdafx.h"
#include <ace/ACE.h>
#include "Receiver.h"
#include "Sender.h"
#include <iostream>
#include <string>
#include <ace/Thread_Manager.h>
#include <ace/OS.h>
ACE_THR_FUNC_RETURN fn(void * arg){
Sender* se = (Sender*) arg;
std::string cmd;
while(true){
std::cout<<std::endl<<"UDP로 전송할 데이터를 입력하세요. 종료시 exit를 입력하세요."<<std::endl;
std::getline( std::cin, cmd);
if( "exit"==cmd){
break;
}
se->send( cmd.c_str());
ACE_OS::sleep(1);
}
ACE_Proactor::instance()->proactor_end_event_loop();
return 0;
}
int _tmain(int argc, _TCHAR* argv[])
{
ACE::init();
{
Receiver re(ACE_Proactor::instance(), "192.168.0.2:1000");
Sender se(ACE_Proactor::instance(), "192.168.0.2:1000");
ACE_Thread_Manager tm;
tm.spawn(fn, &se);
ACE_Proactor::instance()->proactor_run_event_loop();
tm.wait();
}
ACE::fini();
return 0;
}