0

Trying to write a client for a type of server which behaves like an echo server. When I try to send something, it produces a beep sound. I've found that the problem arise at line 356 (on my editor) of win_iocp_socket_service_base.ipp file. The code is:

int result = ::WSASend(impl.socket_, buffers,
        static_cast<DWORD>(buffer_count), &bytes_transferred, flags, op, 0);

Then I made some research.

Continuous boost::asio reads here in the comment of the answer, someone said when a binary data is being written to std::cout.

Why does the following code make my computer beep? here, it seems like the problem is same. They concluded that a '\a' is what produced the sound.

Debugging the application, the buffer of the API function I mentioned earlier, contains the following:

"asd@ıııı2•Z\x1aP"

here "asd@" is my string, the rest changes every time when I debug and I don't know what are they. Now, this is probably the part which the sound is produced, but my question how do I prevent it?

I have the following implementation of a one-round "Correspond" function. Note that I also have a isolated Send() function implementation, which can be paired with ReadUntil() explicitly to achieve same result. Using Send() and ReadUntil() together, the beep sound is still produced. Normally, this shouldn't happen as I am not dealing with low-level API functions, but Boost.Asio. Am I doing something wrong?

CODES

void Correspond(const std::string &data,
                const std::string &delim,
                std::vector<char> &response)
{
    std::shared_ptr<std::vector<char>> localbuffer = std::make_shared<std::vector<char>>(data.begin(), data.end());

    // pass shared_ptr to callback function to prolong the buffer's lifetime
    // !!! perhaps a better buffer management is needed
    socket.async_send(boost::asio::buffer(*localbuffer),
                      std::bind(&TCPClient::on_correspond,
                                this,
                                std::placeholders::_1,
                                std::placeholders::_2,
                                delim,
                                std::ref(response),
                                localbuffer));
}

and following callback implementation

void on_correspond(const boost::system::error_code& errorcode,
                   std::size_t sent,
                   const std::string &delim,
                   std::vector<char> &response,
                   const std::shared_ptr<std::vector<char>> &buffer)
{
    if(errorcode) {
        SLOGERROR(mutex, errorcode.message(), "on_correspond()");
    }

    if(sent == 0) {
        SLOG(mutex, "0 bytes sent w/o errors", "on_correspond()");
    }

    ReadUntil(delim, response);
}

After debugging deep into API, I've found this issue is not related with read function, but I will post it here just to be sure.

void ReadUntil(const std::string &delim, std::vector<char> &response)
{
    boost::asio::async_read_until(socket,
                                  buffer,
                                  delim,
                                  std::bind(&TCPClient::on_readuntil,
                                            this,
                                            std::placeholders::_1,
                                            std::placeholders::_2,
                                            std::ref(response)));
}
void on_readuntil(const boost::system::error_code& errorcode,
                  std::size_t received,
                  std::vector<char> &response)
{
    SLOG(mutex, "on_readuntil invoked", "on_readuntil()");
    SLOG(mutex, received, "on_readuntil");
    // !!! needs error handling, short-read handling and whatnot
    if(errorcode) {
        SLOGERROR(mutex, errorcode.message(), "on_readuntil()");
        return;
    }

    if(received == 0) {
        SLOG(mutex, "0 bytes received w/o errors", "on_readuntil()");
    }

    response.reserve(received);
    std::copy(boost::asio::buffers_begin(buffer.data()),
              boost::asio::buffers_begin(buffer.data()) + received,
              std::back_inserter(response));
    buffer.consume(received);
}
Community
  • 1
  • 1
