/**
 * Copies of internal methods from Zend/zend_execute_API.c
 * These are used to call internal methods (not in the function table) from the external method.
 * TODO: See if xdebug works
 */
int runkit_forward_call_user_function(zend_function *fbc, zend_function *fbc_inner, INTERNAL_FUNCTION_PARAMETERS) /* {{{ */
{
	uint32_t i;
	zend_execute_data *call, dummy_execute_data;
	zend_fcall_info_cache fci_cache_local = {0};
	zend_function *func;
	/* {{{ patch for runkit */
	zend_fcall_info fci = {0};
	zend_fcall_info_cache *fci_cache = NULL;

	fci.size = sizeof(fci);
	fci.object = NULL; // FIXME for methods? // object ? Z_OBJ_P(object) : NULL;
	ZVAL_STR(&fci.function_name, fbc_inner->common.function_name);
	zend_string_addref(fbc_inner->common.function_name);
	fci.retval = return_value;
	fci.param_count = ZEND_CALL_NUM_ARGS(EG(current_execute_data));
	fci.params = ZEND_CALL_ARG(EG(current_execute_data), 1);  // params and param_count From zend_API.c
	fci.no_separation = (zend_bool)1;			  // ???
	/* end patch for runkit }}} */

	ZVAL_UNDEF(fci.retval);

	if (!EG(active)) {
		return FAILURE; /* executor is already inactive */
	}

	if (EG(exception)) {
		return FAILURE; /* we would result in an unstable executor otherwise */
	}

	/* Initialize execute_data */
	if (!EG(current_execute_data)) {
		/* This only happens when we're called outside any execute()'s
		 * It shouldn't be strictly necessary to NULL execute_data out,
		 * but it may make bugs easier to spot
		 */
		memset(&dummy_execute_data, 0, sizeof(zend_execute_data));
		EG(current_execute_data) = &dummy_execute_data;
	} else if (EG(current_execute_data)->func &&
	           ZEND_USER_CODE(EG(current_execute_data)->func->common.type) &&
	           EG(current_execute_data)->opline->opcode != ZEND_DO_FCALL &&
	           EG(current_execute_data)->opline->opcode != ZEND_DO_ICALL &&
	           EG(current_execute_data)->opline->opcode != ZEND_DO_UCALL &&
	           EG(current_execute_data)->opline->opcode != ZEND_DO_FCALL_BY_NAME) {
		/* Insert fake frame in case of include or magic calls */
		dummy_execute_data = *EG(current_execute_data);
		dummy_execute_data.prev_execute_data = EG(current_execute_data);
		dummy_execute_data.call = NULL;
		dummy_execute_data.opline = NULL;
		dummy_execute_data.func = NULL;
		EG(current_execute_data) = &dummy_execute_data;
	}

	if (!fci_cache || !RUNKIT_IS_FCI_CACHE_INITIALIZED(fci_cache)) {
		zend_string *callable_name;
		char *error = NULL;

		if (!fci_cache) {
			fci_cache = &fci_cache_local;
		}

		if (!zend_is_callable_ex(&fci.function_name, fci.object, IS_CALLABLE_CHECK_SILENT, &callable_name, fci_cache, &error)) {
			if (error) {
				zend_error(E_WARNING, "Invalid callback %s, %s", ZSTR_VAL(callable_name), error);
				efree(error);
			}
			if (callable_name) {
				zend_string_release(callable_name);
			}
			if (EG(current_execute_data) == &dummy_execute_data) {
				EG(current_execute_data) = dummy_execute_data.prev_execute_data;
			}
			return FAILURE;
		} else if (error) {
			/* Capitalize the first latter of the error message */
			if (error[0] >= 'a' && error[0] <= 'z') {
				error[0] += ('A' - 'a');
			}
			zend_error(E_DEPRECATED, "%s", error);
			efree(error);
		}
		zend_string_release(callable_name);
	}

	func = fbc_inner;
    fci.object = (func->common.fn_flags & ZEND_ACC_STATIC) ?
	   NULL : fci_cache->object;

    call = zend_vm_stack_push_call_frame(ZEND_CALL_TOP_FUNCTION | ZEND_CALL_DYNAMIC,
	   func, fci.param_count, fci_cache->called_scope, fci.object);
	if (fci.object &&
	    (!EG(objects_store).object_buckets ||
	     !IS_OBJ_VALID(EG(objects_store).object_buckets[fci.object->handle]))) {
		if (EG(current_execute_data) == &dummy_execute_data) {
			EG(current_execute_data) = dummy_execute_data.prev_execute_data;
		}
		return FAILURE;
	}

	if (func->common.fn_flags & (ZEND_ACC_ABSTRACT | ZEND_ACC_DEPRECATED)) {
		if (func->common.fn_flags & ZEND_ACC_ABSTRACT) {
			zend_throw_error(NULL, "Cannot call abstract method %s::%s()", ZSTR_VAL(func->common.scope->name), ZSTR_VAL(func->common.function_name));
			if (EG(current_execute_data) == &dummy_execute_data) {
				EG(current_execute_data) = dummy_execute_data.prev_execute_data;
			}
			return FAILURE;
		}
		if (func->common.fn_flags & ZEND_ACC_DEPRECATED) {
 			zend_error(E_DEPRECATED, "Function %s%s%s() is deprecated",
				func->common.scope ? ZSTR_VAL(func->common.scope->name) : "",
				func->common.scope ? "::" : "",
				ZSTR_VAL(func->common.function_name));
		}
	}

	for (i = 0; i < fci.param_count; i++) {
		zval *param;
		zval *arg = &fci.params[i];

		if (ARG_SHOULD_BE_SENT_BY_REF(func, i + 1)) {
			if (UNEXPECTED(!Z_ISREF_P(arg))) {
				if (!fci.no_separation) {
					/* Separation is enabled -- create a ref */
					ZVAL_NEW_REF(arg, arg);
				} else if (!ARG_MAY_BE_SENT_BY_REF(func, i + 1)) {
					/* By-value send is not allowed -- emit a warning,
					 * but still perform the call with a by-value send. */
					zend_error(E_WARNING,
						"Parameter %d to %s%s%s() expected to be a reference, value given", i + 1,
						func->common.scope ? ZSTR_VAL(func->common.scope->name) : "",
						func->common.scope ? "::" : "",
						ZSTR_VAL(func->common.function_name));
				}
			}
		} else {
			if (Z_ISREF_P(arg) &&
			    !(func->common.fn_flags & ZEND_ACC_CALL_VIA_TRAMPOLINE)) {
				/* don't separate references for __call */
				arg = Z_REFVAL_P(arg);
			}
		}
		param = ZEND_CALL_ARG(call, i + 1);
		ZVAL_COPY(param, arg);
	}

	if (UNEXPECTED(func->op_array.fn_flags & ZEND_ACC_CLOSURE)) {
		ZEND_ASSERT(GC_TYPE((zend_object *)func->op_array.prototype) == IS_OBJECT);
		GC_ADDREF((zend_object *)func->op_array.prototype);
		ZEND_ADD_CALL_FLAG(call, ZEND_CALL_CLOSURE);
	}

	if (func->type == ZEND_USER_FUNCTION) {
		int call_via_handler = (func->common.fn_flags & ZEND_ACC_CALL_VIA_TRAMPOLINE) != 0;
		zend_init_execute_data(call, &func->op_array, fci.retval);
		zend_execute_ex(call);
		if (call_via_handler) {
			/* We must re-initialize function again */
			RUNKIT_CLEAR_FCI_CACHE(fci_cache);
		}
	} else if (func->type == ZEND_INTERNAL_FUNCTION) {
		int call_via_handler = (func->common.fn_flags & ZEND_ACC_CALL_VIA_TRAMPOLINE) != 0;
		ZVAL_NULL(fci.retval);
		call->prev_execute_data = EG(current_execute_data);
		call->return_value = NULL; /* this is not a constructor call */
		EG(current_execute_data) = call;
		if (EXPECTED(zend_execute_internal == NULL)) {
			/* saves one function call if zend_execute_internal is not used */
			func->internal_function.handler(call, fci.retval);
		} else {
			zend_execute_internal(call, fci.retval);
		}
		EG(current_execute_data) = call->prev_execute_data;
		zend_vm_stack_free_args(call);

		/*  We shouldn't fix bad extensions here,
			because it can break proper ones (Bug #34045)
		if (!EX(function_state).function->common.return_reference)
		{
			INIT_PZVAL(f->retval);
		}*/
		if (EG(exception)) {
			zval_ptr_dtor(fci.retval);
			ZVAL_UNDEF(fci.retval);
		}

		if (call_via_handler) {
			/* We must re-initialize function again */
			RUNKIT_CLEAR_FCI_CACHE(fci_cache);
		}
	} else { /* ZEND_OVERLOADED_FUNCTION */
		ZVAL_NULL(fci.retval);

		/* Not sure what should be done here if it's a static method */
		if (fci.object) {
			call->prev_execute_data = EG(current_execute_data);
			EG(current_execute_data) = call;
			fci.object->handlers->call_method(func->common.function_name, fci.object, call, fci.retval);
			EG(current_execute_data) = call->prev_execute_data;
		} else {
			zend_throw_error(NULL, "Cannot call overloaded function for non-object");
		}

		zend_vm_stack_free_args(call);

		if (func->type == ZEND_OVERLOADED_FUNCTION_TEMPORARY) {
			zend_string_release(func->common.function_name);
		}
		efree(func);

		if (EG(exception)) {
			zval_ptr_dtor(fci.retval);
			ZVAL_UNDEF(fci.retval);
		}
	}

	zend_vm_stack_free_call_frame(call);

	if (EG(current_execute_data) == &dummy_execute_data) {
		EG(current_execute_data) = dummy_execute_data.prev_execute_data;
	}

	if (EG(exception)) {
		zend_throw_exception_internal(NULL);
	}
	return SUCCESS;
}
Esempio n. 2
0
static zend_function *zend_closure_get_constructor(zend_object *object) /* {{{ */
{
	zend_error(E_RECOVERABLE_ERROR, "Instantiation of 'Closure' is not allowed");
	return NULL;
}
Esempio n. 3
0
ZEND_API void zend_create_closure(zval *res, zend_function *func, zend_class_entry *scope, zval *this_ptr) /* {{{ */
{
	zend_closure *closure;

	object_init_ex(res, zend_ce_closure);

	closure = (zend_closure *)Z_OBJ_P(res);

	closure->func = *func;
	closure->func.common.prototype = NULL;
	closure->func.common.fn_flags |= ZEND_ACC_CLOSURE;

	if ((scope == NULL) && this_ptr && (Z_TYPE_P(this_ptr) != IS_UNDEF)) {
		/* use dummy scope if we're binding an object without specifying a scope */
		/* maybe it would be better to create one for this purpose */
		scope = zend_ce_closure;
	}

	if (closure->func.type == ZEND_USER_FUNCTION) {
		if (closure->func.op_array.static_variables) {
			HashTable *static_variables = closure->func.op_array.static_variables;

			ALLOC_HASHTABLE(closure->func.op_array.static_variables);
			zend_hash_init(closure->func.op_array.static_variables, zend_hash_num_elements(static_variables), NULL, ZVAL_PTR_DTOR, 0);
			zend_hash_apply_with_arguments(static_variables, zval_copy_static_var, 1, closure->func.op_array.static_variables);
		}
		closure->func.op_array.run_time_cache = NULL;
		if (closure->func.op_array.refcount) {
			(*closure->func.op_array.refcount)++;
		}
	} else {
		/* verify that we aren't binding internal function to a wrong scope */
		if(func->common.scope != NULL) {
			if(scope && !instanceof_function(scope, func->common.scope)) {
				zend_error(E_WARNING, "Cannot bind function %s::%s to scope class %s", func->common.scope->name->val, func->common.function_name->val, scope->name->val);
				scope = NULL;
			}
			if(scope && this_ptr && (func->common.fn_flags & ZEND_ACC_STATIC) == 0 &&
					!instanceof_function(Z_OBJCE_P(this_ptr), closure->func.common.scope)) {
				zend_error(E_WARNING, "Cannot bind function %s::%s to object of class %s", func->common.scope->name->val, func->common.function_name->val, Z_OBJCE_P(this_ptr)->name->val);
				scope = NULL;
				this_ptr = NULL;
			}
		} else {
			/* if it's a free function, we won't set scope & this since they're meaningless */
			this_ptr = NULL;
			scope = NULL;
		}
	}

	ZVAL_UNDEF(&closure->this_ptr);
	/* Invariants:
	 * If the closure is unscoped, it has no bound object.
	 * The the closure is scoped, it's either static or it's bound */
	closure->func.common.scope = scope;
	if (scope) {
		closure->func.common.fn_flags |= ZEND_ACC_PUBLIC;
		if (this_ptr && Z_TYPE_P(this_ptr) == IS_OBJECT && (closure->func.common.fn_flags & ZEND_ACC_STATIC) == 0) {
			ZVAL_COPY(&closure->this_ptr, this_ptr);
		} else {
			closure->func.common.fn_flags |= ZEND_ACC_STATIC;
		}
	}
}
Esempio n. 4
0
/* {{{ pthreads_call_method */
int pthreads_call_method(PTHREADS_CALL_METHOD_PASSTHRU_D) {
	zval 					***argv = NULL, zmethod, *zresult;
	zend_function 			*call = NULL;
	zend_fcall_info 		info;
	zend_fcall_info_cache	cache;
	zend_class_entry		*scope;
	int 					called = -1, argc = ZEND_NUM_ARGS(), access = ZEND_ACC_PUBLIC, mlength = 0;
	char					*lcname;
	zend_bool				unprotect;
	
	if (getThis()) {
		PTHREAD thread = PTHREADS_FETCH;
		if (thread) {
			switch((access=pthreads_modifiers_get(thread->modifiers, method TSRMLS_CC))){
				case ZEND_ACC_PRIVATE:
				case ZEND_ACC_PROTECTED: {
					scope = Z_OBJCE_P(getThis());
					
					/*
					* Stop invalid private method calls
					*/
					if (access == ZEND_ACC_PRIVATE && !PTHREADS_IN_THREAD(thread)) {
						zend_error(
							E_ERROR, 
							"pthreads detected an attempt to call private method %s::%s from outside the threading context", 
							scope->name,
							method
						);
						return FAILURE;
					}
					
					/*
					* Get arguments from stack
					*/
					if (ZEND_NUM_ARGS()) 
					{
						argv = safe_emalloc(sizeof(zval **), argc, 0);
						if (argv) {
							zend_get_parameters_array_ex(argc, argv);
						}
					}
							
					mlength = strlen(method);
					lcname =  calloc(1, mlength+1);
					zend_str_tolower_copy(lcname, method, mlength);
					
					if (zend_hash_find(&scope->function_table, lcname, mlength+1, (void**)&call)==SUCCESS) {
						if (call) {
							/*
							* Make protected method call
							*/
							{
								if (access != ZEND_ACC_PROTECTED || pthreads_modifiers_protect(thread->modifiers, method, &unprotect TSRMLS_CC)) {
								
									ZVAL_STRINGL(&zmethod, method, strlen(method), 0);
									
									info.size = sizeof(info);
									info.object_ptr = getThis();
									info.function_name = &zmethod;
									info.retval_ptr_ptr = &zresult;
									info.no_separation = 1;
									info.symbol_table = NULL;
									info.param_count = argc;
									info.params = argv;
									
									cache.initialized = 1;
									cache.function_handler = call;
									cache.calling_scope = EG(scope);
									cache.called_scope = scope;
									cache.object_ptr = getThis();
									
									if ((called=zend_call_function(&info, &cache TSRMLS_CC))!=SUCCESS) {
										zend_error(
											E_ERROR, 
											"pthreads has experienced an internal error while calling %s method %s::%s and cannot continue", 
											(access == ZEND_ACC_PROTECTED) ? "protected" : "private",
											scope->name,
											method
										);
										called = FAILURE;
									} else {
#if PHP_VERSION_ID > 50399
										{
											zend_op_array *ops = (zend_op_array*) call;
										
											if (ops) {
												if (ops->run_time_cache) {
													efree(ops->run_time_cache);
													ops->run_time_cache = NULL;
												}
											}
										}
#endif
                                        
										if (zresult) {
										    if (!return_value_used) {
											    zval_ptr_dtor(&zresult);
										    } else {
											    ZVAL_ZVAL(return_value, zresult, 1, 1);
										    }
										}
									}
									
									if (access == ZEND_ACC_PROTECTED) {
										pthreads_modifiers_unprotect(thread->modifiers, method, unprotect TSRMLS_CC);
									}
								} else {
									zend_error(
										E_ERROR, 
										"pthreads has experienced an internal error while calling %s method %s::%s and cannot continue", 
										(access == ZEND_ACC_PROTECTED) ? "protected" : "private",
										scope->name,
										method
									);
									called = FAILURE;
								}
							}
						} else {
							zend_error(
								E_ERROR, 
								"pthreads has experienced an internal error while finding %s method %s::%s and cannot continue", 
								(access == ZEND_ACC_PROTECTED) ? "protected" : "private",
								scope->name,
								method
							);
							called = FAILURE;
						}
					}
					/*
					* Free unstacked arguments
					*/
					if (argc) {
						efree(argv);
					}
					free(lcname);
					return called;
				} break;
			}
		}
	}
	
	switch (called) {
		case -1: 
			return zend_handlers->call_method(PTHREADS_CALL_METHOD_PASSTHRU_C);
			
		default: return called;
	}
	
} /* }}} */
/* {{{ proto XmlIndexLookup::XmlIndexLookup()
   Create a new index specification object */
