diff -ur curl-7.10.8.orig/docs/examples/ftpupload.c curl-7.10.8.large_ftp/docs/examples/ftpupload.c
--- curl-7.10.8.orig/docs/examples/ftpupload.c	Mon Mar 17 04:38:08 2003
+++ curl-7.10.8.large_ftp/docs/examples/ftpupload.c	Wed Dec 10 10:43:03 2003
@@ -73,7 +73,7 @@
     curl_easy_setopt(curl, CURLOPT_INFILE, hd_src);
 
     /* and give the size of the upload (optional) */
-    curl_easy_setopt(curl, CURLOPT_INFILESIZE, file_info.st_size);
+    curl_easy_setopt(curl, CURLOPT_INFILESIZE_BIG, file_info.st_size);
 
     /* Now run off and do what you've been told! */
     res = curl_easy_perform(curl);
diff -ur curl-7.10.8.orig/docs/examples/httpput.c curl-7.10.8.large_ftp/docs/examples/httpput.c
--- curl-7.10.8.orig/docs/examples/httpput.c	Tue Sep  3 04:43:32 2002
+++ curl-7.10.8.large_ftp/docs/examples/httpput.c	Wed Dec 10 10:43:18 2003
@@ -85,7 +85,7 @@
     curl_easy_setopt(curl, CURLOPT_INFILE, hd_src);
 
     /* and give the size of the upload (optional) */
-    curl_easy_setopt(curl, CURLOPT_INFILESIZE, file_info.st_size);
+    curl_easy_setopt(curl, CURLOPT_INFILESIZE_BIG, file_info.st_size);
 
     /* Now run off and do what you've been told! */
     res = curl_easy_perform(curl);
diff -ur curl-7.10.8.orig/docs/libcurl/curl_easy_setopt.3 curl-7.10.8.large_ftp/docs/libcurl/curl_easy_setopt.3
--- curl-7.10.8.orig/docs/libcurl/curl_easy_setopt.3	Sat Oct 18 04:54:19 2003
+++ curl-7.10.8.large_ftp/docs/libcurl/curl_easy_setopt.3	Thu Dec 11 11:53:43 2003
@@ -128,9 +128,18 @@
 Also note that \fICURLOPT_NOPROGRESS\fP must be set to FALSE to make this
 function actually get called.
 .TP
+.B CURLOPT_PROGRESSFUNCTION_BIG
+Function pointer that should match the \fIcurl_progress_callback_big\fP
+prototype found in \fI<curl/curl.h>\fP. This function gets called by libcurl
+instead of its internal equivalent with a frequent interval during data
+transfer.  Aside from the data types of its arguments, this callback works
+identically to the one registered by \fICURLOPT_PROGRESSFUNCTION\fP above;
+see its documentation for more details.
+.TP
 .B CURLOPT_PROGRESSDATA
 Pass a pointer that will be untouched by libcurl and passed as the first
-argument in the progress callback set with \fICURLOPT_PROGRESSFUNCTION\fP.
+argument in the progress callback set with \fICURLOPT_PROGRESSFUNCTION\fP
+or \fICURLOPT_PROGRESSFUNCTION_BIG\fP.
 .TP
 .B CURLOPT_HEADERFUNCTION
 Function pointer that should match the following prototype: \fIsize_t
@@ -425,7 +434,7 @@
 .TP
 .B CURLOPT_PUT
 A non-zero parameter tells the library to use HTTP PUT to transfer data. The
-data should be set with CURLOPT_READDATA and CURLOPT_INFILESIZE.
+data should be set with CURLOPT_READDATA and CURLOPT_INFILESIZE_BIG.
 .TP
 .B CURLOPT_POST
 A non-zero parameter tells the library to do a regular HTTP post. This is a
@@ -682,7 +691,11 @@
 techniques).
 .TP
 .B CURLOPT_RESUME_FROM
-Pass a long as parameter. It contains the offset in number of bytes that you
+Pass a long as a parameter. It contains the offset in number of bytes that you
+want the transfer to start from.
+.TP
+.B CURLOPT_RESUME_FROM_BIG
+Pass an off_t as a parameter. It contains the offset in number of bytes that you
 want the transfer to start from.
 .TP
 .B CURLOPT_CUSTOMREQUEST
@@ -714,14 +727,29 @@
 .TP
 .B CURLOPT_INFILESIZE
 When uploading a file to a remote site, this option should be used to tell
-libcurl what the expected size of the infile is.
+libcurl what the expected size of the infile is.  This value should be
+passed as a long.
+.TP
+.B CURLOPT_INFILESIZE_BIG
+When uploading a file to a remote site, this option should be used to tell
+libcurl what the expected size of the infile is.  This value should be
+passed as an off_t.
 .TP
 .B CURLOPT_UPLOAD
 A non-zero parameter tells the library to prepare for an upload. The
-CURLOPT_READDATA and CURLOPT_INFILESIZE are also interesting for uploads.
+CURLOPT_READDATA and CURLOPT_INFILESIZE_BIG are also interesting for uploads.
 .TP
 .B CURLOPT_MAXFILESIZE
-Pass a long as parameter. This allows you to specify the maximum size (in
+Pass a long as a parameter. This allows you to specify the maximum size (in
+bytes) of a file to download. If the file requested is larger than this value,
+the transfer will not start and CURLE_FILESIZE_EXCEEDED will be returned.
+
+NOTE: The file size is not always known prior to download, and for such files
+this option has no effect even if the file transfer ends up being larger than
+this given limit. This concerns both FTP and HTTP transfers.
+.TP
+.B CURLOPT_MAXFILESIZE_BIG
+Pass an off_t as a parameter. This allows you to specify the maximum size (in
 bytes) of a file to download. If the file requested is larger than this value,
 the transfer will not start and CURLE_FILESIZE_EXCEEDED will be returned.
 
diff -ur curl-7.10.8.orig/docs/libcurl/curl_easy_setopt.html curl-7.10.8.large_ftp/docs/libcurl/curl_easy_setopt.html
--- curl-7.10.8.orig/docs/libcurl/curl_easy_setopt.html	Sat Oct 18 05:01:53 2003
+++ curl-7.10.8.large_ftp/docs/libcurl/curl_easy_setopt.html	Thu Dec 11 11:56:42 2003
@@ -158,10 +158,21 @@
            Also note that <I>CURLOPT</I><B>_</B><I>NOPROGRESS</I> must be set to FALSE
            to make this function actually get called.
 
+       <B>CURLOPT_PROGRESSFUNCTION_BIG</B>
+           Function    pointer    that    should    match     the
+           <I>curl</I><B>_</B><I>progress</I><B>_</B><I>callback</I><B>_</B><I>big</I>      prototype     found     in
+           <I>&lt;curl/curl.h&gt;</I>. This function gets  called  by  libcurl
+           instead  of  its  internal  equivalent with a frequent
+           interval during data transfer.  Aside from the data types
+	   of its arguments, it operates identically to the callback
+	   set by <I>CURLOPT</I><B>_</B><I>PROGRESSFUNCTION</I> above;
+	   see its documentation for details.
+
        <B>CURLOPT_PROGRESSDATA</B>
            Pass a pointer that will be untouched by  libcurl  and
            passed  as the first argument in the progress callback
-           set with <I>CURLOPT</I><B>_</B><I>PROGRESSFUNCTION</I>.
+           set with <I>CURLOPT</I><B>_</B><I>PROGRESSFUNCTION</I>
+	   or <I>CURLOPT</I><B>_</B><I>PROGRESSFUNCTION</I><B>_</B><I>BIG</I>.
 
        <B>CURLOPT_HEADERFUNCTION</B>
            Function pointer that should match the following  pro-
@@ -505,7 +516,7 @@
        <B>CURLOPT_PUT</B>
            A non-zero parameter tells the library to use HTTP PUT
            to transfer data. The data should  be  set  with  CUR-
-           LOPT_READDATA and CURLOPT_INFILESIZE.
+           LOPT_READDATA and CURLOPT_INFILESIZE_BIG.
 
        <B>CURLOPT_POST</B>
            A non-zero parameter tells the library to do a regular
@@ -803,7 +814,12 @@
            techniques).
 
        <B>CURLOPT_RESUME_FROM</B>
