--- parser3/src/classes/curl.C 2020/11/10 22:42:24 1.65 +++ parser3/src/classes/curl.C 2024/09/07 16:30:26 1.71 @@ -1,7 +1,8 @@ /** @file Parser: @b curl parser class. - Copyright (c) 2001-2017 Art. Lebedev Studio (http://www.artlebedev.com) + Copyright (c) 2001-2023 Art. Lebedev Studio (http://www.artlebedev.com) + Authors: Konstantin Morshnev */ #include "pa_config_includes.h" @@ -17,7 +18,7 @@ #include "pa_http.h" #include "ltdl.h" -volatile const char * IDENT_CURL_C="$Id: curl.C,v 1.65 2020/11/10 22:42:24 moko Exp $"; +volatile const char * IDENT_CURL_C="$Id: curl.C,v 1.71 2024/09/07 16:30:26 moko Exp $"; class MCurl: public Methoded { public: @@ -116,10 +117,14 @@ static ParserOptions &options(){ class Temp_curl { CURL *saved_curl; ParserOptions *saved_options; + + // every TLS should be referenced elsewhere, or GC will collect it + CURL *thread_curl; + ParserOptions *thread_options; public: Temp_curl() : saved_curl(fcurl), saved_options(foptions){ - fcurl = f_curl_easy_init(); - foptions = new ParserOptions(); + thread_curl = fcurl = f_curl_easy_init(); + thread_options = foptions = new ParserOptions(); f_curl_easy_setopt(fcurl, CURLOPT_IPRESOLVE, CURL_IPRESOLVE_V4); // avoid ipv6 by default } @@ -144,7 +149,8 @@ static void temp_curl(void (*action)(Req Temp_curl temp_curl; action(r,params); } else { - throw Exception("curl", 0, "failed to load curl library %s: %s", curl_library, curl_status); + const char *hint=strcmp(curl_library, "libcurl" LT_MODULE_EXT) ? "" : " (at first call ^curl:options[ $.library[correct.libcurl" LT_MODULE_EXT ".name] ])"; + throw Exception("curl", 0, "failed to load curl library %s%s", curl_status, hint); } } @@ -495,7 +501,7 @@ static void curl_setopt(HashStringValue: if( (res=f_curl_easy_setopt(curl(), CURLOPT_POSTFIELDSIZE, -1L)) == CURLE_OK ) res=f_curl_easy_setopt(curl(), opt->id, curl_urlencode(v.as_string(), r)); } else { - VFile *file=v.as_vfile(String::L_AS_IS); + VFile *file=v.as_vfile(); if( (res=f_curl_easy_setopt(curl(), CURLOPT_POSTFIELDSIZE, (long)file->value_size())) == CURLE_OK ) res=f_curl_easy_setopt(curl(), opt->id, file->value_ptr()); } @@ -784,7 +790,7 @@ static void _curl_load_action(Request& r VHash* vtables=new VHash; result.fields().put("tables", vtables); - for(Array_iterator i(response.headers); i.has_next(); ){ + for(Array_iterator i(response.headers); i; ){ HTTP_Headers::Header header=i.next(); if(asked_charset)