PHP_DBXML_METHOD_BEGIN(XmlIndexLookup, XmlIndexLookup)
{
  zend_error(E_ERROR, "XmlIndexLookup can not be instantiated from PHP");
} PHP_DBXML_METHOD_END()
Esempio n. 6
0
/* }}} */
static void xc_fcntl_unlock(xc_fcntl_mutex_t *fcntl_mutex) /* {{{ */
{
	if (dolock(fcntl_mutex, LCK_UN) < 0) {
		zend_error(E_ERROR, "xc_fcntl_unlock failed errno:%d", errno);
	}
}
Esempio n. 7
0
PHP_METHOD(MongoDB, command) {
  zval limit, *temp, *cmd, *cursor, *ns, *options = 0;
  mongo_db *db;
  mongo_link *link;
  char *cmd_ns;

  if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "z|a", &cmd, &options) == FAILURE) {
    return;
  }
  if (IS_SCALAR_P(cmd)) {
    zend_error(E_WARNING, "MongoDB::command() expects parameter 1 to be an array or object");
    return;
  }

  PHP_MONGO_GET_DB(getThis());

  // create db.$cmd
  MAKE_STD_ZVAL(ns);
  cmd_ns = get_cmd_ns(Z_STRVAL_P(db->name), Z_STRLEN_P(db->name));
  ZVAL_STRING(ns, cmd_ns, 0);

  // create cursor
  MAKE_STD_ZVAL(cursor);
  object_init_ex(cursor, mongo_ce_Cursor);
  MAKE_STD_ZVAL(temp);
  ZVAL_NULL(temp);

  MONGO_METHOD3(MongoCursor, __construct, temp, cursor, db->link, ns, cmd);

  zval_ptr_dtor(&ns);
  zval_ptr_dtor(&temp);
  MAKE_STD_ZVAL(temp);
  ZVAL_NULL(temp);

  // limit
  Z_TYPE(limit) = IS_LONG;
  Z_LVAL(limit) = -1;
  MONGO_METHOD1(MongoCursor, limit, temp, cursor, &limit);

  zval_ptr_dtor(&temp);

  if (options) {
    zval **timeout;
    if (zend_hash_find(HASH_P(options), "timeout", strlen("timeout")+1, (void**)&timeout) == SUCCESS) {
      MAKE_STD_ZVAL(temp);
      ZVAL_NULL(temp);
      MONGO_METHOD1(MongoCursor, timeout, temp, cursor, *timeout);
      zval_ptr_dtor(&temp);
    }
  }

  // make sure commands aren't be sent to slaves
  PHP_MONGO_GET_LINK(db->link);
  if (link->rs) {
    zval slave_okay;
    Z_TYPE(slave_okay) = IS_BOOL;
    Z_LVAL(slave_okay) = 0;

    MAKE_STD_ZVAL(temp);
    ZVAL_NULL(temp);
    MONGO_METHOD1(MongoCursor, slaveOkay, temp, cursor, &slave_okay);
    zval_ptr_dtor(&temp);
  }

  // query
  MONGO_METHOD(MongoCursor, getNext, return_value, cursor);
  clear_exception(return_value TSRMLS_CC);

  zend_objects_store_del_ref(cursor TSRMLS_CC);
  zval_ptr_dtor(&cursor);
}
Esempio n. 8
0
/* {{{ install_class */
static int install_class(apc_class_t cl, apc_context_t* ctxt, int lazy TSRMLS_DC)
{
    zend_class_entry* class_entry = cl.class_entry;
    zend_class_entry* parent = NULL;
    int status;

    /* Special case for mangled names. Mangled names are unique to a file.
     * There is no way two classes with the same mangled name will occur,
     * unless a file is included twice. And if in case, a file is included
     * twice, all mangled name conflicts can be ignored and the class redeclaration
     * error may be deferred till runtime of the corresponding DECLARE_CLASS
     * calls.
     */

    if(cl.name_len != 0 && cl.name[0] == '\0') {
        if(zend_hash_exists(CG(class_table), cl.name, cl.name_len+1)) {
            return SUCCESS;
        }
    }

    if(lazy && cl.name_len != 0 && cl.name[0] != '\0') {
        status = zend_hash_add(APCG(lazy_class_table),
                               cl.name,
                               cl.name_len+1,
                               &cl,
                               sizeof(apc_class_t),
                               NULL);
        if(status == FAILURE) {
            zend_error(E_ERROR, "Cannot redeclare class %s", cl.name);
        }
        return status;
    }

    class_entry =
        apc_copy_class_entry_for_execution(cl.class_entry, ctxt TSRMLS_CC);
    if (class_entry == NULL)
        return FAILURE;


    /* restore parent class pointer for compile-time inheritance */
    if (cl.parent_name != NULL) {
        zend_class_entry** parent_ptr = NULL;
        /*
         * __autoload brings in the old issues with mixed inheritance.
         * When a statically inherited class triggers autoload, it runs
         * afoul of a potential require_once "parent.php" in the previous 
         * line, which when executed provides the parent class, but right
         * now goes and hits __autoload which could fail. 
         * 
         * missing parent == re-compile. 
         *
         * whether __autoload is enabled or not, because __autoload errors
         * cause php to die.
         *
         * Aside: Do NOT pass *strlen(cl.parent_name)+1* because
         * zend_lookup_class_ex does it internally anyway!
         */
        status = zend_lookup_class_ex(cl.parent_name,
                                    strlen(cl.parent_name), 
#ifdef ZEND_ENGINE_2_4
                                    NULL,
#endif
                                    0,
                                    &parent_ptr TSRMLS_CC);
        if (status == FAILURE) {
            if(APCG(report_autofilter)) {
                apc_warning("Dynamic inheritance detected for class %s" TSRMLS_CC, cl.name);
            }
            class_entry->parent = NULL;
            return status;
        }
        else {
            parent = *parent_ptr;
            class_entry->parent = parent;
            zend_do_inheritance(class_entry, parent TSRMLS_CC);
        }
    }

    status = zend_hash_add(EG(class_table),
                           cl.name,
                           cl.name_len+1,
                           &class_entry,
                           sizeof(zend_class_entry*),
                           NULL);

    if (status == FAILURE) {
        apc_error("Cannot redeclare class %s" TSRMLS_CC, cl.name);
    }

    return status;
}
Esempio n. 9
0
void orbit_class_function_call(
    zend_class_entry * pClass,
    int dataType,
    zend_property_reference *pPropertyReference,
    Class_Constructor pConstructor,
    Class_CallFunction pCallFunction,
    INTERNAL_FUNCTION_PARAMETERS)
{
    /* get object */
    zval * object = pPropertyReference->object;

    /* get function name */
    zend_overloaded_element * function_name =
        (zend_overloaded_element *)pPropertyReference->elements_list->tail->data;

    /* handle parameters */
    zval ** arguments = orbit_new_n(zval *, ZEND_NUM_ARGS());
    /*(zval **)emalloc(sizeof(zval *) * ZEND_NUM_ARGS());*/
    if (getParametersArray(ht, ZEND_NUM_ARGS(), arguments) == FAILURE)
    {
        /* TODO: handle error */
    }

    /* constructor or normal function? */
    if (zend_llist_count(pPropertyReference->elements_list) == 1
            && !strcasecmp(function_name->element.value.str.val, pClass->name))
    {
        /* constructor */
        if (pConstructor)
        {
            void * p_data = NULL;
            zend_bool success = (*pConstructor)(&p_data, ZEND_NUM_ARGS(), arguments);

            if (success)
                orbit_save_data(object, dataType, p_data);
        }
        else
        {
            zend_error(E_WARNING, "(Satellite) This class has no constructor");
            \
        }
    }
    else
    {
        /* normal function */
        if (pCallFunction)
        {
            void * p_data = orbit_retrieve_data(object, dataType);

            if (p_data == NULL)
            {
                /*
                 * this means that the constructor has failed earlier!
                 * -- or should NULL be allowed here?
                 */
                php_error(E_WARNING, "(Satellite) Class has no data!");
                RETVAL_NULL();
                goto orbit_class_function_call_exit;
            }

            /* pval * return_value is a part of INTERNAL_FUNCTION_PARAMETERS */
            (*pCallFunction)(p_data, function_name->element.value.str.val,
                             ZEND_NUM_ARGS(), arguments, return_value);
        }
        else
        {
            zend_error(E_WARNING, "(Satellite) Can't call functions in this class");
            \
        }
    }

orbit_class_function_call_exit:
    satellite_delete(arguments);

    /* seems to be required! */
    zval_dtor(&function_name->element);
}
Esempio n. 10
0
ZEND_API void zend_create_closure(zval *res, zend_function *func, zend_class_entry *scope, zend_class_entry *called_scope, zval *this_ptr) /* {{{ */
{
	zend_closure *closure;

	object_init_ex(res, zend_ce_closure);

	closure = (zend_closure *)Z_OBJ_P(res);

	if ((scope == NULL) && this_ptr && (Z_TYPE_P(this_ptr) != IS_UNDEF)) {
		/* use dummy scope if we're binding an object without specifying a scope */
		/* maybe it would be better to create one for this purpose */
		scope = zend_ce_closure;
	}

	if (func->type == ZEND_USER_FUNCTION) {
		memcpy(&closure->func, func, sizeof(zend_op_array));
		closure->func.common.prototype = (zend_function*)closure;
		closure->func.common.fn_flags |= ZEND_ACC_CLOSURE;
		if (closure->func.op_array.static_variables) {
			HashTable *static_variables = closure->func.op_array.static_variables;

			ALLOC_HASHTABLE(closure->func.op_array.static_variables);
			zend_hash_init(closure->func.op_array.static_variables, zend_hash_num_elements(static_variables), NULL, ZVAL_PTR_DTOR, 0);
			zend_hash_apply_with_arguments(static_variables, zval_copy_static_var, 1, closure->func.op_array.static_variables);
		}
		if (UNEXPECTED(!closure->func.op_array.run_time_cache)) {
			closure->func.op_array.run_time_cache = func->op_array.run_time_cache = zend_arena_alloc(&CG(arena), func->op_array.cache_size);
			memset(func->op_array.run_time_cache, 0, func->op_array.cache_size);
		}
		if (closure->func.op_array.refcount) {
			(*closure->func.op_array.refcount)++;
		}
	} else {
		memcpy(&closure->func, func, sizeof(zend_internal_function));
		closure->func.common.prototype = (zend_function*)closure;
		closure->func.common.fn_flags |= ZEND_ACC_CLOSURE;
		/* wrap internal function handler to avoid memory leak */
		if (UNEXPECTED(closure->func.internal_function.handler == zend_closure_internal_handler)) {
			/* avoid infinity recursion, by taking handler from nested closure */
			zend_closure *nested = (zend_closure*)((char*)func - XtOffsetOf(zend_closure, func));
			ZEND_ASSERT(nested->std.ce == zend_ce_closure);
			closure->orig_internal_handler = nested->orig_internal_handler;
		} else {
			closure->orig_internal_handler = closure->func.internal_function.handler;
		}
		closure->func.internal_function.handler = zend_closure_internal_handler;
		/* verify that we aren't binding internal function to a wrong scope */
		if(func->common.scope != NULL) {
			if(scope && !instanceof_function(scope, func->common.scope)) {
				zend_error(E_WARNING, "Cannot bind function %s::%s to scope class %s", ZSTR_VAL(func->common.scope->name), ZSTR_VAL(func->common.function_name), ZSTR_VAL(scope->name));
				scope = NULL;
			}
			if(scope && this_ptr && (func->common.fn_flags & ZEND_ACC_STATIC) == 0 &&
					!instanceof_function(Z_OBJCE_P(this_ptr), closure->func.common.scope)) {
				zend_error(E_WARNING, "Cannot bind function %s::%s to object of class %s", ZSTR_VAL(func->common.scope->name), ZSTR_VAL(func->common.function_name), ZSTR_VAL(Z_OBJCE_P(this_ptr)->name));
				scope = NULL;
				this_ptr = NULL;
			}
		} else {
			/* if it's a free function, we won't set scope & this since they're meaningless */
			this_ptr = NULL;
			scope = NULL;
		}
	}

	ZVAL_UNDEF(&closure->this_ptr);
	/* Invariant:
	 * If the closure is unscoped or static, it has no bound object. */
	closure->func.common.scope = scope;
	closure->called_scope = called_scope;
	if (scope) {
		closure->func.common.fn_flags |= ZEND_ACC_PUBLIC;
		if (this_ptr && Z_TYPE_P(this_ptr) == IS_OBJECT && (closure->func.common.fn_flags & ZEND_ACC_STATIC) == 0) {
			ZVAL_COPY(&closure->this_ptr, this_ptr);
		}
	}
}
Esempio n. 11
0
/* {{{ proto mixed Closure::call(object to [, mixed parameter] [, mixed ...] )
   Call closure, binding to a given object with its class as the scope */