-           Pass a long as parameter. It contains  the  offset  in
+           Pass a long as a parameter. It contains  the  offset  in
+           number  of  bytes  that you want the transfer to start
+           from.
+
+       <B>CURLOPT_RESUME_FROM_BIG</B>
+           Pass an off_t as a parameter. It contains  the  offset  in
            number  of  bytes  that you want the transfer to start
            from.
 
@@ -846,11 +862,17 @@
        <B>CURLOPT_INFILESIZE</B>
            When  uploading  a  file to a remote site, this option
            should be used to tell libcurl what the expected  size
-           of the infile is.
+           of the infile is.  The size should be passed as a long.
+
+       <B>CURLOPT_INFILESIZE_BIG</B>
+           When  uploading  a  file to a remote site, this option
+           should be used to tell libcurl what the expected  size
+           of the infile is.  The size should be passed as an
+	   off_t.
 
        <B>CURLOPT_UPLOAD</B>
            A  non-zero parameter tells the library to prepare for
-           an upload. The CURLOPT_READDATA and CURLOPT_INFILESIZE
+           an upload. The CURLOPT_READDATA and CURLOPT_INFILESIZE_BIG
            are also interesting for uploads.
            Pass  a  long as parameter. This allows you to specify
            the maximum size (in bytes) of a file to download.  If
diff -ur curl-7.10.8.orig/docs/libcurl-the-guide curl-7.10.8.large_ftp/docs/libcurl-the-guide
--- curl-7.10.8.orig/docs/libcurl-the-guide	Thu Dec 19 07:22:36 2002
+++ curl-7.10.8.large_ftp/docs/libcurl-the-guide	Thu Dec 11 11:49:20 2003
@@ -298,9 +298,9 @@
 
  A few protocols won't behave properly when uploads are done without any prior
  knowledge of the expected file size. So, set the upload file size using the
- CURLOPT_INFILESIZE for all known file sizes like this[1]:
+ CURLOPT_INFILESIZE_BIG for all known file sizes like this[1]:
 
-    curl_easy_setopt(easyhandle, CURLOPT_INFILESIZE, file_size);
+    curl_easy_setopt(easyhandle, CURLOPT_INFILESIZE_BIG, file_size);
 
  When you call curl_easy_perform() this time, it'll perform all the necessary
  operations and when it has invoked the upload it'll call your supplied
@@ -516,6 +516,21 @@
  If any of the input arguments is unknown, a 0 will be passed. The first
  argument, the 'clientp' is the pointer you pass to libcurl with
  CURLOPT_PROGRESSDATA. libcurl won't touch it.
+
+ There is also a progress callback that can be registered which uses
+ off_t's rather than doubles.  To use this, register using
+ CURLOPT_PROGRESSFUNCTION_BIG instead of CURLOPT_PROGRESSFUNCTION, and
+ pass a pointer to a function that matches this prototype:
+
+        int progress_callback(void *clientp,
+                              off_t dltotal,
+                              off_t dlnow,
+                              off_t ultotal,
+                              off_t ulnow);
+
+ You may register the clientp data as with the double version above.  Do
+ note, however, that this callback can currently experience difficulty
+ if the size of data exceeds the size of your machine's off_t datatype.
 
 
 libcurl with C++
diff -ur curl-7.10.8.orig/include/curl/curl.h curl-7.10.8.large_ftp/include/curl/curl.h
--- curl-7.10.8.orig/include/curl/curl.h	Sat Nov  1 03:25:51 2003
+++ curl-7.10.8.large_ftp/include/curl/curl.h	Thu Dec 11 11:21:51 2003
@@ -109,6 +109,12 @@
                                       double ultotal,
                                       double ulnow);
 
+typedef int (*curl_progress_callback_big)(void *clientp,
+					  off_t dltotal,
+					  off_t dlnow,
+					  off_t ultotal,
+					  off_t ulnow);
+
   /* Tests have proven that 20K is a very bad buffer size for uploads on
      Windows, while 16K for some odd reason performed a lot better. */
 #define CURL_MAX_WRITE_SIZE 16384
@@ -262,6 +268,7 @@
 #define CURLOPTTYPE_LONG          0
 #define CURLOPTTYPE_OBJECTPOINT   10000
 #define CURLOPTTYPE_FUNCTIONPOINT 20000
+#define CURLOPTTYPE_OFF_T         30000
 
 /* name is uppercase CURLOPT_<name>,
    type is one of the defined CURLOPTTYPE_<type>
@@ -292,6 +299,7 @@
 #define LONG          CURLOPTTYPE_LONG
 #define OBJECTPOINT   CURLOPTTYPE_OBJECTPOINT
 #define FUNCTIONPOINT CURLOPTTYPE_FUNCTIONPOINT
+#define OFF_T         CURLOPTTYPE_OFF_T
 #define CINIT(name,type,number) CURLOPT_/**/name = type + number
 #endif
 
@@ -348,7 +356,12 @@
   /* If the CURLOPT_INFILE is used, this can be used to inform libcurl about
    * how large the file being sent really is. That allows better error
    * checking and better verifies that the upload was succcessful. -1 means
-   * unknown size. */
+   * unknown size.
+   *
+   * For large file support, there is also a _BIG version of the key
+   * which takes an off_t type, allowing platforms with larger off_t
+   * sizes to handle larger files.  See below for INFILESIZE_BIG.
+   */
   CINIT(INFILESIZE, LONG, 14),
 
   /* POST input fields. */
@@ -376,7 +389,12 @@
   /* Set the "low speed time" */
   CINIT(LOW_SPEED_TIME, LONG, 20),
 
-  /* Set the continuation offset */
+  /* Set the continuation offset.
+   *
+   * Note there is also a _BIG version of this key which uses
+   * off_t types, allowing for large file offsets on platforms which
+   * use larger-than-32-bit off_t's.  Look below for RESUME_FROM_BIG.
+   */
   CINIT(RESUME_FROM, LONG, 21),
 
   /* Set cookie in request: */
@@ -471,7 +489,11 @@
 
   /* Function that will be called instead of the internal progress display
    * function. This function should be defined as the curl_progress_callback
-   * prototype defines. */
+   * prototype defines.
+   *
+   * There is also a version of this which works with off_t's rather than
+   * doubles; look below for PROGRESSFUNCTION_BIG.
+   */
   CINIT(PROGRESSFUNCTION, FUNCTIONPOINT, 56),
 
   /* Data passed to the progress callback */
