LinuxQuestions.org
Share your knowledge at the LQ Wiki.
Home Forums Tutorials Articles Register
Go Back   LinuxQuestions.org > Forums > Non-*NIX Forums > Programming
User Name
Password
Programming This forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.

Notices


Reply
  Search this Thread
Old 05-25-2011, 01:59 PM   #1
Arighna
LQ Newbie
 
Registered: May 2011
Posts: 16

Rep: Reputation: Disabled
Non-existent file is also downloaded by curl !!!


Hello All,

I am trying to download a non-existent file from a repository by giving the URL, using curl APIs. It is throwing an error message "The requested URL returned error: 404" but the specified file is downloaded with 0 bytes. My code snippet is as follows :


#include <curl/curl.h>
#include <stdio.h>
#include <math.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <stdlib.h>

static char errorBuffer[CURL_ERROR_SIZE];
size_t D_Write(void *ptr,size_t size, size_t nmemb, FILE *stream)
{
size_t ret;
ret = fwrite(ptr, size, nmemb*size, stream);
return ret;
}
int Download(const char *f_name, const char *p_url)
{
CURLcode ret;
CURL *hnd = curl_easy_init();
FILE *f_ptr = fopen(f_name, "wb");
curl_easy_setopt(hnd, CURLOPT_WRITEDATA,f_ptr);
curl_easy_setopt(hnd, CURLOPT_WRITEFUNCTION,D_Write );
curl_easy_setopt(hnd, CURLOPT_INFILESIZE_LARGE, (curl_off_t)-1);
curl_easy_setopt(hnd, CURLOPT_URL, p_url);
curl_easy_setopt(hnd, CURLOPT_PROXY, NULL);
curl_easy_setopt(hnd, CURLOPT_NOPROGRESS, 0);
curl_easy_setopt(hnd, CURLOPT_HEADER, 0);
curl_easy_setopt(hnd, CURLOPT_FAILONERROR, 1);
curl_easy_setopt(hnd, CURLOPT_UPLOAD, 0);
curl_easy_setopt(hnd, CURLOPT_DIRLISTONLY, 0);
curl_easy_setopt(hnd, CURLOPT_APPEND, 0);
curl_easy_setopt(hnd, CURLOPT_NETRC, 0);
curl_easy_setopt(hnd, CURLOPT_FOLLOWLOCATION, 0);
curl_easy_setopt(hnd, CURLOPT_UNRESTRICTED_AUTH, 0);
curl_easy_setopt(hnd, CURLOPT_TRANSFERTEXT, 0);
curl_easy_setopt(hnd, CURLOPT_USERPWD, NULL);
curl_easy_setopt(hnd, CURLOPT_PROXYUSERPWD, NULL);
curl_easy_setopt(hnd, CURLOPT_NOPROXY, NULL);
curl_easy_setopt(hnd, CURLOPT_RANGE, NULL);
curl_easy_setopt(hnd, CURLOPT_ERRORBUFFER, errorBuffer);
curl_easy_setopt(hnd, CURLOPT_TIMEOUT, 0);
curl_easy_setopt(hnd, CURLOPT_REFERER, NULL);
curl_easy_setopt(hnd, CURLOPT_AUTOREFERER, 0);
curl_easy_setopt(hnd, CURLOPT_USERAGENT, "curl/7.19.7 (i486-pc-linux-gnu) libcurl/7.19.7 OpenSSL/0.9.8k zlib/1.2.3.3 libidn/1.15");
curl_easy_setopt(hnd, CURLOPT_FTPPORT, NULL);
curl_easy_setopt(hnd, CURLOPT_LOW_SPEED_LIMIT, 0);
curl_easy_setopt(hnd, CURLOPT_LOW_SPEED_TIME, 0);
curl_easy_setopt(hnd, CURLOPT_MAX_SEND_SPEED_LARGE, (curl_off_t)0);
curl_easy_setopt(hnd, CURLOPT_MAX_RECV_SPEED_LARGE, (curl_off_t)0);
curl_easy_setopt(hnd, CURLOPT_RESUME_FROM_LARGE, (curl_off_t)0);
curl_easy_setopt(hnd, CURLOPT_COOKIE, NULL);
curl_easy_setopt(hnd, CURLOPT_HTTPHEADER, NULL);
curl_easy_setopt(hnd, CURLOPT_SSLCERT, NULL);
curl_easy_setopt(hnd, CURLOPT_SSLCERTTYPE, NULL);
curl_easy_setopt(hnd, CURLOPT_SSLKEY, NULL);
curl_easy_setopt(hnd, CURLOPT_SSLKEYTYPE, NULL);
curl_easy_setopt(hnd, CURLOPT_KEYPASSWD, NULL);
curl_easy_setopt(hnd, CURLOPT_SSH_PRIVATE_KEYFILE, NULL);
curl_easy_setopt(hnd, CURLOPT_SSH_PUBLIC_KEYFILE, NULL);
curl_easy_setopt(hnd, CURLOPT_SSH_HOST_PUBLIC_KEY_MD5, NULL);
curl_easy_setopt(hnd, CURLOPT_SSL_VERIFYHOST, 2);
curl_easy_setopt(hnd, CURLOPT_MAXREDIRS, 50);
curl_easy_setopt(hnd, CURLOPT_CRLF, 0);
curl_easy_setopt(hnd, CURLOPT_QUOTE, NULL);
curl_easy_setopt(hnd, CURLOPT_POSTQUOTE, NULL);
curl_easy_setopt(hnd, CURLOPT_PREQUOTE, NULL);
curl_easy_setopt(hnd, CURLOPT_WRITEHEADER, NULL);
curl_easy_setopt(hnd, CURLOPT_COOKIEFILE, NULL);
curl_easy_setopt(hnd, CURLOPT_COOKIESESSION, 0);
curl_easy_setopt(hnd, CURLOPT_SSLVERSION, 0);
curl_easy_setopt(hnd, CURLOPT_TIMECONDITION, 0);
curl_easy_setopt(hnd, CURLOPT_TIMEVALUE, 0);
curl_easy_setopt(hnd, CURLOPT_CUSTOMREQUEST, NULL);
//curl_easy_setopt(hnd, CURLOPT_STDERR, errorBuffer);
curl_easy_setopt(hnd, CURLOPT_HTTPPROXYTUNNEL, 0);
/*curl_easy_setopt(hnd, CURLOPT_INTERFACE, NULL);
curl_easy_setopt(hnd, CURLOPT_KRBLEVEL, NULL);
curl_easy_setopt(hnd, CURLOPT_TELNETOPTIONS, NULL);
curl_easy_setopt(hnd, CURLOPT_RANDOM_FILE, NULL);
curl_easy_setopt(hnd, CURLOPT_EGDSOCKET, NULL);*/
curl_easy_setopt(hnd, CURLOPT_CONNECTTIMEOUT, 3);
/* curl_easy_setopt(hnd, CURLOPT_DEBUGFUNCTION, 0x804db80); [REMARK] */
/* curl_easy_setopt(hnd, CURLOPT_DEBUGDATA, 0xbf81fb44); [REMARK] */
curl_easy_setopt(hnd, CURLOPT_VERBOSE, 1);
curl_easy_setopt(hnd, CURLOPT_ENCODING, NULL);
/*curl_easy_setopt(hnd, CURLOPT_FTP_CREATE_MISSING_DIRS, 0);
curl_easy_setopt(hnd, CURLOPT_IPRESOLVE, 0);
curl_easy_setopt(hnd, CURLOPT_FTP_ACCOUNT, NULL);
curl_easy_setopt(hnd, CURLOPT_IGNORE_CONTENT_LENGTH, 0);
curl_easy_setopt(hnd, CURLOPT_FTP_SKIP_PASV_IP, 0);
curl_easy_setopt(hnd, CURLOPT_FTP_FILEMETHOD, 0);
curl_easy_setopt(hnd, CURLOPT_FTP_ALTERNATIVE_TO_USER, NULL);*/
curl_easy_setopt(hnd, CURLOPT_SSL_SESSIONID_CACHE, 1);
/* curl_easy_setopt(hnd, CURLOPT_SOCKOPTFUNCTION, 0x804da50); [REMARK] */
/* curl_easy_setopt(hnd, CURLOPT_SOCKOPTDATA, 0xbf81fb44); [REMARK] */
curl_easy_setopt(hnd, CURLOPT_POSTREDIR, 0);

ret = curl_easy_perform(hnd);

curl_easy_cleanup(hnd);
fclose(f_ptr);
if (ret == CURLE_OK)
{
exit(0);
}
else
{
printf( "Error: %d - %s \n",ret, errorBuffer);
exit(-1);
}
return (int)ret;
}


