X-Git-Url: https://git.m6w6.name/?p=m6w6%2Fext-psi;a=blobdiff_plain;f=php_psi.h;h=dd422b7a848a47b328ad336c82e2f112a7636c87;hp=54d78b0a5b3445feb128eb772a5033b1f09bad86;hb=756a2c4350162a9a7f930bdc0ec7718ff13ea48c;hpb=2421d323be79e4a811a4197914330a8c0124b130 diff --git a/php_psi.h b/php_psi.h index 54d78b0..dd422b7 100644 --- a/php_psi.h +++ b/php_psi.h @@ -60,6 +60,90 @@ void psi_to_object(zval *return_value, set_value *set, impl_val *ret_val); void psi_call(zend_execute_data *execute_data, zval *return_value, impl *impl); +static inline int psi_calc_num_exp_value(num_exp *exp, impl_val *val) { + switch (exp->t) { + case PSI_T_NUMBER: + switch (is_numeric_string(exp->u.numb, strlen(exp->u.numb), (zend_long *) val, (double *) val, 0)) { + case IS_LONG: + return PSI_T_INT64; + case IS_DOUBLE: + return PSI_T_DOUBLE; + } + break; + + case PSI_T_NSNAME: + switch (exp->u.cnst->type->type) { + case PSI_T_INT: + val->i64 = zend_get_constant_str(exp->u.cnst->name, strlen(exp->u.cnst->name))->value.lval; + return PSI_T_INT64; + case PSI_T_FLOAT: + val->dval = zend_get_constant_str(exp->u.cnst->name, strlen(exp->u.cnst->name))->value.dval; + return PSI_T_DOUBLE; + default: + return 0; + } + break; + + case PSI_T_NAME: + switch (real_decl_type(exp->u.dvar->arg->type)->type) { + case PSI_T_INT8: + case PSI_T_UINT8: + case PSI_T_INT16: + case PSI_T_UINT16: + case PSI_T_INT32: + case PSI_T_UINT32: + case PSI_T_INT64: + case PSI_T_UINT64: + memcpy(val, deref_impl_val(exp->u.dvar->arg->let->ptr, exp->u.dvar), sizeof(*val)); + return real_decl_type(exp->u.dvar->arg->type)->type; + + case PSI_T_FLOAT: + case PSI_T_DOUBLE: + memcpy(val, deref_impl_val(exp->u.dvar->arg->let->ptr, exp->u.dvar), sizeof(*val)); + return real_decl_type(exp->u.dvar->arg->type)->type; + + EMPTY_SWITCH_DEFAULT_CASE(); + } + break; + + EMPTY_SWITCH_DEFAULT_CASE(); + } + return 0; +} + +static inline int psi_calc_num_exp(num_exp *exp, impl_val *val) { + impl_val num = {0}; + int num_type = psi_calc_num_exp_value(exp, &num); + + if (exp->operand) { + impl_val tmp = {0}; + int tmp_type = psi_calc_num_exp(exp->operand, &tmp); + + return exp->calculator(num_type, &num, tmp_type, &tmp, val); + } + + memcpy(val, &num, sizeof(*val)); + return num_type; +} + +static inline zend_long psi_long_num_exp(num_exp *exp) { + impl_val val = {0}; + + switch (psi_calc_num_exp(exp, &val)) { + case PSI_T_UINT8: val.u16 = val.u8; + case PSI_T_UINT16: val.u32 = val.u16; + case PSI_T_UINT32: val.u64 = val.u32; + case PSI_T_UINT64: return val.u64; + case PSI_T_INT8: val.i16 = val.i8; + case PSI_T_INT16: val.i32 = val.i16; + case PSI_T_INT32: val.i64 = val.i32; + case PSI_T_INT64: return val.i64; + case PSI_T_FLOAT: val.dval = val.fval; + case PSI_T_DOUBLE: return val.dval; + EMPTY_SWITCH_DEFAULT_CASE(); + } +} + ZEND_BEGIN_MODULE_GLOBALS(psi) char *engine; char *directory;