ZEND_METHOD(Closure, call)
{
	zval *zclosure, *newthis, closure_result;
	zend_closure *closure;
	zend_fcall_info fci;
	zend_fcall_info_cache fci_cache;
	zval *my_params;
	int my_param_count = 0;
	zend_function my_function;
	zend_object *newobj;

	if (zend_parse_parameters(ZEND_NUM_ARGS(), "o*", &newthis, &my_params, &my_param_count) == FAILURE) {
		return;
	}

	zclosure = getThis();
	closure = (zend_closure *) Z_OBJ_P(zclosure);

	if (closure->func.common.fn_flags & ZEND_ACC_STATIC) {
		zend_error(E_WARNING, "Cannot bind an instance to a static closure");
		return;
	}

	if (closure->func.type == ZEND_INTERNAL_FUNCTION) {
		/* verify that we aren't binding internal function to a wrong object */
		if ((closure->func.common.fn_flags & ZEND_ACC_STATIC) == 0 &&
				closure->func.common.scope &&
				!instanceof_function(Z_OBJCE_P(newthis), closure->func.common.scope)) {
			zend_error(E_WARNING, "Cannot bind function %s::%s to object of class %s", ZSTR_VAL(closure->func.common.scope->name), ZSTR_VAL(closure->func.common.function_name), ZSTR_VAL(Z_OBJCE_P(newthis)->name));
			return;
		}
	}

	newobj = Z_OBJ_P(newthis);

	if (newobj->ce != closure->func.common.scope && newobj->ce->type == ZEND_INTERNAL_CLASS) {
		/* rebinding to internal class is not allowed */
		zend_error(E_WARNING, "Cannot bind closure to object of internal class %s", ZSTR_VAL(newobj->ce->name));
		return;
	}

	/* This should never happen as closures will always be callable */
	if (zend_fcall_info_init(zclosure, 0, &fci, &fci_cache, NULL, NULL) != SUCCESS) {
		ZEND_ASSERT(0);
	}

	fci.retval = &closure_result;
	fci.params = my_params;
	fci.param_count = my_param_count;
	fci.object = fci_cache.object = newobj;
	fci_cache.initialized = 1;

	if (fci_cache.function_handler->common.fn_flags & ZEND_ACC_GENERATOR) {
		zval new_closure;
		zend_create_closure(&new_closure, fci_cache.function_handler, Z_OBJCE_P(newthis), closure->called_scope, newthis);
		closure = (zend_closure *) Z_OBJ(new_closure);
		fci_cache.function_handler = &closure->func;
	} else {
		memcpy(&my_function, fci_cache.function_handler, fci_cache.function_handler->type == ZEND_USER_FUNCTION ? sizeof(zend_op_array) : sizeof(zend_internal_function));
		/* use scope of passed object */
		my_function.common.scope = Z_OBJCE_P(newthis);
		fci_cache.function_handler = &my_function;

		/* Runtime cache relies on bound scope to be immutable, hence we need a separate rt cache in case scope changed */
		if (ZEND_USER_CODE(my_function.type) && closure->func.common.scope != Z_OBJCE_P(newthis)) {
			my_function.op_array.run_time_cache = emalloc(my_function.op_array.cache_size);
			memset(my_function.op_array.run_time_cache, 0, my_function.op_array.cache_size);
		}
	}

	if (zend_call_function(&fci, &fci_cache) == SUCCESS && Z_TYPE(closure_result) != IS_UNDEF) {
		ZVAL_COPY_VALUE(return_value, &closure_result);
	}

	if (fci_cache.function_handler->common.fn_flags & ZEND_ACC_GENERATOR) {
		/* copied upon generator creation */
		--GC_REFCOUNT(&closure->std);
	} else if (ZEND_USER_CODE(my_function.type) && closure->func.common.scope != Z_OBJCE_P(newthis)) {
		efree(my_function.op_array.run_time_cache);
	}
}
Esempio n. 12
0
/* {{{ proto Closure Closure::bind(callable old, object to [, mixed scope])
   Create a closure from another one and bind to another object and scope */
