ronin-asm 0.1.0 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
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