Ejemplo n.º 1
0
int cp_symbol_build_func(struct cp_ctype *type, const char *fname, int fn_size)
{
	int i = 1, arg_nr, id;
	int *argsym_id_arr;
	csymbol nfcs;
	csymbol_func *fcs;

	if (cts.top == 0 || fn_size < 0 || !fname) {
		cp_error("invalid function definition.\n");
	}

	argsym_id_arr = NULL;
	memset(&nfcs, 0, sizeof(csymbol));
	csym_type(&nfcs) = FFI_FUNC;

	strncpy(csym_name(&nfcs), fname, fn_size);

	fcs = csym_func(&nfcs);
	fcs->has_var_arg = type->has_var_arg;
	/* Type needed for handling variable args handle */
	if (fcs->has_var_arg && !ctype_lookup_type("void *"))
		cp_symbol_build_pointer(ctype_lookup_type("void"));

	/* Fetch start address of function  */
	fcs->addr = (void *)find_kernel_symbol(csym_name(&nfcs));
	if (!fcs->addr)
		cp_error("wrong function address for %s\n", csym_name(&nfcs));

	/* bottom of the stack is return type */
	fcs->ret_id = ct_stack_ct(0)->ffi_cs_id;

	/* the rest is argument type */
	if (cts.top == 1) {
		/* function takes no argument */
		arg_nr = 0;
	} else {
		arg_nr = cts.top - 1;
		argsym_id_arr = malloc(arg_nr * sizeof(int));
		if (!argsym_id_arr)
			cp_error("failed to allocate memory for function args.\n");
		for (i = 0; i < arg_nr; i++) {
			argsym_id_arr[i] = ct_stack_ct(i+1)->ffi_cs_id;
		}
	}
	fcs->arg_nr = arg_nr;
	fcs->arg_ids = argsym_id_arr;

	id = cp_ctype_reg_csymbol(&nfcs);

	/* clear stack since we have consumed all the ctypes */
	ctype_stack_reset();

	return id;
}
Ejemplo n.º 2
0
void __cp_symbol_dump_struct(csymbol *cs)
{
	int i;
	csymbol *ncs;
	csymbol_struct *stcs = csym_struct(cs);

	printf("=== [%s] definition ==================\n", csym_name(cs));
	for (i = 0; i < stcs->memb_nr; i++) {
		printf("\t(%d) ", i);
		printf("csym_id: %d, ", stcs->members[i].id);
		ncs = &cs_arr[stcs->members[i].id];
		printf("name: %s, ffi_ctype: %d, %s\n",
			stcs->members[i].name, ncs->type, csym_name(ncs));
	}
}
Ejemplo n.º 3
0
Archivo: cdata.c Proyecto: ktap/ktap
ktap_cdata_t *kp_cdata_new_by_id(ktap_state_t *ks, void *val, csymbol_id id)
{
	csymbol *cs = id_to_csym(ks, id);

	switch (csym_type(cs)) {
	case FFI_VOID:
		kp_error(ks, "Error: Cannot new a void type\n");
		return NULL;
	case FFI_UINT8:
	case FFI_INT8:
	case FFI_UINT16:
	case FFI_INT16:
	case FFI_UINT32:
	case FFI_INT32:
	case FFI_UINT64:
	case FFI_INT64:
		return kp_cdata_new_number(ks, val, id);
	case FFI_PTR:
		return kp_cdata_new_ptr(ks, val, 0, id, 0);
	case FFI_STRUCT:
	case FFI_UNION:
		return kp_cdata_new_record(ks, val, id);
	case FFI_FUNC:
		kp_error(ks, "Error: Cannot new a function type\n");
		return NULL;
	case FFI_UNKNOWN:
	default:
		kp_error(ks, "Error: unknown csymbol type %s\n", csym_name(cs));
		return NULL;
	}
}
Ejemplo n.º 4
0
Archivo: cdata.c Proyecto: ktap/ktap
void kp_cdata_record_set(ktap_state_t *ks, ktap_cdata_t *cd,
			 ktap_val_t *key, ktap_val_t *val)
{
	const char *mb_name;
	csymbol *cs, *mb_cs;
	csymbol_struct *csst;
	struct_member *mb;
	char *addr;

	if (!is_shrstring(key)) {
		kp_error(ks, "struct member name should be string\n");
		return;
	}
	mb_name = svalue(key);
	cs = cd_csym(ks, cd);
	csst = csym_struct(cs);
	mb = csymst_mb_by_name(ks, csst, mb_name);
	if (mb == NULL) {
		kp_error(ks, "struct member %s doesn't exist\n", mb_name);
		return;
	}

	mb_cs = id_to_csym(ks, mb->id);
	if (kp_cdata_type_match(ks, mb_cs, val)) {
		kp_error(ks, "struct member should be %s type\n",
			     csym_name(mb_cs));
		return;
	}

	addr = cd_record(cd);
	addr += csym_record_mb_offset_by_name(ks, cs, mb_name);
	kp_cdata_unpack(ks, addr, mb_cs, val);
}
Ejemplo n.º 5
0
Archivo: cdata.c Proyecto: ktap/ktap
void kp_cdata_ptr_set(ktap_state_t *ks, ktap_cdata_t *cd,
		      ktap_val_t *key, ktap_val_t *val)
{
	ktap_number idx;
	csymbol *cs;
	size_t size;
	char *addr;

	if (!is_number(key)) {
		kp_error(ks, "array index should be number\n");
		return;
	}
	idx = nvalue(key);
	if (unlikely(idx < 0 || (cd_ptr_nmemb(cd) >= 0
					&& idx >= cd_ptr_nmemb(cd)))) {
		kp_error(ks, "array index out of bound\n");
		return;
	}

	cs = csym_ptr_deref(ks, cd_csym(ks, cd));
	if (kp_cdata_type_match(ks, cs, val)) {
		kp_error(ks, "array member should be %s type\n", csym_name(cs));
		return;
	}
	size = csym_size(ks, cs);
	addr = cd_ptr(cd);
	addr += size * idx;
	kp_cdata_unpack(ks, addr, cs, val);
}
Ejemplo n.º 6
0
static void init_builtin_type(struct cp_ctype *ct, ffi_type ftype)
{
	csymbol cs;
	int cs_id;

	csym_type(&cs) = ftype;
	strncpy(csym_name(&cs), ffi_type_name(ftype), CSYM_NAME_MAX_LEN);
	cs_id = cp_ctype_reg_csymbol(&cs);

	memset(ct, 0, sizeof(*ct));
	ct->ffi_cs_id = cs_id;
	switch (ftype) {
	case FFI_VOID:		ct_set_type(ct, VOID_TYPE, 0); break;
	case FFI_UINT8:		ct_set_type(ct, INT8_TYPE, 1); break;
	case FFI_INT8:		ct_set_type(ct, INT8_TYPE, 0); break;
	case FFI_UINT16:	ct_set_type(ct, INT16_TYPE, 1); break;
	case FFI_INT16:		ct_set_type(ct, INT16_TYPE, 0); break;
	case FFI_UINT32:	ct_set_type(ct, INT32_TYPE, 1); break;
	case FFI_INT32:		ct_set_type(ct, INT32_TYPE, 0); break;
	case FFI_UINT64:	ct_set_type(ct, INT64_TYPE, 1); break;
	case FFI_INT64:		ct_set_type(ct, INT64_TYPE, 0); break;
	default:		break;
	}
	ct->base_size = ffi_type_size(ftype);
	ct->align_mask = ffi_type_align(ftype) - 1;
	ct->is_defined = 1;
}
Ejemplo n.º 7
0
Archivo: cdata.c Proyecto: ktap/ktap
static void kp_cdata_value(ktap_state_t *ks, ktap_val_t *val, void **out_addr,
			   size_t *out_size, void **temp)
{
	ktap_cdata_t *cd;
	csymbol *cs;
	ffi_type type;

	switch (ttypenv(val)) {
	case KTAP_TYPE_BOOLEAN:
		*out_addr = &bvalue(val);
		*out_size = sizeof(int);
		return;
	case KTAP_TYPE_LIGHTUSERDATA:
		*out_addr = pvalue(val);
		*out_size = sizeof(void *);
		return;
	case KTAP_TYPE_NUMBER:
		*out_addr = &nvalue(val);
		*out_size = sizeof(ktap_number);
		return;
	case KTAP_TYPE_STRING:
		*temp = (void *)svalue(val);
		*out_addr = temp;
		*out_size = sizeof(void *);
		return;
	}

	cd = cdvalue(val);
	cs = cd_csym(ks, cd);
	type = csym_type(cs);
	*out_size = csym_size(ks, cs);
	switch (type) {
	case FFI_VOID:
		kp_error(ks, "Error: Cannot copy data from void type\n");
		return;
	case FFI_UINT8:
	case FFI_INT8:
	case FFI_UINT16:
	case FFI_INT16:
	case FFI_UINT32:
	case FFI_INT32:
	case FFI_UINT64:
	case FFI_INT64:
		*out_addr = &cd_int(cd);
		return;
	case FFI_PTR:
		*out_addr = &cd_ptr(cd);
		return;
	case FFI_STRUCT:
	case FFI_UNION:
		*out_addr = cd_record(cd);
		return;
	case FFI_FUNC:
	case FFI_UNKNOWN:
		kp_error(ks, "Error: internal error for csymbol %s\n",
				csym_name(cs));
		return;
	}
}
Ejemplo n.º 8
0
void __cp_symbol_dump_func(csymbol *cs)
{
	int i;
	csymbol *ncs;
	csymbol_func *fcs = csym_func(cs);

	printf("=== [%s] function definition =============\n", csym_name(cs));
	ncs = cp_csymf_ret(fcs);
	printf("address: %p\n", fcs->addr);
	printf("return type: \n");
	printf("\tcsym_id: %d, ffi_ctype: %d, %s\n",
			fcs->ret_id, ncs->type, csym_name(ncs));
	printf("args type (%d): \n", fcs->arg_nr);
	for (i = 0; i < csymf_arg_nr(fcs); i++) {
	    printf("\t (%d) ", i);
	    printf("csym_id: %d, ", fcs->arg_ids[i]);
	    ncs = cp_csymf_arg(fcs, i);
	    printf("ffi_ctype: %d, %s\n", ncs->type, csym_name(ncs));
	}
}
Ejemplo n.º 9
0
/* build pointer symbol from given csymbol */
int cp_symbol_build_pointer(struct cp_ctype *ct)
{
	int id, ret;
	csymbol ncspt;
	csymbol *ref_cs = ct_ffi_cs(ct);

	/* TODO: Check correctness of multi-level pointer 24.11.2013(unihorn) */
	memset(&ncspt, 0, sizeof(csymbol));
	ncspt.type = FFI_PTR;
	ret = sprintf(ncspt.name, "%s *", csym_name(ref_cs));
	assert(ret < MAX_TYPE_NAME_LEN);

	csym_set_ptr_deref_id(&ncspt, ct->ffi_cs_id);
	id = cp_ctype_reg_csymbol(&ncspt);

	return id;
}
Ejemplo n.º 10
0
static int ffi_type_check(ktap_state_t *ks, csymbol_func *csf, int idx)
{
	StkId arg;
	csymbol *cs;

	if (idx >= csymf_arg_nr(csf))
		return 0;
	arg = kp_arg(ks, idx + 1);
	cs = csymf_arg(ks, csf, idx);

	if (!kp_cdata_type_match(ks, cs, arg))
		return 0;
	else {
		kp_error(ks, "Cannot convert to csymbol %s for arg %d\n",
				csym_name(cs), idx);
		return -1;
	}
}
Ejemplo n.º 11
0
/* push ctype to stack, create new csymbol if needed */
void cp_push_ctype_with_name(struct cp_ctype *ct, const char *name, int nlen)
{
	int i;
	struct cp_ctype *nct;

	if (ctype_stack_free_space() < 1)
		ctype_stack_grow(4);

	/* we have to check pointer here because does type lookup by name
	 * before parsing '*', and for pointers, ct will always be the
	 * original type */
	if (ct->pointers) {
		for (i = 0; i < cte_nr; i++) {
			nct = &(cte_arr[i].ct);
			if (nct->type == ct->type &&
					nct->pointers == ct->pointers) {
				break;
			}
		}

		if (i == cte_nr) {
			/* pointer type not found
			 * create a new pointer symbol for this type */
			/* associate ctype with new csymbol */
			ct->ffi_cs_id = cp_symbol_build_pointer(ct);
			/* register wit new pointer name */
			cp_ctype_reg_type(csym_name(ct_ffi_cs(ct)), ct);
		} else {
			/* pointer type already registered, reinstantiate ct */
			*ct = cte_arr[i].ct;
		}
	}
	memset(ct_stack(cts.top), 0, sizeof(cp_ctype_entry));
	ct_stack(cts.top)->ct = *ct;
	if (name)
		strncpy(ct_stack(cts.top)->name, name, nlen);
	cts.top++;
}