ZEND_METHOD(Closure, bind)
{
	zval *newthis, *zclosure, *scope_arg = NULL;
	zend_closure *closure, *new_closure;
	zend_class_entry *ce, *called_scope;

	if (zend_parse_method_parameters(ZEND_NUM_ARGS(), getThis(), "Oo!|z", &zclosure, zend_ce_closure, &newthis, &scope_arg) == FAILURE) {
		RETURN_NULL();
	}

	closure = (zend_closure *)Z_OBJ_P(zclosure);

	if ((newthis != NULL) && (closure->func.common.fn_flags & ZEND_ACC_STATIC)) {
		zend_error(E_WARNING, "Cannot bind an instance to a static closure");
	}

	if (newthis == NULL && !(closure->func.common.fn_flags & ZEND_ACC_STATIC)
			&& closure->func.common.scope && closure->func.type == ZEND_INTERNAL_FUNCTION) {
		zend_error(E_WARNING, "Cannot unbind $this of internal method");
		return;
	}

	if (scope_arg != NULL) { /* scope argument was given */
		if (Z_TYPE_P(scope_arg) == IS_OBJECT) {
			ce = Z_OBJCE_P(scope_arg);
		} else if (Z_TYPE_P(scope_arg) == IS_NULL) {
			ce = NULL;
		} else {
			zend_string *class_name = zval_get_string(scope_arg);
			if (zend_string_equals_literal(class_name, "static")) {
				ce = closure->func.common.scope;
			} else if ((ce = zend_lookup_class_ex(class_name, NULL, 1)) == NULL) {
				zend_error(E_WARNING, "Class '%s' not found", ZSTR_VAL(class_name));
				zend_string_release(class_name);
				RETURN_NULL();
			}
			zend_string_release(class_name);
		}
		if(ce && ce != closure->func.common.scope && ce->type == ZEND_INTERNAL_CLASS) {
			/* rebinding to internal class is not allowed */
			zend_error(E_WARNING, "Cannot bind closure to scope of internal class %s", ZSTR_VAL(ce->name));
			return;
		}
	} else { /* scope argument not given; do not change the scope by default */
		ce = closure->func.common.scope;
	}

	if (newthis) {
		called_scope = Z_OBJCE_P(newthis);
	} else {
		called_scope = ce;
	}

	zend_create_closure(return_value, &closure->func, ce, called_scope, newthis);
	new_closure = (zend_closure *) Z_OBJ_P(return_value);

	/* Runtime cache relies on bound scope to be immutable, hence we need a separate rt cache in case scope changed */
	if (ZEND_USER_CODE(closure->func.type) && (closure->func.common.scope != new_closure->func.common.scope || (closure->func.op_array.fn_flags & ZEND_ACC_NO_RT_ARENA))) {
		new_closure->func.op_array.run_time_cache = emalloc(new_closure->func.op_array.cache_size);
		memset(new_closure->func.op_array.run_time_cache, 0, new_closure->func.op_array.cache_size);

		new_closure->func.op_array.fn_flags |= ZEND_ACC_NO_RT_ARENA;
	}
}
Esempio n. 13
0
/* }}} */
static XC_SHM_INIT(xc_mmap_init) /* {{{ */
{
#ifdef ZEND_WIN32
#	define TMP_PATH "XCache"
#else
#	define TMP_PATH "/tmp/XCache"
	int fd = -1;
#endif
	xc_shm_t *shm = NULL;
	int ro_ok;
	volatile void *romem;
	char tmpname[sizeof(TMP_PATH) - 1 + 4 * 10 + 100] = { 0 };
	const char *errstr = NULL;
	const char *path = (const char *) arg1;
	static int instanceId = 0;

	CHECK(shm = calloc(1, sizeof(xc_shm_t)), "shm OOM");
	shm->size = size;

	if (path == NULL || !path[0]) {
		snprintf(tmpname, sizeof(tmpname) - 1, "%s.%d.%d.%d", TMP_PATH, (int) getuid(), (int) getpid(), ++instanceId);
		path = tmpname;
	}
#ifdef ZEND_WIN32
	else {
		snprintf(tmpname, sizeof(tmpname) - 1, "%s.%d.%d.%d", path, (int) getuid(), (int) getpid(), ++instanceId);
		path = tmpname;
	}
#endif

	shm->name = strdup(path);

#ifndef ZEND_WIN32
#	define XCACHE_MMAP_PERMISSION (S_IRUSR | S_IWUSR)
	fd = open(shm->name, O_RDWR, XCACHE_MMAP_PERMISSION);
	if (fd == -1) {
		/* do not create file in /dev */
		if (strncmp(shm->name, "/dev", 4) == 0) {
			perror(shm->name);
			errstr = "Cannot open file set by xcache.mmap_path, check the xcache.size/var_size against system limitation";
			goto err;
		}
		fd = open(shm->name, O_CREAT | O_RDWR, XCACHE_MMAP_PERMISSION);
		shm->newfile = 1;
		if (fd == -1) {
			perror(shm->name);
			errstr = "Cannot open or create file set by xcache.mmap_path, check the path permission or check xcache.size/var_size against system limitation";
			goto err;
		}
	}

	if (ftruncate(fd, size) != 0 && errno != EINVAL) {
		perror(shm->name);
		errstr = "Failed to ftruncate the file";
		goto err;
	}
#endif

#ifdef ZEND_WIN32
	shm->hmap = XCacheCreateFileMapping(size, PAGE_READWRITE, shm->name);
	shm->ptr = (LPSTR) MapViewOfFile(shm->hmap, FILE_MAP_WRITE, 0, 0, 0);
#else
	shm->ptr = mmap(NULL, size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);
#endif

	if (shm->ptr == XCACHE_MAP_FAILED) {
		perror(shm->name);
		errstr = "Failed creating file mapping";
		shm->ptr = NULL;
		goto err;
	}

	/* {{{ readonly protection, mmap it readonly and check if ptr_ro works */
	if (readonly_protection) {
		ro_ok = 0;

#ifdef ZEND_WIN32
		shm->hmap_ro = XCacheCreateFileMapping(size, PAGE_READONLY, shm->name);
		shm->ptr_ro = (LPSTR) MapViewOfFile(shm->hmap_ro, FILE_MAP_READ, 0, 0, 0);
#else
		shm->ptr_ro = mmap(NULL, size, PROT_READ, MAP_SHARED, fd, 0);
#endif
		if (shm->ptr_ro == XCACHE_MAP_FAILED) {
			shm->ptr_ro = NULL;
		}
		romem = shm->ptr_ro;

		do {
			if (romem == NULL || romem == shm->ptr) {
				break;
			}
			*(char *)shm->ptr = 1;
			if (*(char *)romem != 1) {
				break;
			}
			*(char *)shm->ptr = 2;
			if (*(char *)romem != 2) {
				break;
			}
			ro_ok = 1;
		} while (0);

		if (ro_ok) {
			shm->diff = PTR_SUB(shm->ptr_ro, (char *) shm->ptr);
			/* no overlap */
			assert((xc_shmsize_t) abs(shm->diff) >= size);
		}
		else {
			if (shm->ptr_ro) {
				munmap(shm->ptr_ro, size);
			}
#ifdef ZEND_WIN32
			if (shm->hmap_ro) {
				CloseHandle(shm->hmap_ro);
			}
#endif
			shm->ptr_ro = NULL;
			shm->diff = 0;
		}
	}

	/* }}} */

#ifndef ZEND_WIN32
	close(fd);

#	ifndef __CYGWIN__
	if (shm->newfile) {
		unlink(shm->name);
	}
#	endif
#endif

	return shm;

err:
#ifndef ZEND_WIN32
	if (fd != -1) {
		close(fd);
	}
#endif
	if (shm) {
		xc_mmap_destroy(shm);
	}
	if (errstr) {
		fprintf(stderr, "%s\n", errstr);
		zend_error(E_ERROR, "%s", errstr);
	}
	return NULL;
}
Esempio n. 14
0
/* {{{ proto object ffmpeg_movie(string filename) 
   Constructor for ffmpeg_movie objects
 */
FFMPEG_PHP_CONSTRUCTOR(ffmpeg_movie, __construct)
{
    int persistent = 0, hashkey_length = 0;
    char *filename = NULL, *fullpath = NULL, *hashkey = NULL;
    zval ***argv;
    ff_movie_context *ffmovie_ctx = NULL;

    /* retrieve arguments */ 
    argv = (zval ***) safe_emalloc(sizeof(zval **), ZEND_NUM_ARGS(), 0);

    if (zend_get_parameters_array_ex(ZEND_NUM_ARGS(), argv) != SUCCESS) {
        efree(argv);
        php_error_docref(NULL TSRMLS_CC, E_ERROR,
                "Error parsing arguments");
    }

    switch (ZEND_NUM_ARGS()) {
        case 2:
            convert_to_boolean_ex(argv[1]);

            if (! INI_BOOL("ffmpeg.allow_persistent") && Z_LVAL_PP(argv[1])) {
                zend_error(E_WARNING, 
                        "Persistent movies have been disabled in php.ini");
                break;
            } 

            persistent = Z_LVAL_PP(argv[1]);

            /* fallthru */
        case 1:
            convert_to_string_ex(argv[0]);
            filename = Z_STRVAL_PP(argv[0]);
            break;
        default:
            WRONG_PARAM_COUNT;
    } 

    if (persistent) {
        list_entry *le;
        /* resolve the fully-qualified path name to use as the hash key */
        fullpath = expand_filepath(filename, NULL TSRMLS_CC);

        hashkey_length = sizeof("ffmpeg-php_")-1 + 
            strlen(SAFE_STRING(filename));
        hashkey = (char *) emalloc(hashkey_length+1);
        snprintf(hashkey, hashkey_length, "ffmpeg-php_%s",
			SAFE_STRING(filename));

        
        /* do we have an existing persistent movie? */
        if (SUCCESS == zend_hash_find(&EG(persistent_list), hashkey, 
                    hashkey_length+1, (void**)&le)) {
            int type;
            
            if (Z_TYPE_P(le) != le_ffmpeg_pmovie) {
                php_error_docref(NULL TSRMLS_CC, E_ERROR, 
                        "Failed to retrieve persistent resource");
            }
            ffmovie_ctx = (ff_movie_context*)le->ptr;
           
            /* sanity check to ensure that the resource is still a valid 
             * regular resource number */
            if (zend_list_find(ffmovie_ctx->rsrc_id, &type) == ffmovie_ctx) {
                /* add a reference to the persistent movie */
                zend_list_addref(ffmovie_ctx->rsrc_id);
            } else {
                //php_error_docref(NULL TSRMLS_CC, E_ERROR, 
                //"Not a valid persistent movie resource");
                ffmovie_ctx->rsrc_id = ZEND_REGISTER_RESOURCE(NULL, 
                        ffmovie_ctx, le_ffmpeg_pmovie);
            }
            
        } else { /* no existing persistant movie, create one */
            list_entry new_le;
            ffmovie_ctx = _php_alloc_ffmovie_ctx(1);

            if (_php_open_movie_file(ffmovie_ctx, filename)) {
                zend_error(E_WARNING, "Can't open movie file %s", filename);
                efree(argv);
                ZVAL_BOOL(getThis(), 0);
                RETURN_FALSE;
            }

            Z_TYPE(new_le) = le_ffmpeg_pmovie;
            new_le.ptr = ffmovie_ctx;

            if (FAILURE == zend_hash_update(&EG(persistent_list), hashkey, 
                        hashkey_length+1, (void *)&new_le, sizeof(list_entry),
                        NULL)) {
                php_error_docref(NULL TSRMLS_CC, E_WARNING, 
                        "Failed to register persistent resource");
            }
            
            ffmovie_ctx->rsrc_id = ZEND_REGISTER_RESOURCE(NULL, ffmovie_ctx, 
                    le_ffmpeg_pmovie);
        }
        
    } else {
        ffmovie_ctx = _php_alloc_ffmovie_ctx(0);
        
        if (_php_open_movie_file(ffmovie_ctx, Z_STRVAL_PP(argv[0]))) {
            zend_error(E_WARNING, "Can't open movie file %s", 
                    Z_STRVAL_PP(argv[0]));
            efree(argv);
            ZVAL_BOOL(getThis(), 0);
            RETURN_FALSE;
        }
        
        /* pass NULL for resource result since we're not returning the resource
           directly, but adding it to the returned object. */
        ffmovie_ctx->rsrc_id = ZEND_REGISTER_RESOURCE(NULL, ffmovie_ctx, 
                le_ffmpeg_movie);
    }

    object_init_ex(getThis(), ffmpeg_movie_class_entry_ptr);
    add_property_resource(getThis(), "ffmpeg_movie", ffmovie_ctx->rsrc_id);

    efree(argv);
    if (fullpath) {
        efree(fullpath);
    }
    if (hashkey) {
        efree(hashkey);
    }
}
Esempio n. 15
0
ZEND_API void wrong_param_count()
{
	zend_error(E_WARNING,"Wrong parameter count for %s()",get_active_function_name());
}
Esempio n. 16
0
/**
 * Checks if a method is callable
 */