int main()
{
Download( "file name", "specified url" ) ;
return 0;
}

This is giving output as

% Total % Received % Xferd Average Speed Time Time Time Current
Dload Upload Total Spent Left Speed
0 0 0 0 0 0 0 0 --:--:-- --:--:-- --:--:-- 0* The requested URL returned error: 404
0 0 0 0 0 0 0 0 --:--:-- --:--:-- --:--:-- 0* Closing connection #0

Error: 22 - The requested URL returned error: 404

And its creating a file of 0 bytes with the specified file name. This should not happen. File should not be created. How to do it?

Some1 plz help. Thanks in advance.
 
Old 05-26-2011, 08:27 PM   #2
ntubski
Senior Member
 
Registered: Nov 2005
Distribution: Debian, Arch
Posts: 3,780

Rep: Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081
Please put your code inside code tags, like this:
Code:
[CODE]your code here[/CODE]
Curl isn't creating the file, it's getting created at the call to fopen.
 
Old 05-28-2011, 12:24 AM   #3
Arighna
LQ Newbie
 
Registered: May 2011
Posts: 16

Original Poster
Rep: Reputation: Disabled
Hi ntubski,

Then plz tell me how can i put a restriction in creating the file, when curl will return the error message.
 
Old 05-28-2011, 07:06 AM   #4
ntubski
Senior Member
 
