ronin-asm 0.1.0 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (41) hide show
  1. data/.ruby-version +1 -0
  2. data/.travis.yml +12 -0
  3. data/ChangeLog.md +32 -6
  4. data/Gemfile +2 -2
  5. data/README.md +30 -22
  6. data/Rakefile +5 -4
  7. data/gemspec.yml +1 -0
  8. data/lib/ronin/asm.rb +1 -1
  9. data/lib/ronin/asm/archs.rb +1 -1
  10. data/lib/ronin/asm/archs/amd64.rb +53 -53
  11. data/lib/ronin/asm/archs/x86.rb +48 -48
  12. data/lib/ronin/asm/asm.rb +1 -1
  13. data/lib/ronin/asm/config.rb +1 -1
  14. data/lib/ronin/asm/immediate_operand.rb +18 -11
  15. data/lib/ronin/asm/instruction.rb +1 -1
  16. data/lib/ronin/asm/memory_operand.rb +22 -16
  17. data/lib/ronin/asm/os.rb +1 -1
  18. data/lib/ronin/asm/os/freebsd.rb +1 -1
  19. data/lib/ronin/asm/os/linux.rb +1 -1
  20. data/lib/ronin/asm/os/os.rb +1 -1
  21. data/lib/ronin/asm/program.rb +60 -33
  22. data/lib/ronin/asm/register.rb +1 -1
  23. data/lib/ronin/asm/shellcode.rb +2 -2
  24. data/lib/ronin/asm/syntax.rb +1 -1
  25. data/lib/ronin/asm/syntax/att.rb +39 -12
  26. data/lib/ronin/asm/syntax/common.rb +40 -2
  27. data/lib/ronin/asm/syntax/intel.rb +27 -28
  28. data/lib/ronin/asm/version.rb +2 -2
  29. data/spec/{asm_spec.rb → asm/asm_spec.rb} +0 -0
  30. data/spec/{immediate_operand_spec.rb → asm/immediate_operand_spec.rb} +2 -0
  31. data/spec/{instruction_spec.rb → asm/instruction_spec.rb} +0 -0
  32. data/spec/{memory_operand_spec.rb → asm/memory_operand_spec.rb} +0 -0
  33. data/spec/{program_spec.rb → asm/program_spec.rb} +106 -50
  34. data/spec/{register_spec.rb → asm/register_spec.rb} +0 -0
  35. data/spec/{shellcode_spec.rb → asm/shellcode_spec.rb} +15 -7
  36. data/spec/{syntax → asm/syntax}/att_spec.rb +15 -5
  37. data/spec/{syntax → asm/syntax}/common_spec.rb +0 -0
  38. data/spec/{syntax → asm/syntax}/intel_spec.rb +24 -6
  39. metadata +16 -16
  40. data/.gemtest +0 -0
  41. data/spec/helpers/database.rb +0 -7
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -38,17 +38,24 @@ module Ronin
38
38
  # The size in bytes of the value.
39
39
  #
40
40
  def initialize(value,width=nil)
41
- value = value.to_i
42
- width ||= case value
43
- when (0x100000000..0xffffffffffffffff),
44
- (-0x7fffffffffffffff..-0x800000000) then 8
45
- when (0x10000..0xffffffff),
46
- (-0x7fffffff..-0x80000) then 4
47
- when (0x100..0xffff), (-0x7fff..-0x80) then 2
48
- when (0..0xff), (-0x7f..0) then 1
49
- end
41
+ super(value.to_i,width)
42
+ end
50
43
 
51
- super(value,width)
44
+ #
45
+ # The width of the immediate operand.
46
+ #
47
+ # @return [8, 4, 2, 1]
48
+ # The width.
49
+ #
50
+ def width
51
+ super || case value
52
+ when (0x100000000..0xffffffffffffffff),
53
+ (-0x7fffffffffffffff..-0x800000000) then 8
54
+ when (0x10000..0xffffffff),
55
+ (-0x7fffffff..-0x80000) then 4
56
+ when (0x100..0xffff), (-0x7fff..-0x80) then 2
57
+ when (0..0xff), (-0x7f..0) then 1
58
+ end
52
59
  end
