Home | History | Annotate | Download | only in libabi
      1 /**
      2  * @file op_abi.c
      3  * This file contains a simple C interface to the ABI-describing functionality,
      4  * the majority of which is implemented in C++. This is the file which is
      5  * intended for use in files outside the /libabi directory.
      6  *
      7  * @remark Copyright 2002, 2005 OProfile authors
      8  * @remark Read the file COPYING
      9  *
     10  * @author Graydon Hoare
     11  * @author Philippe Elie
     12  */
     13 
     14 #include "op_abi.h"
     15 #include "odb.h"
     16 #include "op_sample_file.h"
     17 
     18 #include <stdio.h>
     19 #include <stddef.h>
     20 #include <assert.h>
     21 
     22 static struct op_abi_entry const abi_entries[] = {
     23 	{ "sizeof_double", sizeof(double) },
     24 	{ "sizeof_time_t", sizeof(time_t) },
     25 	{ "sizeof_u8", sizeof(u8) },
     26 	{ "sizeof_u32", sizeof(u32) },
     27 	{ "sizeof_int", sizeof(int) },
     28 	{ "sizeof_unsigned_int", sizeof(unsigned int) },
     29 	{ "sizeof_odb_key_t", sizeof(odb_key_t) },
     30 	{ "sizeof_odb_index_t", sizeof(odb_index_t) },
     31 	{ "sizeof_odb_value_t", sizeof(odb_value_t) },
     32 	{ "sizeof_odb_node_nr_t", sizeof(odb_node_nr_t) },
     33 	{ "sizeof_odb_descr_t", sizeof(odb_descr_t) },
     34 	{ "sizeof_odb_node_t", sizeof(odb_node_t) },
     35 	{ "sizeof_struct_opd_header", sizeof(struct opd_header) },
     36 
     37 	{ "offsetof_node_key", offsetof(odb_node_t, key) },
     38 	{ "offsetof_node_value", offsetof(odb_node_t, value) },
     39 	{ "offsetof_node_next", offsetof(odb_node_t, next) },
     40 
     41 	{ "offsetof_descr_size", offsetof(odb_descr_t, size) },
     42 	{ "offsetof_descr_current_size", offsetof(odb_descr_t, current_size) },
     43 
     44 	{ "offsetof_header_magic", offsetof(struct opd_header, magic) },
     45 	{ "offsetof_header_version", offsetof(struct opd_header, version) },
     46 	{ "offsetof_header_cpu_type", offsetof(struct opd_header, cpu_type) },
     47 	{ "offsetof_header_ctr_event", offsetof(struct opd_header, ctr_event) },
     48 	{ "offsetof_header_ctr_um", offsetof(struct opd_header, ctr_um) },
     49 	{ "offsetof_header_ctr_count", offsetof(struct opd_header, ctr_count) },
     50 	{ "offsetof_header_is_kernel", offsetof(struct opd_header, is_kernel) },
     51 	{ "offsetof_header_cpu_speed", offsetof(struct opd_header, cpu_speed) },
     52 	{ "offsetof_header_mtime", offsetof(struct opd_header, mtime) },
     53 	{ "offsetof_header_cg_to_is_kernel", offsetof(struct opd_header, cg_to_is_kernel), },
     54 	{ "offsetof_header_anon_start", offsetof(struct opd_header, anon_start) },
     55 	{ "offsetof_header_cg_to_anon_start", offsetof(struct opd_header, cg_to_anon_start) },
     56 
     57 	{ NULL, 0 },
     58 };
     59 
     60 
     61 struct op_abi_entry const * get_abi(void)
     62 {
     63 	return abi_entries;
     64 }
     65 
     66 
     67 int op_little_endian(void)
     68 {
     69 	unsigned int probe = 0xff;
     70 	size_t sz = sizeof(unsigned int);
     71 	unsigned char * probe_byte = (unsigned char *)&probe;
     72 
     73 	assert(probe_byte[0] == 0xff || probe_byte[sz - 1] == 0xff);
     74 
     75 	return probe_byte[0] == 0xff;
     76 }
     77 
     78 
     79 int op_write_abi_to_file(char const * abi_file)
     80 {
     81 	FILE * fp;
     82 	struct op_abi_entry const * abi_entry;
     83 
     84 	if ((fp = fopen(abi_file, "w")) == NULL)
     85 		return 0;
     86 
     87 	for (abi_entry = get_abi() ; abi_entry->name != NULL; ++abi_entry)
     88 		fprintf(fp, "%s %u\n", abi_entry->name, abi_entry->offset);
     89 	fprintf(fp, "little_endian %d\n", op_little_endian());
     90 
     91 	fclose(fp);
     92 
     93 	return 1;
     94 }
     95