Re: sending HTTP requests... newbie (continued)



TreatmentPlant wrote:
After many more hours of fiddling to get the right files into the right places, find the missing .dll files, rediscovering that a lot of file are missing from the different versions of the download libraries, rebuilding .lib files etc.... I finally have a "working product" (of sorts)

My next problem...

I can send my data to the server and I get the response back, but the response comes back as a CURLcode datatype. I want to do some more processing on the server repsonse, so am wondering how can I get the response cast(?) as a char array or string? or copied into another datatype variable?

Reading through the curl help files they mumble something about writing the results to a FILE* but I just need to so some text processing, parsing, tokenising etc on the results, I don't want to have to write to a file, then read from the file as I think this double handling unnecessary.

It looks like from the documentation that receiving the data can be
handled by a callback function. That is, you want to define your own
function, then after curl_easy_init() but before curl_easy_perform(),
you want to call curl_easy_setopt() with the CURLOPT_WRITEFUNCTION
constant and the pointer to your callback function. Then when you call
curl_easy_perform(), that will cause your callback function to get run
however many times is necessary to get all the data transferred to you.
You probably also want to call curl_easy_setopt() with the CURLOPT_WRITEDATA
to define the void *stream value that will be passed to your callback.

Basically, libcurl is very flexible and lets you do whatever you want to
with the data, and it does this by providing an interface where it can
call a function and say "here's the next piece of data".

Here's some partial code for an implementation that might write it to
an array and resize that as necessary:

typedef struct CurlBuffer
{
size_t allocated;
size_t used;
char* contents;
} CurlBuffer;

size_t curlReallocWriterCallback(
void *ptr, size_t size, size_t nmemb, void *stream)
{
CurlBuffer *buffer = (CurlBuffer) stream;
size_t bytesIncoming = size * nmemb;

size_t bufferSizeNeeded = buffer->used + bytesIncoming;
if (bufferSizeNeeded > buffer->allocated)
{
void* newContents = realloc(buffer->contents, bufferSizeNeeded);
if (newContents == NULL) { return 0; }

buffer->contents = newContents;
buffer->allocated = bufferSizeNeeded;
}

memmove(buffer->contents + buffer->used, ptr, bytesIncoming);
buffer->used += bytesIncoming;
}

void foo()
{
CURL* handle = curl_easy_init();
CurlBuffer buffer;

buffer.allocated = 0;
buffer.used = 0;
buffer.contents = NULL;

curl_easy_setopt(handle, CURLOPT_WRITEFUNCTION, curlReallocWriterCallback);
curl_easy_setopt(handle, CURLOPT_WRITEDATA, & buffer);

curl_easy_setopt(...... whatever else ......);

CURLcode curlCode = curl_easy_perform_handle();

curl_easy_cleanup(handle);
free(buffer.contents);
}

This code won't be efficient, and the error-handling is omitted, but
hopefully it gets across the general idea. You could also, instead of
buffering everything up front, parse it as it comes across in the stream.
That is, you could make the callback function call your parsing code.

- Logan
.



Relevant Pages

  • gz compression rates with custom buffer callback
    ... what I want to do is a classic output-buffer callback function that gzencodethe buffer. ... There's a native function for that, I know, but I want a little more: compression stats. ... The flag is set, so I can now send the HTTP header to tell the browser we're gonna send some encoded stuff, and then actually encode it. ...
    (comp.lang.php)
  • Re: callback function immediatly called with an empty buffer
    ... > I try to record a wavefile with wavein API. ... > Waveinprepareheader and waveinAddbuffer work fine, with a waveheader ... > buffer large to hold a few seconds audio. ... > Strangely, just after waveinstart, the callback function is executed, ...
    (microsoft.public.win32.programmer.mmedia)
  • IOCTL_DISK_READ
    ... LPBYTE lpOutBuf; ... DeviceIoControl returns true and GetLastError returns 0. ... because my callback function is never called. ...
    (microsoft.public.windowsce.platbuilder)
  • Re: ISampleGrabber
    ... I setup the address to my callback function in SamplGrabber filter.. ... But when it runs I see blank black image (the zero content of the Sample ... I'm not sure how you are determining that the buffer is full of ...
    (microsoft.public.win32.programmer.directx.video)