53
60
 
54
61
  #
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -28,7 +28,7 @@ module Ronin
28
28
  #
29
29
  # @see http://asm.sourceforge.net/articles/linasm.html#Memory
30
30
  #
31
- class MemoryOperand < Struct.new(:base, :offset, :index, :scale)
31
+ class MemoryOperand < Struct.new(:base, :offset, :index, :scale, :width)
32
32
 
33
33
  #
34
34
  # Creates a new Memory Operand.
@@ -48,7 +48,7 @@ module Ronin
48
48
  # @raise [TypeError]
49
49
  # `base` or `index` was not a {Register} or `nil`.
50
50
  #
51
- def initialize(base=nil,offset=0,index=nil,scale=1)
51
+ def initialize(base=nil,offset=0,index=nil,scale=1,width=nil)
52
52
  unless (base.nil? || base.kind_of?(Register))
53
53
  raise(TypeError,"base must be a Register or nil")
54
54
  end
@@ -65,7 +65,11 @@ module Ronin
65
65
  raise(TypeError,"scale must be an Integer")
66
66
  end
67
67
 
68
- super(base,offset,index,scale)
68
+ if base
69
+ width ||= base.width
70
+ end
71
+
72
+ super(base,offset,index,scale,width)
69
73
  end
70
74
 
71
75
  #
@@ -78,7 +82,13 @@ module Ronin
78
82
  # The new Memory Operand.
79
83
  #
80
84
  def +(offset)
81
- MemoryOperand.new(self.base,self.offset+offset,self.index,self.scale)
85
+ MemoryOperand.new(
86
+ self.base,
87
+ self.offset + offset,
88
+ self.index,
89
+ self.scale,
90
+ self.width
91
+ )
82
92
  end
83
93
 
84
94
  #
@@ -91,17 +101,13 @@ module Ronin
91
101
  # The new Memory Operand.
92
102
  #
93
103
  def -(offset)
94
- MemoryOperand.new(self.base,self.offset-offset,self.index,self.scale)
95
- end
96
-
97
- #
98
- # The width of the Memory Operand.
99
- #
100
- # @return [Integer]
101
- # The width taken from the base {Register}.
102
- #
103
- def width
104
- base.width
104
+ MemoryOperand.new(
105
+ self.base,
106
+ self.offset - offset,
107
+ self.index,
108
+ self.scale,
109
+ self.width
110
+ )
105
111
  end
106
112
 
107
113
  end
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -38,14 +38,14 @@ module Ronin
38
38
 
39
39
  # Supported Assembly Syntaxs
40
40
  SYNTAX = {
41
- :att => Syntax::ATT,
42
- :intel => Syntax::Intel
41
+ att: Syntax::ATT,
42
+ intel: Syntax::Intel
43
43
  }
44
44
 
45
45
  # The Assembly Parsers
46
46
  PARSERS = {
47
- :att => :gas,
48
- :intel => :nasm
47
+ att: :gas,
48
+ intel: :nasm
49
49
  }
50
50
 
51
51
  # The targeted architecture
@@ -94,7 +94,7 @@ module Ronin
94
94
  # The given block will be evaluated within the program.
95
95
  #
96
96
  # @example
97
- # Program.new(:arch => :amd64) do
97
+ # Program.new(arch: :amd64) do
98
98
  # push rax
99
99
  # push rbx
100
100
  #
@@ -193,53 +193,73 @@ module Ronin
193
193
  #
194
194
  # Creates an operand of size 1 (byte).
195
195
  #
196
- # @param [Integer] number
196
+ # @param [MemoryOperand, Integer] op
197
197
  # The value of the operand.
198
198
  #
