~ubuntu-branches/ubuntu/intrepid/curl/intrepid

« back to all changes in this revision

Viewing changes to lib/formdata.c

  • Committer: Bazaar Package Importer
  • Author(s): Matthias Klose
  • Date: 2007-05-16 15:16:54 UTC
  • mfrom: (1.1.7 upstream)
  • Revision ID: james.westby@ubuntu.com-20070516151654-jo48r81zempo1qav
Tags: 7.16.2-3ubuntu1
* Merge with Debian; remaining changes:
  - Drop the stunnel build dependency.

Show diffs side-by-side

added added

removed removed

Lines of Context:
5
5
 *                            | (__| |_| |  _ <| |___
6
6
 *                             \___|\___/|_| \_\_____|
7
7
 *
8
 
 * Copyright (C) 1998 - 2006, Daniel Stenberg, <daniel@haxx.se>, et al.
 
8
 * Copyright (C) 1998 - 2007, Daniel Stenberg, <daniel@haxx.se>, et al.
9
9
 *
10
10
 * This software is licensed as described in the file COPYING, which
11
11
 * you should have received as part of this distribution. The terms
18
18
 * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
19
19
 * KIND, either express or implied.
20
20
 *
21
 
 * $Id: formdata.c,v 1.94 2006-07-27 22:35:09 bagder Exp $
 
21
 * $Id: formdata.c,v 1.99 2007-03-31 21:01:18 bagder Exp $
22
22
 ***************************************************************************/
23
23
 
24
24
/*
25
25
  Debug the form generator stand-alone by compiling this source file with:
26
26
 
27
 
  gcc -DHAVE_CONFIG_H -I../ -g -D_FORM_DEBUG -o formdata -I../include formdata.c strequal.c
 
27
  gcc -DHAVE_CONFIG_H -I../ -g -D_FORM_DEBUG -DCURLDEBUG -o formdata -I../include formdata.c strequal.c memdebug.c mprintf.c strerror.c
28
28
 
29
29
  run the 'formdata' executable the output should end with:
30
30
  All Tests seem to have worked ...
63
63
Content-Disposition: attachment; filename="inet_ntoa_r.h"
64
64
Content-Type: text/plain
65
65
...
66
 
Content-Disposition: attachment; filename="Makefile.b32.resp"
 
66
Content-Disposition: attachment; filename="Makefile.b32"
67
67
Content-Type: text/plain
68
68
...
69
69
 
73
73
Content-Disposition: attachment; filename="inet_ntoa_r.h"
74
74
Content-Type: text/plain
75
75
...
76
 
Content-Disposition: attachment; filename="Makefile.b32.resp"
 
76
Content-Disposition: attachment; filename="Makefile.b32"
77
77
Content-Type: text/plain
78
78
...
79
79
Content-Disposition: attachment; filename="inet_ntoa_r.h"
87
87
Content-Disposition: attachment; filename="inet_ntoa_r.h"
88
88
Content-Type: text/plain
89
89
...
90
 
Content-Disposition: attachment; filename="Makefile.b32.resp"
 
90
Content-Disposition: attachment; filename="Makefile.b32"
91
91
Content-Type: text/plain
92
92
...
93
93
Content-Disposition: attachment; filename="inet_ntoa_r.h"
112
112
#include <string.h>
113
113
#include <stdarg.h>
114
114
#include <time.h>
115
 
#ifdef HAVE_SYS_STAT_H
116
 
#include <sys/stat.h>
117
 
#endif
118
115
#if defined(HAVE_LIBGEN_H) && defined(HAVE_BASENAME)
119
116
#include <libgen.h>
120
117
#endif
 
118
#include "urldata.h" /* for struct SessionHandle */
 
119
#include "easyif.h" /* for Curl_convert_... prototypes */
121
120
#include "formdata.h"
122
121
#include "strequal.h"
123
122
#include "memory.h"
283
282
       text/plain so we don't actually need to set this: */
284
283
    contenttype = HTTPPOST_CONTENTTYPE_DEFAULT;
285
284
 
286
 
  for(i=0; i<sizeof(ctts)/sizeof(ctts[0]); i++) {
287
 
    if(strlen(filename) >= strlen(ctts[i].extension)) {
288
 
      if(strequal(filename +
289
 
                  strlen(filename) - strlen(ctts[i].extension),
290
 
                  ctts[i].extension)) {
291
 
        contenttype = ctts[i].type;
292
 
        break;
 
285
  if(filename) { /* in case a NULL was passed in */
 
286
    for(i=0; i<sizeof(ctts)/sizeof(ctts[0]); i++) {
 
287
      if(strlen(filename) >= strlen(ctts[i].extension)) {
 
288
        if(strequal(filename +
 
289
                    strlen(filename) - strlen(ctts[i].extension),
 
290
                    ctts[i].extension)) {
 
291
          contenttype = ctts[i].type;
 
292
          break;
 
293
        }
293
294
      }
294
295
    }
295
296
  }
316
317
 
317
318
  if (buffer_length)
318
319
    length = buffer_length;
319
 
  else {
 
320
  else if(src) {
320
321
    length = strlen(src);
321
322
    add = TRUE;
322
323
  }
 
324
  else
 
325
    /* no length and a NULL src pointer! */
 
326
    return strdup((char *)"");
 
327
 
323
328
  buffer = (char*)malloc(length+add);
324
329
  if (!buffer)
325
330
    return NULL; /* fail */
452
457
       * Set the Name property.
453
458
       */
454
459
    case CURLFORM_PTRNAME:
 
460
#ifdef CURL_DOES_CONVERSIONS
 
461
      /* treat CURLFORM_PTR like CURLFORM_COPYNAME so we'll
 
462
         have safe memory for the eventual conversion */
 
463
#else
455
464
      current_form->flags |= HTTPPOST_PTRNAME; /* fall through */
 
465
#endif
456
466
    case CURLFORM_COPYNAME:
457
467
      if (current_form->name)
458
468
        return_value = CURL_FORMADD_OPTION_TWICE;
528
538
        if (current_form->value) {
529
539
          if (current_form->flags & HTTPPOST_FILENAME) {
530
540
            if (filename) {
531
 
              if (!(current_form = AddFormInfo(strdup(filename),
532
 
                                               NULL, current_form)))
 
541
              if ((current_form = AddFormInfo(strdup(filename),
 
542
                                              NULL, current_form)) == NULL)
533
543
                return_value = CURL_FORMADD_MEMORY;
534
544
            }
535
545
            else
562
572
        if (current_form->value) {
563
573
          if (current_form->flags & HTTPPOST_BUFFER) {
564
574
            if (filename) {
565
 
              if (!(current_form = AddFormInfo(strdup(filename),
566
 
                                               NULL, current_form)))
 
575
              if ((current_form = AddFormInfo(strdup(filename),
 
576
                                              NULL, current_form)) == NULL)
567
577
                return_value = CURL_FORMADD_MEMORY;
568
578
            }
569
579
            else
614
624
        if (current_form->contenttype) {
615
625
          if (current_form->flags & HTTPPOST_FILENAME) {
616
626
            if (contenttype) {
617
 
              if (!(current_form = AddFormInfo(NULL,
618
 
                                               strdup(contenttype),
619
 
                                               current_form)))
 
627
              if ((current_form = AddFormInfo(NULL,
 
628
                                              strdup(contenttype),
 
629
                                              current_form)) == NULL)
620
630
                return_value = CURL_FORMADD_MEMORY;
621
631
            }
622
632
            else
835
845
    *formp = newform;
836
846
 
837
847
  if (size) {
838
 
    if(type == FORM_DATA)
 
848
    if((type == FORM_DATA) || (type == FORM_CONTENT))
839
849
      *size += length;
840
850
    else {
841
851
      /* Since this is a file to be uploaded here, add the size of the actual
872
882
 * Curl_formclean() is used from http.c, this cleans a built FormData linked
873
883
 * list
874
884
 */
875
 
void Curl_formclean(struct FormData *form)
 
885
void Curl_formclean(struct FormData **form_ptr)
 
886
{
 
887
  struct FormData *next, *form;
 
888
 
 
889
  form = *form_ptr;
 
890
  if(!form)
 
891
    return;
 
892
 
 
893
  do {
 
894
    next=form->next;  /* the following form line */
 
895
    free(form->line); /* free the line */
 
896
    free(form);       /* free the struct */
 
897
 
 
898
  } while ((form = next) != NULL); /* continue */
 
899
 
 
900
  *form_ptr = NULL;
 
901
}
 
902
 
 
903
#ifdef CURL_DOES_CONVERSIONS
 
904
/*
 
905
 * Curl_formcovert() is used from http.c, this converts any
 
906
   form items that need to be sent in the network encoding.
 
907
   Returns CURLE_OK on success.
 
908
 */
 
909
CURLcode Curl_formconvert(struct SessionHandle *data, struct FormData *form)
876
910
{
877
911
  struct FormData *next;
 
912
  CURLcode rc;
878
913
 
879
914
  if(!form)
880
 
    return;
 
915
    return CURLE_OK;
 
916
 
 
917
  if(!data)
 
918
    return CURLE_BAD_FUNCTION_ARGUMENT;
881
919
 
882
920
  do {
883
921
    next=form->next;  /* the following form line */
884
 
    free(form->line); /* free the line */
885
 
    free(form);       /* free the struct */
886
 
 
887
 
  } while((form=next)); /* continue */
 
922
    if (form->type == FORM_DATA) {
 
923
      rc = Curl_convert_to_network(data, form->line, form->length);
 
924
      /* Curl_convert_to_network calls failf if unsuccessful */
 
925
      if (rc != CURLE_OK)
 
926
        return rc;
 
927
    }
 
928
  } while ((form = next) != NULL); /* continue */
 
929
  return CURLE_OK;
888
930
}
 
931
#endif /* CURL_DOES_CONVERSIONS */
889
932
 
890
933
/*
891
934
 * curl_formget()
917
960
          if (temp.fp) {
918
961
            fclose(temp.fp);
919
962
          }
920
 
          Curl_formclean(data);
 
963
          Curl_formclean(&data);
921
964
          return -1;
922
965
        }
923
966
      } while (read == sizeof(buffer));
924
967
    } else {
925
968
      if (ptr->length != append(arg, ptr->line, ptr->length)) {
926
 
        Curl_formclean(data);
 
969
        Curl_formclean(&data);
927
970
        return -1;
928
971
      }
929
972
    }
930
973
  }
931
 
  Curl_formclean(data);
 
974
  Curl_formclean(&data);
932
975
  return 0;
933
976
}
934
977
 
961
1004
      free(form->showfilename); /* free the faked file name */
962
1005
    free(form);       /* free the struct */
963
1006
 
964
 
  } while((form=next)); /* continue */
 
1007
  } while ((form = next) != NULL); /* continue */
965
1008
}
966
1009
 
967
1010
#ifndef HAVE_BASENAME
1179
1222
        curList = curList->next;
1180
1223
      }
1181
1224
      if (result) {
1182
 
        Curl_formclean(firstform);
 
1225
        Curl_formclean(&firstform);
1183
1226
        free(boundary);
1184
1227
        return result;
1185
1228
      }
1194
1237
      if(file->contenttype &&
1195
1238
         !checkprefix("text/", file->contenttype)) {
1196
1239
        /* this is not a text content, mention our binary encoding */
1197
 
        size += AddFormData(&form, "\r\nContent-Transfer-Encoding: binary", 0);
 
1240
        result = AddFormDataf(&form, &size,
 
1241
                              "\r\nContent-Transfer-Encoding: binary");
 
1242
        if (result)
 
1243
          break;
1198
1244
      }
1199
1245
#endif
1200
1246
 
1231
1277
             */
1232
1278
            size_t nread;
1233
1279
            char buffer[512];
1234
 
            while((nread = fread(buffer, 1, sizeof(buffer), fileread))) {
1235
 
              result = AddFormData(&form, FORM_DATA, buffer, nread, &size);
 
1280
            while ((nread = fread(buffer, 1, sizeof(buffer), fileread)) != 0) {
 
1281
              result = AddFormData(&form, FORM_CONTENT, buffer, nread, &size);
1236
1282
              if (result)
1237
1283
                break;
1238
1284
            }
1239
1285
          }
1240
1286
 
1241
1287
          if (result) {
1242
 
            Curl_formclean(firstform);
 
1288
            Curl_formclean(&firstform);
1243
1289
            free(boundary);
1244
1290
            return result;
1245
1291
          }
1246
1292
 
1247
1293
        }
1248
1294
        else {
1249
 
          Curl_formclean(firstform);
 
1295
#ifdef _FORM_DEBUG
 
1296
          fprintf(stderr,
 
1297
                  "\n==> Curl_getFormData couldn't open/read \"%s\"\n",
 
1298
                  file->contents);
 
1299
#endif
 
1300
          Curl_formclean(&firstform);
1250
1301
          free(boundary);
1251
1302
          *finalform = NULL;
1252
1303
          return CURLE_READ_ERROR;
1255
1306
      }
1256
1307
      else if (post->flags & HTTPPOST_BUFFER) {
1257
1308
        /* include contents of buffer */
1258
 
        result = AddFormData(&form, FORM_DATA, post->buffer,
 
1309
        result = AddFormData(&form, FORM_CONTENT, post->buffer,
1259
1310
                             post->bufferlength, &size);
1260
1311
          if (result)
1261
1312
            break;
1263
1314
 
1264
1315
      else {
1265
1316
        /* include the contents we got */
1266
 
        result = AddFormData(&form, FORM_DATA, post->contents,
 
1317
        result = AddFormData(&form, FORM_CONTENT, post->contents,
1267
1318
                             post->contentslength, &size);
1268
1319
        if (result)
1269
1320
          break;
1270
1321
      }
1271
 
    } while((file = file->more)); /* for each specified file for this field */
 
1322
    } while ((file = file->more) != NULL); /* for each specified file for this field */
1272
1323
    if (result) {
1273
 
      Curl_formclean(firstform);
 
1324
      Curl_formclean(&firstform);
1274
1325
      free(boundary);
1275
1326
      return result;
1276
1327
    }
1286
1337
        break;
1287
1338
    }
1288
1339
 
1289
 
  } while((post=post->next)); /* for each field */
 
1340
  } while ((post = post->next) != NULL); /* for each field */
1290
1341
  if (result) {
1291
 
    Curl_formclean(firstform);
 
1342
    Curl_formclean(&firstform);
1292
1343
    free(boundary);
1293
1344
    return result;
1294
1345
  }
1298
1349
                       "\r\n--%s--\r\n",
1299
1350
                       boundary);
1300
1351
  if (result) {
1301
 
    Curl_formclean(firstform);
 
1352
    Curl_formclean(&firstform);
1302
1353
    free(boundary);
1303
1354
    return result;
1304
1355
  }
1397
1448
 
1398
1449
    form->data = form->data->next; /* advance */
1399
1450
 
1400
 
  } while(form->data && (form->data->type == FORM_DATA));
 
1451
  } while(form->data && (form->data->type != FORM_FILE));
1401
1452
  /* If we got an empty line and we have more data, we proceed to the next
1402
1453
     line immediately to avoid returning zero before we've reached the end.
1403
1454
     This is the bug reported November 22 1999 on curl 6.3. (Daniel) */
1464
1515
  char value5[] = "value for PTRCONTENTS + CONTENTSLENGTH";
1465
1516
  char value6[] = "value for PTRCOTNENTS + CONTENTSLENGTH + CONTENTTYPE";
1466
1517
  char value7[] = "inet_ntoa_r.h";
1467
 
  char value8[] = "Makefile.b32.resp";
 
1518
  char value8[] = "Makefile.b32";
1468
1519
  char type2[] = "image/gif";
1469
1520
  char type6[] = "text/plain";
1470
1521
  char type7[] = "text/html";
1473
1524
  int value5length = strlen(value4);
1474
1525
  int value6length = strlen(value5);
1475
1526
  int errors = 0;
1476
 
  int size;
 
1527
  CURLcode rc;
 
1528
  size_t size;
1477
1529
  size_t nread;
1478
1530
  char buffer[4096];
1479
1531
  struct curl_httppost *httppost=NULL;
1549
1601
                  CURLFORM_END))
1550
1602
    ++errors;
1551
1603
 
1552
 
  form=Curl_getFormData(httppost, &size);
 
1604
  rc = Curl_getFormData(&form, httppost, NULL, &size);
 
1605
  if(rc != CURLE_OK) {
 
1606
    if(rc != CURLE_READ_ERROR) {
 
1607
      const char *errortext = curl_easy_strerror(rc);
 
1608
      fprintf(stdout, "\n==> Curl_getFormData error: %s\n", errortext);
 
1609
    }
 
1610
    return 0;
 
1611
  }
1553
1612
 
1554
1613
  Curl_FormInit(&formread, form);
1555
1614
 
1557
1616
    nread = Curl_FormReader(buffer, 1, sizeof(buffer),
1558
1617
                            (FILE *)&formread);
1559
1618
 
1560
 
    if(-1 == nread)
 
1619
    if(nread < 1)
1561
1620
      break;
1562
1621
    fwrite(buffer, nread, 1, stdout);
1563
1622
  } while(1);