Cengiz Kandemir
  • 375
  • 1
  • 4
  • 16
  • `here "asd@" is my string, the rest changes every time when I debug` looks like the buffer is read without caring about the size of it, welcome to C++. Might wanna give the boost::asio::buffer a hint about the buffers size. – Blacktempel Jul 27 '16 at 20:44
  • Do you mean I should prepare() the buffer? I was planning to manually manage all commits and consumes but [here](http://stackoverflow.com/questions/28478278/working-with-boostasiostreambuf/28504203?noredirect=1#comment64612843_28504203), someone told me that it is automatically managed if `boost::asio::streambuf` itself is used in asio functions. – Cengiz Kandemir Jul 27 '16 at 21:16
  • Have you tried disabling console output and testing to see if you're still getting the beeps? – Xirema Jul 27 '16 at 21:16
  • @Xirema, Disabling all sorts of console logs/outputs didn't help – Cengiz Kandemir Jul 27 '16 at 21:22
  • @Backtempel, I think I misunderstood what you are trying to say. I thought you are talking about read functions when in fact problem was (probably) about send function. After giving data's size to boost::asio::buffer used in `Send()` and `Correspond()` functions, it stopped beeping (finally). If you write an answer, I shall accept it. I can't believe I missed it :> – Cengiz Kandemir Jul 27 '16 at 21:58
  • @Blacktempel The [`boost::asio::buffer(vector)`](http://www.boost.org/doc/libs/1_61_0/doc/html/boost_asio/reference/buffer/overload23.html) overload being used deduces the size of the buffer. In this case, explicitly providing a size should not be required if one wishes to send the entire buffer. @Cengiz I rarely find a need to explicitly provide size to `boost::asio::buffer()`. If explicitly providing `data.size()` as the size to `boost::asio::buffer()` changes the behavior of the program, then I would be suspicious and investigate further. – Tanner Sansbury Jul 28 '16 at 15:05
  • @Tanner, do you think the problem is on my end? I merely use these async functions. Giving size indeed silenced the beep. Thank you for the tip, I will investigate further. – Cengiz Kandemir Jul 28 '16 at 15:08
  • Given `buffer(*localbuffer)` is the equivalent of `buffer(*localbuffer, localbuffer->size())` and `buffer(*localbuffer, data.size())` ([demo](http://coliru.stacked-crooked.com/a/244301a19d945493)), I would be surprised if that is the fundamental source of the problem. If I was getting a system beep, I would suspect that the ASCII Bell character (0x07) is getting written to the console. In particular, the unicode bullet • (0x2022) that appears in the buffer can be converted into the ASCII Bell character (see [here](https://blogs.msdn.microsoft.com/oldnewthing/20070104-12/?p=28513)). – Tanner Sansbury Jul 28 '16 at 16:37
  • @Tanner, can you read my comment under the answer? It seems like some string contained within the shared_ptr is passed to the WDASend(), which then tries to send it. [this comment](http://stackoverflow.com/questions/38619486/boost-asio-async-send-produces-beep-sound/38626844?noredirect=1#comment64666673_38626844) – Cengiz Kandemir Jul 28 '16 at 19:31
  • @Cengiz I have read the comments and would expect the string contained within the buffer to be passed to `WDASend()`. I still postulate that the ASCII Bell character is being written to a console. – Tanner Sansbury Jul 28 '16 at 20:50
  • @Tanner, I think you are right. It might have been a problem with server writing some problematic character to the console. It could be the case that I've been looking at the wrong side. I made a mistake by chance, and had to recompiled the async echo server example from boost website. This time, I used proper console outputs on the server side, rather than quick jobs. It silenced the problem. If I can isolate it even further, I will write it here. – Cengiz Kandemir Jul 28 '16 at 20:52

1 Answers1

1

here "asd@" is my string, the rest changes every time when I debug

The buffer is read without caring about the size of it, welcome to C++. Give the boost::asio::buffer the buffers size.

Blacktempel
  • 3,935
  • 3
  • 29
  • 53
  • the problem occurred again, unfortunately. After debugging even more, I realized the contents of shared_ptr and the message I am trying to send are the same. Like following `[Raw View] {_Myval2={_Myfirst=0x004828a8 "asd@ııııú¥¿\x2" _Mylast=0x004828ac "ııııú¥¿\x2" _Myend=0x004828ac "ııııú¥¿\x2" } } std::_Compressed_pair >,std::_Vector_val >,1>`. Notice _asd@ııııú¥¿\x2_, this is the exact string that `WSASend()` is trying to send and causing beeps. What do you think the problem is here? – Cengiz Kandemir Jul 28 '16 at 16:19
  • @CengizKandemir Could you post a [MCVE](http://stackoverflow.com/help/mcve) that reproduces your problem ? I'm on phone, I'll take another look at the question later. – Blacktempel Jul 28 '16 at 17:00
  • I can't reproduce the problem properly. The MCVE I tried is not beeping. I also recompiled the echo server example I am using, maybe it was actually the server that was beeping due to some problematic cout on the server side. If I isolate the problem even further, I will write here. – Cengiz Kandemir Jul 28 '16 at 20:36