/* Copyright (C) 2014-2016 Free Software Foundation, Inc. Contributed by Intel Corp. <markus.t.metzger@intel.com> This file is part of GDB. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see <http://www.gnu.org/licenses/>. */ #include "common-defs.h" #include "btrace-common.h" /* See btrace-common.h. */ const char * btrace_format_string (enum btrace_format format) { switch (format) { case BTRACE_FORMAT_NONE: return _("No or unknown format"); case BTRACE_FORMAT_BTS: return _("Branch Trace Store"); case BTRACE_FORMAT_PT: return _("Intel Processor Trace"); } internal_error (__FILE__, __LINE__, _("Unknown branch trace format")); } /* See btrace-common.h. */ void btrace_data_init (struct btrace_data *data) { data->format = BTRACE_FORMAT_NONE; } /* See btrace-common.h. */ void btrace_data_fini (struct btrace_data *data) { switch (data->format) { case BTRACE_FORMAT_NONE: /* Nothing to do. */ return; case BTRACE_FORMAT_BTS: VEC_free (btrace_block_s, data->variant.bts.blocks); return; case BTRACE_FORMAT_PT: xfree (data->variant.pt.data); return; } internal_error (__FILE__, __LINE__, _("Unkown branch trace format.")); } /* See btrace-common.h. */ int btrace_data_empty (struct btrace_data *data) { switch (data->format) { case BTRACE_FORMAT_NONE: return 1; case BTRACE_FORMAT_BTS: return VEC_empty (btrace_block_s, data->variant.bts.blocks); case BTRACE_FORMAT_PT: return (data->variant.pt.size == 0); } internal_error (__FILE__, __LINE__, _("Unkown branch trace format.")); } /* See btrace-common.h. */ void btrace_data_clear (struct btrace_data *data) { btrace_data_fini (data); btrace_data_init (data); } /* See btrace-common.h. */ int btrace_data_append (struct btrace_data *dst, const struct btrace_data *src) { switch (src->format) { case BTRACE_FORMAT_NONE: return 0; case BTRACE_FORMAT_BTS: switch (dst->format) { default: return -1; case BTRACE_FORMAT_NONE: dst->format = BTRACE_FORMAT_BTS; dst->variant.bts.blocks = NULL; /* Fall-through. */ case BTRACE_FORMAT_BTS: { unsigned int blk; /* We copy blocks in reverse order to have the oldest block at index zero. */ blk = VEC_length (btrace_block_s, src->variant.bts.blocks); while (blk != 0) { btrace_block_s *block; block = VEC_index (btrace_block_s, src->variant.bts.blocks, --blk); VEC_safe_push (btrace_block_s, dst->variant.bts.blocks, block); } } } return 0; case BTRACE_FORMAT_PT: switch (dst->format) { default: return -1; case BTRACE_FORMAT_NONE: dst->format = BTRACE_FORMAT_PT; dst->variant.pt.data = NULL; dst->variant.pt.size = 0; /* fall-through. */ case BTRACE_FORMAT_PT: { gdb_byte *data; size_t size; size = src->variant.pt.size + dst->variant.pt.size; data = (gdb_byte *) xmalloc (size); memcpy (data, dst->variant.pt.data, dst->variant.pt.size); memcpy (data + dst->variant.pt.size, src->variant.pt.data, src->variant.pt.size); xfree (dst->variant.pt.data); dst->variant.pt.data = data; dst->variant.pt.size = size; } } return 0; } internal_error (__FILE__, __LINE__, _("Unkown branch trace format.")); }