Registered: Nov 2005
Distribution: Debian, Arch
Posts: 3,780

Rep: Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081
I'm not sure what you mean by "put a restriction", but if you don't want an empty file to be created, just don't fopen the file until you get the first chunk of bytes.
 
1 members found this post helpful.
Old 06-01-2011, 05:48 AM   #5
Arighna
LQ Newbie
 
Registered: May 2011
Posts: 16

Original Poster
Rep: Reputation: Disabled
please tell me where to put fopen in my code.
 
Old 06-01-2011, 06:09 AM   #6
dwhitney67
Senior Member
 
Registered: Jun 2006
Location: Maryland
Distribution: Kubuntu, Fedora, RHEL
Posts: 1,541

Rep: Reputation: 335Reputation: 335Reputation: 335Reputation: 335
Quote:
Originally Posted by Arighna View Post
please tell me where to put fopen in my code.
The file is being created because of the fopen(). The position of the call to fopen() that you have placed in your code is fine; but what you are neglecting to do at the moment is to fully handle the error from libcurl.

Do something like this:
Code:
...

ret = curl_easy_perform(hnd);

curl_easy_cleanup(hnd);

fclose(f_ptr);

if (ret != CURLE_OK)
{
   printf("Error: %d - %s \n", ret, errorBuffer);

   unlink(f_name);   /* remove file */
}

return ret;
 
Old 06-01-2011, 01:19 PM   #7
ntubski
Senior Member
 
Registered: Nov 2005
Distribution: Debian, Arch
Posts: 3,780

Rep: Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081
I was thinking more along the lines of:

Messed that up, see post #9 instead.

Last edited by ntubski; 06-01-2011 at 02:25 PM. Reason: messed up code
 
Old 06-01-2011, 02:09 PM   #8
dwhitney67
Senior Member
 
Registered: Jun 2006
Location: Maryland
Distribution: Kubuntu, Fedora, RHEL
Posts: 1,541

Rep: Reputation: 335Reputation: 335Reputation: 335Reputation: 335
Quote:
Originally Posted by ntubski View Post
I was thinking more along the lines of:
Huh?

Please look at the code you posted; while at it, peruse the man-page for fwrite().
 
Old 06-01-2011, 02:24 PM   #9
ntubski
Senior Member
 
Registered: Nov 2005
Distribution: Debian, Arch
Posts: 3,780

Rep: Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081Reputation: 2081
Quote:
Originally Posted by dwhitney67 View Post
Huh?
I got my parameters backwards.
Code:
typedef struct {
    const char *name;
    FILE *stream;
} FileInfo;

size_t D_Write(char *ptr, size_t size, size_t nmemb, FileInfo *finfo)
{
    size_t ret;
    if (!finfo->stream) {
        finfo->stream = fopen(finfo->name, "wb");
    }
    ret = fwrite(ptr, size, nmemb, finfo->stream);
    return ret;
}
int Download(const char *f_name, const char *p_url)
{
    CURLcode ret;
    CURL *hnd = curl_easy_init();
    FileInfo finfo = { f_name, NULL };
    curl_easy_setopt(hnd, CURLOPT_WRITEDATA, &finfo);
    curl_easy_setopt(hnd, CURLOPT_WRITEFUNCTION, D_Write );
    ...
}
 
Old 06-02-2011, 01:06 AM   #10
Arighna
LQ Newbie
 
Registered: May 2011
Posts: 16

Original Poster
Rep: Reputation: Disabled
thnx dwhitney, unlink worked for me.
 
  


Reply

Tags
[c]



Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off



Similar Threads
Thread Thread Starter Forum Replies Last Post
[SOLVED] curl -K command outputs weird symbols instead of downloading URL from file meridionaljet Linux - Newbie 7 05-16-2011 08:13 PM
Download images from text file using curl Sam71 Programming 4 04-19-2011 04:59 AM
File download says done and stops before file is completely downloaded in Firefox royeo Linux - General 2 12-24-2006 10:02 PM
Cannot get file w/ curl and cannot dig localhost thetawaverider Linux - Networking 1 04-26-2006 07:01 PM
File "sys_errlist.h" non-existent in FC4 JRR883 Linux - Software 6 12-20-2005 08:11 PM

LinuxQuestions.org > Forums > Non-*NIX Forums > Programming

All times are GMT -5. The time now is 09:05 AM.

Main Menu
Advertisement
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
Open Source Consulting | Domain Registration