summaryrefslogtreecommitdiff
path: root/dwarfgen/irepframe.h
diff options
context:
space:
mode:
Diffstat (limited to 'dwarfgen/irepframe.h')
-rw-r--r--dwarfgen/irepframe.h154
1 files changed, 154 insertions, 0 deletions
diff --git a/dwarfgen/irepframe.h b/dwarfgen/irepframe.h
new file mode 100644
index 0000000..3f598f8
--- /dev/null
+++ b/dwarfgen/irepframe.h
@@ -0,0 +1,154 @@
+/*
+ Copyright (C) 2010-2011 David Anderson.
+
+ This program is free software; you can redistribute it and/or modify it
+ under the terms of version 2 of the GNU General Public License as
+ published by the Free Software Foundation.
+
+ This program is distributed in the hope that it would be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
+
+ You should have received a copy of the GNU General Public License along
+ with this program; if not, write the Free Software Foundation, Inc., 51
+ Franklin Street - Fifth Floor, Boston MA 02110-1301, USA.
+
+*/
+
+//
+// irepframe.h
+//
+
+class IRCie {
+public:
+ IRCie(): cie_byte_length_(0), version_(0),
+ code_alignment_factor_(1),
+ data_alignment_factor_(1),
+ return_address_register_rule_(0)
+ {};
+ IRCie(Dwarf_Unsigned length, Dwarf_Unsigned version,
+ const std::string &augmentation, Dwarf_Unsigned code_align,
+ Dwarf_Signed data_align, Dwarf_Half return_reg_rule,
+ const void * init_instrs, Dwarf_Unsigned instrs_len):
+ cie_byte_length_(length), version_(version),
+ augmentation_(augmentation), code_alignment_factor_(code_align),
+ data_alignment_factor_(data_align),
+ return_address_register_rule_(return_reg_rule)
+ {
+ const Dwarf_Small *x =
+ reinterpret_cast<const Dwarf_Small *>(init_instrs);
+ for(Dwarf_Unsigned i = 0; i < instrs_len; ++i) {
+ initial_instructions_.push_back(x[i]);
+ }
+ }
+ void insert_fde_index(unsigned i) { fde_index_.push_back(i); };
+ ~IRCie() {};
+ void get_basic_cie_data(Dwarf_Unsigned * version,
+ std::string * aug,
+ Dwarf_Unsigned * code_align,
+ Dwarf_Signed * data_align,
+ Dwarf_Half * ret_addr_reg) {
+ *version = version_;
+ *aug = augmentation_;
+ *code_align = code_alignment_factor_;
+ *data_align = data_alignment_factor_;
+ *ret_addr_reg = return_address_register_rule_;
+ }
+ void get_init_instructions(Dwarf_Unsigned *len,
+ void **bytes) {
+ *len = initial_instructions_.size();
+ *bytes = reinterpret_cast<void *>(&initial_instructions_[0]);
+ };
+
+private:
+ // Byte length 0 if not known yet.
+ Dwarf_Unsigned cie_byte_length_;
+ Dwarf_Unsigned version_;
+ std::string augmentation_;
+ Dwarf_Unsigned code_alignment_factor_;
+ Dwarf_Signed data_alignment_factor_;
+ Dwarf_Half return_address_register_rule_;
+ std::vector<Dwarf_Small> initial_instructions_;
+ // fde_index is the array of indexes into fdedata_
+ // that are fdes used by this cie.
+ std::vector<unsigned> fde_index_;
+};
+class IRFde {
+public:
+ IRFde(): low_pc_(0), func_length_(0),
+ cie_offset_(0), cie_index_(-1),
+ fde_offset_(0) {};
+ IRFde(Dwarf_Addr low_pc,Dwarf_Unsigned func_length,
+ Dwarf_Ptr fde_bytes, Dwarf_Unsigned fde_length,
+ Dwarf_Off cie_offset,Dwarf_Signed cie_index,
+ Dwarf_Off fde_offset): low_pc_(low_pc), func_length_(func_length),
+ cie_offset_(cie_offset), cie_index_(cie_index),
+ fde_offset_(fde_offset) {
+ const Dwarf_Small *x =
+ reinterpret_cast<const Dwarf_Small *>(fde_bytes);
+ for(Dwarf_Unsigned i = 0; i < fde_length; ++i) {
+ fde_bytes_.push_back(x[i]);
+ }
+ };
+ ~IRFde() {};
+ Dwarf_Signed cie_index() { return cie_index_; };
+ void get_fde_base_data(Dwarf_Addr *lowpc, Dwarf_Unsigned * funclen,
+ Dwarf_Signed *cie_index_input) {
+ *lowpc = low_pc_;
+ *funclen = func_length_;
+ *cie_index_input = cie_index_;
+ };
+ void get_fde_instrs_into_ir(Dwarf_Ptr ip,Dwarf_Unsigned len ) {
+ const Dwarf_Small *x =
+ reinterpret_cast<const Dwarf_Small *>(ip);
+ for(Dwarf_Unsigned i = 0; i < len; ++i) {
+ fde_instrs_.push_back(x[i]);
+ }
+ };
+
+ void get_fde_instructions(Dwarf_Unsigned *len,
+ void **bytes) {
+ *len = fde_instrs_.size();
+ *bytes = reinterpret_cast<void *>(&fde_instrs_[0]);
+ };
+ void fde_instrs () {
+ };
+
+private:
+ Dwarf_Addr low_pc_;
+ Dwarf_Unsigned func_length_;
+ // fde_bytes_ may be empty if content bytes not yet created.
+ std::vector<Dwarf_Small> fde_bytes_;
+
+ std::vector<Dwarf_Small> fde_instrs_;
+ // cie_offset may be 0 if not known yet.
+ Dwarf_Off cie_offset_;
+ // cie_index is the index in ciedata_ of
+ // the applicable CIE. Begins with index 0.
+ Dwarf_Signed cie_index_;
+ // fde_offset may be 0 if not yet known.
+ Dwarf_Off fde_offset_;
+};
+
+class IRFrame {
+public:
+ IRFrame() {};
+ ~IRFrame() {};
+ void insert_cie(IRCie &cie) {
+ ciedata_.push_back(cie);
+ }
+ void insert_fde(IRFde &fdedata) {
+ fdedata_.push_back(fdedata);
+ unsigned findex = fdedata_.size() -1;
+ Dwarf_Signed cindex = fdedata.cie_index();
+ if( cindex != -1) {
+ IRCie & mycie = ciedata_[cindex];
+ mycie.insert_fde_index(findex);
+ }
+ }
+ std::vector<IRCie> &get_cie_vec() { return ciedata_; };
+ std::vector<IRFde> &get_fde_vec() { return fdedata_; };
+private:
+ std::vector<IRCie> ciedata_;
+ std::vector<IRFde> fdedata_;
+};