Making a packet in boost asio

I need to make this simple chat program:
http://www.boost.org/doc/libs/1_55_0/doc/html/boost_asio/example/cpp11/chat/

To send a generic packet instead of a single message:
1
2
3
4
5
struct packet
{
  std::string username;
  std::string message;
};

-I'm lost because their example is blank of comments.

-All I know is that there is serialization example that uses packets, but its not compatible and I think serialization is not necessary at the moment.

It would make my day if you could compile and explain how you did it c:
Provide for implicit conversions between packet and chat_message.
And then use the same program(s).

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
#ifndef CHAT_MESSAGE_HPP
#define CHAT_MESSAGE_HPP

#include <cstdio>
#include <cstdlib>
#include <cstring>

/////////////  added //////////////////
#include <string>
#include <algorithm>

struct packet
{
  std::string username;
  std::string message;
};
////////////////////////////////////////

class chat_message
{
public:
  enum { header_length = 4 };
  enum { max_body_length = 512 }; // increase if required

  // ...

  /////////////  added //////////////////
  // use a colon to seperate user name and message
  static constexpr char seperator = ':' ;

  // note: non-exlicit constructor; can imlicitly convert packet to chat_message
  chat_message( const packet& pkt )
  {
      const std::string body = pkt.username + seperator + pkt.message ;

      // fill up to to max length
      body_length_ = std::min( body.size(), std::size_t( max_body_length ) ) ;
      std::copy( body.begin(), body.begin() + body_length_, data_ ) ;
  }

  // note: non-exlicit conversion operator;
  // can imlicitly convert chat_message to packet

  operator packet () const
  {
      const auto end = data_ + body_length_ ;
      const auto sep = std::find( data_, end, seperator ) ; // locate seperator
      if( sep == end ) { /* error, bad packet */ } ;
      return { std::string( data_, sep ), std::string( sep+1, end )  } ;
  }

  ////////////////////////////////////////

   // ...

private:
  char data_[header_length + max_body_length];
  std::size_t body_length_;
};

#endif // CHAT_MESSAGE_HPP 


And in chat_client.cpp:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
void chat_client::*do_read_body()
  {
    boost::asio::async_read(socket_,
        boost::asio::buffer(read_msg_.body(), read_msg_.body_length()),
        [this](boost::system::error_code ec, std::size_t /*length*/)
        {
          if (!ec)
          {

            // std::cout.write(read_msg_.body(), read_msg_.body_length());
            const packet pkt = read_msg_ ; // implicit conversion from chat_message => packet
            std::cout << "message from " << pkt.username << ": " << pkt.message << '\n' ;
            //std::cout << "\n";

            do_read_header();
          }
          else
          {
            socket_.close();
          }
        });
  }


And

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
/*
char line[chat_message::max_body_length + 1];
while (std::cin.getline(line, chat_message::max_body_length + 1))
{
  chat_message msg;
  msg.body_length(std::strlen(line));
  std::memcpy(msg.body(), line, msg.body_length());
  msg.encode_header();
  c.write(msg);
}
*/

packet pkt ;
while( std::cout << "user name? " && std::getline( std::cin, pkt.username ) &&
       std::cout << "message? " && std::getline( std::cin, pkt.message ) )
{
    c.write(pkt) ; // implicit conversion from packet => chat_message
}
Thanks!
Topic archived. No new replies allowed.