199
- # @return [ImmediateOperand]
199
+ # @return [MemoryOperand, ImmediateOperand]
200
200
  # The new operand value.
201
201
  #
202
- def byte(number)
203
- ImmediateOperand.new(number,1)
202
+ def byte(op)
203
+ case op
204
+ when MemoryOperand
205
+ MemoryOperand.new(op.base,op.offset,op.index,op.scale,1)
206
+ else
207
+ ImmediateOperand.new(op,1)
208
+ end
204
209
  end
205
210
 
206
211
  #
207
212
  # Creates a operand of size 2 (bytes).
208
213
  #
209
- # @param [Integer] number
214
+ # @param [MemoryOperand, Integer] op
210
215
  # The value of the operand.
211
216
  #
212
- # @return [ImmediateOperand]
217
+ # @return [MemoryOperand, ImmediateOperand]
213
218
  # The new operand value.
214
219
  #
215
- def word(number)
216
- ImmediateOperand.new(number,2)
220
+ def word(op)
221
+ case op
222
+ when MemoryOperand
223
+ MemoryOperand.new(op.base,op.offset,op.index,op.scale,2)
224
+ else
225
+ ImmediateOperand.new(op,2)
226
+ end
217
227
  end
218
228
 
219
229
  #
220
230
  # Creates a operand of size 4 (bytes).
221
231
  #
222
- # @param [Integer] number
232
+ # @param [MemoryOperand, Integer] op
223
233
  # The value of the operand.
224
234
  #
225
235
  # @return [ImmediateOperand]
226
236
  # The new operand value.
227
237
  #
228
- def dword(number)
229
- ImmediateOperand.new(number,4)
238
+ def dword(op)
239
+ case op
240
+ when MemoryOperand
241
+ MemoryOperand.new(op.base,op.offset,op.index,op.scale,4)
242
+ else
243
+ ImmediateOperand.new(op,4)
244
+ end
230
245
  end
231
246
 
232
247
  #
233
248
  # Creates a operand of size 8 (bytes).
234
249
  #
235
- # @param [Integer] number
250
+ # @param [MemoryOperand, Integer] op
236
251
  # The value of the operand.
237
252
  #
238
- # @return [ImmediateOperand]
253
+ # @return [MemoryOperand, ImmediateOperand]
239
254
  # The new operand.
240
255
  #
241
- def qword(number)
242
- ImmediateOperand.new(number,8)
256
+ def qword(op)
257
+ case op
258
+ when MemoryOperand
259
+ MemoryOperand.new(op.base,op.offset,op.index,op.scale,8)
260
+ else
261
+ ImmediateOperand.new(op,8)
262
+ end
243
263
  end
244
264
 
245
265
  #
@@ -318,15 +338,15 @@ module Ronin
318
338
  #
319
339
  # Generic method for setting a register.
320
340
  #
321
- # @param [Register, Immediate, Integer] value
322
- # The new value for the register.
323
- #
324
341
  # @param [Symbol] name
325
342
  # The name of the reigster.
326
343
  #
344
+ # @param [Register, Immediate, Integer] value
345
+ # The new value for the register.
346
+ #
327
347
  # @abstract
328
348
  #
329
- def register_set(value,name)
349
+ def register_set(name,value)
330
350
  end
331
351
 
332
352
  #
@@ -386,10 +406,17 @@ module Ronin
386
406
  # @param [Symbol] syntax
387
407
  # The syntax to compile the program to.
388
408
  #
389
- def to_asm(syntax=:att)
409
+ def to_asm(syntax=:intel)
390
410
  SYNTAX[syntax].emit_program(self)
391
411
  end
392
412
 
413
+ #
414
+ # @see #to_s
415
+ #
416
+ def to_s
417
+ to_asm
418
+ end
419
+
393
420
  #
394
421
  # Assembles the program.
395
422
  #
@@ -399,7 +426,7 @@ module Ronin
399
426
  # @param [Hash] options
400
427
  # Additional options.
