Reputation: 19
I am using the #include <sys/socket.h>
library socket connection with server and using vector
of type char
for receiving the data from the socket connection which as shown below:
struct sockaddr_in serv_addr;
int sock, valread;
sock = 0;
if ((sock = socket(AF_INET, SOCK_STREAM, 0)) < 0)
{
printf("\n Socket creation error \n");
}
serv_addr.sin_family = AF_INET;
serv_addr.sin_port = htons(PORT);
// Convert IPv4 and IPv6 addresses from text to binary form
if (inet_pton(AF_INET, "0.0.0.0", &serv_addr.sin_addr) <= 0)
{
printf("\nInvalid address/ Address not supported \n");
}
if (connect(sock, (struct sockaddr *)&serv_addr, sizeof(serv_addr)) < 0)
{
printf("\nConnection Failed \n");
}
std::vector<char> buffer = {0};
buffer.reserve(1024);
read(sock, buffer.data(), 1024);
Since the server response size is variable in length but not more than 1024
so that why the size of buffer
fixed to 1024
.
Now since I am receiving variable size response I want to know the size of the buffer
.
I tried following:
std::cout<<sizeof(buffer)<<" "<<buffer.size();
and output is
sizeof(buffer) = 32
buffer.size() = 1
if I try 1024
value that comes up with the some garbage values which is as follow:
for (int i = 0; i < 1024; i++)
{
std::cout<<buffer[i];
}
output:
[{"xmin": 95, "ymin": 147, "ymax": 276, "xmax": 193}, {"xmin": 42, "ymin": 353, "ymax": 488, "xmax": 123}, {"xmin": 85, "ymin": 19, "ymax": 166, "xmax": 145}, {"xmin": 1, "ymin": 254, "ymax": 327, "xmax": 107}, {"xmin": 393, "ymin": 281, "ymax": 419, "xmax": 463}, {"xmin": 379, "ymin": 316, "ymax": 457, "xmax": 442}]������� ��!� )��0� 8��?� G��N� V��]� e��l� t��{� ����� ����� ����� ����� ���Ʈ ή�ծ ݮ��� ����� ����
So is there any way we can get exact size of response?
Upvotes: 0
Views: 1354
Reputation: 155145
Always inspect return-values in C-style APIs!
C-style APIs are directly callable from most other programming languages, including C++. Because portable C doesn't support thrown exceptions C-style library APIs are designed indicate error conditions typically through return-values (e.g. returning NULL
or a negative value) while output data (e.g. byte buffers, struct pointers, etc) is passed through pointers passed as parameters. Because C exposes raw program memory it means that you can easily crash your process (or worse...) if you attempt to use an invalid pointer or if the library you're using indicates it's in an invalid-state or terminal-state (e.g. eof
on file streams).
POSIX's read
function returns the number of bytes actually written into the buffer.
https://man7.org/linux/man-pages/man2/read.2.html
On success, the number of bytes read is returned (zero indicates end of file), and the file position is advanced by this number.
It is not an error if this number is smaller than the number of bytes requested; this may happen for example because fewer bytes are actually available right now (maybe because we were close to end-of-file, or because we are reading from a pipe, or from a terminal), or because
read()
was interrupted by a signal.
Note this part:
this may happen for example because fewer bytes are actually available right now
...which means you need to call read
in a loop until it returns zero.
Like so:
using std::vector<char>; // Consider using `std::Array` instead as it's a fixed-size buffer.
//
const size_t bufferLength = 1024;
vector<char> buffer(/*n:*/ bufferLength);
char* bufferPtr = buffer.data();
size_t totalRead = 0;
while( totalRead < bufferLength )
{
char* bufferPtrOffset = bufferPtr + totalRead;
ssize_t bytesRead = read( /*fd:*/ sock, /*buffer:*/ bufferPtrOffset, /*count:*/ bufferLength - totalRead );
if( bytesRead < 0 )
{
// TODO: Error condition. Throw an exception or something.
}
else if( bytesRead == 0 )
{
break;
}
else
{
totalRead += bytesRead;
}
}
Upvotes: 1
Reputation: 19
As per the @Dai. I should use the return value of the function read
Thanks again.
Upvotes: 0