Hello,

On Tue, Dec 15, 2009 at 7:23 PM, Germán Diago <germandiago@gmail.com> wrote:
Hello. I'm implementing a fully asynchronous server and I would like to know
the order of async operations.

The server receives, first of all, a size, and later the data.

The onSizeRead handler allocates the memory required to store the data
that is coming after
the async_read.
So I would like to know if this buffer will be available when
onDataRead is called.

You have to guarantee that by allocating the buffer on the heap, by using a object that it is not on the local scope of your async call, or by using other methods. The important thing is to ensure the buffer will be alive between the call to the async operation and the call to the async operation handler.
 

so I get the size and data with two async_read operations.

I would like to know if the relative order of the async calls is
respected, since I'm
reading from the same socket for both operations and I need the
resources dictated by the first read
before using the second one.

The relative order of the async calls is respected if you actively ensure that. If you request a size_read and data_read, both async, one after another without waiting for the first to complete, then there is no guarantee that they will be performed in the right order... to do that one could write something like this:

/*  Reads the size of the incoming data */
void TCP_connection::read_header()
{
    unsigned char* header = new unsigned char[header_size];    //header_size is a const defined by your application, you could use for example sizeof(unsigned short)

    boost::asio::async_read(socket, boost::asio::buffer(header, header_size),
                            boost::bind(&TCP_connection::OnSizeRead, this,
                            boost::asio::placeholders::error,
                            header, boost::asio::placeholders::bytes_transferred));
}
/* Starts the data receive  */
void TCP_connection::onSizeRead(const boost::system::error_code& error, const unsigned char* header, std::size_t bytes)
{
    if(!error)
    {
        unsigned short message_length;
        memcpy(&message_lenght, header, sizeof(header_size));

        if(message_lenght > 0)
        {
unsigned char* data = new unsigned char[message_length];
boost::asio::async_read(socket, boost::asio::buffer(data, message_length),
                     boost::bind(&TCP_connection::onDataRead, this,
                     boost::asio::placeholders::error,
                     data, boost::asio::placeholders::bytes_transferred));
        }
    }
    delete[ ] header;
}

This ensures that the size of the data is always read first. Also, note that in this example i use buffer allocation with the operator new(). You might want to use buffers already allocated and then instead of deleting them, just set them free to reuse. The only requirement is that you have enough space to accomodate the data and that the buffer will outlive the call to the async operation.

Hope it helps,
 
_______________________________________________
Boost-users mailing list
Boost-users@lists.boost.org
http://lists.boost.org/mailman/listinfo.cgi/boost-users


--
Matheus Araújo Aguiar
Computer Scientist
matheus.pit@gmail.com