diff --git a/src/lceasy.c b/src/lceasy.c index 6bfdd84..2b8bd56 100644 --- a/src/lceasy.c +++ b/src/lceasy.c @@ -83,9 +83,6 @@ int lcurl_easy_create(lua_State *L, int error_mode){ p->multi = NULL; #if LCURL_CURL_VER_GE(7,56,0) p->mime = NULL; -#endif -#if LCURL_CURL_VER_GE(7,63,0) - p->url = NULL; #endif p->storage = lcurl_storage_init(L); p->wr.cb_ref = p->wr.ud_ref = LUA_NOREF; @@ -130,31 +127,11 @@ static int lcurl_easy_to_s(lua_State *L){ return 1; } -static int lcurl_easy_cleanup(lua_State *L){ - lcurl_easy_t *p = lcurl_geteasy(L); +static int lcurl_easy_cleanup_storage(lua_State *L, lcurl_easy_t *p){ int i; - if(p->multi){ - LCURL_UNUSED_VAR CURLMcode code = lcurl__multi_remove_handle(L, p->multi, p); - - //! @todo what I can do if I can not remove it??? - } - - if(p->curl){ - lua_State *curL; - - // In my tests when I cleanup some easy handle. - // timerfunction called only for single multi handle. - // Also may be this function may call `close` callback - // for `curl_mimepart` structure. - curL = p->L; lcurl__easy_assign_lua(L, p, L, 1); - curl_easy_cleanup(p->curl); -#ifndef LCURL_RESET_NULL_LUA - if(curL != NULL) -#endif - lcurl__easy_assign_lua(L, p, curL, 1); - - p->curl = NULL; + if(p->storage != LUA_NOREF){ + p->storage = lcurl_storage_free(L, p->storage); } p->post = NULL; @@ -162,14 +139,6 @@ static int lcurl_easy_cleanup(lua_State *L){ p->mime = NULL; #endif -#if LCURL_CURL_VER_GE(7,63,0) - p->url = NULL; -#endif - - if(p->storage != LUA_NOREF){ - p->storage = lcurl_storage_free(L, p->storage); - } - luaL_unref(L, LCURL_LUA_REGISTRY, p->wr.cb_ref); luaL_unref(L, LCURL_LUA_REGISTRY, p->wr.ud_ref); luaL_unref(L, LCURL_LUA_REGISTRY, p->rd.cb_ref); @@ -221,8 +190,37 @@ static int lcurl_easy_cleanup(lua_State *L){ for(i = 0; i < LCURL_LIST_COUNT; ++i){ p->lists[i] = LUA_NOREF; } +} +static int lcurl_easy_cleanup(lua_State *L){ + lcurl_easy_t *p = lcurl_geteasy(L); lua_settop(L, 1); + + if(p->multi){ + LCURL_UNUSED_VAR CURLMcode code = lcurl__multi_remove_handle(L, p->multi, p); + + //! @todo what I can do if I can not remove it??? + } + + if(p->curl){ + lua_State *curL; + + // In my tests when I cleanup some easy handle. + // timerfunction called only for single multi handle. + // Also may be this function may call `close` callback + // for `curl_mimepart` structure. + curL = p->L; lcurl__easy_assign_lua(L, p, L, 1); + curl_easy_cleanup(p->curl); +#ifndef LCURL_RESET_NULL_LUA + if(curL != NULL) +#endif + lcurl__easy_assign_lua(L, p, curL, 1); + + p->curl = NULL; + } + + lcurl_easy_cleanup_storage(L, p); + lua_pushnil(L); lua_rawset(L, LCURL_USERVALUES); @@ -305,15 +303,8 @@ static int lcurl_easy_reset(lua_State *L){ curl_easy_reset(p->curl); lua_settop(L, 1); - if(p->storage != LUA_NOREF){ - int i; - for (i = 0; i < LCURL_LIST_COUNT; ++i) { - p->lists[i] = LUA_NOREF; - } - lcurl_storage_free(L, p->storage); - p->storage = lcurl_storage_init(L); - lua_settop(L, 1); - } + lcurl_easy_cleanup_storage(L, p); + p->storage = lcurl_storage_init(L); return 1; } @@ -621,8 +612,6 @@ static int lcurl_easy_set_CURLU(lua_State *L) { lcurl_storage_preserve_iv(L, p->storage, CURLOPT_CURLU, 2); - p->url = url; - lua_settop(L, 1); return 1; } @@ -1030,8 +1019,6 @@ static int lcurl_easy_unset_CURLU(lua_State *L) { lcurl_storage_remove_i(L, p->storage, CURLOPT_CURLU); - p->url = NULL; - lua_settop(L, 1); return 1; } diff --git a/src/lceasy.h b/src/lceasy.h index f4518d9..702a9d3 100644 --- a/src/lceasy.h +++ b/src/lceasy.h @@ -75,10 +75,6 @@ typedef struct lcurl_easy_tag{ lcurl_mime_t *mime; #endif -#if LCURL_CURL_VER_GE(7,63,0) - lcurl_url_t *url; -#endif - CURL *curl; int storage; int lists[LCURL_LIST_COUNT]; diff --git a/src/lcutils.c b/src/lcutils.c index 5b85774..adf895a 100644 --- a/src/lcutils.c +++ b/src/lcutils.c @@ -115,8 +115,8 @@ int lcurl_storage_free(lua_State *L, int storage){ lua_pop(L, 1); } } - lua_pop(L, 1); luaL_unref(L, LCURL_LUA_REGISTRY, storage); + lua_pop(L, 2); return LUA_NOREF; } diff --git a/test/test_easy.lua b/test/test_easy.lua index 6efba8f..2710764 100644 --- a/test/test_easy.lua +++ b/test/test_easy.lua @@ -889,16 +889,16 @@ function test_reset() do local form = curl.form() e = curl.easy{httppost = form} - pfrom = weak_ptr(form) + pform = weak_ptr(form) end gc_collect() - assert(pfrom.value) + assert(pform.value) assert_equal(e, e:reset()) gc_collect() - assert(not pfrom.value) + assert(not pform.value) end end @@ -1027,6 +1027,8 @@ end local _ENV = TEST_CASE'unset_callback_ctx' if ENABLE then +local HSTS = curl.version_info().features.HSTS + local c function setup() @@ -1057,6 +1059,19 @@ local function test_cb(name) gc_collect() assert_nil(pctx.value) + + do local ctx = {} + pctx = weak_ptr(ctx) + assert(set(c, function() end, ctx)) + end + + gc_collect() + assert_table(pctx.value) + + c:reset() + + gc_collect() + assert_nil(pctx.value) end function test_read() test_cb('readfunction') end @@ -1069,6 +1084,11 @@ function test_fnmatch() test_cb('fnmatch_function') end function test_chunk_bgn() test_cb('chunk_bgn_function') end function test_chunk_end() test_cb('chunk_end_function') end +if curl.OPT_HSTSREADFUNCTION and HSTS then +function test_hstsreadfunction() test_cb('hstsreadfunction') end +function test_hstswritefunction() test_cb('hstswritefunction') end +end + end local _ENV = TEST_CASE'set_slist' if ENABLE then diff --git a/test/test_mime.lua b/test/test_mime.lua index 762d896..c3d5ef2 100644 --- a/test/test_mime.lua +++ b/test/test_mime.lua @@ -207,6 +207,27 @@ function test_mimepost_does_not_ref_to_easy() assert_nil(peasy.value) end +function test_cleanup_on_easy_reset() + + local mime do + mime = weak_ptr(easy:mime()) + easy:setopt_mimepost(mime.value) + end + + gc_collect() + + assert_not_nil(mime.value) + + easy:reset() + + gc_collect(10) + + assert_nil(mime.value) + + easy:setopt{url = GET_URL, writefunction = function() end} + easy:perform() +end + end local _ENV = TEST_CASE'mime basic' if not curl.OPT_MIMEPOST then @@ -573,6 +594,38 @@ function test_pass_args() assert_match('Content%-Transfer%-Encoding:%s*base64', info) end +local function easy_dump_mime(easy, mime, url) + assert(mime:addpart{ + data = 'hello'; + encoder = 'base64'; + name = 'test'; + filename = 'test.html'; + type = 'test/html'; + headers = { + 'X-Custom-Header: hello'; + } + }) + + easy:setopt{ + mimepost = mime; + } + + assert(easy:setopt{ + url = GET_URL; + customrequest = "GET"; + + writefunction = function()end; + }) + + if not ok then return nil, err end + + ok, err = easy:perform() + + if not ok then return nil, err end + + return table.concat(buffer) +end + end RUN()