Last active
August 29, 2015 14:01
-
-
Save mdg/fde0fedafb0de42ae411 to your computer and use it in GitHub Desktop.
Keyur's patches for Etsy API Concurrency
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Here's the source RPM we built on: | |
http://vault.centos.org/6.5/os/Source/SPackages/curl-7.19.7-37.el6_4.src.rpm | |
The PHP release we applied the patch on is 5.4.26: | |
http://us1.php.net/get/php-5.4.26.tar.gz/from/a/mirror |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
diff --git a/include/curl/multi.h b/include/curl/multi.h | |
index 153f772..0f4cc74 100644 | |
--- a/include/curl/multi.h | |
+++ b/include/curl/multi.h | |
@@ -68,6 +68,31 @@ typedef enum { | |
CURLM_LAST | |
} CURLMcode; | |
+/* NOTE: if you add a state here, add the name to the statename[] array | |
+ * in multi.c as well! | |
+ */ | |
+typedef enum { | |
+ CURLM_STATE_FIRST = -1, /* not a true state, never use this */ | |
+ CURLM_STATE_INIT, /* start in this state */ | |
+ CURLM_STATE_CONNECT, /* resolve/connect has been sent off */ | |
+ CURLM_STATE_WAITRESOLVE, /* awaiting the resolve to finalize */ | |
+ CURLM_STATE_WAITCONNECT, /* awaiting the connect to finalize */ | |
+ CURLM_STATE_WAITPROXYCONNECT, /* awaiting proxy CONNECT to finalize */ | |
+ CURLM_STATE_PROTOCONNECT, /* completing the protocol-specific connect phase */ | |
+ CURLM_STATE_WAITDO, /* wait for our turn to send the request */ | |
+ CURLM_STATE_DO, /* start send off the request (part 1) */ | |
+ CURLM_STATE_DOING, /* sending off the request (part 1) */ | |
+ CURLM_STATE_DO_MORE, /* send off the request (part 2) */ | |
+ CURLM_STATE_DO_DONE, /* done sending off request */ | |
+ CURLM_STATE_WAITPERFORM, /* wait for our turn to read the response */ | |
+ CURLM_STATE_PERFORM, /* transfer data */ | |
+ CURLM_STATE_TOOFAST, /* wait because limit-rate exceeded */ | |
+ CURLM_STATE_DONE, /* post data transfer operation */ | |
+ CURLM_STATE_COMPLETED, /* operation complete */ | |
+ | |
+ CURLM_STATE_LAST /* not a true state, never use this */ | |
+} CURLMstate; | |
+ | |
/* just to make code nicer when using curl_multi_socket() you can now check | |
for CURLM_CALL_MULTI_SOCKET too in the same style it works for | |
curl_multi_perform() and CURLM_CALL_MULTI_PERFORM */ | |
@@ -120,6 +144,17 @@ CURL_EXTERN CURLMcode curl_multi_remove_handle(CURLM *multi_handle, | |
CURL *curl_handle); | |
/* | |
+ * Name: curl_multi_get_handle_state() | |
+ * | |
+ * Desc: get the state of the handle from the multi stack | |
+ * | |
+ * Returns: CURLMcode type, general multi error code. | |
+ */ | |
+CURL_EXTERN CURLMcode curl_multi_get_handle_state(CURLM *multi_handle, | |
+ CURL *curl_handle, | |
+ CURLMstate *state); | |
+ | |
+ /* | |
* Name: curl_multi_fdset() | |
* | |
* Desc: Ask curl for its fd_set sets. The app can use these to select() or | |
diff --git a/lib/multi.c b/lib/multi.c | |
index 48df928..572aae1 100644 | |
--- a/lib/multi.c | |
+++ b/lib/multi.c | |
@@ -65,30 +65,6 @@ struct Curl_message { | |
struct Curl_message *next; | |
}; | |
-/* NOTE: if you add a state here, add the name to the statename[] array as | |
- well! | |
-*/ | |
-typedef enum { | |
- CURLM_STATE_INIT, /* start in this state */ | |
- CURLM_STATE_CONNECT, /* resolve/connect has been sent off */ | |
- CURLM_STATE_WAITRESOLVE, /* awaiting the resolve to finalize */ | |
- CURLM_STATE_WAITCONNECT, /* awaiting the connect to finalize */ | |
- CURLM_STATE_WAITPROXYCONNECT, /* awaiting proxy CONNECT to finalize */ | |
- CURLM_STATE_PROTOCONNECT, /* completing the protocol-specific connect phase */ | |
- CURLM_STATE_WAITDO, /* wait for our turn to send the request */ | |
- CURLM_STATE_DO, /* start send off the request (part 1) */ | |
- CURLM_STATE_DOING, /* sending off the request (part 1) */ | |
- CURLM_STATE_DO_MORE, /* send off the request (part 2) */ | |
- CURLM_STATE_DO_DONE, /* done sending off request */ | |
- CURLM_STATE_WAITPERFORM, /* wait for our turn to read the response */ | |
- CURLM_STATE_PERFORM, /* transfer data */ | |
- CURLM_STATE_TOOFAST, /* wait because limit-rate exceeded */ | |
- CURLM_STATE_DONE, /* post data transfer operation */ | |
- CURLM_STATE_COMPLETED, /* operation complete */ | |
- | |
- CURLM_STATE_LAST /* not a true state, never use this */ | |
-} CURLMstate; | |
- | |
/* we support N sockets per easy handle. Set the corresponding bit to what | |
action we should wait for */ | |
#define MAX_SOCKSPEREASYHANDLE 5 | |
@@ -732,6 +708,30 @@ CURLMcode curl_multi_remove_handle(CURLM *multi_handle, | |
return CURLM_BAD_EASY_HANDLE; /* twasn't found */ | |
} | |
+CURLMcode curl_multi_get_handle_state(CURLM *multi_handle, | |
+ CURL *curl_handle, | |
+ CURLMstate *state) | |
+{ | |
+ struct Curl_multi *multi=(struct Curl_multi *)multi_handle; | |
+ struct Curl_one_easy *easy; | |
+ | |
+ /* First, make some basic checks that the CURLM handle is a good handle */ | |
+ if(!GOOD_MULTI_HANDLE(multi)) | |
+ return CURLM_BAD_HANDLE; | |
+ | |
+ /* Verify that we got a somewhat good easy handle too */ | |
+ if(!GOOD_EASY_HANDLE(curl_handle)) | |
+ return CURLM_BAD_EASY_HANDLE; | |
+ | |
+ /* pick-up from the 'curl_handle' the kept position in the list */ | |
+ easy = ((struct SessionHandle *)curl_handle)->multi_pos; | |
+ if (!easy) | |
+ return CURLM_BAD_EASY_HANDLE; | |
+ | |
+ *state = easy->state; | |
+ return CURLM_OK; | |
+} | |
+ | |
bool Curl_multi_canPipeline(const struct Curl_multi* multi) | |
{ | |
return multi->pipelining_enabled; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
From ed7b42be199d3c8ccd5d4fdcf17726b8875a4757 Mon Sep 17 00:00:00 2001 | |
From: Keyur Govande <keyur@php.net> | |
Date: Wed, 17 Jul 2013 00:04:24 +0000 | |
Subject: [PATCH] Add in new curl method | |
--- | |
ext/curl/config.m4 | 7 +++++++ | |
ext/curl/interface.c | 34 +++++++++++++++++++++++++++++++++- | |
ext/curl/multi.c | 28 ++++++++++++++++++++++++++++ | |
ext/curl/php_curl.h | 3 +++ | |
4 files changed, 71 insertions(+), 1 deletion(-) | |
diff --git a/ext/curl/config.m4 b/ext/curl/config.m4 | |
index fbb4f5b..385f52b 100644 | |
--- a/ext/curl/config.m4 | |
+++ b/ext/curl/config.m4 | |
@@ -152,6 +152,13 @@ int main(int argc, char *argv[]) | |
$CURL_LIBS -L$CURL_DIR/$PHP_LIBDIR | |
]) | |
+ PHP_CHECK_LIBRARY(curl,curl_multi_get_handle_state, | |
+ [ | |
+ AC_DEFINE(HAVE_CURL_MULTI_HANDLE_STATE,1,[ ]) | |
+ ],[],[ | |
+ $CURL_LIBS -L$CURL_DIR/$PHP_LIBDIR | |
+ ]) | |
+ | |
if test "$PHP_CURLWRAPPERS" != "no" ; then | |
AC_DEFINE(PHP_CURL_URL_WRAPPERS,1,[ ]) | |
fi | |
diff --git a/ext/curl/interface.c b/ext/curl/interface.c | |
index 531f15b..999e763 100644 | |
--- a/ext/curl/interface.c | |
+++ b/ext/curl/interface.c | |
@@ -327,6 +327,14 @@ ZEND_BEGIN_ARG_INFO(arginfo_curl_multi_remove_handle, 0) | |
ZEND_ARG_INFO(0, ch) | |
ZEND_END_ARG_INFO() | |
+#if HAVE_CURL_MULTI_HANDLE_STATE | |
+ZEND_BEGIN_ARG_INFO(arginfo_curl_multi_get_handle_state, 0) | |
+ ZEND_ARG_INFO(0, mh) | |
+ ZEND_ARG_INFO(0, ch) | |
+ ZEND_ARG_INFO(0, state) | |
+ZEND_END_ARG_INFO() | |
+#endif | |
+ | |
ZEND_BEGIN_ARG_INFO_EX(arginfo_curl_multi_select, 0, 0, 1) | |
ZEND_ARG_INFO(0, mh) | |
ZEND_ARG_INFO(0, timeout) | |
@@ -367,6 +375,9 @@ const zend_function_entry curl_functions[] = { | |
PHP_FE(curl_multi_init, arginfo_curl_multi_init) | |
PHP_FE(curl_multi_add_handle, arginfo_curl_multi_add_handle) | |
PHP_FE(curl_multi_remove_handle, arginfo_curl_multi_remove_handle) | |
+#if HAVE_CURL_MULTI_HANDLE_STATE | |
+ PHP_FE(curl_multi_get_handle_state, arginfo_curl_multi_get_handle_state) | |
+#endif | |
PHP_FE(curl_multi_select, arginfo_curl_multi_select) | |
PHP_FE(curl_multi_exec, arginfo_curl_multi_exec) | |
PHP_FE(curl_multi_getcontent, arginfo_curl_multi_getcontent) | |
@@ -722,7 +733,6 @@ PHP_MINIT_FUNCTION(curl) | |
REGISTER_CURL_CONSTANT(CURLINFO_LOCAL_PORT); | |
#endif | |
- | |
/* cURL protocol constants (curl_version) */ | |
REGISTER_CURL_CONSTANT(CURL_VERSION_IPV6); | |
REGISTER_CURL_CONSTANT(CURL_VERSION_KERBEROS4); | |
@@ -732,6 +742,28 @@ PHP_MINIT_FUNCTION(curl) | |
/* version constants */ | |
REGISTER_CURL_CONSTANT(CURLVERSION_NOW); | |
+#if HAVE_CURL_MULTI_HANDLE_STATE | |
+ /* Curl handle state during multi */ | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_FIRST); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_INIT); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_CONNECT); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_WAITRESOLVE); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_WAITCONNECT); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_WAITPROXYCONNECT); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_PROTOCONNECT); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_WAITDO); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_DO); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_DOING); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_DO_MORE); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_DO_DONE); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_WAITPERFORM); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_PERFORM); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_TOOFAST); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_DONE); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_COMPLETED); | |
+ REGISTER_CURL_CONSTANT(CURLM_STATE_LAST); | |
+#endif | |
+ | |
/* Error Constants */ | |
REGISTER_CURL_CONSTANT(CURLE_OK); | |
REGISTER_CURL_CONSTANT(CURLE_UNSUPPORTED_PROTOCOL); | |
diff --git a/ext/curl/multi.c b/ext/curl/multi.c | |
index 38c1f1a..d5556bd 100644 | |
--- a/ext/curl/multi.c | |
+++ b/ext/curl/multi.c | |
@@ -155,6 +155,34 @@ PHP_FUNCTION(curl_multi_remove_handle) | |
} | |
/* }}} */ | |
+#if HAVE_CURL_MULTI_HANDLE_STATE | |
+/* {{{ proto int curl_multi_get_handle_state(resource mh, resource ch, int ¤t_state) | |
+ Get the state of the curl-handle which is part of the multi-handle */ | |
+PHP_FUNCTION(curl_multi_get_handle_state) | |
+{ | |
+ zval *z_mh; | |
+ zval *z_ch; | |
+ zval *z_cur_state; | |
+ php_curlm *mh; | |
+ php_curl *ch; | |
+ CURLMstate cur_state = CURLM_STATE_FIRST; | |
+ int result; | |
+ | |
+ if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "rrz", &z_mh, &z_ch, &z_cur_state) == FAILURE) { | |
+ return; | |
+ } | |
+ | |
+ ZEND_FETCH_RESOURCE(mh, php_curlm *, &z_mh, -1, le_curl_multi_handle_name, le_curl_multi_handle); | |
+ ZEND_FETCH_RESOURCE(ch, php_curl *, &z_ch, -1, le_curl_name, le_curl); | |
+ | |
+ result = curl_multi_get_handle_state(mh->multi, ch->cp, &cur_state); | |
+ ZVAL_LONG(z_cur_state, cur_state); | |
+ | |
+ RETURN_LONG(result); | |
+} | |
+/* }}} */ | |
+#endif // HAVE_CURL_MULTI_HANDLE_STATE | |
+ | |
static void _make_timeval_struct(struct timeval *to, double timeout) /* {{{ */ | |
{ | |
unsigned long conv; | |
diff --git a/ext/curl/php_curl.h b/ext/curl/php_curl.h | |
index 945f0a4..0080703 100644 | |
--- a/ext/curl/php_curl.h | |
+++ b/ext/curl/php_curl.h | |
@@ -72,6 +72,9 @@ PHP_FUNCTION(curl_close); | |
PHP_FUNCTION(curl_multi_init); | |
PHP_FUNCTION(curl_multi_add_handle); | |
PHP_FUNCTION(curl_multi_remove_handle); | |
+#if HAVE_CURL_MULTI_HANDLE_STATE | |
+PHP_FUNCTION(curl_multi_get_handle_state); | |
+#endif | |
PHP_FUNCTION(curl_multi_select); | |
PHP_FUNCTION(curl_multi_exec); | |
PHP_FUNCTION(curl_multi_getcontent); | |
-- | |
1.8.1.6 | |
@swestcott I don't believe so. You can see the discussion on the curl mailing list from a couple years back.
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Just watched https://vimeo.com/channels/phpday/104905610. Has this PR been accepted upstream?