Buffered Stream Sockets
The buffered_socket is a convenience which extends the functionality of the basic socket interface. The buffered socket object can be created with any connected socket. It supports send and recv, but the object may read more bytes than the user requests, and save them to return on the next receive. This can increase efficiency of applications which want to do small reads, and allows an efficient recvln method which is useful for line-oriented protocols. Include cleanbuf.h to use this facility.
buffered_socket b(socket &s [, int size ]);
buffered_socket b;    b(socket &s [, int size ]);

This constructs a buffered_socket object, b. The size is the amount of local storage allocated, and defaults to 1024 bytes. The constructor assumes that s supports the send and recv operations, and later operations will fail if this is not true.

Note: the object b retains a reference to s, which should not be closed or destroyed (probably not touched at all) while b is in use.

Note that the object can be declared first, then given its construction parameters later. This behavior was added to simplify the use of try/catch where the catch may need the object in remain in scope.

int i = recv(buffered_socket &b, const void *buf, int size [, int flags ] );
This has the same client semantics as the regular socket recv. The only difference is that it may actually request and receive more than size bytes from the underlying socket, s in the constructor. These bytes will be returned on successive reads, retaining the their order. The recv call may perform no operation on s if it already has enough buffered bytes.
int i = recvln(buffered_socket &b, const void *buf, int size [, char term ] [, int flags ] );
The recvln method behaves like recv, except that it stops reading at the first occurrence of the terminator character term, which is newline by default. It will continue to try to get data until buf is full, or until term is found. This is very useful for protocols which use line breaks, such as HTTP, FTP, and the email protocols. If found, term will be the last item in buf. If term is not sent, recvln is equivalent to recv.
int i = send(buffered_socket &b, const void *buf, int size [, int flags ] );
int i = send(buffered_socket &b, const string &data [, int flags ] );
This just calls send on the socket object s specified at b's construction. A future version of the library may attempt to buffer sending, but this one does not.

The flags arguments are the same as for plain sockets. The implementation tries to handle the cleansocks-approved flags correctly, though the MSG_WAITALL flag is meaningless for recvln.

If you send a native sockets flag, it will be simply forwarded to the underlying socket operations. There is no guarantee that this will produce the desired overall behavior.

Unlike a basic socket object, a buffered_socket may not be assigned or copied.