Class: Crokus::RandomGen
- Inherits:
-
Object
- Object
- Crokus::RandomGen
- Defined in:
- lib/crokus/cfg_random_gen.rb
Constant Summary collapse
- ARITH =
{ :add => "+", :sub => "-", :mul => "*", :div => "/", #:shift_r => ">>", #:shift_l => "<<", }
- COMP =
{ :gt => ">", :gte => ">=", :lt => "<", :lte => "<=", :eq => "==", :neq => "!=" }
- COMPA =
[:gt,:lt,:eq,:neq,:gte,:lte]
- ACCUM =
[:add_assign,:sub_assign,:mul_assign,:div_assign]
- LOGIC =
[:or,:and,:xor]
- MINUS =
Token.new [:sub,"-",[0,0]]
Instance Attribute Summary collapse
-
#cfg ⇒ Object
Returns the value of attribute cfg.
-
#options ⇒ Object
Returns the value of attribute options.
Instance Method Summary collapse
- #create_assign ⇒ Object
- #create_assignee ⇒ Object
- #create_binary_expression(depth) ⇒ Object
- #create_binary_op ⇒ Object
- #create_cfg ⇒ Object
- #create_cond_op ⇒ Object
- #create_condition ⇒ Object
- #create_expression ⇒ Object
- #create_inputs ⇒ Object
- #create_internal_arrays ⇒ Object
- #create_output_assigns ⇒ Object
- #create_outputs ⇒ Object
- #create_unary_expression ⇒ Object
- #create_variables ⇒ Object
- #gen_dot ⇒ Object
- #gen_for_block(level) ⇒ Object
- #gen_if_block(level) ⇒ Object
- #gen_plain_block(level) ⇒ Object
- #gen_while_block(level) ⇒ Object
- #generate_c ⇒ Object
- #init_cfg ⇒ Object
- #init_random_generators ⇒ Object
-
#initialize(options = {}) ⇒ RandomGen
constructor
A new instance of RandomGen.
- #populate(bb) ⇒ Object
- #populate_all ⇒ Object
- #print_infos ⇒ Object
- #rec_create_bbs(level = 0) ⇒ Object
- #register_readables(ary) ⇒ Object
- #run(params) ⇒ Object
Constructor Details
#initialize(options = {}) ⇒ RandomGen
Returns a new instance of RandomGen.
19 20 21 |
# File 'lib/crokus/cfg_random_gen.rb', line 19 def initialize ={} @options= end |
Instance Attribute Details
#cfg ⇒ Object
Returns the value of attribute cfg.
17 18 19 |
# File 'lib/crokus/cfg_random_gen.rb', line 17 def cfg @cfg end |
#options ⇒ Object
Returns the value of attribute options.
16 17 18 |
# File 'lib/crokus/cfg_random_gen.rb', line 16 def @options end |
Instance Method Details
#create_assign ⇒ Object
208 209 210 211 212 |
# File 'lib/crokus/cfg_random_gen.rb', line 208 def create_assign lhs=create_assignee rhs=create_expression() Assign.new(lhs,ASSIGN,rhs) end |
#create_assignee ⇒ Object
214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 |
# File 'lib/crokus/cfg_random_gen.rb', line 214 def create_assignee if @params["nb_int_arrays"]>0 case r=rand(0..10) when 0..3 name,size=@cfg.infos["internal_arrays"].sample.first var=@readables.sample @readables.rotate! abs_func=Ident.new(Token.create "abs") return Indexed.new(name,FunCall.new(abs_func,[Binary.new(var,MOD,size)])) end end assignee=@vars.first @vars.rotate! return assignee end |
#create_binary_expression(depth) ⇒ Object
242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 |
# File 'lib/crokus/cfg_random_gen.rb', line 242 def create_binary_expression depth if depth <= 1 lhs=create_unary_expression rhs=create_unary_expression else lhs=create_binary_expression(depth-1) rhs=create_binary_expression(depth-1) end op=create_binary_op if op.val=="/" and lhs.to_s=="0" return create_binary_expression(depth) else return Parenth.new(Binary.new(lhs,op,rhs)) end end |
#create_binary_op ⇒ Object
282 283 284 285 286 287 288 |
# File 'lib/crokus/cfg_random_gen.rb', line 282 def create_binary_op kind,val=ARITH.sample if @params["accept_integer_division"]==false and kind==:div return create_binary_op # retry end Token.new([kind,val,[0,0]]) end |
#create_cfg ⇒ Object
109 110 111 112 113 114 |
# File 'lib/crokus/cfg_random_gen.rb', line 109 def create_cfg puts " |-->[+] building cfg" while @cfg.size < @params["nb_basic_blocks"] rec_create_bbs end end |
#create_cond_op ⇒ Object
290 291 292 293 |
# File 'lib/crokus/cfg_random_gen.rb', line 290 def create_cond_op kind,val=COMP.sample Token.new([kind,val,[0,0]]) end |
#create_condition ⇒ Object
230 231 232 233 234 235 |
# File 'lib/crokus/cfg_random_gen.rb', line 230 def create_condition lhs=create_expression() op =create_cond_op() rhs=create_expression() Binary.new(lhs,op,rhs) end |
#create_expression ⇒ Object
237 238 239 240 |
# File 'lib/crokus/cfg_random_gen.rb', line 237 def create_expression depth=@rng["assigns_expression_depth"].call.to_i return create_binary_expression(depth) end |
#create_inputs ⇒ Object
73 74 75 76 77 78 |
# File 'lib/crokus/cfg_random_gen.rb', line 73 def create_inputs name="in_0" @inputs=(1..@params["nb_inputs"]).map{|idx| Ident.new(Token.create name=name.succ)} register_readables @inputs @cfg.infos["inputs"]=@inputs end |
#create_internal_arrays ⇒ Object
100 101 102 103 104 105 106 107 |
# File 'lib/crokus/cfg_random_gen.rb', line 100 def create_internal_arrays @cfg.infos["internal_arrays"]||=[] (1..@params["nb_int_arrays"]).each do |idx| size=@rng["size_int_arrays"].call.to_i size=IntLit.new(Token.create(size.to_s)) @cfg.infos["internal_arrays"] << {Ident.new(Token.create("t#{idx}")) => size} end end |
#create_output_assigns ⇒ Object
93 94 95 96 97 98 |
# File 'lib/crokus/cfg_random_gen.rb', line 93 def create_output_assigns @cfg.infos["output_assigns"]||=[] @outputs.each do |ident| @cfg.infos["output_assigns"] << {ident => create_expression} end end |
#create_outputs ⇒ Object
80 81 82 83 84 |
# File 'lib/crokus/cfg_random_gen.rb', line 80 def create_outputs name="out_0" @outputs=(1..@params["nb_outputs"]).map{|idx| Ident.new(Token.create name=name.succ)} @cfg.infos["outputs"]=@outputs end |
#create_unary_expression ⇒ Object
295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 |
# File 'lib/crokus/cfg_random_gen.rb', line 295 def create_unary_expression r=rand(0..10) case r when 1 return IntLit.new Token.create rand(0..255).to_s when 2 return Parenth.new(Unary.new(MINUS,@readables.sample)) when 3 name,size=@cfg.infos["internal_arrays"].sample.first var=@readables.sample abs_func=Ident.new(Token.create "abs") index=FunCall.new(abs_func,[Binary.new(var,MOD,size)]) return Indexed.new(name,index) #eg : t[abs(a % 4)] else return @readables.sample end end |
#create_variables ⇒ Object
86 87 88 89 90 91 |
# File 'lib/crokus/cfg_random_gen.rb', line 86 def create_variables name="`" # succ is 'a' @vars=(1..@params["nb_int_vars"]).map{|idx| Ident.new(Token.create name=name.succ)} register_readables @vars @cfg.infos["int_vars"]=@vars end |
#gen_dot ⇒ Object
47 48 49 |
# File 'lib/crokus/cfg_random_gen.rb', line 47 def gen_dot @cfg.print verbose=false end |
#gen_for_block(level) ⇒ Object
174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 |
# File 'lib/crokus/cfg_random_gen.rb', line 174 def gen_for_block level @cfg << cond_bb = BasicBlock.new(:start_for => true) @index||="idx_0" @index=@index.succ loop_index=Ident.new Token.create @index cond_bb.infos["loop_index"]=loop_index @cfg.infos["loop_indexes"]||=[] @cfg.infos["loop_indexes"] << loop_index cond_bb.infos["loop_index_bound"]=@rng["forloop_iterations"].call.to_i @cfg << trueBranch = BasicBlock.new @cfg << falseBranch = BasicBlock.new @cfg << postBranch = BasicBlock.new(:loop_body_end => true) @current.to cond_bb cond_bb.to trueBranch cond_bb.to falseBranch @current= trueBranch rec_create_bbs(level+1) @current.to postBranch @current=postBranch @current.to cond_bb @current=falseBranch end |
#gen_if_block(level) ⇒ Object
140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 |
# File 'lib/crokus/cfg_random_gen.rb', line 140 def gen_if_block level @current.infos[:cond]=create_condition @current.infos[:start_if]=true @cfg << trueBranch =BasicBlock.new @cfg << falseBranch=BasicBlock.new @cfg << mergeBranch=BasicBlock.new @current.to trueBranch @current.to falseBranch @current=trueBranch rec_create_bbs(level+1) @current.to mergeBranch @current=falseBranch rec_create_bbs(level+1) @current.to mergeBranch @current=mergeBranch end |
#gen_plain_block(level) ⇒ Object
134 135 136 137 138 |
# File 'lib/crokus/cfg_random_gen.rb', line 134 def gen_plain_block level @cfg << bb=BasicBlock.new @current.to bb @current=bb end |
#gen_while_block(level) ⇒ Object
160 161 162 163 164 165 166 167 168 169 170 171 172 |
# File 'lib/crokus/cfg_random_gen.rb', line 160 def gen_while_block level @cfg << cond_bb = BasicBlock.new(:start_while => true) cond_bb.infos[:cond]=create_condition @cfg << trueBranch = BasicBlock.new @cfg << falseBranch = BasicBlock.new @current.to cond_bb cond_bb.to trueBranch cond_bb.to falseBranch @current = trueBranch rec_create_bbs(level+1) @current.to cond_bb @current=falseBranch end |
#generate_c ⇒ Object
313 314 315 |
# File 'lib/crokus/cfg_random_gen.rb', line 313 def generate_c PrinterC.new().print(cfg) end |
#init_cfg ⇒ Object
51 52 53 54 |
# File 'lib/crokus/cfg_random_gen.rb', line 51 def init_cfg @cfg=CFG.new(@params["name"]) @current=@cfg.starter end |
#init_random_generators ⇒ Object
56 57 58 59 60 61 62 63 64 65 |
# File 'lib/crokus/cfg_random_gen.rb', line 56 def init_random_generators puts " |-->[+] init parameterized random generators" @rng={} @params.each do |key,val| if key.start_with? "avg_" name=key[4..-1] @rng[name]=Distribution::Normal.rng(mean=val,sigma=0.5) #sigma=1 ? end end end |
#populate(bb) ⇒ Object
202 203 204 205 206 |
# File 'lib/crokus/cfg_random_gen.rb', line 202 def populate bb @rng["assigns_per_bbs"].call.to_i.times do bb << create_assign end end |
#populate_all ⇒ Object
197 198 199 200 |
# File 'lib/crokus/cfg_random_gen.rb', line 197 def populate_all puts " |-->[+] populate cfg" @cfg.each{|bb| populate bb} end |
#print_infos ⇒ Object
42 43 44 45 |
# File 'lib/crokus/cfg_random_gen.rb', line 42 def print_infos puts " |-->[+] infos about CFG :" puts " |-->[+] #basic blocks : #{@cfg.size}" end |
#rec_create_bbs(level = 0) ⇒ Object
116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 |
# File 'lib/crokus/cfg_random_gen.rb', line 116 def rec_create_bbs level=0 if @cfg.size < @params["nb_basic_blocks"] type = [:plain,:if,:while,:for].sample case type when :plain gen_plain_block(level) when :if gen_if_block(level) when :while gen_while_block(level) if @params["accept_while_loops"] when :for gen_for_block(level) else raise "unknown cfg type : #{type}" end end end |
#register_readables(ary) ⇒ Object
67 68 69 70 71 |
# File 'lib/crokus/cfg_random_gen.rb', line 67 def register_readables ary @readables||=[] @readables << ary @readables.flatten! end |
#run(params) ⇒ Object
23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 |
# File 'lib/crokus/cfg_random_gen.rb', line 23 def run params puts "[+] running random C code generation" puts " |-->[+] reading parameters file '#{params}'" @params=YAML.load(File.read(params)) init_cfg init_random_generators create_inputs create_outputs create_variables create_internal_arrays create_output_assigns create_cfg gen_dot # to see the structure, before hacking the content populate_all generate_c print_infos end |