@@ -691,8 +713,35 @@
   CINIT(IPRESOLVE, LONG, 113),
 
   /* Set this option to limit the size of a file that will be downloaded from
-     an HTTP or FTP server. */
+     an HTTP or FTP server.
+
+     Note there is also _BIG version which adds large file support for
+     platforms which have larger off_t sizes.  See MAXFILESIZE_BIG below. */
   CINIT(MAXFILESIZE, LONG, 114),
+
+  /* See the comment for INFILESIZE above, but in short, specifies
+   * the size of the file being uploaded.  -1 means unknown.
+   */
+  CINIT(INFILESIZE_BIG, OFF_T, 115),
+
+  /* Sets the continuation offset.  There is also a LONG version of this;
+   * look above for RESUME_FROM.
+   */
+  CINIT(RESUME_FROM_BIG, OFF_T, 116),
+
+  /* Sets the maximum size of data that will be downloaded from
+   * an HTTP or FTP server.  See MAXFILESIZE above for the LONG version.
+   */
+  CINIT(MAXFILESIZE_BIG, OFF_T, 117),
+
+  /* Sets an alternative progress function which will be used instead
+   * of the normal internal progress display.  This function should match
+   * the curl_progress_callback_big function prototype.
+   *
+   * Note there is another progress function which can be defined using
+   * doubles rather than off_t's; see above for PROGRESSFUNCTION.
+   */
+  CINIT(PROGRESSFUNCTION_BIG, FUNCTIONPOINT, 118),
 
   CURLOPT_LASTENTRY /* the last unused */
 } CURLoption;
diff -ur curl-7.10.8.orig/lib/dict.c curl-7.10.8.large_ftp/lib/dict.c
--- curl-7.10.8.orig/lib/dict.c	Wed Oct 15 13:35:34 2003
+++ curl-7.10.8.large_ftp/lib/dict.c	Wed Dec 10 09:49:23 2003
@@ -91,7 +91,7 @@
   struct SessionHandle *data=conn->data;
 
   char *path = conn->path;
-  long *bytecount = &conn->bytecount;
+  off_t *bytecount = &conn->bytecount;
 
   if(conn->bits.user_passwd) {
     /* AUTH is missing */
diff -ur curl-7.10.8.orig/lib/easy.c curl-7.10.8.large_ftp/lib/easy.c
--- curl-7.10.8.orig/lib/easy.c	Wed Oct 15 13:35:34 2003
+++ curl-7.10.8.large_ftp/lib/easy.c	Wed Dec 10 10:41:04 2003
@@ -202,6 +202,7 @@
   func_T param_func = (func_T)0;
   long param_long = 0;
   void *param_obj = NULL;
+  off_t param_offset = 0;
   struct SessionHandle *data = curl;
   CURLcode ret=CURLE_FAILED_INIT;
 
@@ -224,9 +225,14 @@
     param_obj = va_arg(arg, void *);
     ret = Curl_setopt(data, tag, param_obj);
   }