static int zephir_alt_is_callable_check_method(zend_class_entry *ce, int check_flags, char *method_name, unsigned int method_len, zend_fcall_info_cache *fcc, char **error, unsigned long method_key TSRMLS_DC)
{
	int retval = 0;

	#ifndef ZEPHIR_RELEASE
	int call_via_handler = 0;
	#endif

	if (error) {
		*error = NULL;
	}

	if (!method_key) {
		method_key = zend_inline_hash_func(method_name, method_len + 1);
	}

	/* Try to fetch find static method of given class. */
	if (likely(zephir_hash_quick_find(&ce->function_table, method_name, method_len + 1, method_key, (void**) &fcc->function_handler) == SUCCESS)) {
		retval = 1;
		if ((fcc->function_handler->op_array.fn_flags & ZEND_ACC_CHANGED) && ZEPHIR_EG(scope) && instanceof_function(fcc->function_handler->common.scope, EG(scope) TSRMLS_CC)) {
			zend_function *priv_fbc;
			if (zephir_hash_quick_find(&ZEPHIR_EG(scope)->function_table, method_name, method_len + 1, method_key, (void **) &priv_fbc)==SUCCESS && (priv_fbc->common.fn_flags & ZEND_ACC_PRIVATE) && priv_fbc->common.scope == EG(scope)) {
				fcc->function_handler = priv_fbc;
			}
		}
		#ifndef ZEPHIR_RELEASE
		if ((check_flags & IS_CALLABLE_CHECK_NO_ACCESS) == 0 && (fcc->calling_scope && (fcc->calling_scope->__call || fcc->calling_scope->__callstatic))) {
			if (fcc->function_handler->op_array.fn_flags & ZEND_ACC_PRIVATE) {
				if (!zend_check_private(fcc->function_handler, ce, method_name, method_len TSRMLS_CC)) {
					retval = 0;
					fcc->function_handler = NULL;
					goto get_function_via_handler;
				}
			} else {
				if (fcc->function_handler->common.fn_flags & ZEND_ACC_PROTECTED) {
					if (!zend_check_protected(fcc->function_handler->common.scope, ZEPHIR_EG(scope))) {
						retval = 0;
						fcc->function_handler = NULL;
						goto get_function_via_handler;
					}
				}
			}
		}
		#endif
	} else {
		#ifndef ZEPHIR_RELEASE
		get_function_via_handler:
		if (Z_OBJ_HT_P(fcc->object_ptr)->get_method) {
			#if PHP_VERSION_ID < 50400
			fcc->function_handler = Z_OBJ_HT_P(fcc->object_ptr)->get_method(&fcc->object_ptr, method_name, method_len TSRMLS_CC);
			#else
			fcc->function_handler = Z_OBJ_HT_P(fcc->object_ptr)->get_method(&fcc->object_ptr, method_name, method_len, NULL TSRMLS_CC);
			#endif
			if (fcc->function_handler) {
				retval = 1;
				call_via_handler = (fcc->function_handler->common.fn_flags & ZEND_ACC_CALL_VIA_HANDLER) != 0;
			}
		}
		#endif
	}

	if (retval) {
		#ifndef ZEPHIR_RELEASE
		if (fcc->calling_scope && !call_via_handler) {
			if (!fcc->object_ptr && (fcc->function_handler->common.fn_flags & ZEND_ACC_ABSTRACT)) {
				if (error) {
					zephir_spprintf(error, 0, "cannot call abstract method %s::%s()", fcc->calling_scope->name, fcc->function_handler->common.function_name);
					retval = 0;
				} else {
					zend_error(E_ERROR, "Cannot call abstract method %s::%s()", fcc->calling_scope->name, fcc->function_handler->common.function_name);
				}
			}
			if (retval && (check_flags & IS_CALLABLE_CHECK_NO_ACCESS) == 0) {
				if (fcc->function_handler->op_array.fn_flags & ZEND_ACC_PRIVATE) {
					if (!zend_check_private(fcc->function_handler, ce, method_name, method_len TSRMLS_CC)) {
						if (error) {
							if (*error) {
								efree(*error);
							}
							zephir_spprintf(error, 0, "cannot access private method %s::%s()", fcc->calling_scope->name, fcc->function_handler->common.function_name);
						}
						retval = 0;
					}
				} else {
					if ((fcc->function_handler->common.fn_flags & ZEND_ACC_PROTECTED)) {
						if (!zend_check_protected(fcc->function_handler->common.scope, EG(scope))) {
							if (error) {
								if (*error) {
									efree(*error);
								}
								zephir_spprintf(error, 0, "cannot access protected method %s::%s()", fcc->calling_scope->name, fcc->function_handler->common.function_name);
							}
							retval = 0;
						}
					}
				}
			}
		}
		#endif
	} else {
		if (error && !(check_flags & IS_CALLABLE_CHECK_SILENT)) {
			if (fcc->calling_scope) {
				if (error) {
					zephir_spprintf(error, 0, "class '%s' does not have a method '%s'", fcc->calling_scope->name, method_name);
				}
			} else {
				if (error) {
					zephir_spprintf(error, 0, "function '%s' does not exist", method_name);
				}
			}
		}
	}

	if (retval) {
		fcc->initialized = 1;
	}
	return retval;
}
Esempio n. 17
0
void sapnwrfc_throw_connection_exception(RFC_ERROR_INFO error_info, char *msg, ...)
{
    va_list args;
    zend_string *message;
    zval info;
    zval ex;

    va_start(args, msg);
    message = vstrpprintf(0, msg, args);
    va_end(args);

    array_init(&info);

    zend_replace_error_handling(EH_THROW, sapnwrfc_connection_exception_ce, NULL);

    object_init_ex(&ex, sapnwrfc_connection_exception_ce);
    zend_update_property_string(sapnwrfc_connection_exception_ce, &ex, "message", sizeof("message") - 1, ZSTR_VAL(message));
    zend_update_property_long(sapnwrfc_connection_exception_ce, &ex, "code", sizeof("code") - 1, error_info.code);

    // populate errorInfo array
    add_assoc_long(&info, "code", error_info.code);
    add_assoc_str(&info, "key", sapuc_to_zend_string(error_info.key));
    add_assoc_str(&info, "message", sapuc_to_zend_string(error_info.message));

    switch(error_info.group) {
        case LOGON_FAILURE:                   // Error message raised when logon fails
        case COMMUNICATION_FAILURE:           // Problems with the network connection (or backend broke down and killed the connection)
        case EXTERNAL_RUNTIME_FAILURE:        // Problems in the RFC runtime of the external program (i.e "this" library)
            // no additional properties, just the generic one's from above
            break;
        case ABAP_APPLICATION_FAILURE:        // ABAP Exception raised in ABAP function modules
        case ABAP_RUNTIME_FAILURE:            // ABAP Message raised in ABAP function modules or in ABAP runtime of the backend (e.g Kernel)
        case EXTERNAL_APPLICATION_FAILURE:    // Problems in the external program (e.g in the external server implementation)
        case EXTERNAL_AUTHORIZATION_FAILURE:  // Problems raised in the authorization check handler provided by the external server implementation
            add_assoc_str(&info, "abapMsgClass", sapuc_to_zend_string(error_info.abapMsgClass));
            add_assoc_str(&info, "abapMsgType", sapuc_to_zend_string(error_info.abapMsgType));
            add_assoc_str(&info, "abapMsgNumber", sapuc_to_zend_string(error_info.abapMsgNumber));
            add_assoc_str(&info, "abapMsgV1", sapuc_to_zend_string(error_info.abapMsgV1));
            add_assoc_str(&info, "abapMsgV2", sapuc_to_zend_string(error_info.abapMsgV2));
            add_assoc_str(&info, "abapMsgV3", sapuc_to_zend_string(error_info.abapMsgV3));
            add_assoc_str(&info, "abapMsgV4", sapuc_to_zend_string(error_info.abapMsgV4));
            break;
        case RFC_OK: // LCOV_EXCL_START
            zend_error(E_ERROR, "Internal error: exception handler called for RFC_OK");
            zend_replace_error_handling(EH_NORMAL, NULL, NULL);
            zend_string_release(message);
            return;
            // LCOV_EXCL_STOP
        default:
            zend_error(E_ERROR, "Internal error: unknown error group");
            zend_replace_error_handling(EH_NORMAL, NULL, NULL);
            zend_string_release(message);
            return;
    }

    zend_update_property(sapnwrfc_connection_exception_ce, &ex, "errorInfo", sizeof("errorInfo") - 1, &info);

    zval_ptr_dtor(&info);
    zend_string_release(message);

    zend_throw_exception_object(&ex);
    zend_replace_error_handling(EH_NORMAL, NULL, NULL);
}
Esempio n. 18
0
void bc_out_of_memory (void)
{
  zend_error(E_ERROR, "bcmath: out of memory!");
}
Esempio n. 19
0
static void php_browscap_parser_cb(zval *arg1, zval *arg2, zval *arg3, int callback_type, void *arg) /* {{{ */
{
	browser_data *bdata = arg;
	int persistent = bdata->htab->u.flags & HASH_FLAG_PERSISTENT;

	if (!arg1) {
		return;
	}

	switch (callback_type) {
		case ZEND_INI_PARSER_ENTRY:
			if (Z_TYPE(bdata->current_section) != IS_UNDEF && arg2) {
				zval new_property;
				zend_string *new_key;

				/* parent entry can not be same as current section -> causes infinite loop! */
				if (!strcasecmp(Z_STRVAL_P(arg1), "parent") &&
					bdata->current_section_name != NULL &&
					!strcasecmp(bdata->current_section_name, Z_STRVAL_P(arg2))
				) {
					zend_error(E_CORE_ERROR, "Invalid browscap ini file: "
						"'Parent' value cannot be same as the section name: %s "
						"(in file %s)", bdata->current_section_name, INI_STR("browscap"));
					return;
				}

				/* Set proper value for true/false settings */
				if ((Z_STRLEN_P(arg2) == 2 && !strncasecmp(Z_STRVAL_P(arg2), "on", sizeof("on") - 1)) ||
					(Z_STRLEN_P(arg2) == 3 && !strncasecmp(Z_STRVAL_P(arg2), "yes", sizeof("yes") - 1)) ||
					(Z_STRLEN_P(arg2) == 4 && !strncasecmp(Z_STRVAL_P(arg2), "true", sizeof("true") - 1))
				) {
					ZVAL_NEW_STR(&new_property, zend_string_init("1", sizeof("1")-1, persistent));
				} else if (
					(Z_STRLEN_P(arg2) == 2 && !strncasecmp(Z_STRVAL_P(arg2), "no", sizeof("no") - 1)) ||
					(Z_STRLEN_P(arg2) == 3 && !strncasecmp(Z_STRVAL_P(arg2), "off", sizeof("off") - 1)) ||
					(Z_STRLEN_P(arg2) == 4 && !strncasecmp(Z_STRVAL_P(arg2), "none", sizeof("none") - 1)) ||
					(Z_STRLEN_P(arg2) == 5 && !strncasecmp(Z_STRVAL_P(arg2), "false", sizeof("false") - 1))
				) {
					// TODO: USE ZSTR_EMPTY_ALLOC()?
					ZVAL_NEW_STR(&new_property, zend_string_init("", sizeof("")-1, persistent));
				} else { /* Other than true/false setting */
					ZVAL_STR(&new_property, zend_string_dup(Z_STR_P(arg2), persistent));
				}
				new_key = zend_string_dup(Z_STR_P(arg1), persistent);
				zend_str_tolower(ZSTR_VAL(new_key), ZSTR_LEN(new_key));
				zend_hash_update(Z_ARRVAL(bdata->current_section), new_key, &new_property);
				zend_string_release(new_key);
			}
			break;
		case ZEND_INI_PARSER_SECTION: {
				zval processed;
				zval unprocessed;

				/*printf("'%s' (%d)\n",$1.value.str.val,$1.value.str.len + 1);*/
				if (persistent) {
					ZVAL_NEW_PERSISTENT_ARR(&bdata->current_section);
				} else {
					ZVAL_NEW_ARR(&bdata->current_section);
				}
				zend_hash_init(Z_ARRVAL(bdata->current_section), 0, NULL,
						(dtor_func_t) (persistent?browscap_entry_dtor_persistent
												 :browscap_entry_dtor_request),
						persistent);
				if (bdata->current_section_name) {
					pefree(bdata->current_section_name, persistent);
				}
				bdata->current_section_name = pestrndup(Z_STRVAL_P(arg1),
						Z_STRLEN_P(arg1), persistent);

				zend_hash_update(bdata->htab, Z_STR_P(arg1), &bdata->current_section);

				ZVAL_STR(&processed, Z_STR_P(arg1));
				ZVAL_STR(&unprocessed, zend_string_dup(Z_STR_P(arg1), persistent));

				convert_browscap_pattern(&processed, persistent);
				zend_hash_str_update(Z_ARRVAL(bdata->current_section), "browser_name_regex", sizeof("browser_name_regex")-1, &processed);
				zend_hash_str_update(Z_ARRVAL(bdata->current_section), "browser_name_pattern", sizeof("browser_name_pattern")-1, &unprocessed);
			}
			break;
	}
}
Esempio n. 20
0
/* PHP */
static ZEND_FUNCTION(hs_compress)
{
    zval *data;
    size_t data_len;
    size_t sink_sz = 0;
    size_t poll_sz = 0;
    HSE_sink_res sres;
    HSE_poll_res pres;
    HSE_finish_res fres;
    //Default window_sz2 and lookahead_sz2 values
    uint8_t window = DEF_WINDOW_SZ2;
    uint8_t lookahead = DEF_LOOKAHEAD_SZ2;

    if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC,
                              "z|ll", &data, &window,
                              &lookahead) == FAILURE) {
        RETURN_FALSE;
    }

    if (Z_TYPE_P(data) != IS_STRING) {
        zend_error(E_WARNING, "hs_compress : expects parameter to be string.");
        RETURN_FALSE;
    }

    //Allocate encoder
    heatshrink_encoder *hse = heatshrink_encoder_alloc(window, lookahead);
    if (hse == NULL) {
        zend_error(E_WARNING, "hs_compress : heatshrink_encoder_alloc error. Check window and lookahead values.");
        RETURN_FALSE;
    }

    data_len = Z_STRLEN_P(data);
    //TODO: think of better way to compute outbuff size
    size_t outbuff_len = data_len+1;
    unsigned char *outbuff = (unsigned char *) emalloc(outbuff_len);

    size_t sunk = 0;
    do {
        sres = heatshrink_encoder_sink(hse, (unsigned char *) &(Z_STRVAL_P(data)[sunk]), data_len - sunk, &sink_sz);
        if (sres < 0) {
            zend_error(E_WARNING, "hs_compress : heatshrink_encoder_sink error");
            efree(outbuff);
            heatshrink_encoder_free(hse);
            RETURN_FALSE;
        }
        sunk += sink_sz;
        
        do {
            do {
                pres = heatshrink_encoder_poll(hse, &outbuff[poll_sz], outbuff_len - poll_sz, &sink_sz);

                if (pres < 0) {
                    zend_error(E_WARNING, "hs_compress : heatshrink_encoder_poll error");
                    efree(outbuff);
                    heatshrink_encoder_free(hse);
                    RETURN_FALSE;
                }
                poll_sz += sink_sz;
                if (poll_sz == outbuff_len && pres == HSER_POLL_MORE) {
                    //TODO: think of bettery way to compute buffer reallocation size
                    outbuff_len += data_len/2;
                    outbuff = erealloc(outbuff, outbuff_len);
                }

            } while (pres == HSER_POLL_MORE);
            
            if (sunk == data_len) {
                fres = heatshrink_encoder_finish(hse);
                if (fres < 0) {
                    zend_error(E_WARNING, "hs_compress : heatshrink_encoder_finish error");
                    efree(outbuff);
                    heatshrink_encoder_free(hse);
                    RETURN_FALSE;
                }
                if (fres == HSER_FINISH_DONE) {
                    RETVAL_STRINGL((char *) outbuff, poll_sz, 1);
                    efree(outbuff);
                    heatshrink_encoder_free(hse);
                    return;
                }
            }
        } while (fres == HSER_FINISH_MORE);
    } while (sunk < data_len);

    zend_error(E_WARNING, "hs_compress : general error");
    efree(outbuff);
    heatshrink_encoder_free(hse);
    RETURN_FALSE;
}
Esempio n. 21
0
/* {{{ writes a property to a thread in the appropriate way */
void pthreads_write_property(PTHREADS_WRITE_PROPERTY_PASSTHRU_D) {
	PTHREAD pthreads = PTHREADS_FETCH_FROM(object);
	zval *mstring = NULL;
	zend_bool nulled = 0;
	zend_bool locked;
	
	if (member == NULL || Z_TYPE_P(member) == IS_NULL) {
	    /* for anonymous members, 
	        we acquire the lock and increment a counter
	        we do not store any additional information or perform any lookups */
		pthreads_lock_acquire(pthreads->store->lock, &locked TSRMLS_CC);
		{
			if (member == NULL) {
			    MAKE_STD_ZVAL(member);
			    
			    nulled = 1;
			}
			
			ZVAL_LONG(member, pthreads->store->next++);
		}
		pthreads_lock_release(pthreads->store->lock, locked TSRMLS_CC);
	}

	if (Z_TYPE_P(member) != IS_STRING) {
		ALLOC_ZVAL(mstring);
		*mstring = *member;
		zval_copy_ctor(
			mstring
		);
		INIT_PZVAL(mstring);
		convert_to_string(mstring);
		if(nulled) 
			FREE_ZVAL(member);
		member = mstring;
#if PHP_VERSION_ID > 50399
		key = NULL;
#endif
	}

	if (Z_TYPE_P(member)==IS_STRING) {
		switch(Z_TYPE_P(value)){
			case IS_STRING:
			case IS_LONG:
			case IS_ARRAY:
			case IS_OBJECT:
			case IS_NULL:
			case IS_DOUBLE:
			case IS_RESOURCE:
			case IS_BOOL: {
				if (pthreads_store_write(pthreads->store, Z_STRVAL_P(member), Z_STRLEN_P(member), &value TSRMLS_CC)!=SUCCESS){
					zend_error(
						E_WARNING, 
						"pthreads failed to write member %s::$%s", 
						Z_OBJCE_P(object)->name, Z_STRVAL_P(member)
					);
				}
			} break;
			
			default: {
				zend_error(
					E_WARNING, 
					"pthreads detected an attempt to use an unsupported kind of data for %s::$%s", 
					Z_OBJCE_P(object)->name, Z_STRVAL_P(member)
				);
			}
		}
	} else zend_error(
		E_WARNING,
		"pthreads detected an attempt to use an unsupported kind of key in %s", 
		Z_OBJCE_P(object)->name
	);

	if (mstring != NULL) {
		zval_ptr_dtor(&mstring);
	}
}
Esempio n. 22
0
/**
 * @brief Reads an item from @a arr at position @a index and stores it to @a return_value
 * @param return_value[out] Return value
 * @param arr Array
 * @param index Index
 * @param silent 0 to suppress all warnings, @c PH_NOISY to enable
 * @return Whether the operation succeeded
 * @retval @c FAILURE Failure, @a arr is not an array
 * @retval @c SUCCESS Success
 * @throw @c E_WARNING if @c arr is not an array and @c silent = @c PH_NOISY
 * @throw @c E_WARNING if @c index is not of the supported type and @c silent = @c PH_NOISY
 * @throw @c E_NOTICE if @c index does not exist and @c silent = @c PH_NOISY
 * @warning @c *return_value should be either @c NULL (preferred) or point to not initialized memory; if @c *return_value points to a valid variable, mmemory leak is possible
 * @note @c index will be handled as follows: @c NULL is treated as an empty string, @c double values are cast to @c integer, @c bool or @c resource are treated as @c integer
 */
