Comme vu at the libcurl documentation for curl_easy_setopt()
, la fonction de rappel est appelée autant de fois que nécessaire pour fournir tous les octets de la page récupérée. Votre fonction écrase le même tampon à chaque appel, avec le résultat qu'après curl_easy_perform()
a fini d'aller chercher le fichier, vous avez seulement quelque chose qui soit dans l'appel final à tobuffer()
gauche.
En résumé, votre fonction tobuffer()
doit faire autre chose que remplacer le même tampon à chaque appel.
mise à jour
Par exemple, vous pouvez faire quelque chose comme le code suivant complètement non testé:
struct buf {
char *buffer;
size_t bufferlen;
size_t writepos;
} buffer = {0};
size_t tobuffer(char *ptr, size_t size, size_t nmemb, void *stream)
{
size_t nbytes = size*nmemb;
if (!buffer.buffer) {
buffer.buffer = malloc(1024);
buffer.bufferlen = 1024;
buffer.writepos = 0;
}
if (buffer.writepos + nbytes < buffer.bufferlen) {
buffer.bufferlen = 2 * buffer.bufferlen;
buffer.buffer = realloc(buffer, buffer.bufferlen);
}
assert(buffer.buffer != NULL);
memcpy(buffer.buffer+buffer.writepos,ptr,nbytes);
return nbytes;
}
À un certain moment plus tard dans votre programme, vous devrez libérer la mémoire allouée quelque chose comme ça :
void freebuffer(struct buf *b) {
free(b->buffer);
b->buffer = NULL;
b->bufferlen = 0;
b->writepos = 0;
}
, notez aussi que je l'ai utilisé memcpy()
au lieu de strncpy()
pour déplacer les données vers le tampon. Ceci est important car libcurl ne prétend pas que les données passées à la fonction de rappel sont en réalité une chaîne ASCII terminée par NUL. En particulier, si vous récupérez un fichier image .gif, il peut certainement contenir (et contiendra) zéro octet dans le fichier que vous souhaitez conserver dans votre tampon. strncpy()
va arrêter la copie après la première NUL qu'il voit dans les données source.
Comme un exercice pour le lecteur, j'ai laissé toute la gestion des erreurs de ce code. Vous devez en mettre.En outre, j'ai également laissé dans une fuite de mémoire juteuse au hasard que l'appel à realloc()
échoue.
Une autre amélioration consisterait à utiliser l'option permettant à la valeur du paramètre stream
d'être rappelé par l'appelant libcurl. Cela pourrait être utilisé pour allouer gérer votre tampon sans utiliser de variables globales. Je recommande fortement de le faire aussi.
pouvez-vous me dire alors comment puis-je faire pour stocker le contenu entier dans un tableau de caractères global – raj
J'ai ajouté un exemple de code.Ce n'est pas testé.Mais il devrait être un point de départ. – RBerteig