401
428
  #
402
- # @option options [Symbol, String] :syntax (:att)
429
+ # @option options [Symbol, String] :syntax (:intel)
403
430
  # The syntax to compile the program to.
404
431
  #
405
432
  # @option options [Symbol] :format (:bin)
@@ -424,7 +451,7 @@ module Ronin
424
451
  # The path to the assembled program.
425
452
  #
426
453
  def assemble(output,options={})
427
- syntax = options.fetch(:syntax,:att)
454
+ syntax = options.fetch(:syntax,:intel)
428
455
  format = options.fetch(:format,:bin)
429
456
  parser = PARSERS[syntax]
430
457
 
@@ -433,11 +460,11 @@ module Ronin
433
460
  source.close
434
461
 
435
462
  YASM::Program.assemble(
436
- :file => source.path,
437
- :parser => PARSERS[syntax],
438
- :target => @arch,
439
- :output_format => format,
440
- :output => output
463
+ file: source.path,
464
+ parser: PARSERS[syntax],
465
+ target: @arch,
466
+ output_format: format,
467
+ output: output
441
468
  )
442
469
 
443
470
  return output
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -60,7 +60,7 @@ module Ronin
60
60
  def assemble(options={})
61
61
  output = Tempfile.new(['ronin-shellcode', '.bin']).path
62
62
 
63
- super(output,options.merge(:format => :bin))
63
+ super(output,options.merge(format: :bin))
64
64
 
65
65
  return File.new(output,'rb').read
66
66
  end
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -1,7 +1,7 @@
1
1
  #
2
2
  # Ronin ASM - A Ruby DSL for crafting Assembly programs and Shellcode.
3
3
  #
4
- # Copyright (c) 2007-2012 Hal Brodigan (postmodern.mod3 at gmail.com)
4
+ # Copyright (c) 2007-2013 Hal Brodigan (postmodern.mod3 at gmail.com)
5
5
  #
6
6
  # This file is part of Ronin ASM.
7
7
  #
@@ -87,6 +87,23 @@ module Ronin
87
87
  return asm
88
88
  end
89
89
 
90
+ #
91
+ # Emits multiple operands.
92
+ #
93
+ # @param [Array<ImmediateOperand, MemoryOperand, Register, Symbol>] ops
94
+ # The Array of operands.
95
+ #
96
+ # @return [String]
97
+ # The formatted operands.
98
+ #
99
+ def self.emit_operands(ops)
100
+ if ops.length > 1
101
+ [*ops[1..-1], ops[0]].map { |op| emit_operand(op) }.join(",\t")
102
+ else
103
+ super(ops)
104
+ end
105
+ end
106
+
90
107
  #
91
108
  # Emits an instruction.
92
109
  #
@@ -111,23 +128,33 @@ module Ronin
111
128
  end
112
129
 
113
130
  #
114
- # Emits a program.
131
+ # Emits a section name.
132
+ #
133
+ # @param [Symbol] name
134
+ # The section name.
135
+ #
136
+ # @return [String]
137
+ # The formatted section name.
138
+ #
139
+ # @since 0.2.0
140
+ #
141
+ def self.emit_section(name)
142
+ ".#{name}"
143
+ end
144
+
145
+ #
146
+ # Emits the program's prologue.
115
147
  #
116
148
  # @param [Program] program
117
149
  # The program.
118
150
  #
119
151
  # @return [String]
120
- # The formatted program.
152
+ # The formatted prologue.
121
153
  #
122
- def self.emit_program(program)
123
- asm = super(program)
124
-
125
- # prepend the `.code64` directive for YASM
126
- if program.arch == :amd64
127
- asm = [".code64", '', asm].join($/)
128
- end
129
-
130
- return asm
154
+ # @since 0.2.0
155
+ #
156
+ def self.emit_prologue(program)
157
+ ".code#{BITS[program.arch]}"
131
158
  end
132
159
 
133
160
  end