int zephir_array_fetch(zval **return_value, zval *arr, zval *index, int flags TSRMLS_DC){

	zval **zv;
	HashTable *ht;
	int result;
	ulong uidx = 0;
	char *sidx = NULL;

	if (Z_TYPE_P(arr) == IS_ARRAY) {
		ht = Z_ARRVAL_P(arr);
		switch (Z_TYPE_P(index)) {
			case IS_NULL:
				result = zephir_hash_find(ht, ZEND_STRS(""), (void**) &zv);
				sidx   = "";
				break;

			case IS_DOUBLE:
				uidx   = (ulong)Z_DVAL_P(index);
				result = zend_hash_index_find(ht, uidx, (void**) &zv);
				break;

			case IS_LONG:
			case IS_BOOL:
			case IS_RESOURCE:
				uidx   = Z_LVAL_P(index);
				result = zend_hash_index_find(ht, uidx, (void**) &zv);
				break;

			case IS_STRING:
				sidx   = Z_STRLEN_P(index) ? Z_STRVAL_P(index) : "";
				result = zend_symtable_find(ht, Z_STRVAL_P(index), Z_STRLEN_P(index)+1, (void**) &zv);
				break;

			default:
				if ((flags & PH_NOISY) == PH_NOISY) {
					zend_error(E_WARNING, "Illegal offset type");
				}
				result = FAILURE;
				break;
		}

		if (result != FAILURE) {
			*return_value = *zv;
			if ((flags & PH_READONLY) != PH_READONLY) {
				Z_ADDREF_PP(return_value);
			}
			return SUCCESS;
		}

		if ((flags & PH_NOISY) == PH_NOISY) {
			if (sidx == NULL) {
				zend_error(E_NOTICE, "Undefined index: %ld", uidx);
			} else {
				zend_error(E_NOTICE, "Undefined index: %s", sidx);
			}
		}
	}

	*return_value = ZEPHIR_GLOBAL(global_null);
	return FAILURE;
}
Esempio n. 23
0
zend_object_iterator *php_com_iter_get(zend_class_entry *ce, zval *object, int by_ref)
{
	php_com_dotnet_object *obj;
	struct php_com_iterator *I;
	IEnumVARIANT *iev = NULL;
	DISPPARAMS dp;
	VARIANT v;
	unsigned long n_fetched;
	zval ptr;

	if (by_ref) {
		zend_error(E_ERROR, "An iterator cannot be used with foreach by reference");
	}

	obj = CDNO_FETCH(object);

	if (V_VT(&obj->v) != VT_DISPATCH && !V_ISARRAY(&obj->v)) {
		php_error_docref(NULL, E_WARNING, "variant is not an object or array VT=%d", V_VT(&obj->v));
		return NULL;
	}

	memset(&dp, 0, sizeof(dp));
	VariantInit(&v);

	I = (struct php_com_iterator*)ecalloc(1, sizeof(*I));
	zend_iterator_init(&I->iter);
	I->iter.funcs = &com_iter_funcs;
	Z_PTR(I->iter.data) = I;
	I->code_page = obj->code_page;
	ZVAL_UNDEF(&I->zdata);
	VariantInit(&I->safe_array);
	VariantInit(&I->v);

	if (V_ISARRAY(&obj->v)) {
		LONG bound;
		UINT dims;

		dims = SafeArrayGetDim(V_ARRAY(&obj->v));

		if (dims != 1) {
			php_error_docref(NULL, E_WARNING,
				   "Can only handle single dimension variant arrays (this array has %d)", dims);
			goto fail;
		}

		/* same semantics as foreach on a PHP array;
		 * make a copy and enumerate that copy */
		VariantCopy(&I->safe_array, &obj->v);

		/* determine the key value for the array */
		SafeArrayGetLBound(V_ARRAY(&I->safe_array), 1, &bound);
		SafeArrayGetUBound(V_ARRAY(&I->safe_array), 1, &I->sa_max);

		/* pre-fetch the element */
		if (php_com_safearray_get_elem(&I->safe_array, &I->v, bound)) {
			I->key = bound;
			ZVAL_NULL(&ptr);
			php_com_zval_from_variant(&ptr, &I->v, I->code_page);
			ZVAL_COPY_VALUE(&I->zdata, &ptr);
		} else {
			I->key = (ulong)-1;
		}

	} else {
		/* can we enumerate it? */
		if (FAILED(IDispatch_Invoke(V_DISPATCH(&obj->v), DISPID_NEWENUM,
						&IID_NULL, LOCALE_SYSTEM_DEFAULT, DISPATCH_METHOD|DISPATCH_PROPERTYGET,
						&dp, &v, NULL, NULL))) {
			goto fail;
		}

		/* get something useful out of it */
		if (V_VT(&v) == VT_UNKNOWN) {
			IUnknown_QueryInterface(V_UNKNOWN(&v), &IID_IEnumVARIANT, (void**)&iev);
		} else if (V_VT(&v) == VT_DISPATCH) {
			IDispatch_QueryInterface(V_DISPATCH(&v), &IID_IEnumVARIANT, (void**)&iev);
		}

		VariantClear(&v);

		if (iev == NULL) {
			goto fail;
		}

		I->ev = iev;

		/* Get the first element now */
		if (SUCCEEDED(IEnumVARIANT_Next(I->ev, 1, &I->v, &n_fetched)) && n_fetched > 0) {
			/* indicate that we have element 0 */
			I->key = 0;
			ZVAL_NULL(&ptr);
			php_com_zval_from_variant(&ptr, &I->v, I->code_page);
			ZVAL_COPY_VALUE(&I->zdata, &ptr);
		} else {
			/* indicate that there are no more items */
			I->key = (ulong)-1;
		}
	}

	return &I->iter;

fail:
	if (I) {
		VariantClear(&I->safe_array);
		VariantClear(&I->v);
		efree(I);
	}
	return NULL;
}
Esempio n. 24
0
int php_com_process_typeinfo(ITypeInfo *typeinfo, HashTable *id_to_name, int printdef, GUID *guid, int codepage)
{
	TYPEATTR *attr;
	FUNCDESC *func;
	int i;
	OLECHAR *olename;
	char *ansiname = NULL;
	size_t ansinamelen;
	int ret = 0;

	if (FAILED(ITypeInfo_GetTypeAttr(typeinfo, &attr))) {
		return 0;
	}

	/* verify that it is suitable */
	if (id_to_name == NULL || attr->typekind == TKIND_DISPATCH) {

		if (guid) {
			memcpy(guid, &attr->guid, sizeof(GUID));
		}

		if (printdef) {
			char *guidstring;

			ITypeInfo_GetDocumentation(typeinfo, MEMBERID_NIL, &olename, NULL, NULL, NULL);
			ansiname = php_com_olestring_to_string(olename, &ansinamelen, codepage);
			SysFreeString(olename);

			guidstring = php_com_string_from_clsid(&attr->guid, codepage);
			php_printf("class %s { /* GUID=%s */\n", ansiname, guidstring);
			efree(guidstring);

			efree(ansiname);
		}

		if (id_to_name) {
			zend_hash_init(id_to_name, 0, NULL, ZVAL_PTR_DTOR, 0);
		}

		/* So we've got the dispatch interface; lets list the event methods */
		for (i = 0; i < attr->cFuncs; i++) {
			zval tmp;
			DISPID lastid = 0;	/* for props */
			int isprop;

			if (FAILED(ITypeInfo_GetFuncDesc(typeinfo, i, &func)))
				break;

			isprop = (func->invkind & DISPATCH_PROPERTYGET || func->invkind & DISPATCH_PROPERTYPUT);

			if (!isprop || lastid != func->memid) {

				lastid = func->memid;

				ITypeInfo_GetDocumentation(typeinfo, func->memid, &olename, NULL, NULL, NULL);
				ansiname = php_com_olestring_to_string(olename, &ansinamelen, codepage);
				SysFreeString(olename);

				if (printdef) {
					int j;
					char *funcdesc;
					size_t funcdesclen;
					unsigned int cnames = 0;
					BSTR *names;

					names = (BSTR*)safe_emalloc((func->cParams + 1), sizeof(BSTR), 0);

					ITypeInfo_GetNames(typeinfo, func->memid, names, func->cParams + 1, &cnames);
					/* first element is the function name */
					SysFreeString(names[0]);

					php_printf("\t/* DISPID=%d */\n", func->memid);

					if (func->elemdescFunc.tdesc.vt != VT_VOID) {
						php_printf("\t/* %s [%d] */\n",
								vt_to_string(func->elemdescFunc.tdesc.vt),
								func->elemdescFunc.tdesc.vt
								);
					}

					if (isprop) {

						ITypeInfo_GetDocumentation(typeinfo, func->memid, NULL, &olename, NULL, NULL);
						if (olename) {
							funcdesc = php_com_olestring_to_string(olename, &funcdesclen, codepage);
							SysFreeString(olename);
							php_printf("\t/* %s */\n", funcdesc);
							efree(funcdesc);
						}

						php_printf("\tvar $%s;\n\n", ansiname);

					} else {
						/* a function */

						php_printf("\tfunction %s(\n", ansiname);

						for (j = 0; j < func->cParams; j++) {
							ELEMDESC *elem = &func->lprgelemdescParam[j];

							php_printf("\t\t/* %s [%d] ", vt_to_string(elem->tdesc.vt), elem->tdesc.vt);

							if (elem->paramdesc.wParamFlags & PARAMFLAG_FIN)
								php_printf("[in]");
							if (elem->paramdesc.wParamFlags & PARAMFLAG_FOUT)
								php_printf("[out]");

							if (elem->tdesc.vt == VT_PTR) {
								/* what does it point to ? */
								php_printf(" --> %s [%d] ",
										vt_to_string(elem->tdesc.lptdesc->vt),
										elem->tdesc.lptdesc->vt
										);
							}

							/* when we handle prop put and get, this will look nicer */
							if (j+1 < (int)cnames) {
								funcdesc = php_com_olestring_to_string(names[j+1], &funcdesclen, codepage);
								SysFreeString(names[j+1]);
							} else {
								funcdesc = "???";
							}

							php_printf(" */ %s%s%c\n",
									elem->tdesc.vt == VT_PTR ? "&$" : "$",
									funcdesc,
									j == func->cParams - 1 ? ' ' : ','
									);

							if (j+1 < (int)cnames) {
								efree(funcdesc);
							}
						}

						php_printf("\t\t)\n\t{\n");

						ITypeInfo_GetDocumentation(typeinfo, func->memid, NULL, &olename, NULL, NULL);
						if (olename) {
							funcdesc = php_com_olestring_to_string(olename, &funcdesclen, codepage);
							SysFreeString(olename);
							php_printf("\t\t/* %s */\n", funcdesc);
							efree(funcdesc);
						}

						php_printf("\t}\n");
					}

					efree(names);
				}

				if (id_to_name) {
					zend_str_tolower(ansiname, ansinamelen);
					ZVAL_STRINGL(&tmp, ansiname, ansinamelen);
					zend_hash_index_update(id_to_name, func->memid, &tmp);
					// TODO: avoid reallocation???
					efree(ansiname);
				}
			}
			ITypeInfo_ReleaseFuncDesc(typeinfo, func);
		}

		if (printdef) {
			php_printf("}\n");
		}

		ret = 1;
	} else {
		zend_error(E_WARNING, "That's not a dispatchable interface!! type kind = %08x", attr->typekind);
	}

	ITypeInfo_ReleaseTypeAttr(typeinfo, attr);

	return ret;
}
Esempio n. 25
0
/* {{{ MongoCursor->__construct
 */
