]> granicus.if.org Git - curl/commitdiff
curl tool: OOM handling fixes
authorYang Tse <yangsita@gmail.com>
Wed, 5 Oct 2011 20:01:42 +0000 (22:01 +0200)
committerYang Tse <yangsita@gmail.com>
Wed, 5 Oct 2011 20:01:42 +0000 (22:01 +0200)
src/tool_operate.c
src/tool_urlglob.c
src/tool_urlglob.h

index b7da80a7177b651a2a4f7cba727eb5ba7ccdc313..9a06098a07fcccd942fc6946db5648c48fe23efe 100644 (file)
@@ -441,10 +441,18 @@ int operate(struct Configurable *config, int argc, argv_item_t argv[])
       if(!up && !infiles)
         Curl_nop_stmt;
       else {
-        if(inglob)
-          uploadfile = glob_next_url(inglob);
-        else if(!up)
+        if(inglob) {
+          res = glob_next_url(&uploadfile, inglob);
+          if(res == CURLE_OUT_OF_MEMORY)
+            helpf(config->errors, "out of memory\n");
+        }
+        else if(!up) {
           uploadfile = strdup(infiles);
+          if(!uploadfile) {
+            helpf(config->errors, "out of memory\n");
+            res = CURLE_OUT_OF_MEMORY;
+          }
+        }
         else
           uploadfile = NULL;
         if(!uploadfile)
@@ -492,10 +500,17 @@ int operate(struct Configurable *config, int argc, argv_item_t argv[])
         outs.stream = stdout;
         outs.config = config;
 
-        if(urls)
-          this_url = glob_next_url(urls);
+        if(urls) {
+          res = glob_next_url(&this_url, urls);
+          if(res)
+            goto show_error;
+        }
         else if(!i) {
           this_url = strdup(urlnode->url);
+          if(!this_url) {
+            res = CURLE_OUT_OF_MEMORY;
+            goto show_error;
+          }
         }
         else
           this_url = NULL;
@@ -541,12 +556,11 @@ int operate(struct Configurable *config, int argc, argv_item_t argv[])
           else if(urls) {
             /* fill '#1' ... '#9' terms from URL pattern */
             char *storefile = outfile;
-            outfile = glob_match_url(storefile, urls);
+            res = glob_match_url(&outfile, storefile, urls);
             Curl_safefree(storefile);
-            if(!outfile) {
+            if(res) {
               /* bad globbing */
               warnf(config, "bad output glob!\n");
-              res = CURLE_FAILED_INIT;
               goto quit_urls;
             }
           }
index 108fc3987f7c0646f584015f9710ef3d1c440a45..f5c09a1e83e30cf95511442ea5a94db31a2f34ca 100644 (file)
@@ -419,7 +419,7 @@ void glob_cleanup(URLGlob* glob)
   Curl_safefree(glob);
 }
 
-char *glob_next_url(URLGlob *glob)
+int glob_next_url(char **globbed, URLGlob *glob)
 {
   URLPattern *pat;
   char *lit;
@@ -429,6 +429,8 @@ char *glob_next_url(URLGlob *glob)
   size_t buflen = glob->urllen + 1;
   char *buf = glob->glob_buffer;
 
+  *globbed = NULL;
+
   if(!glob->beenhere)
     glob->beenhere = 1;
   else {
@@ -464,11 +466,13 @@ char *glob_next_url(URLGlob *glob)
         break;
       default:
         printf("internal error: invalid pattern type (%d)\n", (int)pat->type);
-        exit (CURLE_FAILED_INIT);
+        return CURLE_FAILED_INIT;
       }
     }
-    if(carry)          /* first pattern ptr has run into overflow, done! */
-      return NULL;
+    if(carry) {         /* first pattern ptr has run into overflow, done! */
+      /* TODO: verify if this should actally return CURLE_OK. */
+      return CURLE_OK; /* CURLE_OK to match previous behavior */
+    }
   }
 
   for(j = 0; j < glob->size; ++j) {
@@ -502,15 +506,20 @@ char *glob_next_url(URLGlob *glob)
         break;
       default:
         printf("internal error: invalid pattern type (%d)\n", (int)pat->type);
-        exit (CURLE_FAILED_INIT);
+        return CURLE_FAILED_INIT;
       }
     }
   }
   *buf = '\0';
-  return strdup(glob->glob_buffer);
+
+  *globbed = strdup(glob->glob_buffer);
+  if(!*globbed)
+    return CURLE_OUT_OF_MEMORY;
+
+  return CURLE_OK;
 }
 
-char *glob_match_url(char *filename, URLGlob *glob)
+int glob_match_url(char **result, char *filename, URLGlob *glob)
 {
   char *target;
   size_t allocsize;
@@ -519,6 +528,8 @@ char *glob_match_url(char *filename, URLGlob *glob)
   size_t appendlen = 0;
   size_t stringlen = 0;
 
+  *result = NULL;
+
   /* We cannot use the glob_buffer for storage here since the filename may
    * be longer than the URL we use. We allocate a good start size, then
    * we need to realloc in case of need.
@@ -527,7 +538,7 @@ char *glob_match_url(char *filename, URLGlob *glob)
                                        trailing zero */
   target = malloc(allocsize);
   if(!target)
-    return NULL; /* major failure */
+    return CURLE_OUT_OF_MEMORY;
 
   while(*filename) {
     if(*filename == '#' && ISDIGIT(filename[1])) {
@@ -563,7 +574,7 @@ char *glob_match_url(char *filename, URLGlob *glob)
           printf("internal error: invalid pattern type (%d)\n",
                  (int)pat.type);
           Curl_safefree(target);
-          return NULL;
+          return CURLE_FAILED_INIT;
         }
       }
       else {
@@ -585,7 +596,7 @@ char *glob_match_url(char *filename, URLGlob *glob)
       newstr = realloc(target, allocsize + 1);
       if(!newstr) {
         Curl_safefree(target);
-        return NULL;
+        return CURLE_OUT_OF_MEMORY;
       }
       target = newstr;
     }
@@ -593,5 +604,7 @@ char *glob_match_url(char *filename, URLGlob *glob)
     stringlen += appendlen;
   }
   target[stringlen]= '\0';
-  return target;
+  *result = target;
+  return CURLE_OK;
 }
+
index cf54a9b1682d26faafb8be3f785bb28b8227f954..18281bf61c0eff430f4c5ab077305a603dce3ae8 100644 (file)
@@ -64,8 +64,8 @@ typedef struct {
 } URLGlob;
 
 int glob_url(URLGlob**, char*, int *, FILE *);
-char* glob_next_url(URLGlob*);
-char* glob_match_url(char*, URLGlob *);
+int glob_next_url(char **, URLGlob *);
+int glob_match_url(char **, char*, URLGlob *);
 void glob_cleanup(URLGlob* glob);
 
 #endif /* HEADER_CURL_TOOL_URLGLOB_H */