On 7/7/07, ara.t.howard <ara.t.howard / gmail.com> wrote:
>
> On Jul 6, 2007, at 12:29 PM, jannis / harderweb.de wrote:
>
> > The method used in this captcha is very is to break. In fact I can
> > solve
> > the captchas 6 times as fast as it takes to generate them (locally)
> > in
> > only 63 lines of code. I do this by generating a regexp for each
> > possible
> > character. As the characters don't get damaged by the noise (as they
> > get
> > in most image bases captchas) this works all of the time.
>
>
> hmmm - not for me?
>
>
>
> cfp:~ > ruby a.rb
>                     user     system      total        real
> generate:      0.140000   0.020000   0.170000 (  0.178928)
> setup:         0.020000   0.000000   0.020000 (  0.022138)
> break:       Flatulent.version : 0.0.4
> a.rb:63: failed on attempt 1 (RuntimeError)
>          from /opt/local/lib/ruby/1.8/benchmark.rb:293:in `measure'
>          from /opt/local/lib/ruby/1.8/benchmark.rb:377:in `report'
>          from a.rb:63
>          from /opt/local/lib/ruby/1.8/benchmark.rb:177:in `benchmark'
>          from /opt/local/lib/ruby/1.8/benchmark.rb:207:in `bm'
>          from a.rb:59
>
>
>
> cfp:~ > cat a.rb
> require 'flatulent'
> require 'benchmark'
> require 'flatulent'
>
> class Deflatulent
>    def initialize font="big"
>      font = Text::Figlet::Font.new(File.join(Flatulent.fontdir,font
> +".flf"))
>      typesetter = Text::Figlet::Typesetter.new font
>      letters = ('A'..'Z').to_a + ('1'..'9').to_a
>      @lines_array = letters.map{|letter| [letter,
> gen_figlet_lines_array(typesetter[letter])] }
>    end
>
>    def deflatulent string
>      if string =~ /<pre id='[a-zA-Z0-9_-]+_element' style='.*?'>(.*?)<
> \/ pre>/m
>        string = $1
>        [[/<\/?span>/,''],["&nbsp;"," "],["<br>","\n"],["&lt;","<"],
> ["&gt;",">"],["&quot;",'"'],["&amp;","&"]].each do |args|
>          string.gsub!(*args)
>        end
>      end
>
>      width = string.index("\n")
>      string.tr!("\n","")
>      solution = []
>
>      @lines_array.each do |(letter,(length,lines))|
>
>        re = "(?="
>        lines.each{|line| re << line << ".{#{width-length}}" }
>        re << ")"
>
>        string.scan(Regexp.new(re, Regexp::MULTILINE)) do
>          solution[$~.begin(0) % width] = letter
>        end
>      end
>
>      solution.join
>    end
>
> private
>    def gen_figlet_lines_array string
>      lines = string.split("\n")
>      lines.shift while lines.first.strip.empty?
>      lines.pop   while lines.last.strip.empty?
>
>      lines.each{|e|e[0,1]=""} while lines.all?{|e|e[0,1]==' '}
>      lines.each{|e|e[-1,1]=""} while lines.all?{|e|e[-1,1]==' '}
>
>      [lines[0].length,lines.map{|e|e.split('').map{|q|(q == ' ' ?
> '.' : Regexp.escape(q))}.join}]
>    end
> end
>
> defl = html = code = nil
> pairs = Array.new(200)
>
> GC.disable
> i = 0
>
> begin
>    Benchmark.bm(13) do |x|
>      i += 1
>      x.report("generate:") { flat = Flatulent.new; html = flat.form;
> code = flat.string }
>      x.report("setup:")    { defl = Deflatulent.new  }
>      x.report("break:")    { raise "failed on attempt #{ i }" unless
> defl.deflatulent(html) == code }
>      x.report("generate 200:") { 200.times{|index| flat =
> Flatulent.new; pairs[index] = [flat.form,flat.string] } }
>      x.report("break 200:") { pairs.map{|(html,code)| raise unless
> defl.deflatulent(html) == code } }
>    end
> ensure
>    puts "Flatulent.version : #{ Flatulent.version }"
> end
>
>
> nevertheless, i'm not for one second claiming flatulent is ready for
> prime time.  however, i will state that i think it's quite a bit of
> work if you use it in the intended way, which is for the html to make
> an ajax call to get the flatulent source because this make said
> source available only to javascript.  no doubt someone could crack it
> from there, but the latest version adds vertical and horizontal
> offset to each char.  my version is turning that source into a png.
> anyhow, the attention is welcome - but next time send a patch!  ;-)
>
> -a
> --
> we can deny everything, except that we have the possibility of being
> better. simply reflect on that.
> h.h. the 14th dalai lama
>
>
>
>
>

Ara,
That is because you set defl and flat inside a block, without setting
the variables to nil before the block is executed, so they stay
existing for the actual decode stage.


-- 
Chris Carter
concentrationstudios.com
brynmawrcs.com