PHP_METHOD(MongoCursor, __construct) {
  zval *zlink = 0, *zns = 0, *zquery = 0, *zfields = 0, *empty, *timeout;
  zval **data;
  mongo_cursor *cursor;
  mongo_link *link;

  if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "Oz|zz", &zlink,
                            mongo_ce_Mongo, &zns, &zquery, &zfields) == FAILURE) {
    return;
  }
  if ((zquery && IS_SCALAR_P(zquery)) || (zfields && IS_SCALAR_P(zfields))) {
    zend_error(E_WARNING, "MongoCursor::__construct() expects parameters 3 and 4 to be arrays or objects");
    return;
  }

  // if query or fields weren't passed, make them default to an empty array
  MAKE_STD_ZVAL(empty);
  object_init(empty);

  // these are both initialized to the same zval, but that's okay because
  // there's no way to change them without creating a new cursor
  if (!zquery || (Z_TYPE_P(zquery) == IS_ARRAY && zend_hash_num_elements(HASH_P(zquery)) == 0)) {
    zquery = empty;
  }
  if (!zfields) {
    zfields = empty;
  }

  cursor = (mongo_cursor*)zend_object_store_get_object(getThis() TSRMLS_CC);

  // db connection
  cursor->resource = zlink;
  zval_add_ref(&zlink);

  // db connection resource
  PHP_MONGO_GET_LINK(zlink);
  cursor->link = link;

  // change ['x', 'y', 'z'] into {'x' : 1, 'y' : 1, 'z' : 1}
  if (Z_TYPE_P(zfields) == IS_ARRAY) {
    HashPosition pointer;
    zval *fields;

    MAKE_STD_ZVAL(fields);
    array_init(fields);

    // fields to return
    for(zend_hash_internal_pointer_reset_ex(Z_ARRVAL_P(zfields), &pointer);
        zend_hash_get_current_data_ex(Z_ARRVAL_P(zfields), (void**) &data, &pointer) == SUCCESS;
        zend_hash_move_forward_ex(Z_ARRVAL_P(zfields), &pointer)) {
      int key_type, key_len;
      ulong index;
      char *key;

      key_type = zend_hash_get_current_key_ex(Z_ARRVAL_P(zfields), &key, (uint*)&key_len, &index, NO_DUP, &pointer);

      if (key_type == HASH_KEY_IS_LONG) {
        if (Z_TYPE_PP(data) == IS_STRING) {
          add_assoc_long(fields, Z_STRVAL_PP(data), 1);
        }
        else {
          zval_ptr_dtor(&empty);
          zval_ptr_dtor(&fields);
          zend_throw_exception(mongo_ce_Exception, "field names must be strings", 0 TSRMLS_CC);
          return;
        }
      }
      else {
        add_assoc_zval(fields, key, *data);
        zval_add_ref(data);
      }
    }
    cursor->fields = fields;
  }
  // if it's already an object, we don't have to worry
  else {
    cursor->fields = zfields;
    zval_add_ref(&zfields);
  }

  // ns
  convert_to_string(zns);
  cursor->ns = estrdup(Z_STRVAL_P(zns));

  // query
  cursor->query = zquery;
  zval_add_ref(&zquery);

  // reset iteration pointer, just in case
  MONGO_METHOD(MongoCursor, reset, return_value, getThis());

  cursor->at = 0;
  cursor->num = 0;
  cursor->special = 0;
  cursor->persist = 0;

  timeout = zend_read_static_property(mongo_ce_Cursor, "timeout", strlen("timeout"), NOISY TSRMLS_CC);
  cursor->timeout = Z_LVAL_P(timeout);

  cursor->opts = link->slave_okay ? (1 << 2) : 0;

  // get rid of extra ref
  zval_ptr_dtor(&empty);
}
Esempio n. 26
0
PHP_METHOD(swoole_lock, __construct)
{
	long type = SW_MUTEX;
	char *filelock;
	int filelock_len = 0;
	int ret;

	if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "|ls", &type, &filelock, &filelock_len) == FAILURE)
	{
		RETURN_FALSE;
	}
	swLock *lock = SwooleG.memory_pool->alloc(SwooleG.memory_pool, sizeof(swLock));
	if(lock == NULL)
	{
		zend_error(E_WARNING, "SwooleLock: alloc fail");
		RETURN_FALSE;
	}

	switch(type)
	{
	case SW_RWLOCK:
		ret = swRWLock_create(lock, 1);
		break;
	case SW_FILELOCK:
		if(filelock_len <= 0)
		{
			zend_error(E_ERROR, "SwooleLock: filelock require lock file name.");
			RETURN_FALSE;
		}
		int fd;
		if ((fd = open(filelock, O_RDWR | O_CREAT, 0666)) < 0)
		{
			zend_error(E_WARNING, "SwooleLock: open file[%s] fail. Error: %s [%d]", filelock, strerror(errno), errno);
			RETURN_FALSE;
		}
		ret = swFileLock_create(lock, fd);
		break;
	case SW_SEM:
		ret = swSem_create(lock, IPC_PRIVATE, 1);
		break;
#ifdef HAVE_SPINLOCK
	case SW_SPINLOCK:
		ret = swSpinLock_create(lock, 1);
		break;
#endif
	case SW_MUTEX:
	default:
		ret = swMutex_create(lock, 1);
		break;
	}
	if(ret < 0)
	{
		zend_error(E_WARNING, "SwooleLock: create lock fail");
		RETURN_FALSE;
	}
	zval *zres;
	MAKE_STD_ZVAL(zres);

	ZEND_REGISTER_RESOURCE(zres, lock, le_swoole_lock);
	zend_update_property(swoole_lock_class_entry_ptr, getThis(), ZEND_STRL("_lock"), zres TSRMLS_CC);

	RETURN_TRUE;
}
Esempio n. 27
0
/* {{{ proto Closure::__construct()
   Private constructor preventing instantiation */
