Class: Indis::ARM::CodeParser

Inherits:
Object
  • Object
show all
Defined in:
lib/indis-arm/code_parser.rb

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(target) ⇒ CodeParser

Returns a new instance of CodeParser.



29
30
31
32
33
34
35
# File 'lib/indis-arm/code_parser.rb', line 29

def initialize(target)
  @target = target
  @map = target.vmmap
  
  @endianness = :little
  @state = CpuState.new
end

Instance Attribute Details

#endiannessObject

Returns the value of attribute endianness.



27
28
29
# File 'lib/indis-arm/code_parser.rb', line 27

def endianness
  @endianness
end

Class Method Details

.instruction_masksObject



83
84
85
86
87
# File 'lib/indis-arm/code_parser.rb', line 83

def instruction_masks
  @instruction_masks = load_instructions unless @instruction_masks

  @instruction_masks
end

.load_instructionsObject



89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
# File 'lib/indis-arm/code_parser.rb', line 89

def load_instructions
  masks = {}
  
  InstructionLoader.instance.load.each do |klass|
    m = klass.bits_mask
    a = masks[m]
    unless a
      a = []
      masks[m] = a
    end
    
    a << klass
  end
  
  masks
end

Instance Method Details

#reparse_section(sect) ⇒ Object



37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
# File 'lib/indis-arm/code_parser.rb', line 37

def reparse_section(sect)
  virt_addr = sect.vmaddr
  io = StringIO.new(sect.bytes)
  
  while virt_addr < sect.vmaddr + sect.vmsize
    @state.pc = virt_addr + 8 # XXX: 4 for thumb
    
    bytes = io.read(4)

    unless @map.has_unmapped(virt_addr, 4)
      virt_addr += 4 # TODO: skip 2 for thumb
      next
    end
    
    i = build_instruction(virt_addr, bytes.unpack('V')[0])
    @map.map(i)
    @target.publish_event(:instruction_mapped, i)
    
    if i.size == 2
      io.ungetbyte(bytes[2..-1])
      virt_addr += 2
    else
      virt_addr += 4
    end
  end
end