Sfoglia il codice sorgente

Store the default certs in the PHP persistent list instead

Stanley Cheung 8 anni fa
parent
commit
ee7633be52

+ 1 - 3
src/php/ext/grpc/channel.c

@@ -289,9 +289,7 @@ PHP_METHOD(Channel, __construct) {
   }
   channel->wrapper = malloc(sizeof(grpc_channel_wrapper));
   channel->wrapper->key = key;
-  char *target_cpy = malloc(target_length + 1);
-  strcpy(target_cpy, target);
-  channel->wrapper->target = target_cpy;
+  channel->wrapper->target = strdup(target);
   channel->wrapper->args_hashstr = sha1str;
   if (creds != NULL && creds->hashstr != NULL) {
     channel->wrapper->creds_hashstr = creds->hashstr;

+ 66 - 11
src/php/ext/grpc/channel_credentials.c

@@ -57,15 +57,28 @@ zend_class_entry *grpc_ce_channel_credentials;
 #if PHP_MAJOR_VERSION >= 7
 static zend_object_handlers channel_credentials_ce_handlers;
 #endif
-static char *default_pem_root_certs = NULL;
+static gpr_mu cc_persistent_list_mu;
+int le_cc_plink;
+const char *persistent_list_key = "default_root_certs";
 
 static grpc_ssl_roots_override_result get_ssl_roots_override(
     char **pem_root_certs) {
-  *pem_root_certs = default_pem_root_certs;
-  if (default_pem_root_certs == NULL) {
+  TSRMLS_FETCH();
+  php_grpc_zend_resource *rsrc;
+  php_grpc_int key_len = strlen(persistent_list_key);
+
+  gpr_mu_lock(&cc_persistent_list_mu);
+  if (PHP_GRPC_PERSISTENT_LIST_FIND(&EG(persistent_list), persistent_list_key,
+                                    key_len, rsrc)) {
+    channel_credentials_persistent_le_t *le =
+      (channel_credentials_persistent_le_t *)rsrc->ptr;
+    *pem_root_certs = le->default_root_certs;
+    gpr_mu_unlock(&cc_persistent_list_mu);
+    return GRPC_SSL_ROOTS_OVERRIDE_OK;
+  } else {
+    gpr_mu_unlock(&cc_persistent_list_mu);
     return GRPC_SSL_ROOTS_OVERRIDE_FAIL;
   }
-  return GRPC_SSL_ROOTS_OVERRIDE_OK;
 }
 
 /* Frees and destroys an instance of wrapped_grpc_channel_credentials */
@@ -100,6 +113,27 @@ zval *grpc_php_wrap_channel_credentials(grpc_channel_credentials *wrapped,
   return credentials_object;
 }
 
+void update_root_certs_persistent_list(char *pem_roots,
+                                       php_grpc_int pem_roots_length
+                                       TSRMLS_DC) {
+
+  php_grpc_zend_resource new_rsrc;
+  channel_credentials_persistent_le_t *le;
+  php_grpc_int key_len = strlen(persistent_list_key);
+  new_rsrc.type = le_cc_plink;
+  le = malloc(sizeof(channel_credentials_persistent_le_t));
+
+  char *tmp = malloc(pem_roots_length+1);
+  memcpy(tmp, pem_roots, pem_roots_length+1);
+  le->default_root_certs = tmp;
+
+  new_rsrc.ptr = le;
+  gpr_mu_lock(&cc_persistent_list_mu);
+  PHP_GRPC_PERSISTENT_LIST_UPDATE(&EG(persistent_list), persistent_list_key,
+                                  key_len, (void *)&new_rsrc);
+  gpr_mu_unlock(&cc_persistent_list_mu);
+}
+
 /**
  * Set default roots pem.
  * @param string $pem_roots PEM encoding of the server root certificates
@@ -116,13 +150,21 @@ PHP_METHOD(ChannelCredentials, setDefaultRootsPem) {
                          "setDefaultRootsPem expects 1 string", 1 TSRMLS_CC);
     return;
   }
-  char *default_certs = php_grpc_get_default_pem_root_certs(TSRMLS_C);
-  if (default_certs == NULL) {
-    default_certs = gpr_malloc((pem_roots_length + 1) * sizeof(char));
-    memcpy(default_certs, pem_roots, pem_roots_length + 1);
-    php_grpc_update_default_pem_root_certs(default_certs TSRMLS_CC);
+  php_grpc_zend_resource *rsrc;
+  php_grpc_int key_len = strlen(persistent_list_key);
+  if (!(PHP_GRPC_PERSISTENT_LIST_FIND(&EG(persistent_list),
+                                      persistent_list_key,
+                                      key_len, rsrc))) {
+    update_root_certs_persistent_list(pem_roots,
+                                      pem_roots_length TSRMLS_CC);
+  } else {
+    channel_credentials_persistent_le_t *le =
+      (channel_credentials_persistent_le_t *)rsrc->ptr;
+    if (strcmp(pem_roots, le->default_root_certs) != 0) {
+      update_root_certs_persistent_list(pem_roots, pem_roots_length
+                                        TSRMLS_CC);
+    }
   }
-  default_pem_root_certs = default_certs;
 }
 
 /**
@@ -231,6 +273,14 @@ PHP_METHOD(ChannelCredentials, createInsecure) {
   RETURN_NULL();
 }
 
+static void php_grpc_channel_credentials_plink_dtor(
+    php_grpc_zend_resource *rsrc TSRMLS_DC) {
+  channel_credentials_persistent_le_t *le =
+    (channel_credentials_persistent_le_t *)rsrc->ptr;
+  free(le->default_root_certs);
+  free(le);
+}
+
 ZEND_BEGIN_ARG_INFO_EX(arginfo_setDefaultRootsPem, 0, 0, 1)
   ZEND_ARG_INFO(0, pem_roots)
 ZEND_END_ARG_INFO()
@@ -266,12 +316,17 @@ static zend_function_entry channel_credentials_methods[] = {
   PHP_FE_END
 };
 
-void grpc_init_channel_credentials(TSRMLS_D) {
+GRPC_STARTUP_FUNCTION(channel_credentials) {
   zend_class_entry ce;
   INIT_CLASS_ENTRY(ce, "Grpc\\ChannelCredentials",
                    channel_credentials_methods);
   ce.create_object = create_wrapped_grpc_channel_credentials;
   grpc_ce_channel_credentials = zend_register_internal_class(&ce TSRMLS_CC);
+  gpr_mu_init(&cc_persistent_list_mu);
+  le_cc_plink = zend_register_list_destructors_ex(
+      NULL, php_grpc_channel_credentials_plink_dtor,
+      "Channel Credentials persistent default certs", module_number);
   PHP_GRPC_INIT_HANDLER(wrapped_grpc_channel_credentials,
                         channel_credentials_ce_handlers);
+  return SUCCESS;
 }

+ 5 - 1
src/php/ext/grpc/channel_credentials.h

@@ -76,6 +76,10 @@ static inline wrapped_grpc_channel_credentials
 #endif /* PHP_MAJOR_VERSION */
 
 /* Initializes the ChannelCredentials PHP class */
-void grpc_init_channel_credentials(TSRMLS_D);
+GRPC_STARTUP_FUNCTION(channel_credentials);
+
+typedef struct _channel_credentials_persistent_le {
+  char *default_root_certs;
+} channel_credentials_persistent_le_t;
 
 #endif /* NET_GRPC_PHP_GRPC_CHANNEL_CREDENTIALS_H_ */

+ 2 - 10
src/php/ext/grpc/php_grpc.c

@@ -49,6 +49,7 @@
 #include <ext/standard/info.h>
 #include "php_grpc.h"
 
+ZEND_DECLARE_MODULE_GLOBALS(grpc)
 static PHP_GINIT_FUNCTION(grpc);
 
 /* {{{ grpc_functions[]
@@ -242,7 +243,7 @@ PHP_MINIT_FUNCTION(grpc) {
   GRPC_STARTUP(channel);
   grpc_init_server(TSRMLS_C);
   grpc_init_timeval(TSRMLS_C);
-  grpc_init_channel_credentials(TSRMLS_C);
+  GRPC_STARTUP(channel_credentials);
   grpc_init_call_credentials(TSRMLS_C);
   grpc_init_server_credentials(TSRMLS_C);
   return SUCCESS;
@@ -296,18 +297,9 @@ PHP_RINIT_FUNCTION(grpc) {
  */
 static PHP_GINIT_FUNCTION(grpc) {
   grpc_globals->initialized = 0;
-  grpc_globals->pem_root_certs = NULL;
 }
 /* }}} */
 
-void php_grpc_update_default_pem_root_certs(char *default_certs TSRMLS_DC) {
-  GRPC_G(pem_root_certs) = default_certs;
-}
-
-char *php_grpc_get_default_pem_root_certs(TSRMLS_D) {
-  return GRPC_G(pem_root_certs);
-}
-
 /* The previous line is meant for vim and emacs, so it can correctly fold and
    unfold functions in source code. See the corresponding marks just before
    function definition, where the functions purpose is also documented. Please

+ 0 - 6
src/php/ext/grpc/php_grpc.h

@@ -73,7 +73,6 @@ PHP_RINIT_FUNCTION(grpc);
 */
 ZEND_BEGIN_MODULE_GLOBALS(grpc)
   zend_bool initialized;
-  char *pem_root_certs;
 ZEND_END_MODULE_GLOBALS(grpc)
 
 /* In every utility function you add that needs to use variables
@@ -92,13 +91,8 @@ ZEND_END_MODULE_GLOBALS(grpc)
 #define GRPC_G(v) (grpc_globals.v)
 #endif
 
-ZEND_DECLARE_MODULE_GLOBALS(grpc)
-
 #define GRPC_STARTUP_FUNCTION(module)  ZEND_MINIT_FUNCTION(grpc_##module)
 #define GRPC_STARTUP(module)           \
   ZEND_MODULE_STARTUP_N(grpc_##module)(INIT_FUNC_ARGS_PASSTHRU)
 
-void php_grpc_update_default_pem_root_certs(char *default_certs TSRMLS_DC);
-char *php_grpc_get_default_pem_root_certs(TSRMLS_D);
-
 #endif /* PHP_GRPC_H */