ZEND_METHOD(Closure, __construct)
{
	zend_error(E_RECOVERABLE_ERROR, "Instantiation of 'Closure' is not allowed");
}
Esempio n. 28
0
ZEND_METHOD(afk_app, run){/*{{{*/
	zval **uri;
	char *c=NULL, *a=NULL;
	zval *arr = PG(http_globals)[TRACK_VARS_GET];
	//从http_globals中寻找get参数,确认Controller和action的值。
	if(arr && Z_TYPE_P(arr) == IS_ARRAY){
		if(zend_hash_find(HASH_OF(arr), HTTP_CONTRONLLER_PARAM, strlen(HTTP_CONTRONLLER_PARAM)+1, (void **)&uri) == SUCCESS){
			c = Z_STRVAL_PP(uri);
		}else{
			c = "index";
		}
		if(zend_hash_find(HASH_OF(arr), HTTP_ACTION_PARAM, strlen(HTTP_ACTION_PARAM)+1, (void **)&uri) == SUCCESS){
			a = Z_STRVAL_PP(uri);
		}else{
			a = "index";
		}
	}
	//寻找对应的Controller和action方法所在的文件。
	char *controller_path;
	spprintf(&controller_path, 0, "%s/controller/%s.php", APP_DIR, c);

	FILE *fp;
	//php_printf("%s\n", controller_path);
	//文件存在则引入该文件。不存在则报错。
	
	if( (fp = fopen(controller_path, "r")) != NULL){
		fclose(fp);
		int dummy = 1;

		zend_file_handle file_handle;
		zend_op_array *op_array;

		file_handle.filename = controller_path;
		file_handle.free_filename = 0;
		file_handle.type = ZEND_HANDLE_FILENAME;
		file_handle.opened_path = NULL;
		file_handle.handle.fp = NULL;

		op_array = zend_compile_file(&file_handle, ZEND_INCLUDE TSRMLS_CC);
		if (op_array && file_handle.handle.stream.handle) {
			int dummy = 1;         

			if (!file_handle.opened_path) {
				file_handle.opened_path = controller_path;
			}

			php_printf("opened_path: %s\n", file_handle.opened_path);
			zend_hash_add(&EG(included_files), file_handle.opened_path, strlen(file_handle.opened_path)+1, (void *)&dummy, sizeof(int), NULL);
		}
		zend_destroy_file_handle(&file_handle TSRMLS_CC);
		if(op_array){
			php_printf("execute op_array \n");

			//保存旧的环境变量
			zval ** __old_return_value_pp   = EG(return_value_ptr_ptr); 
			zend_op ** __old_opline_ptr     = EG(opline_ptr); 
			zend_op_array * __old_op_array  = EG(active_op_array);
			zend_function_state * __old_func_state = EG(function_state_ptr); 

			//执行op_array
			zval *result = NULL;
			EG(return_value_ptr_ptr) = &result;
			EG(active_op_array) = op_array;
			zend_execute(op_array TSRMLS_CC);
			destroy_op_array(op_array TSRMLS_CC);
			efree(op_array);

			//恢复旧的环境变量
			EG(return_value_ptr_ptr) = __old_return_value_pp;
			EG(opline_ptr)           = __old_opline_ptr; 
			EG(active_op_array)      = __old_op_array; 
			EG(function_state_ptr)   = __old_func_state;
		}
	}else{
		char *error;
		spprintf(&error, 0, "cann't find file %s", controller_path);
		zend_error(1, error);
	}
	//dispatcher 调用分发的请求。
	/**
	 *在EG(class_table)查找相应的类,然后调用它的方法。
	 */
	zend_class_entry **class = NULL;
	char  *class_name = emalloc(strlen(c)+strlen("Controller")+1);
	class_name = strcpy(class_name, c);
	class_name = strcat(class_name, zend_str_tolower_dup("Controller", strlen("Controller")+1)); //Notice: class name need tolower.
	if(zend_hash_find(EG(class_table), class_name, strlen(class_name)+1, (void *)&class) != SUCCESS){
		char *error;
		spprintf(&error, 0, "cann't find the controller class: %s ", class_name);
		php_printf("%s", class_name);
		efree(class_name);
		efree(class);
		zend_error(1, error);
	}
	efree(class_name);

	zval *obj, *function_name, *retval;
	MAKE_STD_ZVAL(obj);
	MAKE_STD_ZVAL(function_name);
	MAKE_STD_ZVAL(retval);
	object_init_ex(obj, *class);
	//php_var_dump(&obj, 1 TSRMLS_CC);

	ZVAL_STRINGL(function_name, "indexaction", strlen("indexaction"), 1);
	call_user_function(&((*class)->function_table), &obj, function_name, retval, 0, NULL TSRMLS_CC);

	zval_ptr_dtor(&obj);
	zval_ptr_dtor(&function_name);
	zval_ptr_dtor(&retval);
	//efree(class);

	RETURN_BOOL(1);
}/*}}}*/
Esempio n. 29
0
/* {{{ proto XmlTransaction::XmlTransaction(object dbenv [, string name])
   Create a new container using an optional dbenv (can be null) and name */
PHP_DBXML_METHOD_BEGIN(XmlTransaction, XmlTransaction)
{
  zend_error(E_ERROR, "XmlTransaction can not be instantiated from PHP");
} PHP_DBXML_METHOD_END()
Esempio n. 30
0
PHPAPI int php_setcookie(char *name, int name_len, char *value, int value_len, time_t expires, char *path, int path_len, char *domain, int domain_len, int secure, int url_encode, int httponly TSRMLS_DC)
{
	char *cookie;
	int len=sizeof("Set-Cookie: ");
	zend_string *dt;
	sapi_header_line ctr = {0};
	int result;
	zend_string *encoded_value = NULL;

	if (name && strpbrk(name, "=,; \t\r\n\013\014") != NULL) {   /* man isspace for \013 and \014 */
		zend_error( E_WARNING, "Cookie names cannot contain any of the following '=,; \\t\\r\\n\\013\\014'" );
		return FAILURE;
	}

	if (!url_encode && value && strpbrk(value, ",; \t\r\n\013\014") != NULL) { /* man isspace for \013 and \014 */
		zend_error( E_WARNING, "Cookie values cannot contain any of the following ',; \\t\\r\\n\\013\\014'" );
		return FAILURE;
	}

	len += name_len;
	if (value && url_encode) {
		encoded_value = php_url_encode(value, value_len);
		len += encoded_value->len;
	} else if (value) {
		encoded_value = zend_string_init(value, value_len, 0);
		len += encoded_value->len;
	}

	if (path) {
		len += path_len;
	}
	if (domain) {
		len += domain_len;
	}

	cookie = emalloc(len + 100);

	if (value && value_len == 0) {
		/*
		 * MSIE doesn't delete a cookie when you set it to a null value
		 * so in order to force cookies to be deleted, even on MSIE, we
		 * pick an expiry date in the past
		 */
		dt = php_format_date("D, d-M-Y H:i:s T", sizeof("D, d-M-Y H:i:s T")-1, 1, 0 TSRMLS_CC);
		snprintf(cookie, len + 100, "Set-Cookie: %s=deleted; expires=%s; Max-Age=0", name, dt->val);
		zend_string_free(dt);
	} else {
		snprintf(cookie, len + 100, "Set-Cookie: %s=%s", name, value ? encoded_value->val : "");
		if (expires > 0) {
			const char *p;
			char tsdelta[13];
			strlcat(cookie, COOKIE_EXPIRES, len + 100);
			dt = php_format_date("D, d-M-Y H:i:s T", sizeof("D, d-M-Y H:i:s T")-1, expires, 0 TSRMLS_CC);
			/* check to make sure that the year does not exceed 4 digits in length */
			p = zend_memrchr(dt->val, '-', dt->len);
			if (!p || *(p + 5) != ' ') {
				zend_string_free(dt);
				efree(cookie);
				zend_string_free(encoded_value);
				zend_error(E_WARNING, "Expiry date cannot have a year greater than 9999");
				return FAILURE;
			}
			strlcat(cookie, dt->val, len + 100);
			zend_string_free(dt);

			snprintf(tsdelta, sizeof(tsdelta), ZEND_LONG_FMT, (zend_long) difftime(expires, time(NULL)));
			strlcat(cookie, COOKIE_MAX_AGE, len + 100);
			strlcat(cookie, tsdelta, len + 100);
		}
	}

	if (encoded_value) {
		zend_string_free(encoded_value);
	}

	if (path && path_len > 0) {
		strlcat(cookie, COOKIE_PATH, len + 100);
		strlcat(cookie, path, len + 100);
	}
	if (domain && domain_len > 0) {
		strlcat(cookie, COOKIE_DOMAIN, len + 100);
		strlcat(cookie, domain, len + 100);
	}
	if (secure) {
		strlcat(cookie, COOKIE_SECURE, len + 100);
	}
	if (httponly) {
		strlcat(cookie, COOKIE_HTTPONLY, len + 100);
	}

	ctr.line = cookie;
	ctr.line_len = strlen(cookie);

	result = sapi_header_op(SAPI_HEADER_ADD, &ctr TSRMLS_CC);
	efree(cookie);
	return result;
}