Annotation of embedaddon/curl/src/tool_setopt.c, revision 1.1
1.1 ! misho 1: /***************************************************************************
! 2: * _ _ ____ _
! 3: * Project ___| | | | _ \| |
! 4: * / __| | | | |_) | |
! 5: * | (__| |_| | _ <| |___
! 6: * \___|\___/|_| \_\_____|
! 7: *
! 8: * Copyright (C) 1998 - 2020, Daniel Stenberg, <daniel@haxx.se>, et al.
! 9: *
! 10: * This software is licensed as described in the file COPYING, which
! 11: * you should have received as part of this distribution. The terms
! 12: * are also available at https://curl.haxx.se/docs/copyright.html.
! 13: *
! 14: * You may opt to use, copy, modify, merge, publish, distribute and/or sell
! 15: * copies of the Software, and permit persons to whom the Software is
! 16: * furnished to do so, under the terms of the COPYING file.
! 17: *
! 18: * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
! 19: * KIND, either express or implied.
! 20: *
! 21: ***************************************************************************/
! 22: #include "tool_setup.h"
! 23:
! 24: #ifndef CURL_DISABLE_LIBCURL_OPTION
! 25:
! 26: #define ENABLE_CURLX_PRINTF
! 27: /* use our own printf() functions */
! 28: #include "curlx.h"
! 29:
! 30: #include "tool_cfgable.h"
! 31: #include "tool_easysrc.h"
! 32: #include "tool_setopt.h"
! 33: #include "tool_convert.h"
! 34:
! 35: #include "memdebug.h" /* keep this as LAST include */
! 36:
! 37: /* Lookup tables for converting setopt values back to symbols */
! 38: /* For enums, values may be in any order. */
! 39: /* For bit masks, put combinations first, then single bits, */
! 40: /* and finally any "NONE" value. */
! 41:
! 42: #define NV(e) {#e, e}
! 43: #define NV1(e, v) {#e, (v)}
! 44: #define NVEND {NULL, 0} /* sentinel to mark end of list */
! 45:
! 46: const NameValue setopt_nv_CURLPROXY[] = {
! 47: NV(CURLPROXY_HTTP),
! 48: NV(CURLPROXY_HTTP_1_0),
! 49: NV(CURLPROXY_HTTPS),
! 50: NV(CURLPROXY_SOCKS4),
! 51: NV(CURLPROXY_SOCKS5),
! 52: NV(CURLPROXY_SOCKS4A),
! 53: NV(CURLPROXY_SOCKS5_HOSTNAME),
! 54: NVEND,
! 55: };
! 56:
! 57: const NameValue setopt_nv_CURL_SOCKS_PROXY[] = {
! 58: NV(CURLPROXY_SOCKS4),
! 59: NV(CURLPROXY_SOCKS5),
! 60: NV(CURLPROXY_SOCKS4A),
! 61: NV(CURLPROXY_SOCKS5_HOSTNAME),
! 62: NVEND,
! 63: };
! 64:
! 65: const NameValueUnsigned setopt_nv_CURLAUTH[] = {
! 66: NV(CURLAUTH_ANY), /* combination */
! 67: NV(CURLAUTH_ANYSAFE), /* combination */
! 68: NV(CURLAUTH_BASIC),
! 69: NV(CURLAUTH_DIGEST),
! 70: NV(CURLAUTH_GSSNEGOTIATE),
! 71: NV(CURLAUTH_NTLM),
! 72: NV(CURLAUTH_DIGEST_IE),
! 73: NV(CURLAUTH_NTLM_WB),
! 74: NV(CURLAUTH_ONLY),
! 75: NV(CURLAUTH_NONE),
! 76: NVEND,
! 77: };
! 78:
! 79: const NameValue setopt_nv_CURL_HTTP_VERSION[] = {
! 80: NV(CURL_HTTP_VERSION_NONE),
! 81: NV(CURL_HTTP_VERSION_1_0),
! 82: NV(CURL_HTTP_VERSION_1_1),
! 83: NV(CURL_HTTP_VERSION_2_0),
! 84: NV(CURL_HTTP_VERSION_2TLS),
! 85: NV(CURL_HTTP_VERSION_3),
! 86: NVEND,
! 87: };
! 88:
! 89: const NameValue setopt_nv_CURL_SSLVERSION[] = {
! 90: NV(CURL_SSLVERSION_DEFAULT),
! 91: NV(CURL_SSLVERSION_TLSv1),
! 92: NV(CURL_SSLVERSION_SSLv2),
! 93: NV(CURL_SSLVERSION_SSLv3),
! 94: NV(CURL_SSLVERSION_TLSv1_0),
! 95: NV(CURL_SSLVERSION_TLSv1_1),
! 96: NV(CURL_SSLVERSION_TLSv1_2),
! 97: NV(CURL_SSLVERSION_TLSv1_3),
! 98: NVEND,
! 99: };
! 100:
! 101: const NameValue setopt_nv_CURL_TIMECOND[] = {
! 102: NV(CURL_TIMECOND_IFMODSINCE),
! 103: NV(CURL_TIMECOND_IFUNMODSINCE),
! 104: NV(CURL_TIMECOND_LASTMOD),
! 105: NV(CURL_TIMECOND_NONE),
! 106: NVEND,
! 107: };
! 108:
! 109: const NameValue setopt_nv_CURLFTPSSL_CCC[] = {
! 110: NV(CURLFTPSSL_CCC_NONE),
! 111: NV(CURLFTPSSL_CCC_PASSIVE),
! 112: NV(CURLFTPSSL_CCC_ACTIVE),
! 113: NVEND,
! 114: };
! 115:
! 116: const NameValue setopt_nv_CURLUSESSL[] = {
! 117: NV(CURLUSESSL_NONE),
! 118: NV(CURLUSESSL_TRY),
! 119: NV(CURLUSESSL_CONTROL),
! 120: NV(CURLUSESSL_ALL),
! 121: NVEND,
! 122: };
! 123:
! 124: const NameValueUnsigned setopt_nv_CURLSSLOPT[] = {
! 125: NV(CURLSSLOPT_ALLOW_BEAST),
! 126: NV(CURLSSLOPT_NO_REVOKE),
! 127: NV(CURLSSLOPT_NO_PARTIALCHAIN),
! 128: NV(CURLSSLOPT_REVOKE_BEST_EFFORT),
! 129: NVEND,
! 130: };
! 131:
! 132: const NameValue setopt_nv_CURL_NETRC[] = {
! 133: NV(CURL_NETRC_IGNORED),
! 134: NV(CURL_NETRC_OPTIONAL),
! 135: NV(CURL_NETRC_REQUIRED),
! 136: NVEND,
! 137: };
! 138:
! 139: /* These mappings essentially triplicated - see
! 140: * tool_libinfo.c and tool_paramhlp.c */
! 141: const NameValue setopt_nv_CURLPROTO[] = {
! 142: NV(CURLPROTO_ALL), /* combination */
! 143: NV(CURLPROTO_DICT),
! 144: NV(CURLPROTO_FILE),
! 145: NV(CURLPROTO_FTP),
! 146: NV(CURLPROTO_FTPS),
! 147: NV(CURLPROTO_GOPHER),
! 148: NV(CURLPROTO_HTTP),
! 149: NV(CURLPROTO_HTTPS),
! 150: NV(CURLPROTO_IMAP),
! 151: NV(CURLPROTO_IMAPS),
! 152: NV(CURLPROTO_LDAP),
! 153: NV(CURLPROTO_LDAPS),
! 154: NV(CURLPROTO_POP3),
! 155: NV(CURLPROTO_POP3S),
! 156: NV(CURLPROTO_RTSP),
! 157: NV(CURLPROTO_SCP),
! 158: NV(CURLPROTO_SFTP),
! 159: NV(CURLPROTO_SMB),
! 160: NV(CURLPROTO_SMBS),
! 161: NV(CURLPROTO_SMTP),
! 162: NV(CURLPROTO_SMTPS),
! 163: NV(CURLPROTO_TELNET),
! 164: NV(CURLPROTO_TFTP),
! 165: NVEND,
! 166: };
! 167:
! 168: /* These options have non-zero default values. */
! 169: static const NameValue setopt_nv_CURLNONZERODEFAULTS[] = {
! 170: NV1(CURLOPT_SSL_VERIFYPEER, 1),
! 171: NV1(CURLOPT_SSL_VERIFYHOST, 1),
! 172: NV1(CURLOPT_SSL_ENABLE_NPN, 1),
! 173: NV1(CURLOPT_SSL_ENABLE_ALPN, 1),
! 174: NV1(CURLOPT_TCP_NODELAY, 1),
! 175: NV1(CURLOPT_PROXY_SSL_VERIFYPEER, 1),
! 176: NV1(CURLOPT_PROXY_SSL_VERIFYHOST, 1),
! 177: NV1(CURLOPT_SOCKS5_AUTH, 1),
! 178: NVEND
! 179: };
! 180:
! 181: /* Format and add code; jump to nomem on malloc error */
! 182: #define ADD(args) do { \
! 183: ret = easysrc_add args; \
! 184: if(ret) \
! 185: goto nomem; \
! 186: } while(0)
! 187: #define ADDF(args) do { \
! 188: ret = easysrc_addf args; \
! 189: if(ret) \
! 190: goto nomem; \
! 191: } while(0)
! 192: #define NULL_CHECK(p) do { \
! 193: if(!p) { \
! 194: ret = CURLE_OUT_OF_MEMORY; \
! 195: goto nomem; \
! 196: } \
! 197: } while(0)
! 198:
! 199: #define DECL0(s) ADD((&easysrc_decl, s))
! 200: #define DECL1(f,a) ADDF((&easysrc_decl, f,a))
! 201:
! 202: #define DATA0(s) ADD((&easysrc_data, s))
! 203: #define DATA1(f,a) ADDF((&easysrc_data, f,a))
! 204: #define DATA2(f,a,b) ADDF((&easysrc_data, f,a,b))
! 205: #define DATA3(f,a,b,c) ADDF((&easysrc_data, f,a,b,c))
! 206:
! 207: #define CODE0(s) ADD((&easysrc_code, s))
! 208: #define CODE1(f,a) ADDF((&easysrc_code, f,a))
! 209: #define CODE2(f,a,b) ADDF((&easysrc_code, f,a,b))
! 210: #define CODE3(f,a,b,c) ADDF((&easysrc_code, f,a,b,c))
! 211:
! 212: #define CLEAN0(s) ADD((&easysrc_clean, s))
! 213: #define CLEAN1(f,a) ADDF((&easysrc_clean, f,a))
! 214:
! 215: #define REM0(s) ADD((&easysrc_toohard, s))
! 216: #define REM1(f,a) ADDF((&easysrc_toohard, f,a))
! 217: #define REM2(f,a,b) ADDF((&easysrc_toohard, f,a,b))
! 218:
! 219: /* Escape string to C string syntax. Return NULL if out of memory.
! 220: * Is this correct for those wacky EBCDIC guys? */
! 221: static char *c_escape(const char *str, size_t len)
! 222: {
! 223: const char *s;
! 224: unsigned char c;
! 225: char *escaped, *e;
! 226:
! 227: if(len == CURL_ZERO_TERMINATED)
! 228: len = strlen(str);
! 229:
! 230: /* Check for possible overflow. */
! 231: if(len > (~(size_t) 0) / 4)
! 232: return NULL;
! 233:
! 234: /* Allocate space based on worst-case */
! 235: escaped = malloc(4 * len + 1);
! 236: if(!escaped)
! 237: return NULL;
! 238:
! 239: e = escaped;
! 240: for(s = str; (c = *s) != '\0'; s++) {
! 241: if(c == '\n') {
! 242: strcpy(e, "\\n");
! 243: e += 2;
! 244: }
! 245: else if(c == '\r') {
! 246: strcpy(e, "\\r");
! 247: e += 2;
! 248: }
! 249: else if(c == '\t') {
! 250: strcpy(e, "\\t");
! 251: e += 2;
! 252: }
! 253: else if(c == '\\') {
! 254: strcpy(e, "\\\\");
! 255: e += 2;
! 256: }
! 257: else if(c == '"') {
! 258: strcpy(e, "\\\"");
! 259: e += 2;
! 260: }
! 261: else if(! isprint(c)) {
! 262: msnprintf(e, 5, "\\%03o", (unsigned)c);
! 263: e += 4;
! 264: }
! 265: else
! 266: *e++ = c;
! 267: }
! 268: *e = '\0';
! 269: return escaped;
! 270: }
! 271:
! 272: /* setopt wrapper for enum types */
! 273: CURLcode tool_setopt_enum(CURL *curl, struct GlobalConfig *config,
! 274: const char *name, CURLoption tag,
! 275: const NameValue *nvlist, long lval)
! 276: {
! 277: CURLcode ret = CURLE_OK;
! 278: bool skip = FALSE;
! 279:
! 280: ret = curl_easy_setopt(curl, tag, lval);
! 281: if(!lval)
! 282: skip = TRUE;
! 283:
! 284: if(config->libcurl && !skip && !ret) {
! 285: /* we only use this for real if --libcurl was used */
! 286: const NameValue *nv = NULL;
! 287: for(nv = nvlist; nv->name; nv++) {
! 288: if(nv->value == lval)
! 289: break; /* found it */
! 290: }
! 291: if(! nv->name) {
! 292: /* If no definition was found, output an explicit value.
! 293: * This could happen if new values are defined and used
! 294: * but the NameValue list is not updated. */
! 295: CODE2("curl_easy_setopt(hnd, %s, %ldL);", name, lval);
! 296: }
! 297: else {
! 298: CODE2("curl_easy_setopt(hnd, %s, (long)%s);", name, nv->name);
! 299: }
! 300: }
! 301:
! 302: nomem:
! 303: return ret;
! 304: }
! 305:
! 306: /* setopt wrapper for flags */
! 307: CURLcode tool_setopt_flags(CURL *curl, struct GlobalConfig *config,
! 308: const char *name, CURLoption tag,
! 309: const NameValue *nvlist, long lval)
! 310: {
! 311: CURLcode ret = CURLE_OK;
! 312: bool skip = FALSE;
! 313:
! 314: ret = curl_easy_setopt(curl, tag, lval);
! 315: if(!lval)
! 316: skip = TRUE;
! 317:
! 318: if(config->libcurl && !skip && !ret) {
! 319: /* we only use this for real if --libcurl was used */
! 320: char preamble[80]; /* should accommodate any symbol name */
! 321: long rest = lval; /* bits not handled yet */
! 322: const NameValue *nv = NULL;
! 323: msnprintf(preamble, sizeof(preamble),
! 324: "curl_easy_setopt(hnd, %s, ", name);
! 325: for(nv = nvlist; nv->name; nv++) {
! 326: if((nv->value & ~ rest) == 0) {
! 327: /* all value flags contained in rest */
! 328: rest &= ~ nv->value; /* remove bits handled here */
! 329: CODE3("%s(long)%s%s",
! 330: preamble, nv->name, rest ? " |" : ");");
! 331: if(!rest)
! 332: break; /* handled them all */
! 333: /* replace with all spaces for continuation line */
! 334: msnprintf(preamble, sizeof(preamble), "%*s", strlen(preamble), "");
! 335: }
! 336: }
! 337: /* If any bits have no definition, output an explicit value.
! 338: * This could happen if new bits are defined and used
! 339: * but the NameValue list is not updated. */
! 340: if(rest)
! 341: CODE2("%s%ldL);", preamble, rest);
! 342: }
! 343:
! 344: nomem:
! 345: return ret;
! 346: }
! 347:
! 348: /* setopt wrapper for bitmasks */
! 349: CURLcode tool_setopt_bitmask(CURL *curl, struct GlobalConfig *config,
! 350: const char *name, CURLoption tag,
! 351: const NameValueUnsigned *nvlist,
! 352: long lval)
! 353: {
! 354: CURLcode ret = CURLE_OK;
! 355: bool skip = FALSE;
! 356:
! 357: ret = curl_easy_setopt(curl, tag, lval);
! 358: if(!lval)
! 359: skip = TRUE;
! 360:
! 361: if(config->libcurl && !skip && !ret) {
! 362: /* we only use this for real if --libcurl was used */
! 363: char preamble[80];
! 364: unsigned long rest = (unsigned long)lval;
! 365: const NameValueUnsigned *nv = NULL;
! 366: msnprintf(preamble, sizeof(preamble),
! 367: "curl_easy_setopt(hnd, %s, ", name);
! 368: for(nv = nvlist; nv->name; nv++) {
! 369: if((nv->value & ~ rest) == 0) {
! 370: /* all value flags contained in rest */
! 371: rest &= ~ nv->value; /* remove bits handled here */
! 372: CODE3("%s(long)%s%s",
! 373: preamble, nv->name, rest ? " |" : ");");
! 374: if(!rest)
! 375: break; /* handled them all */
! 376: /* replace with all spaces for continuation line */
! 377: msnprintf(preamble, sizeof(preamble), "%*s", strlen(preamble), "");
! 378: }
! 379: }
! 380: /* If any bits have no definition, output an explicit value.
! 381: * This could happen if new bits are defined and used
! 382: * but the NameValue list is not updated. */
! 383: if(rest)
! 384: CODE2("%s%luUL);", preamble, rest);
! 385: }
! 386:
! 387: nomem:
! 388: return ret;
! 389: }
! 390:
! 391: /* Generate code for a struct curl_slist. */
! 392: static CURLcode libcurl_generate_slist(struct curl_slist *slist, int *slistno)
! 393: {
! 394: CURLcode ret = CURLE_OK;
! 395: char *escaped = NULL;
! 396:
! 397: /* May need several slist variables, so invent name */
! 398: *slistno = ++easysrc_slist_count;
! 399:
! 400: DECL1("struct curl_slist *slist%d;", *slistno);
! 401: DATA1("slist%d = NULL;", *slistno);
! 402: CLEAN1("curl_slist_free_all(slist%d);", *slistno);
! 403: CLEAN1("slist%d = NULL;", *slistno);
! 404: for(; slist; slist = slist->next) {
! 405: Curl_safefree(escaped);
! 406: escaped = c_escape(slist->data, CURL_ZERO_TERMINATED);
! 407: if(!escaped)
! 408: return CURLE_OUT_OF_MEMORY;
! 409: DATA3("slist%d = curl_slist_append(slist%d, \"%s\");",
! 410: *slistno, *slistno, escaped);
! 411: }
! 412:
! 413: nomem:
! 414: Curl_safefree(escaped);
! 415: return ret;
! 416: }
! 417:
! 418: static CURLcode libcurl_generate_mime(CURL *curl,
! 419: struct GlobalConfig *config,
! 420: tool_mime *toolmime,
! 421: int *mimeno); /* Forward. */
! 422:
! 423: /* Wrapper to generate source code for a mime part. */
! 424: static CURLcode libcurl_generate_mime_part(CURL *curl,
! 425: struct GlobalConfig *config,
! 426: tool_mime *part,
! 427: int mimeno)
! 428: {
! 429: CURLcode ret = CURLE_OK;
! 430: int submimeno = 0;
! 431: char *escaped = NULL;
! 432: const char *data = NULL;
! 433: const char *filename = part->filename;
! 434:
! 435: /* Parts are linked in reverse order. */
! 436: if(part->prev) {
! 437: ret = libcurl_generate_mime_part(curl, config, part->prev, mimeno);
! 438: if(ret)
! 439: return ret;
! 440: }
! 441:
! 442: /* Create the part. */
! 443: CODE2("part%d = curl_mime_addpart(mime%d);", mimeno, mimeno);
! 444:
! 445: switch(part->kind) {
! 446: case TOOLMIME_PARTS:
! 447: ret = libcurl_generate_mime(curl, config, part, &submimeno);
! 448: if(!ret) {
! 449: CODE2("curl_mime_subparts(part%d, mime%d);", mimeno, submimeno);
! 450: CODE1("mime%d = NULL;", submimeno); /* Avoid freeing in CLEAN. */
! 451: }
! 452: break;
! 453:
! 454: case TOOLMIME_DATA:
! 455: #ifdef CURL_DOES_CONVERSIONS
! 456: /* Data will be set in ASCII, thus issue a comment with clear text. */
! 457: escaped = c_escape(part->data, CURL_ZERO_TERMINATED);
! 458: NULL_CHECK(escaped);
! 459: CODE1("/* \"%s\" */", escaped);
! 460:
! 461: /* Our data is always textual: convert it to ASCII. */
! 462: {
! 463: size_t size = strlen(part->data);
! 464: char *cp = malloc(size + 1);
! 465:
! 466: NULL_CHECK(cp);
! 467: memcpy(cp, part->data, size + 1);
! 468: ret = convert_to_network(cp, size);
! 469: data = cp;
! 470: }
! 471: #else
! 472: data = part->data;
! 473: #endif
! 474: if(!ret) {
! 475: Curl_safefree(escaped);
! 476: escaped = c_escape(data, CURL_ZERO_TERMINATED);
! 477: NULL_CHECK(escaped);
! 478: CODE2("curl_mime_data(part%d, \"%s\", CURL_ZERO_TERMINATED);",
! 479: mimeno, escaped);
! 480: }
! 481: break;
! 482:
! 483: case TOOLMIME_FILE:
! 484: case TOOLMIME_FILEDATA:
! 485: escaped = c_escape(part->data, CURL_ZERO_TERMINATED);
! 486: NULL_CHECK(escaped);
! 487: CODE2("curl_mime_filedata(part%d, \"%s\");", mimeno, escaped);
! 488: if(part->kind == TOOLMIME_FILEDATA && !filename) {
! 489: CODE1("curl_mime_filename(part%d, NULL);", mimeno);
! 490: }
! 491: break;
! 492:
! 493: case TOOLMIME_STDIN:
! 494: if(!filename)
! 495: filename = "-";
! 496: /* FALLTHROUGH */
! 497: case TOOLMIME_STDINDATA:
! 498: /* Can only be reading stdin in the current context. */
! 499: CODE1("curl_mime_data_cb(part%d, -1, (curl_read_callback) fread, \\",
! 500: mimeno);
! 501: CODE0(" (curl_seek_callback) fseek, NULL, stdin);");
! 502: break;
! 503: default:
! 504: /* Other cases not possible in this context. */
! 505: break;
! 506: }
! 507:
! 508: if(!ret && part->encoder) {
! 509: Curl_safefree(escaped);
! 510: escaped = c_escape(part->encoder, CURL_ZERO_TERMINATED);
! 511: NULL_CHECK(escaped);
! 512: CODE2("curl_mime_encoder(part%d, \"%s\");", mimeno, escaped);
! 513: }
! 514:
! 515: if(!ret && filename) {
! 516: Curl_safefree(escaped);
! 517: escaped = c_escape(filename, CURL_ZERO_TERMINATED);
! 518: NULL_CHECK(escaped);
! 519: CODE2("curl_mime_filename(part%d, \"%s\");", mimeno, escaped);
! 520: }
! 521:
! 522: if(!ret && part->name) {
! 523: Curl_safefree(escaped);
! 524: escaped = c_escape(part->name, CURL_ZERO_TERMINATED);
! 525: NULL_CHECK(escaped);
! 526: CODE2("curl_mime_name(part%d, \"%s\");", mimeno, escaped);
! 527: }
! 528:
! 529: if(!ret && part->type) {
! 530: Curl_safefree(escaped);
! 531: escaped = c_escape(part->type, CURL_ZERO_TERMINATED);
! 532: NULL_CHECK(escaped);
! 533: CODE2("curl_mime_type(part%d, \"%s\");", mimeno, escaped);
! 534: }
! 535:
! 536: if(!ret && part->headers) {
! 537: int slistno;
! 538:
! 539: ret = libcurl_generate_slist(part->headers, &slistno);
! 540: if(!ret) {
! 541: CODE2("curl_mime_headers(part%d, slist%d, 1);", mimeno, slistno);
! 542: CODE1("slist%d = NULL;", slistno); /* Prevent CLEANing. */
! 543: }
! 544: }
! 545:
! 546: nomem:
! 547: #ifdef CURL_DOES_CONVERSIONS
! 548: if(data)
! 549: free((char *) data);
! 550: #endif
! 551:
! 552: Curl_safefree(escaped);
! 553: return ret;
! 554: }
! 555:
! 556: /* Wrapper to generate source code for a mime structure. */
! 557: static CURLcode libcurl_generate_mime(CURL *curl,
! 558: struct GlobalConfig *config,
! 559: tool_mime *toolmime,
! 560: int *mimeno)
! 561: {
! 562: CURLcode ret = CURLE_OK;
! 563:
! 564: /* May need several mime variables, so invent name. */
! 565: *mimeno = ++easysrc_mime_count;
! 566: DECL1("curl_mime *mime%d;", *mimeno);
! 567: DATA1("mime%d = NULL;", *mimeno);
! 568: CODE1("mime%d = curl_mime_init(hnd);", *mimeno);
! 569: CLEAN1("curl_mime_free(mime%d);", *mimeno);
! 570: CLEAN1("mime%d = NULL;", *mimeno);
! 571:
! 572: if(toolmime->subparts) {
! 573: DECL1("curl_mimepart *part%d;", *mimeno);
! 574: ret = libcurl_generate_mime_part(curl, config,
! 575: toolmime->subparts, *mimeno);
! 576: }
! 577:
! 578: nomem:
! 579: return ret;
! 580: }
! 581:
! 582: /* setopt wrapper for CURLOPT_MIMEPOST */
! 583: CURLcode tool_setopt_mimepost(CURL *curl, struct GlobalConfig *config,
! 584: const char *name, CURLoption tag,
! 585: curl_mime *mimepost)
! 586: {
! 587: CURLcode ret = curl_easy_setopt(curl, tag, mimepost);
! 588: int mimeno = 0;
! 589:
! 590: if(!ret && config->libcurl) {
! 591: ret = libcurl_generate_mime(curl, config,
! 592: config->current->mimeroot, &mimeno);
! 593:
! 594: if(!ret)
! 595: CODE2("curl_easy_setopt(hnd, %s, mime%d);", name, mimeno);
! 596: }
! 597:
! 598: nomem:
! 599: return ret;
! 600: }
! 601:
! 602: /* setopt wrapper for curl_slist options */
! 603: CURLcode tool_setopt_slist(CURL *curl, struct GlobalConfig *config,
! 604: const char *name, CURLoption tag,
! 605: struct curl_slist *list)
! 606: {
! 607: CURLcode ret = CURLE_OK;
! 608:
! 609: ret = curl_easy_setopt(curl, tag, list);
! 610:
! 611: if(config->libcurl && list && !ret) {
! 612: int i;
! 613:
! 614: ret = libcurl_generate_slist(list, &i);
! 615: if(!ret)
! 616: CODE2("curl_easy_setopt(hnd, %s, slist%d);", name, i);
! 617: }
! 618:
! 619: nomem:
! 620: return ret;
! 621: }
! 622:
! 623: /* generic setopt wrapper for all other options.
! 624: * Some type information is encoded in the tag value. */
! 625: CURLcode tool_setopt(CURL *curl, bool str, struct GlobalConfig *config,
! 626: const char *name, CURLoption tag, ...)
! 627: {
! 628: va_list arg;
! 629: char buf[256];
! 630: const char *value = NULL;
! 631: bool remark = FALSE;
! 632: bool skip = FALSE;
! 633: bool escape = FALSE;
! 634: char *escaped = NULL;
! 635: CURLcode ret = CURLE_OK;
! 636:
! 637: va_start(arg, tag);
! 638:
! 639: if(tag < CURLOPTTYPE_OBJECTPOINT) {
! 640: /* Value is expected to be a long */
! 641: long lval = va_arg(arg, long);
! 642: long defval = 0L;
! 643: const NameValue *nv = NULL;
! 644: for(nv = setopt_nv_CURLNONZERODEFAULTS; nv->name; nv++) {
! 645: if(!strcmp(name, nv->name)) {
! 646: defval = nv->value;
! 647: break; /* found it */
! 648: }
! 649: }
! 650:
! 651: msnprintf(buf, sizeof(buf), "%ldL", lval);
! 652: value = buf;
! 653: ret = curl_easy_setopt(curl, tag, lval);
! 654: if(lval == defval)
! 655: skip = TRUE;
! 656: }
! 657: else if(tag < CURLOPTTYPE_OFF_T) {
! 658: /* Value is some sort of object pointer */
! 659: void *pval = va_arg(arg, void *);
! 660:
! 661: /* function pointers are never printable */
! 662: if(tag >= CURLOPTTYPE_FUNCTIONPOINT) {
! 663: if(pval) {
! 664: value = "functionpointer";
! 665: remark = TRUE;
! 666: }
! 667: else
! 668: skip = TRUE;
! 669: }
! 670:
! 671: else if(pval && str) {
! 672: value = (char *)pval;
! 673: escape = TRUE;
! 674: }
! 675: else if(pval) {
! 676: value = "objectpointer";
! 677: remark = TRUE;
! 678: }
! 679: else
! 680: skip = TRUE;
! 681:
! 682: ret = curl_easy_setopt(curl, tag, pval);
! 683:
! 684: }
! 685: else {
! 686: /* Value is expected to be curl_off_t */
! 687: curl_off_t oval = va_arg(arg, curl_off_t);
! 688: msnprintf(buf, sizeof(buf),
! 689: "(curl_off_t)%" CURL_FORMAT_CURL_OFF_T, oval);
! 690: value = buf;
! 691: ret = curl_easy_setopt(curl, tag, oval);
! 692:
! 693: if(!oval)
! 694: skip = TRUE;
! 695: }
! 696:
! 697: va_end(arg);
! 698:
! 699: if(config->libcurl && !skip && !ret) {
! 700: /* we only use this for real if --libcurl was used */
! 701:
! 702: if(remark)
! 703: REM2("%s set to a %s", name, value);
! 704: else {
! 705: if(escape) {
! 706: escaped = c_escape(value, CURL_ZERO_TERMINATED);
! 707: NULL_CHECK(escaped);
! 708: CODE2("curl_easy_setopt(hnd, %s, \"%s\");", name, escaped);
! 709: }
! 710: else
! 711: CODE2("curl_easy_setopt(hnd, %s, %s);", name, value);
! 712: }
! 713: }
! 714:
! 715: nomem:
! 716: Curl_safefree(escaped);
! 717: return ret;
! 718: }
! 719:
! 720: #else /* CURL_DISABLE_LIBCURL_OPTION */
! 721:
! 722: #include "tool_cfgable.h"
! 723: #include "tool_setopt.h"
! 724:
! 725: #endif /* CURL_DISABLE_LIBCURL_OPTION */
! 726:
! 727: /*
! 728: * tool_setopt_skip() allows the curl tool code to avoid setopt options that
! 729: * are explicitly disabled in the build.
! 730: */
! 731: bool tool_setopt_skip(CURLoption tag)
! 732: {
! 733: #ifdef CURL_DISABLE_PROXY
! 734: #define USED_TAG
! 735: switch(tag) {
! 736: case CURLOPT_HAPROXYPROTOCOL:
! 737: case CURLOPT_HTTPPROXYTUNNEL:
! 738: case CURLOPT_NOPROXY:
! 739: case CURLOPT_PRE_PROXY:
! 740: case CURLOPT_PROXY:
! 741: case CURLOPT_PROXYAUTH:
! 742: case CURLOPT_PROXY_CAINFO:
! 743: case CURLOPT_PROXY_CAPATH:
! 744: case CURLOPT_PROXY_CRLFILE:
! 745: case CURLOPT_PROXYHEADER:
! 746: case CURLOPT_PROXY_KEYPASSWD:
! 747: case CURLOPT_PROXYPASSWORD:
! 748: case CURLOPT_PROXY_PINNEDPUBLICKEY:
! 749: case CURLOPT_PROXYPORT:
! 750: case CURLOPT_PROXY_SERVICE_NAME:
! 751: case CURLOPT_PROXY_SSLCERT:
! 752: case CURLOPT_PROXY_SSLCERTTYPE:
! 753: case CURLOPT_PROXY_SSL_CIPHER_LIST:
! 754: case CURLOPT_PROXY_SSLKEY:
! 755: case CURLOPT_PROXY_SSLKEYTYPE:
! 756: case CURLOPT_PROXY_SSL_OPTIONS:
! 757: case CURLOPT_PROXY_SSL_VERIFYHOST:
! 758: case CURLOPT_PROXY_SSL_VERIFYPEER:
! 759: case CURLOPT_PROXY_SSLVERSION:
! 760: case CURLOPT_PROXY_TLS13_CIPHERS:
! 761: case CURLOPT_PROXY_TLSAUTH_PASSWORD:
! 762: case CURLOPT_PROXY_TLSAUTH_TYPE:
! 763: case CURLOPT_PROXY_TLSAUTH_USERNAME:
! 764: case CURLOPT_PROXY_TRANSFER_MODE:
! 765: case CURLOPT_PROXYTYPE:
! 766: case CURLOPT_PROXYUSERNAME:
! 767: case CURLOPT_PROXYUSERPWD:
! 768: return TRUE;
! 769: default:
! 770: break;
! 771: }
! 772: #endif
! 773: #ifdef CURL_DISABLE_FTP
! 774: #define USED_TAG
! 775: switch(tag) {
! 776: case CURLOPT_FTPPORT:
! 777: case CURLOPT_FTP_ACCOUNT:
! 778: case CURLOPT_FTP_ALTERNATIVE_TO_USER:
! 779: case CURLOPT_FTP_FILEMETHOD:
! 780: case CURLOPT_FTP_SKIP_PASV_IP:
! 781: case CURLOPT_FTP_USE_EPRT:
! 782: case CURLOPT_FTP_USE_EPSV:
! 783: case CURLOPT_FTP_USE_PRET:
! 784: case CURLOPT_KRBLEVEL:
! 785: return TRUE;
! 786: default:
! 787: break;
! 788: }
! 789: #endif
! 790: #ifdef CURL_DISABLE_RTSP
! 791: #define USED_TAG
! 792: switch(tag) {
! 793: case CURLOPT_INTERLEAVEDATA:
! 794: return TRUE;
! 795: default:
! 796: break;
! 797: }
! 798: #endif
! 799: #if defined(CURL_DISABLE_HTTP) || defined(CURL_DISABLE_COOKIES)
! 800: #define USED_TAG
! 801: switch(tag) {
! 802: case CURLOPT_COOKIE:
! 803: case CURLOPT_COOKIEFILE:
! 804: case CURLOPT_COOKIEJAR:
! 805: case CURLOPT_COOKIESESSION:
! 806: return TRUE;
! 807: default:
! 808: break;
! 809: }
! 810: #endif
! 811: #if defined(CURL_DISABLE_TELNET)
! 812: #define USED_TAG
! 813: switch(tag) {
! 814: case CURLOPT_TELNETOPTIONS:
! 815: return TRUE;
! 816: default:
! 817: break;
! 818: }
! 819: #endif
! 820: #ifdef CURL_DISABLE_TFTP
! 821: #define USED_TAG
! 822: switch(tag) {
! 823: case CURLOPT_TFTP_BLKSIZE:
! 824: case CURLOPT_TFTP_NO_OPTIONS:
! 825: return TRUE;
! 826: default:
! 827: break;
! 828: }
! 829: #endif
! 830: #ifdef CURL_DISABLE_NETRC
! 831: #define USED_TAG
! 832: switch(tag) {
! 833: case CURLOPT_NETRC:
! 834: case CURLOPT_NETRC_FILE:
! 835: return TRUE;
! 836: default:
! 837: break;
! 838: }
! 839: #endif
! 840:
! 841: #ifndef USED_TAG
! 842: (void)tag;
! 843: #endif
! 844: return FALSE;
! 845: }
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>