File:  [ELWIX - Embedded LightWeight unIX -] / embedaddon / curl / lib / version.c
Revision 1.1.1.1 (vendor branch): download - view: text, annotated - select for diffs - revision graph
Wed Jun 3 10:01:15 2020 UTC (5 years ago) by misho
Branches: curl, MAIN
CVS tags: v7_70_0p4, HEAD
curl

    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: 
   23: #include "curl_setup.h"
   24: 
   25: #include <curl/curl.h>
   26: #include "urldata.h"
   27: #include "vtls/vtls.h"
   28: #include "http2.h"
   29: #include "vssh/ssh.h"
   30: #include "quic.h"
   31: #include "curl_printf.h"
   32: 
   33: #ifdef USE_ARES
   34: #  if defined(CURL_STATICLIB) && !defined(CARES_STATICLIB) && \
   35:      (defined(WIN32) || defined(__SYMBIAN32__))
   36: #    define CARES_STATICLIB
   37: #  endif
   38: #  include <ares.h>
   39: #endif
   40: 
   41: #ifdef USE_LIBIDN2
   42: #include <idn2.h>
   43: #endif
   44: 
   45: #ifdef USE_LIBPSL
   46: #include <libpsl.h>
   47: #endif
   48: 
   49: #if defined(HAVE_ICONV) && defined(CURL_DOES_CONVERSIONS)
   50: #include <iconv.h>
   51: #endif
   52: 
   53: #ifdef USE_LIBRTMP
   54: #include <librtmp/rtmp.h>
   55: #endif
   56: 
   57: #ifdef HAVE_ZLIB_H
   58: #include <zlib.h>
   59: #ifdef __SYMBIAN32__
   60: /* zlib pollutes the namespace with this definition */
   61: #undef WIN32
   62: #endif
   63: #endif
   64: 
   65: #ifdef HAVE_BROTLI
   66: #include <brotli/decode.h>
   67: #endif
   68: 
   69: #ifdef HAVE_BROTLI
   70: static size_t brotli_version(char *buf, size_t bufsz)
   71: {
   72:   uint32_t brotli_version = BrotliDecoderVersion();
   73:   unsigned int major = brotli_version >> 24;
   74:   unsigned int minor = (brotli_version & 0x00FFFFFF) >> 12;
   75:   unsigned int patch = brotli_version & 0x00000FFF;
   76: 
   77:   return msnprintf(buf, bufsz, "%u.%u.%u", major, minor, patch);
   78: }
   79: #endif
   80: 
   81: /*
   82:  * curl_version() returns a pointer to a static buffer.
   83:  *
   84:  * It is implemented to work multi-threaded by making sure repeated invokes
   85:  * generate the exact same string and never write any temporary data like
   86:  * zeros in the data.
   87:  */
   88: 
   89: #define VERSION_PARTS 14 /* number of substrings we can concatenate */
   90: 
   91: char *curl_version(void)
   92: {
   93:   static char out[300];
   94:   char *outp;
   95:   size_t outlen;
   96:   const char *src[VERSION_PARTS];
   97: #ifdef USE_SSL
   98:   char ssl_version[200];
   99: #endif
  100: #ifdef HAVE_LIBZ
  101:   char z_version[40];
  102: #endif
  103: #ifdef HAVE_BROTLI
  104:   char br_version[40] = "brotli/";
  105: #endif
  106: #ifdef USE_ARES
  107:   char cares_version[40];
  108: #endif
  109: #if defined(USE_LIBIDN2)
  110:   char idn_version[40];
  111: #endif
  112: #ifdef USE_LIBPSL
  113:   char psl_version[40];
  114: #endif
  115: #if defined(HAVE_ICONV) && defined(CURL_DOES_CONVERSIONS)
  116:   char iconv_version[40]="iconv";
  117: #endif
  118: #ifdef USE_SSH
  119:   char ssh_version[40];
  120: #endif
  121: #ifdef USE_NGHTTP2
  122:   char h2_version[40];
  123: #endif
  124: #ifdef ENABLE_QUIC
  125:   char h3_version[40];
  126: #endif
  127: #ifdef USE_LIBRTMP
  128:   char rtmp_version[40];
  129: #endif
  130:   int i = 0;
  131:   int j;
  132: 
  133: #ifdef DEBUGBUILD
  134:   /* Override version string when environment variable CURL_VERSION is set */
  135:   const char *debugversion = getenv("CURL_VERSION");
  136:   if(debugversion) {
  137:     strncpy(out, debugversion, sizeof(out)-1);
  138:     out[sizeof(out)-1] = '\0';
  139:     return out;
  140:   }
  141: #endif
  142: 
  143:   src[i++] = LIBCURL_NAME "/" LIBCURL_VERSION;
  144: #ifdef USE_SSL
  145:   Curl_ssl_version(ssl_version, sizeof(ssl_version));
  146:   src[i++] = ssl_version;
  147: #endif
  148: #ifdef HAVE_LIBZ
  149:   msnprintf(z_version, sizeof(z_version), "zlib/%s", zlibVersion());
  150:   src[i++] = z_version;
  151: #endif
  152: #ifdef HAVE_BROTLI
  153:   brotli_version(&br_version[7], sizeof(br_version) - 7);
  154:   src[i++] = br_version;
  155: #endif
  156: #ifdef USE_ARES
  157:   msnprintf(cares_version, sizeof(cares_version),
  158:             "c-ares/%s", ares_version(NULL));
  159:   src[i++] = cares_version;
  160: #endif
  161: #ifdef USE_LIBIDN2
  162:   msnprintf(idn_version, sizeof(idn_version),
  163:             "libidn2/%s", idn2_check_version(NULL));
  164:   src[i++] = idn_version;
  165: #elif defined(USE_WIN32_IDN)
  166:   src[i++] = (char *)"WinIDN";
  167: #endif
  168: 
  169: #ifdef USE_LIBPSL
  170:   msnprintf(psl_version, sizeof(psl_version), "libpsl/%s", psl_get_version());
  171:   src[i++] = psl_version;
  172: #endif
  173: #if defined(HAVE_ICONV) && defined(CURL_DOES_CONVERSIONS)
  174: #ifdef _LIBICONV_VERSION
  175:   msnprintf(iconv_version, sizeof(iconv_version), "iconv/%d.%d",
  176:             _LIBICONV_VERSION >> 8, _LIBICONV_VERSION & 255);
  177: #else
  178:   /* version unknown, let the default stand */
  179: #endif /* _LIBICONV_VERSION */
  180:   src[i++] = iconv_version;
  181: #endif
  182: #ifdef USE_SSH
  183:   Curl_ssh_version(ssh_version, sizeof(ssh_version));
  184:   src[i++] = ssh_version;
  185: #endif
  186: #ifdef USE_NGHTTP2
  187:   Curl_http2_ver(h2_version, sizeof(h2_version));
  188:   src[i++] = h2_version;
  189: #endif
  190: #ifdef ENABLE_QUIC
  191:   Curl_quic_ver(h3_version, sizeof(h3_version));
  192:   src[i++] = h3_version;
  193: #endif
  194: #ifdef USE_LIBRTMP
  195:   {
  196:     char suff[2];
  197:     if(RTMP_LIB_VERSION & 0xff) {
  198:       suff[0] = (RTMP_LIB_VERSION & 0xff) + 'a' - 1;
  199:       suff[1] = '\0';
  200:     }
  201:     else
  202:       suff[0] = '\0';
  203: 
  204:     msnprintf(rtmp_version, sizeof(rtmp_version), "librtmp/%d.%d%s",
  205:               RTMP_LIB_VERSION >> 16, (RTMP_LIB_VERSION >> 8) & 0xff,
  206:               suff);
  207:     src[i++] = rtmp_version;
  208:   }
  209: #endif
  210: 
  211:   DEBUGASSERT(i <= VERSION_PARTS);
  212: 
  213:   outp = &out[0];
  214:   outlen = sizeof(out);
  215:   for(j = 0; j < i; j++) {
  216:     size_t n = strlen(src[j]);
  217:     /* we need room for a space, the string and the final zero */
  218:     if(outlen <= (n + 2))
  219:       break;
  220:     if(j) {
  221:       /* prepend a space if not the first */
  222:       *outp++ = ' ';
  223:       outlen--;
  224:     }
  225:     memcpy(outp, src[j], n);
  226:     outp += n;
  227:     outlen -= n;
  228:   }
  229:   *outp = 0;
  230: 
  231:   return out;
  232: }
  233: 
  234: /* data for curl_version_info
  235: 
  236:    Keep the list sorted alphabetically. It is also written so that each
  237:    protocol line has its own #if line to make things easier on the eye.
  238:  */
  239: 
  240: static const char * const protocols[] = {
  241: #ifndef CURL_DISABLE_DICT
  242:   "dict",
  243: #endif
  244: #ifndef CURL_DISABLE_FILE
  245:   "file",
  246: #endif
  247: #ifndef CURL_DISABLE_FTP
  248:   "ftp",
  249: #endif
  250: #if defined(USE_SSL) && !defined(CURL_DISABLE_FTP)
  251:   "ftps",
  252: #endif
  253: #ifndef CURL_DISABLE_GOPHER
  254:   "gopher",
  255: #endif
  256: #ifndef CURL_DISABLE_HTTP
  257:   "http",
  258: #endif
  259: #if defined(USE_SSL) && !defined(CURL_DISABLE_HTTP)
  260:   "https",
  261: #endif
  262: #ifndef CURL_DISABLE_IMAP
  263:   "imap",
  264: #endif
  265: #if defined(USE_SSL) && !defined(CURL_DISABLE_IMAP)
  266:   "imaps",
  267: #endif
  268: #ifndef CURL_DISABLE_LDAP
  269:   "ldap",
  270: #if !defined(CURL_DISABLE_LDAPS) && \
  271:     ((defined(USE_OPENLDAP) && defined(USE_SSL)) || \
  272:      (!defined(USE_OPENLDAP) && defined(HAVE_LDAP_SSL)))
  273:   "ldaps",
  274: #endif
  275: #endif
  276: #ifdef CURL_ENABLE_MQTT
  277:   "mqtt",
  278: #endif
  279: #ifndef CURL_DISABLE_POP3
  280:   "pop3",
  281: #endif
  282: #if defined(USE_SSL) && !defined(CURL_DISABLE_POP3)
  283:   "pop3s",
  284: #endif
  285: #ifdef USE_LIBRTMP
  286:   "rtmp",
  287: #endif
  288: #ifndef CURL_DISABLE_RTSP
  289:   "rtsp",
  290: #endif
  291: #if defined(USE_SSH) && !defined(USE_WOLFSSH)
  292:   "scp",
  293: #endif
  294: #ifdef USE_SSH
  295:   "sftp",
  296: #endif
  297: #if !defined(CURL_DISABLE_SMB) && defined(USE_NTLM) && \
  298:    (CURL_SIZEOF_CURL_OFF_T > 4) && \
  299:    (!defined(USE_WINDOWS_SSPI) || defined(USE_WIN32_CRYPTO))
  300:   "smb",
  301: #  ifdef USE_SSL
  302:   "smbs",
  303: #  endif
  304: #endif
  305: #ifndef CURL_DISABLE_SMTP
  306:   "smtp",
  307: #endif
  308: #if defined(USE_SSL) && !defined(CURL_DISABLE_SMTP)
  309:   "smtps",
  310: #endif
  311: #ifndef CURL_DISABLE_TELNET
  312:   "telnet",
  313: #endif
  314: #ifndef CURL_DISABLE_TFTP
  315:   "tftp",
  316: #endif
  317: 
  318:   NULL
  319: };
  320: 
  321: static curl_version_info_data version_info = {
  322:   CURLVERSION_NOW,
  323:   LIBCURL_VERSION,
  324:   LIBCURL_VERSION_NUM,
  325:   OS, /* as found by configure or set by hand at build-time */
  326:   0 /* features is 0 by default */
  327: #ifdef ENABLE_IPV6
  328:   | CURL_VERSION_IPV6
  329: #endif
  330: #ifdef USE_SSL
  331:   | CURL_VERSION_SSL
  332: #endif
  333: #ifdef USE_NTLM
  334:   | CURL_VERSION_NTLM
  335: #endif
  336: #if !defined(CURL_DISABLE_HTTP) && defined(USE_NTLM) && \
  337:   defined(NTLM_WB_ENABLED)
  338:   | CURL_VERSION_NTLM_WB
  339: #endif
  340: #ifdef USE_SPNEGO
  341:   | CURL_VERSION_SPNEGO
  342: #endif
  343: #ifdef USE_KERBEROS5
  344:   | CURL_VERSION_KERBEROS5
  345: #endif
  346: #ifdef HAVE_GSSAPI
  347:   | CURL_VERSION_GSSAPI
  348: #endif
  349: #ifdef USE_WINDOWS_SSPI
  350:   | CURL_VERSION_SSPI
  351: #endif
  352: #ifdef HAVE_LIBZ
  353:   | CURL_VERSION_LIBZ
  354: #endif
  355: #ifdef DEBUGBUILD
  356:   | CURL_VERSION_DEBUG
  357: #endif
  358: #ifdef CURLDEBUG
  359:   | CURL_VERSION_CURLDEBUG
  360: #endif
  361: #ifdef CURLRES_ASYNCH
  362:   | CURL_VERSION_ASYNCHDNS
  363: #endif
  364: #if (CURL_SIZEOF_CURL_OFF_T > 4) && \
  365:     ( (SIZEOF_OFF_T > 4) || defined(USE_WIN32_LARGE_FILES) )
  366:   | CURL_VERSION_LARGEFILE
  367: #endif
  368: #if defined(CURL_DOES_CONVERSIONS)
  369:   | CURL_VERSION_CONV
  370: #endif
  371: #if defined(USE_TLS_SRP)
  372:   | CURL_VERSION_TLSAUTH_SRP
  373: #endif
  374: #if defined(USE_NGHTTP2)
  375:   | CURL_VERSION_HTTP2
  376: #endif
  377: #if defined(ENABLE_QUIC)
  378:   | CURL_VERSION_HTTP3
  379: #endif
  380: #if defined(USE_UNIX_SOCKETS)
  381:   | CURL_VERSION_UNIX_SOCKETS
  382: #endif
  383: #if defined(USE_LIBPSL)
  384:   | CURL_VERSION_PSL
  385: #endif
  386: #if defined(CURL_WITH_MULTI_SSL)
  387:   | CURL_VERSION_MULTI_SSL
  388: #endif
  389: #if defined(HAVE_BROTLI)
  390:   | CURL_VERSION_BROTLI
  391: #endif
  392: #if defined(USE_ALTSVC)
  393:   | CURL_VERSION_ALTSVC
  394: #endif
  395:   ,
  396:   NULL, /* ssl_version */
  397:   0,    /* ssl_version_num, this is kept at zero */
  398:   NULL, /* zlib_version */
  399:   protocols,
  400:   NULL, /* c-ares version */
  401:   0,    /* c-ares version numerical */
  402:   NULL, /* libidn version */
  403:   0,    /* iconv version */
  404:   NULL, /* ssh lib version */
  405:   0,    /* brotli_ver_num */
  406:   NULL, /* brotli version */
  407:   0,    /* nghttp2 version number */
  408:   NULL, /* nghttp2 version string */
  409:   NULL, /* quic library string */
  410: #ifdef CURL_CA_BUNDLE
  411:   CURL_CA_BUNDLE, /* cainfo */
  412: #else
  413:   NULL,
  414: #endif
  415: #ifdef CURL_CA_PATH
  416:   CURL_CA_PATH  /* capath */
  417: #else
  418:   NULL
  419: #endif
  420: };
  421: 
  422: curl_version_info_data *curl_version_info(CURLversion stamp)
  423: {
  424: #if defined(USE_SSH)
  425:   static char ssh_buffer[80];
  426: #endif
  427: #ifdef USE_SSL
  428: #ifdef CURL_WITH_MULTI_SSL
  429:   static char ssl_buffer[200];
  430: #else
  431:   static char ssl_buffer[80];
  432: #endif
  433: #endif
  434: #ifdef HAVE_BROTLI
  435:   static char brotli_buffer[80];
  436: #endif
  437: 
  438: #ifdef USE_SSL
  439:   Curl_ssl_version(ssl_buffer, sizeof(ssl_buffer));
  440:   version_info.ssl_version = ssl_buffer;
  441:   if(Curl_ssl->supports & SSLSUPP_HTTPS_PROXY)
  442:     version_info.features |= CURL_VERSION_HTTPS_PROXY;
  443:   else
  444:     version_info.features &= ~CURL_VERSION_HTTPS_PROXY;
  445: #endif
  446: 
  447: #ifdef HAVE_LIBZ
  448:   version_info.libz_version = zlibVersion();
  449:   /* libz left NULL if non-existing */
  450: #endif
  451: #ifdef USE_ARES
  452:   {
  453:     int aresnum;
  454:     version_info.ares = ares_version(&aresnum);
  455:     version_info.ares_num = aresnum;
  456:   }
  457: #endif
  458: #ifdef USE_LIBIDN2
  459:   /* This returns a version string if we use the given version or later,
  460:      otherwise it returns NULL */
  461:   version_info.libidn = idn2_check_version(IDN2_VERSION);
  462:   if(version_info.libidn)
  463:     version_info.features |= CURL_VERSION_IDN;
  464: #elif defined(USE_WIN32_IDN)
  465:   version_info.features |= CURL_VERSION_IDN;
  466: #endif
  467: 
  468: #if defined(HAVE_ICONV) && defined(CURL_DOES_CONVERSIONS)
  469: #ifdef _LIBICONV_VERSION
  470:   version_info.iconv_ver_num = _LIBICONV_VERSION;
  471: #else
  472:   /* version unknown */
  473:   version_info.iconv_ver_num = -1;
  474: #endif /* _LIBICONV_VERSION */
  475: #endif
  476: 
  477: #if defined(USE_SSH)
  478:   Curl_ssh_version(ssh_buffer, sizeof(ssh_buffer));
  479:   version_info.libssh_version = ssh_buffer;
  480: #endif
  481: 
  482: #ifdef HAVE_BROTLI
  483:   version_info.brotli_ver_num = BrotliDecoderVersion();
  484:   brotli_version(brotli_buffer, sizeof(brotli_buffer));
  485:   version_info.brotli_version = brotli_buffer;
  486: #endif
  487: 
  488: #ifdef USE_NGHTTP2
  489:   {
  490:     nghttp2_info *h2 = nghttp2_version(0);
  491:     version_info.nghttp2_ver_num = h2->version_num;
  492:     version_info.nghttp2_version = h2->version_str;
  493:   }
  494: #endif
  495: 
  496: #ifdef ENABLE_QUIC
  497:   {
  498:     static char quicbuffer[80];
  499:     Curl_quic_ver(quicbuffer, sizeof(quicbuffer));
  500:     version_info.quic_version = quicbuffer;
  501:   }
  502: #endif
  503: 
  504:   (void)stamp; /* avoid compiler warnings, we don't use this */
  505:   return &version_info;
  506: }

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>