-  else {
+  else if(tag < CURLOPTTYPE_OFF_T) {
+    /* This is a function pointer type */
     param_func = va_arg(arg, func_T );
     ret = Curl_setopt(data, tag, param_func);
+  } else {
+    /* This is an off_t type */
+    param_offset = va_arg(arg, off_t);
+    ret = Curl_setopt(data, tag, param_offset);
   }
 
   va_end(arg);
diff -ur curl-7.10.8.orig/lib/file.c curl-7.10.8.large_ftp/lib/file.c
--- curl-7.10.8.orig/lib/file.c	Fri Oct 31 13:18:01 2003
+++ curl-7.10.8.large_ftp/lib/file.c	Thu Dec 11 10:33:48 2003
@@ -163,12 +163,12 @@
   */
   CURLcode res = CURLE_OK;
   struct stat statbuf;
-  unsigned long expected_size=0;
+  off_t expected_size=0;
   bool fstated=FALSE;
   ssize_t nread;
   struct SessionHandle *data = conn->data;
   char *buf = data->state.buffer;
-  int bytecount = 0;
+  off_t bytecount = 0;
   struct timeval start = Curl_tvnow();
   struct timeval now = start;
   int fd;
@@ -188,7 +188,7 @@
      date. */
   if(data->set.no_body && data->set.include_header && fstated) {
     CURLcode result;
-    sprintf(buf, "Content-Length: %lu\r\n", expected_size);
+    sprintf(buf, "Content-Length: " OFF_T_FMT "\r\n", expected_size);
     result = Curl_client_write(data, CLIENTWRITE_BOTH, buf, 0);
     if(result)
       return result;
@@ -217,7 +217,7 @@
   }
 
   /* Added by Dolbneff A.V & Spiridonoff A.V */
-  if (conn->resume_from <= (long)expected_size)
+  if (conn->resume_from <= expected_size)
     expected_size -= conn->resume_from;
   else
     /* Is this error code suitable in such situation? */
diff -ur curl-7.10.8.orig/lib/ftp.c curl-7.10.8.large_ftp/lib/ftp.c
--- curl-7.10.8.orig/lib/ftp.c	Fri Oct 31 13:36:43 2003
+++ curl-7.10.8.large_ftp/lib/ftp.c	Thu Dec 11 10:31:36 2003
@@ -283,9 +283,16 @@
        */
       if(ftp->cache) {
         /* we had data in the "cache", copy that instead of doing an actual
-           read */
-        memcpy(ptr, ftp->cache, ftp->cache_size);
-        gotbytes = ftp->cache_size;
+         * read
+	 *
+	 * Dave Meyer, December 2003:
+	 * ftp->cache_size is cast to int here.  This should be safe,
+	 * because it would have been populated with something of size
+	 * int to begin with, even though its datatype may be larger
+	 * than an int.
+	 */
+        memcpy(ptr, ftp->cache, (int)ftp->cache_size);
+        gotbytes = (int)ftp->cache_size;
         free(ftp->cache);    /* free the cache */
         ftp->cache = NULL;   /* clear the pointer */
         ftp->cache_size = 0; /* zero the size just in case */
@@ -363,9 +370,9 @@
              already!  Cleverly figured out by Eric Lavigne in December
              2001. */
           ftp->cache_size = gotbytes - i;
-          ftp->cache = (char *)malloc(ftp->cache_size);
+          ftp->cache = (char *)malloc((int)ftp->cache_size);
           if(ftp->cache)
-            memcpy(ftp->cache, line_start, ftp->cache_size);
+            memcpy(ftp->cache, line_start, (int)ftp->cache_size);
           else
             return CURLE_OUT_OF_MEMORY; /**BANG**/
         }
@@ -635,7 +642,7 @@
     if((-1 != data->set.infilesize) &&
        (data->set.infilesize != *ftp->bytecountp) &&
        !data->set.crlf) {
-      failf(data, "Uploaded unaligned file size (%d out of %d bytes)",
+      failf(data, "Uploaded unaligned file size (" OFF_T_FMT " out of " OFF_T_FMT " bytes)",
             *ftp->bytecountp, data->set.infilesize);
       return CURLE_PARTIAL_FILE;
     }
@@ -643,7 +650,8 @@
   else {
     if((-1 != conn->size) && (conn->size != *ftp->bytecountp) &&
        (conn->maxdownload != *ftp->bytecountp)) {
-      failf(data, "Received only partial file: %d bytes", *ftp->bytecountp);
+      failf(data, "Received only partial file: " OFF_T_FMT " bytes",
+	    *ftp->bytecountp);
       return CURLE_PARTIAL_FILE;
     }
     else if(!ftp->dont_check &&
@@ -831,7 +839,7 @@
 
 static
 CURLcode ftp_getsize(struct connectdata *conn, char *file,
-                      ssize_t *size)
+                      off_t *size)
 {
   struct SessionHandle *data = conn->data;
   int ftpcode;
@@ -846,7 +854,7 @@
 
   if(ftpcode == 213) {
     /* get the size from the ascii string: */
-    *size = atoi(buf+4);
+    *size = strtoll(buf+4, NULL, 0);
   }
   else
     return CURLE_FTP_COULDNT_GET_SIZE;
@@ -1569,7 +1577,7 @@
 
   /* the ftp struct is already inited in Curl_ftp_connect() */
   struct FTP *ftp = conn->proto.ftp;
-  long *bytecountp = ftp->bytecountp;
+  off_t *bytecountp = ftp->bytecountp;
 
   if(data->set.upload) {
 
@@ -1601,7 +1609,7 @@
       if(conn->resume_from < 0 ) {
         /* we could've got a specified offset from the command line,
            but now we know we didn't */
-        ssize_t gottensize;
+        off_t gottensize;
 
         if(CURLE_OK != ftp_getsize(conn, ftp->file, &gottensize)) {
           failf(data, "Couldn't get remote file size");
@@ -1612,7 +1620,7 @@
 
       if(conn->resume_from) {
         /* do we still game? */
-        int passed=0;
+        off_t passed=0;
         /* enable append instead */
         data->set.ftp_append = 1;
 
@@ -1620,19 +1628,20 @@
            input. If we knew it was a proper file we could've just
            fseek()ed but we only have a stream here */
         do {
-          int readthisamountnow = (conn->resume_from - passed);
-          int actuallyread;
+          off_t readthisamountnow = (conn->resume_from - passed);
+          off_t actuallyread;
 
           if(readthisamountnow > BUFSIZE)
             readthisamountnow = BUFSIZE;
 
           actuallyread =
-            conn->fread(data->state.buffer, 1, readthisamountnow,
+            conn->fread(data->state.buffer, 1, (size_t)readthisamountnow,
                         conn->fread_in);
 
           passed += actuallyread;
           if(actuallyread != readthisamountnow) {
-            failf(data, "Could only read %d bytes from the input", passed);
+            failf(data, "Could only read " OFF_T_FMT " bytes from the input",
+		  passed);
             return CURLE_FTP_COULDNT_USE_REST;
           }
         }
@@ -1690,7 +1699,7 @@
     /* When we know we're uploading a specified file, we can get the file
        size prior to the actual upload. */
 
-    Curl_pgrsSetUploadSize(data, data->set.infilesize);
+    Curl_pgrsSetUploadSize(data, (double)data->set.infilesize);
 
     result = Curl_Transfer(conn, -1, -1, FALSE, NULL, /* no download */
                       conn->secondarysocket, bytecountp);
@@ -1701,18 +1710,18 @@
   else if(!data->set.no_body) {
     /* Retrieve file or directory */
     bool dirlist=FALSE;
-    long downloadsize=-1;
+    off_t downloadsize=-1;
 
     if(conn->bits.use_range && conn->range) {
-      long from, to;
-      int totalsize=-1;
+      off_t from, to;
+      off_t totalsize=-1;
       char *ptr;
       char *ptr2;
 
-      from=strtol(conn->range, &ptr, 0);
+      from=strtoll(conn->range, &ptr, 0);
       while(ptr && *ptr && (isspace((int)*ptr) || (*ptr=='-')))
         ptr++;
-      to=strtol(ptr, &ptr2, 0);
+      to=strtoll(ptr, &ptr2, 0);
       if(ptr == ptr2) {
         /* we didn't get any digit */
         to=-1;
@@ -1720,24 +1729,25 @@
       if((-1 == to) && (from>=0)) {
         /* X - */
         conn->resume_from = from;
-        infof(data, "FTP RANGE %d to end of file\n", from);
+        infof(data, "FTP RANGE " OFF_T_FMT " to end of file\n", from);
       }
       else if(from < 0) {
         /* -Y */
         totalsize = -from;
         conn->maxdownload = -from;
         conn->resume_from = from;
-        infof(data, "FTP RANGE the last %d bytes\n", totalsize);
+        infof(data, "FTP RANGE the last " OFF_T_FMT " bytes\n", totalsize);
       }
       else {
         /* X-Y */
         totalsize = to-from;
         conn->maxdownload = totalsize+1; /* include the last mentioned byte */
         conn->resume_from = from;
-        infof(data, "FTP RANGE from %d getting %d bytes\n", from,
-              conn->maxdownload);
+        infof(data,
+	      "FTP RANGE from " OFF_T_FMT " getting " OFF_T_FMT " bytes\n",
+	      from, conn->maxdownload);
       }
-      infof(data, "range-download from %d to %d, totally %d bytes\n",
+      infof(data, "range-download from " OFF_T_FMT " to " OFF_T_FMT ", totally " OFF_T_FMT " bytes\n",
             from, to, totalsize);
       ftp->dont_check = TRUE; /* dont check for successful transfer */
     }
@@ -1762,7 +1772,7 @@
             (data->set.ftp_list_only?"NLST":"LIST"));
     }
     else {
-      ssize_t foundsize;
+      off_t foundsize;
 
       /* Set type to binary (unless specified ASCII) */
       result = ftp_transfertype(conn, data->set.ftp_ascii);
@@ -1812,7 +1822,7 @@
           if(conn->resume_from< 0) {
             /* We're supposed to download the last abs(from) bytes */
             if(foundsize < -conn->resume_from) {
-              failf(data, "Offset (%d) was beyond file size (%d)",
+              failf(data, "Offset (" OFF_T_FMT ") was beyond file size (" OFF_T_FMT ")",
                     conn->resume_from, foundsize);
               return CURLE_FTP_BAD_DOWNLOAD_RESUME;
             }
@@ -1823,7 +1833,7 @@
           }
           else {
             if(foundsize < conn->resume_from) {
-              failf(data, "Offset (%d) was beyond file size (%d)",
+              failf(data, "Offset (" OFF_T_FMT ") was beyond file size (" OFF_T_FMT ")",
                     conn->resume_from, foundsize);
               return CURLE_FTP_BAD_DOWNLOAD_RESUME;
             }
@@ -1844,10 +1854,10 @@
         }
 	
         /* Set resume file transfer offset */
-        infof(data, "Instructs server to resume from offset %d\n",
+        infof(data, "Instructs server to resume from offset " OFF_T_FMT "\n",
               conn->resume_from);
 
-        FTPSENDF(conn, "REST %d", conn->resume_from);
+        FTPSENDF(conn, "REST " OFF_T_FMT, conn->resume_from);
 
         result = Curl_GetFTPResponse(&nread, conn, &ftpcode);
         if(result)
@@ -1885,7 +1895,7 @@
         E:
         125 Data connection already open; Transfer starting. */
 
-      int size=-1; /* default unknown size */
+      off_t size=-1; /* default unknown size */
 
 
       /*
@@ -1927,7 +1937,7 @@
           /* only if we have nothing but digits: */
           if(bytes++) {
             /* get the number! */
-            size = atoi(bytes);
+            size = strtoll(bytes, NULL, 0);
           }
             
         }
@@ -1941,7 +1951,7 @@
           return result;
       }
 
-      infof(data, "Getting file with size: %d\n", size);
+      infof(data, "Getting file with size: " OFF_T_FMT "\n", size);
 
       /* FTP download: */
       result=Curl_Transfer(conn, conn->secondarysocket, size, FALSE,
@@ -2057,7 +2067,7 @@
     /* The SIZE command is _not_ RFC 959 specified, and therefor many servers
        may not support it! It is however the only way we have to get a file's
        size! */
-    ssize_t filesize;
+    off_t filesize;
     ssize_t nread;
     int ftpcode;
 
@@ -2073,7 +2083,7 @@
     result = ftp_getsize(conn, ftp->file, &filesize);
 
     if(CURLE_OK == result) {
-      sprintf(buf, "Content-Length: %d\r\n", filesize);
+      sprintf(buf, "Content-Length: " OFF_T_FMT "\r\n", filesize);
       result = Curl_client_write(data, CLIENTWRITE_BOTH, buf, 0);
       if(result)
         return result;
diff -ur curl-7.10.8.orig/lib/http.c curl-7.10.8.large_ftp/lib/http.c
--- curl-7.10.8.orig/lib/http.c	Fri Oct 31 13:43:22 2003
+++ curl-7.10.8.large_ftp/lib/http.c	Thu Dec 11 10:26:14 2003
@@ -1219,25 +1219,25 @@
 
     if(conn->resume_from) {
       /* do we still game? */
-      int passed=0;
+      off_t passed=0;
 
       /* Now, let's read off the proper amount of bytes from the
          input. If we knew it was a proper file we could've just
          fseek()ed but we only have a stream here */
       do {
-        int readthisamountnow = (conn->resume_from - passed);
-        int actuallyread;
+        off_t readthisamountnow = (conn->resume_from - passed);
+        off_t actuallyread;
 
         if(readthisamountnow > BUFSIZE)
           readthisamountnow = BUFSIZE;
 
         actuallyread =
-          data->set.fread(data->state.buffer, 1, readthisamountnow,
+          data->set.fread(data->state.buffer, 1, (size_t)readthisamountnow,
                           data->set.in);
 
         passed += actuallyread;
         if(actuallyread != readthisamountnow) {
-          failf(data, "Could only read %d bytes from the input",
+          failf(data, "Could only read " OFF_T_FMT " bytes from the input",
                 passed);
           return CURLE_READ_ERROR;
         }
@@ -1273,16 +1273,18 @@
 
       if(conn->resume_from) {
         /* This is because "resume" was selected */
-        long total_expected_size= conn->resume_from + data->set.infilesize;
-        conn->allocptr.rangeline = aprintf("Content-Range: bytes %s%ld/%ld\r\n",
-                                      conn->range, total_expected_size-1,
-                                      total_expected_size);
+        off_t total_expected_size= conn->resume_from + data->set.infilesize;
+        conn->allocptr.rangeline =
+	    aprintf("Content-Range: bytes %s" OFF_T_FMT "/" OFF_T_FMT "\r\n",
+		    conn->range, total_expected_size-1,
+		    total_expected_size);
       }
       else {
         /* Range was selected and then we just pass the incoming range and 
            append total size */
-        conn->allocptr.rangeline = aprintf("Content-Range: bytes %s/%d\r\n",
-                                      conn->range, data->set.infilesize);
+        conn->allocptr.rangeline =
+	    aprintf("Content-Range: bytes %s/" OFF_T_FMT "\r\n",
+		    conn->range, data->set.infilesize);
       }
     }
   }
@@ -1511,13 +1513,13 @@
       if((data->set.infilesize>0) && !conn->bits.upload_chunky)
         /* only add Content-Length if not uploading chunked */
         add_bufferf(req_buffer,
-                    "Content-Length: %d\r\n", /* file size */
+                    "Content-Length: " OFF_T_FMT "\r\n", /* file size */
                     data->set.infilesize );
 
       add_bufferf(req_buffer, "\r\n");
 
       /* set the upload size to the progress meter */
-      Curl_pgrsSetUploadSize(data, data->set.infilesize);
+      Curl_pgrsSetUploadSize(data, (double)data->set.infilesize);
 
       /* this sends the buffer and frees all the buffer resources */
       result = add_buffer_send(req_buffer, conn->firstsocket, conn,
@@ -1594,7 +1596,7 @@
       }
       else {
         /* set the upload size to the progress meter */
-        Curl_pgrsSetUploadSize(data, data->set.infilesize);
+        Curl_pgrsSetUploadSize(data, (double)data->set.infilesize);
 
         /* set the pointer to mark that we will send the post body using
            the read callback */
diff -ur curl-7.10.8.orig/lib/progress.c curl-7.10.8.large_ftp/lib/progress.c
--- curl-7.10.8.orig/lib/progress.c	Wed Oct 15 13:35:34 2003
+++ curl-7.10.8.large_ftp/lib/progress.c	Thu Dec 11 11:42:50 2003
@@ -57,13 +57,14 @@
 {
 #define ONE_KILOBYTE 1024
 #define ONE_MEGABYTE (1024*1024)
+#define ONE_GIGABYTE (1024*1024*1024)
 
   if(bytes < 100000) {
     sprintf(max5, "%5d", (int)bytes);
     return max5;
   }
   if(bytes < (9999*ONE_KILOBYTE)) {
-    sprintf(max5, "%4dk", (int)bytes/ONE_KILOBYTE);
+    sprintf(max5, "%4dk", (int)(bytes/ONE_KILOBYTE));
     return max5;
   }
   if(bytes < (100*ONE_MEGABYTE)) {
@@ -71,7 +72,16 @@
     sprintf(max5, "%4.1fM", bytes/ONE_MEGABYTE);
     return max5;
   }
-  sprintf(max5, "%4dM", (int)bytes/ONE_MEGABYTE);
+  if(bytes < (9999.0*ONE_MEGABYTE)) {
+    sprintf(max5, "%4dM", (int)(bytes/ONE_MEGABYTE));
+    return max5;
+  }
+  if(bytes < (100.0*ONE_GIGABYTE)) {
+    /* As with megs, pring with decimal place when below 100 gigs. */
+    sprintf(max5, "%4.1fG", bytes/ONE_GIGABYTE);
+    return max5;
+  }
+  sprintf(max5, "%4dG", (int)(bytes/ONE_GIGABYTE));
   return max5;
 }
 
@@ -228,7 +238,8 @@
   else if(!(data->progress.flags & PGRS_HEADERS_OUT)) {
     if (!data->progress.callback) {
       if(conn->resume_from)
-        fprintf(data->set.err, "** Resuming transfer from byte position %d\n",
+        fprintf(data->set.err,
+		"** Resuming transfer from byte position " OFF_T_FMT "\n",
                 conn->resume_from);
       fprintf(data->set.err,
               "  %% Total    %% Received %% Xferd  Average Speed          Time             Curr.\n"
@@ -317,6 +328,32 @@
                                 data->progress.uploaded);
     if(result)
       failf(data, "Callback aborted");
+    return result;
+  }
+  else if(data->set.fprogress_big) {
+    /* There's an off_t-based progress function which we now
+     * call in preference to our own.
+     */
+
+    /* TODO:  How do we fix the datatypes passed to this?
+     *        It would be nice to switch size_dl and friends
+     *        into off_t's, but that may actually fail miserably
+     *        on systems where the off_t is only 32 bits -- we'd
+     *        potentially run into trouble if the progress meter
+     *        was called across multiple files, which could produce
+     *        sizes outside of the 32-bit range, e.g., imagine
+     *        downloading 10 full CD images -- that's 6.5 GB of
+     *        data, even though no single file is > 2 GB.
+     */
+    result = data->set.fprogress_big(data->set.progress_client,
+				     (off_t)data->progress.size_dl,
+				     (off_t)data->progress.downloaded,
+				     (off_t)data->progress.size_ul,
+				     (off_t)data->progress.uploaded);
+
+    if(result) {
+      failf(data, "Callback aborted");
+    }
     return result;
   }
 
diff -ur curl-7.10.8.orig/lib/setup.h curl-7.10.8.large_ftp/lib/setup.h
--- curl-7.10.8.orig/lib/setup.h	Wed Oct 15 13:35:34 2003
+++ curl-7.10.8.large_ftp/lib/setup.h	Thu Dec 11 10:23:53 2003
@@ -207,6 +207,25 @@
 typedef struct in_addr Curl_ipconnect;
 #endif
 
+/* Set up proper handling of internal printf/scanf formats
+ * based on the size of the off_t data type.
+ *
+ * Essentially, we need to use the right %x spec when
+ * reading off_t's:  long long off_t's use %lld, while
+ * regular off_t's use %d.  Further, I've heard rumors
+ * that some systems don't even use %lld for their long
+ * long values...
+ *
+ * The check for this is shamelessly based off of the
+ * /usr/include/features.h check for 64-bit file offsets
+ * found on linux systems.
+ */
+#if defined _FILE_OFFSET_BITS && _FILE_OFFSET_BITS == 64
+#define OFF_T_FMT "%lld"
+#else
+#define OFF_T_FMT "%d"
+#endif
+
 #if 0
 #if (SIZEOF_OFF_T > 4)
 /* off_t is bigger than 4 bytes, and that makes it our prefered variable
diff -ur curl-7.10.8.orig/lib/transfer.c curl-7.10.8.large_ftp/lib/transfer.c
--- curl-7.10.8.orig/lib/transfer.c	Fri Oct 24 14:54:34 2003
+++ curl-7.10.8.large_ftp/lib/transfer.c	Thu Dec 11 10:33:17 2003
@@ -590,14 +590,14 @@
                info about the true size of the document we didn't get now. */
             if ((k->httpcode != 416) &&
                 checkprefix("Content-Length:", k->p) &&
-                sscanf (k->p+15, " %ld", &k->contentlength)) {
+                sscanf (k->p+15, " " OFF_T_FMT, &k->contentlength)) {
               if (data->set.max_filesize && k->contentlength > 
                   data->set.max_filesize) {
                 failf(data, "Maximum file size exceeded");
                 return CURLE_FILESIZE_EXCEEDED;
               }
               conn->size = k->contentlength;
-              Curl_pgrsSetDownloadSize(data, k->contentlength);
+              Curl_pgrsSetDownloadSize(data, (double)k->contentlength);
             }
             /* check for Content-Type: header lines to get the mime-type */
             else if (checkprefix("Content-Type:", k->p)) {
@@ -710,8 +710,8 @@
                 k->content_encoding = COMPRESS;
             }
             else if (checkprefix("Content-Range:", k->p)) {
-              if (sscanf (k->p+14, " bytes %d-", &k->offset) ||
-                  sscanf (k->p+14, " bytes: %d-", &k->offset)) {
+              if (sscanf (k->p+14, " bytes " OFF_T_FMT "-", &k->offset) ||
+                  sscanf (k->p+14, " bytes: " OFF_T_FMT "-", &k->offset)) {
                 /* This second format was added August 1st 2000 by Igor
                    Khristophorov since Sun's webserver JavaWebServer/1.1.1
                    obviously sends the header this way! :-( */
@@ -938,7 +938,7 @@
 
           if((-1 != conn->maxdownload) &&
              (k->bytecount + nread >= conn->maxdownload)) {
-            nread = conn->maxdownload - k->bytecount;
+            nread = (ssize_t) (conn->maxdownload - k->bytecount);
             if(nread < 0 ) /* this should be unusual */
               nread = 0;
 
@@ -1204,7 +1204,7 @@
     
   if (data->set.timeout &&
       ((Curl_tvdiff(k->now, k->start)/1000) >= data->set.timeout)) {
-    failf (data, "Operation timed out with %d out of %d bytes received",
+    failf (data, "Operation timed out with " OFF_T_FMT " out of " OFF_T_FMT " bytes received",
            k->bytecount, conn->size);
     return CURLE_OPERATION_TIMEOUTED;
   }
@@ -1218,7 +1218,7 @@
     if(!(data->set.no_body) && k->contentlength &&
        (k->bytecount != k->contentlength) &&
        !conn->newurl) {
-      failf(data, "transfer closed with %d bytes remaining to read",
+      failf(data, "transfer closed with " OFF_T_FMT " bytes remaining to read",
             k->contentlength-k->bytecount);
       return CURLE_PARTIAL_FILE;
     }
@@ -1268,7 +1268,7 @@
   if (!conn->bits.getheader) {
     k->header = FALSE;
     if(conn->size > 0)
-      Curl_pgrsSetDownloadSize(data, conn->size);
+      Curl_pgrsSetDownloadSize(data, (double)conn->size);
   }
   /* we want header and/or body, if neither then don't do this! */
   if(conn->bits.getheader || !data->set.no_body) {
@@ -1937,12 +1937,12 @@
 CURLcode 
 Curl_Transfer(struct connectdata *c_conn, /* connection data */
               int sockfd,       /* socket to read from or -1 */
-              int size,         /* -1 if unknown at this point */
+              off_t size,       /* -1 if unknown at this point */
               bool getheader,   /* TRUE if header parsing is wanted */
-              long *bytecountp, /* return number of bytes read or NULL */
+              off_t *bytecountp, /* return number of bytes read or NULL */
               int writesockfd,  /* socket to write to, it may very well be
                                    the same we read from. -1 disables */
-              long *writebytecountp /* return number of bytes written or
+              off_t *writebytecountp /* return number of bytes written or
                                        NULL */
               )
 {
diff -ur curl-7.10.8.orig/lib/transfer.h curl-7.10.8.large_ftp/lib/transfer.h
--- curl-7.10.8.orig/lib/transfer.h	Thu Jan 16 13:08:13 2003
+++ curl-7.10.8.large_ftp/lib/transfer.h	Wed Dec 10 09:49:23 2003
@@ -38,11 +38,11 @@
 CURLcode 
 Curl_Transfer (struct connectdata *data,
                int sockfd,		/* socket to read from or -1 */
-               int size,		/* -1 if unknown at this point */
+               off_t size,		/* -1 if unknown at this point */
                bool getheader,     	/* TRUE if header parsing is wanted */
-               long *bytecountp,	/* return number of bytes read */
+               off_t *bytecountp,	/* return number of bytes read */
                int writesockfd,      /* socket to write to, it may very well be
                                         the same we read from. -1 disables */
-               long *writebytecountp /* return number of bytes written */
+               off_t *writebytecountp /* return number of bytes written */
 );
 #endif
diff -ur curl-7.10.8.orig/lib/url.c curl-7.10.8.large_ftp/lib/url.c
--- curl-7.10.8.orig/lib/url.c	Fri Oct 31 13:18:01 2003
+++ curl-7.10.8.large_ftp/lib/url.c	Thu Dec 11 11:15:09 2003
@@ -705,6 +705,13 @@
      */
     data->set.infilesize = va_arg(param, long);
     break;
+  case CURLOPT_INFILESIZE_BIG:
+    /*
+     * If known, this should inform curl about the file size of the
+     * to-be-uploaded file.
+     */
+    data->set.infilesize = va_arg(param, off_t);
+    break;
   case CURLOPT_LOW_SPEED_LIMIT:
     /*
      * The low speed limit that if transfers are below this for
@@ -925,6 +932,17 @@
       data->progress.callback = FALSE; /* NULL enforces internal */
 
     break;
+  case CURLOPT_PROGRESSFUNCTION_BIG:
+    /*
+     * Progress callback function working with off_t's.
+     */
+    data->set.fprogress_big = va_arg(param, curl_progress_callback_big);
+    if(data->set.fprogress_big)
+      data->progress.callback = TRUE; /* no longer internal */
+    else
+      data->progress.callback = FALSE; /* NULL enforces internal */
+
+    break;
   case CURLOPT_PROGRESSDATA:
     /*
      * Custom client data to pass to the progress callback
@@ -949,6 +967,12 @@
      */
     data->set.set_resume_from = va_arg(param, long);
     break;
+  case CURLOPT_RESUME_FROM_BIG:
+    /*
+     * Resume transfer at the give file position
+     */
+    data->set.set_resume_from = va_arg(param, off_t);
+    break;
   case CURLOPT_DEBUGFUNCTION:
     /*
      * stderr write callback.
@@ -1245,6 +1269,13 @@
     data->set.max_filesize = va_arg(param, long);
     break;
 
+  case CURLOPT_MAXFILESIZE_BIG:
+    /*
+     * Set the maximum size of a file to download.
+     */
+    data->set.max_filesize = va_arg(param, off_t);
+    break;
+
   default:
     /* unknown tag and its companion, just ignore: */
     return CURLE_FAILED_INIT; /* correct this */
@@ -2337,7 +2368,8 @@
   if(conn->resume_from) {
     if(!conn->bits.use_range) {
       /* if it already was in use, we just skip this */
-      snprintf(resumerange, sizeof(resumerange), "%d-", conn->resume_from);
+      snprintf(resumerange, sizeof(resumerange), OFF_T_FMT "-",
+	       conn->resume_from);
       conn->range=strdup(resumerange); /* tell ourselves to fetch this range */
       conn->bits.rangestringalloc = TRUE; /* mark as allocated */
       conn->bits.use_range = 1; /* switch on range usage */
@@ -2853,7 +2885,8 @@
      */
     conn->resume_from = data->set.set_resume_from;
     if (conn->resume_from) {
-        snprintf(resumerange, sizeof(resumerange), "%d-", conn->resume_from);
+        snprintf(resumerange, sizeof(resumerange), OFF_T_FMT "-",
+		 conn->resume_from);
         if (conn->bits.rangestringalloc == TRUE)
             free(conn->range);
 
diff -ur curl-7.10.8.orig/lib/urldata.h curl-7.10.8.large_ftp/lib/urldata.h
--- curl-7.10.8.orig/lib/urldata.h	Sat Oct 18 13:14:33 2003
+++ curl-7.10.8.large_ftp/lib/urldata.h	Thu Dec 11 11:26:36 2003
@@ -210,8 +210,8 @@
 
   const char *p_pragma;      /* Pragma: string */
   const char *p_accept;      /* Accept: string */
-  long readbytecount; 
-  long writebytecount;
+  off_t readbytecount; 
+  off_t writebytecount;
 
   /* For FORM posting */
   struct Form form;
@@ -239,7 +239,7 @@
  * FTP unique setup
  ***************************************************************************/
 struct FTP {
-  long *bytecountp;
+  off_t *bytecountp;
   char *user;    /* user name string */
   char *passwd;  /* password string */
   char *urlpath; /* the originally given path part of the URL */
@@ -249,7 +249,7 @@
   char *entrypath; /* the PWD reply when we logged on */
 
   char *cache;       /* data cache between getresponse()-calls */
-  size_t cache_size; /* size of cache in bytes */
+  off_t cache_size; /* size of cache in bytes */
   bool dont_check;  /* Set to TRUE to prevent the final (post-transfer)
                        file size and 226/250 status check. It should still
                        read the line, just ignore the result. */
@@ -304,9 +304,9 @@
  */
 
 struct Curl_transfer_keeper {
-  int bytecount;                /* total number of bytes read */
+  off_t bytecount;                /* total number of bytes read */
   int writebytecount;           /* number of bytes written */
-  long contentlength;           /* size of incoming data */
+  off_t contentlength;           /* size of incoming data */
   struct timeval start;         /* transfer started at this time */
   struct timeval now;           /* current time */
   bool header;	                /* incoming data has HTTP header */
@@ -326,7 +326,7 @@
   char *end_ptr;		/* within buf */
   char *p;			/* within headerbuff */
   bool content_range;      	/* set TRUE if Content-Range: was found */
-  int offset;	                /* possible resume offset read from the
+  off_t offset;	                /* possible resume offset read from the
                                    Content-Range: header */
   int httpcode;		        /* error code from the 'HTTP/1.? XXX' line */
   int httpversion;		/* the HTTP version*10 */
@@ -425,12 +425,12 @@
   unsigned short remote_port; /* what remote port to connect to,
                                  not the proxy port! */
   char *ppath;
-  long bytecount;
+  off_t bytecount;
   long headerbytecount;  /* only count received headers */
 
   char *range; /* range, if used. See README for detailed specification on
                   this syntax. */
-  ssize_t resume_from; /* continue [ftp] transfer from here */
+  off_t resume_from; /* continue [ftp] transfer from here */
 
   char *proxyhost; /* name of the http proxy host */
 
@@ -444,7 +444,7 @@
   struct timeval created; /* creation time */
   int firstsocket;     /* the main socket to use */
   int secondarysocket; /* for i.e ftp transfers */
-  long maxdownload; /* in bytes, the maximum amount of data to fetch, 0
+  off_t maxdownload; /* in bytes, the maximum amount of data to fetch, 0
                        means unlimited */
   
   struct ssl_connect_data ssl; /* this is for ssl-stuff */
@@ -482,13 +482,13 @@
 
   /* READ stuff */
   int sockfd;		 /* socket to read from or -1 */
-  int size;		 /* -1 if unknown at this point */
-  long *bytecountp;	 /* return number of bytes read or NULL */
+  off_t size;		 /* -1 if unknown at this point */
+  off_t *bytecountp;	 /* return number of bytes read or NULL */
           
   /* WRITE stuff */
   int writesockfd;       /* socket to write to, it may very well be
                             the same we read from. -1 disables */
-  long *writebytecountp; /* return number of bytes written or NULL */
+  off_t *writebytecountp; /* return number of bytes written or NULL */
 
   /** Dynamicly allocated strings, may need to be freed before this **/
   /** struct is killed.                                             **/
@@ -777,6 +777,7 @@
   curl_write_callback fwrite_header; /* function that stores headers */
   curl_read_callback fread;          /* function that reads the input */
   curl_progress_callback fprogress;  /* function for progress information */
+  curl_progress_callback_big fprogress_big;  /* off_t progress function */
   curl_debug_callback fdebug;      /* function that write informational data */
   void *progress_client; /* pointer to pass to the progress callback */
   curl_passwd_callback fpasswd;      /* call for password */
@@ -784,10 +785,10 @@
   long timeout;         /* in seconds, 0 means no timeout */
   long connecttimeout;  /* in seconds, 0 means no timeout */
   long ftp_response_timeout; /* in seconds, 0 means no timeout */
-  long infilesize;      /* size of file to upload, -1 means unknown */
+  off_t infilesize;      /* size of file to upload, -1 means unknown */
   long low_speed_limit; /* bytes/second */
   long low_speed_time;  /* number of seconds */
-  int set_resume_from;  /* continue [ftp] transfer from here */
+  off_t set_resume_from;  /* continue [ftp] transfer from here */
   char *cookie;         /* HTTP cookie string to send */
   struct curl_slist *headers; /* linked list of extra headers */
   struct HttpPost *httppost;  /* linked list of POST data */
@@ -829,7 +830,7 @@
 
   int ip_version; 
 
-  long max_filesize; /* Maximum file size to download */
+  off_t max_filesize; /* Maximum file size to download */
   
 /* Here follows boolean settings that define how to behave during
    this session. They are STATIC, set by libcurl users or at least initially
diff -ur curl-7.10.8.orig/src/main.c curl-7.10.8.large_ftp/src/main.c
--- curl-7.10.8.orig/src/main.c	Fri Oct 31 13:18:01 2003
+++ curl-7.10.8.large_ftp/src/main.c	Wed Dec 10 12:51:22 2003
@@ -500,14 +500,14 @@
   bool resume_from_current;
   bool disable_epsv;
   bool disable_eprt;
-  long resume_from;
+  off_t resume_from;
   char *postfields;
   long postfieldsize;
   char *referer;
   long timeout;
   long connecttimeout;
   long maxredirs;
-  long max_filesize;
+  off_t max_filesize;
   char *headerfile;
   char *ftpport;
   char *iface;
@@ -1070,6 +1070,39 @@
   return retcode;  
 }
 
+/**
+ * Parses the given string looking for an offset (which may be
+ * a larger-than-integer value).
+ *
+ * @param val  the offset to populate
+ * @param str  the buffer containing the offset
+ * @return zero if successful, non-zero if failure.
+ */
+static int str2offset(off_t *val, char *str) {
+    if (sizeof(off_t) == 8) {
+	/* Ugly, but without going through a bunch of rigamarole,
+	 * we don't have the definitions for LLONG_{MIN,MAX} or
+	 * LONG_LONG_{MIN,MAX}.
+	 */
+#ifndef LLONG_MAX
+#define LLONG_MAX 0x7FFFFFFFFFFFFFFF
+#define LLONG_MIN 0x8000000000000000
+#endif
+
+	*val = strtoll(str, NULL, 0);
+	if ((*val == LLONG_MAX || *val == LLONG_MIN) && errno == ERANGE) {
+	    return 1;
+	}
+    } else {
+	*val = strtol(str, NULL, 0);
+	if ((*val == LONG_MIN || *val == LONG_MAX) && errno == ERANGE) {
+	    return 1;
+	}
+    }
+
+    return 0;
+}
+
 static void checkpasswd(const char *kind, /* for what purpose */
                         char **userpwd) /* pointer to allocated string */
 {
@@ -1427,7 +1460,7 @@
         GetStr(&config->krb4level, nextarg);
         break;
       case 'y': /* --max-filesize */
-        if(str2num(&config->max_filesize, nextarg))
+        if(str2offset(&config->max_filesize, nextarg))
           return PARAM_BAD_NUMERIC;
         break;
       case 'z': /* --disable-eprt */
@@ -1519,7 +1552,7 @@
     case 'C':
       /* This makes us continue an ftp transfer at given position */
       if(!curl_strequal(nextarg, "-")) {
-        if(str2num(&config->resume_from, nextarg))
+        if(str2offset(&config->resume_from, nextarg))
           return PARAM_BAD_NUMERIC;
         config->resume_from_current = FALSE;
       }
@@ -2305,7 +2338,7 @@
   double prev;
   int width;
   FILE *out; /* where to write everything to */
-  int initial_size;
+  off_t initial_size;
 };
 
 int myprogress (void *clientp,
@@ -2606,7 +2639,7 @@
   bool infdfopen;
   FILE *headerfilep = NULL;
   char *urlbuffer=NULL;
-  long uploadfilesize; /* -1 means unknown */
+  off_t uploadfilesize; /* -1 means unknown */
   bool stillflags=TRUE;
 
   bool allocuseragent=FALSE;
@@ -3130,7 +3163,7 @@
         }
 
         /* size of uploaded file: */
-        curl_easy_setopt(curl, CURLOPT_INFILESIZE, uploadfilesize);
+        curl_easy_setopt(curl, CURLOPT_INFILESIZE_BIG, uploadfilesize);
         curl_easy_setopt(curl, CURLOPT_URL, url);     /* what to fetch */
         curl_easy_setopt(curl, CURLOPT_PROXY, config->proxy); /* proxy to use */
         curl_easy_setopt(curl, CURLOPT_HEADER, config->conf&CONF_HEADER);
@@ -3173,7 +3206,7 @@
         curl_easy_setopt(curl, CURLOPT_FTPPORT, config->ftpport);
         curl_easy_setopt(curl, CURLOPT_LOW_SPEED_LIMIT, config->low_speed_limit);
         curl_easy_setopt(curl, CURLOPT_LOW_SPEED_TIME, config->low_speed_time);
-        curl_easy_setopt(curl, CURLOPT_RESUME_FROM,
+        curl_easy_setopt(curl, CURLOPT_RESUME_FROM_BIG,
                          config->use_resume?config->resume_from:0);
         curl_easy_setopt(curl, CURLOPT_COOKIE, config->cookie);
         curl_easy_setopt(curl, CURLOPT_HTTPHEADER, config->headers);
@@ -3291,7 +3324,8 @@
 
         /* new in curl 7.10.8 */
         if (config->max_filesize)
-          curl_easy_setopt(curl, CURLOPT_MAXFILESIZE, config->max_filesize);
+          curl_easy_setopt(curl, CURLOPT_MAXFILESIZE_BIG,
+			   config->max_filesize);
 
         res = curl_easy_perform(curl);
         
diff -ur curl-7.10.8.orig/tests/libtest/lib505.c curl-7.10.8.large_ftp/tests/libtest/lib505.c
--- curl-7.10.8.orig/tests/libtest/lib505.c	Tue Apr 15 07:20:21 2003
+++ curl-7.10.8.large_ftp/tests/libtest/lib505.c	Wed Dec 10 10:42:11 2003
@@ -92,8 +92,8 @@
     curl_easy_setopt(curl, CURLOPT_INFILE, hd_src);
 
     /* and give the size of the upload (optional) */
-    curl_easy_setopt(curl, CURLOPT_INFILESIZE,
-                     (long)file_info.st_size);
+    curl_easy_setopt(curl, CURLOPT_INFILESIZE_BIG,
+                     file_info.st_size);
 
     /* Now run off and do what you've been told! */
     res = curl_easy_perform(curl);
