raptcha 0.0.1 → 2.0.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.
- data/README +0 -88
- data/Rakefile +364 -0
- data/image.sh +24 -0
- data/images/raptcha.png +0 -0
- data/lib/raptcha.rb +377 -2063
- metadata +56 -128
- data/bin/raptcha +0 -2225
- data/gemspec.rb +0 -28
- data/install.rb +0 -210
- data/out +0 -0
- data/rails/README +0 -182
- data/rails/Rakefile +0 -10
- data/rails/app/controllers/application.rb +0 -7
- data/rails/app/controllers/raptcha_controller.rb +0 -43
- data/rails/app/helpers/application_helper.rb +0 -3
- data/rails/config/boot.rb +0 -45
- data/rails/config/database.yml +0 -36
- data/rails/config/environment.rb +0 -62
- data/rails/config/environments/development.rb +0 -21
- data/rails/config/environments/production.rb +0 -18
- data/rails/config/environments/test.rb +0 -19
- data/rails/config/lighttpd.conf +0 -54
- data/rails/config/routes.rb +0 -23
- data/rails/doc/README_FOR_APP +0 -2
- data/rails/lib/raptcha.rb +0 -2225
- data/rails/log/development.log +0 -16
- data/rails/log/fastcgi.crash.log +0 -4
- data/rails/log/lighttpd.access.log +0 -2
- data/rails/log/lighttpd.error.log +0 -3
- data/rails/log/production.log +0 -0
- data/rails/log/server.log +0 -0
- data/rails/log/test.log +0 -0
- data/rails/public/404.html +0 -30
- data/rails/public/500.html +0 -30
- data/rails/public/dispatch.cgi +0 -10
- data/rails/public/dispatch.fcgi +0 -24
- data/rails/public/dispatch.rb +0 -10
- data/rails/public/favicon.ico +0 -0
- data/rails/public/images/rails.png +0 -0
- data/rails/public/index.html +0 -277
- data/rails/public/javascripts/application.js +0 -2
- data/rails/public/javascripts/controls.js +0 -833
- data/rails/public/javascripts/dragdrop.js +0 -942
- data/rails/public/javascripts/effects.js +0 -1088
- data/rails/public/javascripts/prototype.js +0 -2515
- data/rails/public/robots.txt +0 -1
- data/rails/script/about +0 -3
- data/rails/script/breakpointer +0 -3
- data/rails/script/console +0 -3
- data/rails/script/destroy +0 -3
- data/rails/script/generate +0 -3
- data/rails/script/performance/benchmarker +0 -3
- data/rails/script/performance/profiler +0 -3
- data/rails/script/plugin +0 -3
- data/rails/script/process/inspector +0 -3
- data/rails/script/process/reaper +0 -3
- data/rails/script/process/spawner +0 -3
- data/rails/script/runner +0 -3
- data/rails/script/server +0 -3
- data/rails/test/test_helper.rb +0 -28
- data/rails/tmp/sessions/ruby_sess.04085f44b9141c9d +0 -0
- data/raptcha-0.0.1.gem +0 -0
- data/samples.rb +0 -19
data/rails/config/boot.rb
DELETED
@@ -1,45 +0,0 @@
|
|
1
|
-
# Don't change this file. Configuration is done in config/environment.rb and config/environments/*.rb
|
2
|
-
|
3
|
-
unless defined?(RAILS_ROOT)
|
4
|
-
root_path = File.join(File.dirname(__FILE__), '..')
|
5
|
-
|
6
|
-
unless RUBY_PLATFORM =~ /(:?mswin|mingw)/
|
7
|
-
require 'pathname'
|
8
|
-
root_path = Pathname.new(root_path).cleanpath(true).to_s
|
9
|
-
end
|
10
|
-
|
11
|
-
RAILS_ROOT = root_path
|
12
|
-
end
|
13
|
-
|
14
|
-
unless defined?(Rails::Initializer)
|
15
|
-
if File.directory?("#{RAILS_ROOT}/vendor/rails")
|
16
|
-
require "#{RAILS_ROOT}/vendor/rails/railties/lib/initializer"
|
17
|
-
else
|
18
|
-
require 'rubygems'
|
19
|
-
|
20
|
-
environment_without_comments = IO.readlines(File.dirname(__FILE__) + '/environment.rb').reject { |l| l =~ /^#/ }.join
|
21
|
-
environment_without_comments =~ /[^#]RAILS_GEM_VERSION = '([\d.]+)'/
|
22
|
-
rails_gem_version = $1
|
23
|
-
|
24
|
-
if version = defined?(RAILS_GEM_VERSION) ? RAILS_GEM_VERSION : rails_gem_version
|
25
|
-
# Asking for 1.1.6 will give you 1.1.6.5206, if available -- makes it easier to use beta gems
|
26
|
-
rails_gem = Gem.cache.search('rails', "~>#{version}.0").sort_by { |g| g.version.version }.last
|
27
|
-
|
28
|
-
if rails_gem
|
29
|
-
gem "rails", "=#{rails_gem.version.version}"
|
30
|
-
require rails_gem.full_gem_path + '/lib/initializer'
|
31
|
-
else
|
32
|
-
STDERR.puts %(Cannot find gem for Rails ~>#{version}.0:
|
33
|
-
Install the missing gem with 'gem install -v=#{version} rails', or
|
34
|
-
change environment.rb to define RAILS_GEM_VERSION with your desired version.
|
35
|
-
)
|
36
|
-
exit 1
|
37
|
-
end
|
38
|
-
else
|
39
|
-
gem "rails"
|
40
|
-
require 'initializer'
|
41
|
-
end
|
42
|
-
end
|
43
|
-
|
44
|
-
Rails::Initializer.run(:set_load_path)
|
45
|
-
end
|
data/rails/config/database.yml
DELETED
@@ -1,36 +0,0 @@
|
|
1
|
-
# MySQL (default setup). Versions 4.1 and 5.0 are recommended.
|
2
|
-
#
|
3
|
-
# Install the MySQL driver:
|
4
|
-
# gem install mysql
|
5
|
-
# On MacOS X:
|
6
|
-
# gem install mysql -- --include=/usr/local/lib
|
7
|
-
# On Windows:
|
8
|
-
# gem install mysql
|
9
|
-
# Choose the win32 build.
|
10
|
-
# Install MySQL and put its /bin directory on your path.
|
11
|
-
#
|
12
|
-
# And be sure to use new-style password hashing:
|
13
|
-
# http://dev.mysql.com/doc/refman/5.0/en/old-client.html
|
14
|
-
development:
|
15
|
-
adapter: mysql
|
16
|
-
database: rails_development
|
17
|
-
username: root
|
18
|
-
password:
|
19
|
-
host: localhost
|
20
|
-
|
21
|
-
# Warning: The database defined as 'test' will be erased and
|
22
|
-
# re-generated from your development database when you run 'rake'.
|
23
|
-
# Do not set this db to the same as development or production.
|
24
|
-
test:
|
25
|
-
adapter: mysql
|
26
|
-
database: rails_test
|
27
|
-
username: root
|
28
|
-
password:
|
29
|
-
host: localhost
|
30
|
-
|
31
|
-
production:
|
32
|
-
adapter: mysql
|
33
|
-
database: rails_production
|
34
|
-
username: root
|
35
|
-
password:
|
36
|
-
host: localhost
|
data/rails/config/environment.rb
DELETED
@@ -1,62 +0,0 @@
|
|
1
|
-
# Be sure to restart your web server when you modify this file.
|
2
|
-
|
3
|
-
# Uncomment below to force Rails into production mode when
|
4
|
-
# you don't control web/app server and can't set it the proper way
|
5
|
-
# ENV['RAILS_ENV'] ||= 'production'
|
6
|
-
|
7
|
-
# Specifies gem version of Rails to use when vendor/rails is not present
|
8
|
-
RAILS_GEM_VERSION = '1.2.3' unless defined? RAILS_GEM_VERSION
|
9
|
-
|
10
|
-
# Bootstrap the Rails environment, frameworks, and default configuration
|
11
|
-
require File.join(File.dirname(__FILE__), 'boot')
|
12
|
-
|
13
|
-
Rails::Initializer.run do |config|
|
14
|
-
# Settings in config/environments/* take precedence over those specified here
|
15
|
-
|
16
|
-
# Skip frameworks you're not going to use (only works if using vendor/rails)
|
17
|
-
# config.frameworks -= [ :action_web_service, :action_mailer ]
|
18
|
-
|
19
|
-
# Only load the plugins named here, by default all plugins in vendor/plugins are loaded
|
20
|
-
# config.plugins = %W( exception_notification ssl_requirement )
|
21
|
-
|
22
|
-
# Add additional load paths for your own custom dirs
|
23
|
-
# config.load_paths += %W( #{RAILS_ROOT}/extras )
|
24
|
-
|
25
|
-
# Force all environments to use the same logger level
|
26
|
-
# (by default production uses :info, the others :debug)
|
27
|
-
# config.log_level = :debug
|
28
|
-
|
29
|
-
# Use the database for sessions instead of the file system
|
30
|
-
# (create the session table with 'rake db:sessions:create')
|
31
|
-
# config.action_controller.session_store = :active_record_store
|
32
|
-
|
33
|
-
# Use SQL instead of Active Record's schema dumper when creating the test database.
|
34
|
-
# This is necessary if your schema can't be completely dumped by the schema dumper,
|
35
|
-
# like if you have constraints or database-specific column types
|
36
|
-
# config.active_record.schema_format = :sql
|
37
|
-
|
38
|
-
# Activate observers that should always be running
|
39
|
-
# config.active_record.observers = :cacher, :garbage_collector
|
40
|
-
|
41
|
-
# Make Active Record use UTC-base instead of local time
|
42
|
-
# config.active_record.default_timezone = :utc
|
43
|
-
|
44
|
-
# See Rails::Configuration for more options
|
45
|
-
end
|
46
|
-
|
47
|
-
# Add new inflection rules using the following format
|
48
|
-
# (all these examples are active by default):
|
49
|
-
# Inflector.inflections do |inflect|
|
50
|
-
# inflect.plural /^(ox)$/i, '\1en'
|
51
|
-
# inflect.singular /^(ox)en/i, '\1'
|
52
|
-
# inflect.irregular 'person', 'people'
|
53
|
-
# inflect.uncountable %w( fish sheep )
|
54
|
-
# end
|
55
|
-
|
56
|
-
# Add new mime types for use in respond_to blocks:
|
57
|
-
# Mime::Type.register "text/richtext", :rtf
|
58
|
-
# Mime::Type.register "application/x-mobile", :mobile
|
59
|
-
|
60
|
-
# Include your application configuration below
|
61
|
-
|
62
|
-
require 'raptcha'
|
@@ -1,21 +0,0 @@
|
|
1
|
-
# Settings specified here will take precedence over those in config/environment.rb
|
2
|
-
|
3
|
-
# In the development environment your application's code is reloaded on
|
4
|
-
# every request. This slows down response time but is perfect for development
|
5
|
-
# since you don't have to restart the webserver when you make code changes.
|
6
|
-
config.cache_classes = false
|
7
|
-
|
8
|
-
# Log error messages when you accidentally call methods on nil.
|
9
|
-
config.whiny_nils = true
|
10
|
-
|
11
|
-
# Enable the breakpoint server that script/breakpointer connects to
|
12
|
-
config.breakpoint_server = true
|
13
|
-
|
14
|
-
# Show full error reports and disable caching
|
15
|
-
config.action_controller.consider_all_requests_local = true
|
16
|
-
config.action_controller.perform_caching = false
|
17
|
-
config.action_view.cache_template_extensions = false
|
18
|
-
config.action_view.debug_rjs = true
|
19
|
-
|
20
|
-
# Don't care if the mailer can't send
|
21
|
-
config.action_mailer.raise_delivery_errors = false
|
@@ -1,18 +0,0 @@
|
|
1
|
-
# Settings specified here will take precedence over those in config/environment.rb
|
2
|
-
|
3
|
-
# The production environment is meant for finished, "live" apps.
|
4
|
-
# Code is not reloaded between requests
|
5
|
-
config.cache_classes = true
|
6
|
-
|
7
|
-
# Use a different logger for distributed setups
|
8
|
-
# config.logger = SyslogLogger.new
|
9
|
-
|
10
|
-
# Full error reports are disabled and caching is turned on
|
11
|
-
config.action_controller.consider_all_requests_local = false
|
12
|
-
config.action_controller.perform_caching = true
|
13
|
-
|
14
|
-
# Enable serving of images, stylesheets, and javascripts from an asset server
|
15
|
-
# config.action_controller.asset_host = "http://assets.example.com"
|
16
|
-
|
17
|
-
# Disable delivery errors, bad email addresses will be ignored
|
18
|
-
# config.action_mailer.raise_delivery_errors = false
|
@@ -1,19 +0,0 @@
|
|
1
|
-
# Settings specified here will take precedence over those in config/environment.rb
|
2
|
-
|
3
|
-
# The test environment is used exclusively to run your application's
|
4
|
-
# test suite. You never need to work with it otherwise. Remember that
|
5
|
-
# your test database is "scratch space" for the test suite and is wiped
|
6
|
-
# and recreated between test runs. Don't rely on the data there!
|
7
|
-
config.cache_classes = true
|
8
|
-
|
9
|
-
# Log error messages when you accidentally call methods on nil.
|
10
|
-
config.whiny_nils = true
|
11
|
-
|
12
|
-
# Show full error reports and disable caching
|
13
|
-
config.action_controller.consider_all_requests_local = true
|
14
|
-
config.action_controller.perform_caching = false
|
15
|
-
|
16
|
-
# Tell ActionMailer not to deliver emails to the real world.
|
17
|
-
# The :test delivery method accumulates sent emails in the
|
18
|
-
# ActionMailer::Base.deliveries array.
|
19
|
-
config.action_mailer.delivery_method = :test
|
data/rails/config/lighttpd.conf
DELETED
@@ -1,54 +0,0 @@
|
|
1
|
-
# Default configuration file for the lighttpd web server
|
2
|
-
# Start using ./script/server lighttpd
|
3
|
-
|
4
|
-
server.bind = "0.0.0.0"
|
5
|
-
server.port = 3000
|
6
|
-
|
7
|
-
server.modules = ( "mod_rewrite", "mod_accesslog", "mod_fastcgi", "mod_compress", "mod_expire" )
|
8
|
-
|
9
|
-
server.error-handler-404 = "/dispatch.fcgi"
|
10
|
-
server.pid-file = CWD + "/tmp/pids/lighttpd.pid"
|
11
|
-
server.document-root = CWD + "/public/"
|
12
|
-
|
13
|
-
server.errorlog = CWD + "/log/lighttpd.error.log"
|
14
|
-
accesslog.filename = CWD + "/log/lighttpd.access.log"
|
15
|
-
|
16
|
-
url.rewrite = ( "^/$" => "index.html", "^([^.]+)$" => "$1.html" )
|
17
|
-
|
18
|
-
compress.filetype = ( "text/plain", "text/html", "text/css", "text/javascript" )
|
19
|
-
compress.cache-dir = CWD + "/tmp/cache"
|
20
|
-
|
21
|
-
expire.url = ( "/favicon.ico" => "access 3 days",
|
22
|
-
"/images/" => "access 3 days",
|
23
|
-
"/stylesheets/" => "access 3 days",
|
24
|
-
"/javascripts/" => "access 3 days" )
|
25
|
-
|
26
|
-
|
27
|
-
# Change *-procs to 2 if you need to use Upload Progress or other tasks that
|
28
|
-
# *need* to execute a second request while the first is still pending.
|
29
|
-
fastcgi.server = ( ".fcgi" => ( "localhost" => (
|
30
|
-
"min-procs" => 1,
|
31
|
-
"max-procs" => 1,
|
32
|
-
"socket" => CWD + "/tmp/sockets/fcgi.socket",
|
33
|
-
"bin-path" => CWD + "/public/dispatch.fcgi",
|
34
|
-
"bin-environment" => ( "RAILS_ENV" => "development" )
|
35
|
-
) ) )
|
36
|
-
|
37
|
-
mimetype.assign = (
|
38
|
-
".css" => "text/css",
|
39
|
-
".gif" => "image/gif",
|
40
|
-
".htm" => "text/html",
|
41
|
-
".html" => "text/html",
|
42
|
-
".jpeg" => "image/jpeg",
|
43
|
-
".jpg" => "image/jpeg",
|
44
|
-
".js" => "text/javascript",
|
45
|
-
".png" => "image/png",
|
46
|
-
".swf" => "application/x-shockwave-flash",
|
47
|
-
".txt" => "text/plain"
|
48
|
-
)
|
49
|
-
|
50
|
-
# Making sure file uploads above 64k always work when using IE or Safari
|
51
|
-
# For more information, see http://trac.lighttpd.net/trac/ticket/360
|
52
|
-
$HTTP["useragent"] =~ "^(.*MSIE.*)|(.*AppleWebKit.*)$" {
|
53
|
-
server.max-keep-alive-requests = 0
|
54
|
-
}
|
data/rails/config/routes.rb
DELETED
@@ -1,23 +0,0 @@
|
|
1
|
-
ActionController::Routing::Routes.draw do |map|
|
2
|
-
# The priority is based upon order of creation: first created -> highest priority.
|
3
|
-
|
4
|
-
# Sample of regular route:
|
5
|
-
# map.connect 'products/:id', :controller => 'catalog', :action => 'view'
|
6
|
-
# Keep in mind you can assign values other than :controller and :action
|
7
|
-
|
8
|
-
# Sample of named route:
|
9
|
-
# map.purchase 'products/:id/purchase', :controller => 'catalog', :action => 'purchase'
|
10
|
-
# This route can be invoked with purchase_url(:id => product.id)
|
11
|
-
|
12
|
-
# You can have the root of your site routed by hooking up ''
|
13
|
-
# -- just remember to delete public/index.html.
|
14
|
-
# map.connect '', :controller => "welcome"
|
15
|
-
|
16
|
-
# Allow downloading Web Service WSDL as a file with an extension
|
17
|
-
# instead of a file named 'wsdl'
|
18
|
-
map.connect ':controller/service.wsdl', :action => 'wsdl'
|
19
|
-
|
20
|
-
# Install the default route as the lowest priority.
|
21
|
-
map.connect ':controller/:action/:id.:format'
|
22
|
-
map.connect ':controller/:action/:id'
|
23
|
-
end
|
data/rails/doc/README_FOR_APP
DELETED
data/rails/lib/raptcha.rb
DELETED
@@ -1,2225 +0,0 @@
|
|
1
|
-
#! /usr/bin/env ruby
|
2
|
-
|
3
|
-
module Raptcha
|
4
|
-
#--{{{
|
5
|
-
VERSION = '0.0.1' unless defined? Raptcha::VERSION
|
6
|
-
def self.version() VERSION end
|
7
|
-
|
8
|
-
require 'base64'
|
9
|
-
require 'socket'
|
10
|
-
|
11
|
-
begin
|
12
|
-
require 'rubygems'
|
13
|
-
rescue LoadError
|
14
|
-
nil
|
15
|
-
end
|
16
|
-
|
17
|
-
begin
|
18
|
-
require 'RMagick'
|
19
|
-
rescue LoadError
|
20
|
-
begin
|
21
|
-
require 'Rmagick'
|
22
|
-
rescue LoadError
|
23
|
-
require 'rmagick'
|
24
|
-
end
|
25
|
-
end
|
26
|
-
|
27
|
-
=begin
|
28
|
-
#--{{{
|
29
|
-
# all of this in inlined in the BEGIN block below...
|
30
|
-
|
31
|
-
libdir = __FILE__.gsub %r'\.rb$', '/'
|
32
|
-
begin
|
33
|
-
$:.unshift libdir
|
34
|
-
require 'pervasives'
|
35
|
-
require 'attributes'
|
36
|
-
require 'crypt/blowfish'
|
37
|
-
ensure
|
38
|
-
$:.shift
|
39
|
-
end
|
40
|
-
#--}}}
|
41
|
-
=end
|
42
|
-
|
43
|
-
module Image
|
44
|
-
#--{{{
|
45
|
-
singleton_class =
|
46
|
-
class << self
|
47
|
-
self
|
48
|
-
end
|
49
|
-
|
50
|
-
singleton_class.module_eval do
|
51
|
-
attribute('key'){ "--img--#{ Raptcha.mac_address }--#{ Raptcha.hostname }--"[0,56] }
|
52
|
-
|
53
|
-
attribute('distort'){ Hash[
|
54
|
-
:low => [0, 100],
|
55
|
-
:medium => [3, 50],
|
56
|
-
:high => [5, 30],
|
57
|
-
] }
|
58
|
-
|
59
|
-
attribute('default'){ Hash[
|
60
|
-
:width => 142,
|
61
|
-
:height => 30,
|
62
|
-
:distort => :medium,
|
63
|
-
#:background => 'black',
|
64
|
-
#:foreground => 'springgreen',
|
65
|
-
:background => 'white',
|
66
|
-
:foreground => 'springgreen3',
|
67
|
-
:format => 'png',
|
68
|
-
:font_family => 'monoco',
|
69
|
-
:pointsize => 22,
|
70
|
-
:implode => 0.2,
|
71
|
-
] }
|
72
|
-
|
73
|
-
|
74
|
-
def create kw = {}
|
75
|
-
kw = default.update kw.to_options
|
76
|
-
|
77
|
-
word = kw[:word]
|
78
|
-
encrypted = kw[:encrypted] || kw[:e]
|
79
|
-
word ||= Raptcha.decrypt(encrypted, :key => key) if encrypted
|
80
|
-
word ||= Raptcha.word
|
81
|
-
word = word.split(%r"").join(" ")
|
82
|
-
|
83
|
-
kw[:width] = kw[:width].to_i
|
84
|
-
kw[:height] = kw[:height].to_i
|
85
|
-
kw[:implode] = kw[:implode].to_f
|
86
|
-
|
87
|
-
img = Magick::Image.new(kw[:width], kw[:height]) do |i|
|
88
|
-
i.background_color = kw[:background]
|
89
|
-
i.format = kw[:format]
|
90
|
-
end
|
91
|
-
|
92
|
-
draw = Magick::Draw.new
|
93
|
-
|
94
|
-
# text
|
95
|
-
draw.stroke = kw[:foreground]
|
96
|
-
draw.stroke_width = 0
|
97
|
-
draw.font_family = kw[:font_family]
|
98
|
-
draw.pointsize = kw[:pointsize]
|
99
|
-
#draw.pointsize = kw[:height] * 0.75
|
100
|
-
draw.fill = kw[:foreground]
|
101
|
-
draw.gravity = Magick::NorthGravity
|
102
|
-
draw.annotate img, 0, 0, 5, 5, word
|
103
|
-
|
104
|
-
# line
|
105
|
-
draw.stroke = kw[:foreground]
|
106
|
-
draw.stroke_width = 1
|
107
|
-
#draw.line 5, kw[:height]*0.33, kw[:width]-5, kw[:height]*0.33
|
108
|
-
#draw.line 5, kw[:height]*0.66, kw[:width]-5, kw[:height]*0.66
|
109
|
-
draw.line 5, kw[:height]*0.65, kw[:width]-5, kw[:height]*0.65
|
110
|
-
|
111
|
-
draw.draw img
|
112
|
-
|
113
|
-
img = img.wave *distort[kw[:distort]]
|
114
|
-
img = img.implode kw[:implode]
|
115
|
-
|
116
|
-
img.to_blob
|
117
|
-
end
|
118
|
-
|
119
|
-
def inline kw ={}
|
120
|
-
Base64.encode64(create(kw))
|
121
|
-
end
|
122
|
-
end
|
123
|
-
#--}}}
|
124
|
-
end
|
125
|
-
|
126
|
-
class Error < ::StandardError; end
|
127
|
-
class NoInput < Error; end
|
128
|
-
class BadInput < Error; end
|
129
|
-
class Expired < Error; end
|
130
|
-
|
131
|
-
singleton_class =
|
132
|
-
class << self
|
133
|
-
self
|
134
|
-
end
|
135
|
-
|
136
|
-
singleton_class.module_eval do
|
137
|
-
attribute('key'){ "--key--#{ mac_address }--#{ hostname }--"[0,56] }
|
138
|
-
attribute('src'){ '/raptcha' }
|
139
|
-
attribute('gravity'){ 'west' }
|
140
|
-
attribute('hostname'){ Socket.gethostname }
|
141
|
-
attribute('user'){ ENV['USER'] || ENV['LOGNAME'] || 'raptcha' }
|
142
|
-
attribute('alphabet'){ ('A' .. 'Z').to_a }
|
143
|
-
attribute('ttl'){ 30 * 60 }
|
144
|
-
|
145
|
-
attribute('close_enough'){ Hash[
|
146
|
-
'0OoQ' => '0',
|
147
|
-
'1l' => '1',
|
148
|
-
'2zZ' => '2',
|
149
|
-
'5sS' => '5',
|
150
|
-
'kKxX' => 'x',
|
151
|
-
] }
|
152
|
-
|
153
|
-
def valid? params
|
154
|
-
#--{{{
|
155
|
-
begin
|
156
|
-
validate! params
|
157
|
-
rescue NoInput
|
158
|
-
nil
|
159
|
-
rescue BadInput
|
160
|
-
false
|
161
|
-
rescue Expired
|
162
|
-
false
|
163
|
-
end
|
164
|
-
#--}}}
|
165
|
-
end
|
166
|
-
|
167
|
-
def validate! params
|
168
|
-
#--{{{
|
169
|
-
if params.has_key? 'raptcha'
|
170
|
-
raptcha = params['raptcha']
|
171
|
-
|
172
|
-
textarea = raptcha['t']
|
173
|
-
word = raptcha['w']
|
174
|
-
timebomb = raptcha['b']
|
175
|
-
|
176
|
-
raise NoInput unless textarea and word and timebomb
|
177
|
-
|
178
|
-
word = decrypt word
|
179
|
-
timebomb = decrypt timebomb
|
180
|
-
|
181
|
-
begin
|
182
|
-
timebomb = Integer timebomb
|
183
|
-
timebomb = Time.at(timebomb).utc
|
184
|
-
now = Time.now.utc
|
185
|
-
raise Expired unless now < timebomb
|
186
|
-
rescue
|
187
|
-
raise Expired
|
188
|
-
end
|
189
|
-
|
190
|
-
raise BadInput unless fuzzy(word) == fuzzy(textarea)
|
191
|
-
|
192
|
-
textarea
|
193
|
-
else
|
194
|
-
validate! 'raptcha' => params
|
195
|
-
end
|
196
|
-
#--}}}
|
197
|
-
end
|
198
|
-
|
199
|
-
def fuzzy word
|
200
|
-
#--{{{
|
201
|
-
result = word.to_s.downcase
|
202
|
-
close_enough.each do |charset, replace|
|
203
|
-
result.gsub! %r"[#{ charset }]", replace
|
204
|
-
end
|
205
|
-
result
|
206
|
-
#--}}}
|
207
|
-
end
|
208
|
-
|
209
|
-
attribute 'input_north'
|
210
|
-
attribute 'input_south'
|
211
|
-
attribute 'input_east'
|
212
|
-
attribute 'input_west'
|
213
|
-
|
214
|
-
def input kw = {}
|
215
|
-
#--{{{
|
216
|
-
kw.to_options!
|
217
|
-
|
218
|
-
kw[:src] ||= Raptcha.src
|
219
|
-
kw[:word] ||= Raptcha.word
|
220
|
-
kw[:timebomb] ||= Raptcha.timebomb
|
221
|
-
kw[:gravity] ||= Raptcha.gravity
|
222
|
-
|
223
|
-
encrypted_word = encrypt kw[:word], :key => Raptcha.key
|
224
|
-
encrypted_timebomb = encrypt kw[:timebomb], :key => Raptcha.key
|
225
|
-
|
226
|
-
west = north = east = south = nil
|
227
|
-
case gravity.to_s
|
228
|
-
when /w(est)?/
|
229
|
-
west = Raptcha.img(kw)
|
230
|
-
when /n(orth)?/
|
231
|
-
north = Raptcha.img(kw) + '<br>'
|
232
|
-
when /e(ast)?/
|
233
|
-
east = Raptcha.img(kw)
|
234
|
-
when /s(outh)?/
|
235
|
-
south = '<br>' + Raptcha.img(kw)
|
236
|
-
end
|
237
|
-
|
238
|
-
<<-html
|
239
|
-
<div class="raptcha">
|
240
|
-
#{ input_north }#{ input_west }
|
241
|
-
#{ north } #{ west }
|
242
|
-
<input type="textarea" name="raptcha[t]" value="" class="raptcha_t"/>
|
243
|
-
<input type="hidden" name="raptcha[w]" value="#{ encrypted_word }" class="raptcha_w"/>
|
244
|
-
<input type="hidden" name="raptcha[b]" value="#{ encrypted_timebomb }" class="raptcha_b"/>
|
245
|
-
#{ east } #{ south }
|
246
|
-
#{ input_east } #{ input_south }
|
247
|
-
</div>
|
248
|
-
html
|
249
|
-
|
250
|
-
#--}}}
|
251
|
-
end
|
252
|
-
alias_method "tag", "input"
|
253
|
-
|
254
|
-
def img kw = {}
|
255
|
-
#--{{{
|
256
|
-
kw.to_options!
|
257
|
-
return(inline(kw)) if kw[:inline]
|
258
|
-
src = kw[:src] || Raptcha.src
|
259
|
-
word = kw[:word] || Raptcha.word
|
260
|
-
encrypted_word = encrypt word, :key => Image.key
|
261
|
-
<<-html
|
262
|
-
<img src="#{ src }?e=#{ CGI.escape encrypted_word }" alt="raptcha.png" class="raptcha_i"/>
|
263
|
-
html
|
264
|
-
#--}}}
|
265
|
-
end
|
266
|
-
|
267
|
-
def inline kw = {}
|
268
|
-
#--{{{
|
269
|
-
<<-html
|
270
|
-
<img src="data:image/png;base64,#{ Image.inline kw }" alt="raptcha.png" class="raptcha_i"/>
|
271
|
-
html
|
272
|
-
#--}}}
|
273
|
-
end
|
274
|
-
|
275
|
-
def timebomb
|
276
|
-
#--{{{
|
277
|
-
Time.now.utc.to_i + Raptcha.ttl
|
278
|
-
#--}}}
|
279
|
-
end
|
280
|
-
|
281
|
-
def word size = 6
|
282
|
-
#--{{{
|
283
|
-
w = '' and size.times{ w << alphabet[rand(alphabet.size - 1)]} and w
|
284
|
-
#--}}}
|
285
|
-
end
|
286
|
-
|
287
|
-
def image *a, &b
|
288
|
-
#--{{{
|
289
|
-
Raptcha::Image.create *a, &b
|
290
|
-
#--}}}
|
291
|
-
end
|
292
|
-
|
293
|
-
def mac_address
|
294
|
-
#--{{{
|
295
|
-
return @mac_address if defined? @mac_address
|
296
|
-
re = %r/[^:\-](?:[0-9A-F][0-9A-F][:\-]){5}[0-9A-F][0-9A-F][^:\-]/io
|
297
|
-
cmds = '/sbin/ifconfig', '/bin/ifconfig', 'ifconfig', 'ipconfig /all'
|
298
|
-
|
299
|
-
null = test(?e, '/dev/null') ? '/dev/null' : 'NUL'
|
300
|
-
|
301
|
-
lines = nil
|
302
|
-
cmds.each do |cmd|
|
303
|
-
stdout = IO.popen("#{ cmd } 2> #{ null }"){|fd| fd.readlines} rescue next
|
304
|
-
next unless stdout and stdout.size > 0
|
305
|
-
lines = stdout and break
|
306
|
-
end
|
307
|
-
raise "all of #{ cmds.join ' ' } failed" unless lines
|
308
|
-
|
309
|
-
candidates = lines.select{|line| line =~ re}
|
310
|
-
raise 'no mac address candidates' unless candidates.first
|
311
|
-
candidates.map!{|c| c[re]}
|
312
|
-
|
313
|
-
maddr = candidates.first
|
314
|
-
raise 'no mac address found' unless maddr
|
315
|
-
|
316
|
-
maddr.strip!
|
317
|
-
maddr.instance_eval{ @list = candidates; def list() @list end }
|
318
|
-
|
319
|
-
@mac_address = maddr
|
320
|
-
#--}}}
|
321
|
-
end
|
322
|
-
|
323
|
-
def blowfish
|
324
|
-
#--{{{
|
325
|
-
@blowfish ||= Hash.new{|h,k| h[k] = Crypt::Blowfish.new(k)}
|
326
|
-
#--}}}
|
327
|
-
end
|
328
|
-
|
329
|
-
def encrypt string, kw = {}
|
330
|
-
#--{{{
|
331
|
-
kw.to_options!
|
332
|
-
k = kw[:key] || key
|
333
|
-
Base64.encode64(blowfish[k].encrypt_string(string.to_s)).chop # kill "\n"
|
334
|
-
#--}}}
|
335
|
-
end
|
336
|
-
|
337
|
-
def decrypt string, kw = {}
|
338
|
-
#--{{{
|
339
|
-
kw.to_options!
|
340
|
-
k = kw[:key] || key
|
341
|
-
blowfish[k].decrypt_string(Base64.decode64("#{ string }\n")).strip
|
342
|
-
#--}}}
|
343
|
-
end
|
344
|
-
|
345
|
-
|
346
|
-
def render controller, params
|
347
|
-
#--{{{
|
348
|
-
controller.instance_eval do
|
349
|
-
send_data Raptcha.image(params), :type => 'image/png', :disposition => 'inline', :filename => 'raptcha.png'
|
350
|
-
end
|
351
|
-
#--}}}
|
352
|
-
end
|
353
|
-
end
|
354
|
-
#--}}}
|
355
|
-
end
|
356
|
-
|
357
|
-
|
358
|
-
if $0 == __FILE__
|
359
|
-
#--{{{
|
360
|
-
(( Main = Object.new )).instance_eval do
|
361
|
-
def run
|
362
|
-
@argv = ARGV.dup
|
363
|
-
mode = @argv.detect{|arg| arg !~ %r"[=:]"} || 'raptcha'
|
364
|
-
@argv.delete mode
|
365
|
-
send mode
|
366
|
-
end
|
367
|
-
|
368
|
-
def raptcha
|
369
|
-
kw = {}
|
370
|
-
@argv.each{|kv| k, v = kv.split(%r"[=:]").map{|x| x.strip}; kw.update k => v}
|
371
|
-
STDOUT.write Raptcha.image(kw)
|
372
|
-
end
|
373
|
-
|
374
|
-
def generate
|
375
|
-
what = @argv.shift
|
376
|
-
send "generate_#{ what }"
|
377
|
-
end
|
378
|
-
|
379
|
-
def generate_controller
|
380
|
-
src = DATA.read
|
381
|
-
if test ?d, 'app'
|
382
|
-
path = File.join 'app', 'controllers', 'raptcha_controller.rb'
|
383
|
-
if test ?e, path
|
384
|
-
puts "exists #{ path }"
|
385
|
-
exit 1
|
386
|
-
end
|
387
|
-
open path, 'w' do |fd|
|
388
|
-
fd.puts src
|
389
|
-
end
|
390
|
-
puts "#{ path }"
|
391
|
-
else
|
392
|
-
puts "generated #{ src }"
|
393
|
-
end
|
394
|
-
end
|
395
|
-
|
396
|
-
def generate_lib
|
397
|
-
src = IO.read(__FILE__)
|
398
|
-
if test ?d, 'app'
|
399
|
-
path = File.join 'lib', 'raptcha.rb'
|
400
|
-
if test ?e, path
|
401
|
-
puts "exists #{ path }"
|
402
|
-
exit 1
|
403
|
-
end
|
404
|
-
open path, 'w' do |fd|
|
405
|
-
fd.puts src
|
406
|
-
end
|
407
|
-
puts "#{ path }"
|
408
|
-
else
|
409
|
-
puts "generated #{ src }"
|
410
|
-
end
|
411
|
-
end
|
412
|
-
end
|
413
|
-
Main.run
|
414
|
-
#--}}}
|
415
|
-
end
|
416
|
-
|
417
|
-
BEGIN {
|
418
|
-
#--{{{
|
419
|
-
unless Hash.new.respond_to? 'to_options' #--{{{
|
420
|
-
def to_options
|
421
|
-
inject(Hash.new){|h, kv| h.update kv.first.to_s.to_sym => kv.last}
|
422
|
-
end
|
423
|
-
def to_options!
|
424
|
-
h = to_options
|
425
|
-
clear
|
426
|
-
update h
|
427
|
-
end
|
428
|
-
end #--}}}
|
429
|
-
|
430
|
-
module Pervasives #--{{{
|
431
|
-
VERSION = "1.0.0" unless defined? Pervasives::VERSION
|
432
|
-
def self.version() VERSION end
|
433
|
-
class ::Class
|
434
|
-
def __pervasive__ m, *a, &b
|
435
|
-
(( Class.instance_method(m) rescue Module.instance_method(m) rescue Object.instance_method(m) )).bind(self).call(*a, &b)
|
436
|
-
end
|
437
|
-
end
|
438
|
-
class ::Module
|
439
|
-
def __pervasive__ m, *a, &b
|
440
|
-
(( Module.instance_method(m) rescue Object.instance_method(m) )).bind(self).call(*a, &b)
|
441
|
-
end
|
442
|
-
end
|
443
|
-
class ::Object
|
444
|
-
def __pervasive__ m, *a, &b
|
445
|
-
(( Object.instance_method(m) )).bind(self).call(*a, &b)
|
446
|
-
end
|
447
|
-
end
|
448
|
-
|
449
|
-
class Proxy
|
450
|
-
instance_methods.each{|m| undef_method m unless m[%r/__/]}
|
451
|
-
def initialize obj
|
452
|
-
@obj = obj
|
453
|
-
end
|
454
|
-
def method_missing m, *a, &b
|
455
|
-
@obj.__pervasive__ m, *a, &b
|
456
|
-
end
|
457
|
-
def __obj__
|
458
|
-
@obj
|
459
|
-
end
|
460
|
-
end
|
461
|
-
end #--}}}
|
462
|
-
|
463
|
-
module Attributes #--{{{
|
464
|
-
VERSION = '3.5.0'
|
465
|
-
def self.version() VERSION end
|
466
|
-
|
467
|
-
def attributes *a, &b
|
468
|
-
unless a.empty?
|
469
|
-
hashes, names = a.partition{|x| Hash === x}
|
470
|
-
|
471
|
-
names_and_defaults = {}
|
472
|
-
hashes.each{|h| names_and_defaults.update h}
|
473
|
-
names.flatten.compact.each{|name| names_and_defaults.update name => nil}
|
474
|
-
|
475
|
-
names_and_defaults.each do |name, default|
|
476
|
-
init = b || lambda { default }
|
477
|
-
ivar, getter, setter, query, banger =
|
478
|
-
"@#{ name }", "#{ name }", "#{ name }=", "#{ name }?", "#{ name }!"
|
479
|
-
|
480
|
-
define_method(setter) do |value|
|
481
|
-
__pervasive__('instance_variable_set', ivar, value)
|
482
|
-
end
|
483
|
-
|
484
|
-
define_method(getter) do |*value|
|
485
|
-
unless value.empty?
|
486
|
-
__pervasive__('send', setter, value.shift)
|
487
|
-
else
|
488
|
-
defined = __pervasive__('instance_eval', "defined? #{ ivar }")
|
489
|
-
__pervasive__('send', setter, __pervasive__('instance_eval', &init)) unless defined
|
490
|
-
__pervasive__('instance_variable_get', ivar)
|
491
|
-
end
|
492
|
-
end
|
493
|
-
|
494
|
-
define_method(banger) do
|
495
|
-
__pervasive__('send', setter, __pervasive__('instance_eval', &init))
|
496
|
-
__pervasive__('instance_variable_get', ivar)
|
497
|
-
end
|
498
|
-
|
499
|
-
alias_method query, getter
|
500
|
-
|
501
|
-
(attributes << name.to_s).uniq!
|
502
|
-
attributes
|
503
|
-
end
|
504
|
-
else
|
505
|
-
begin
|
506
|
-
__attribute_list__
|
507
|
-
rescue NameError
|
508
|
-
singleton_class =
|
509
|
-
class << self
|
510
|
-
self
|
511
|
-
end
|
512
|
-
klass = self
|
513
|
-
singleton_class.module_eval do
|
514
|
-
attribute_list = []
|
515
|
-
define_method('attribute_list'){ klass == self ? attribute_list : raise(NameError) }
|
516
|
-
alias_method '__attribute_list__', 'attribute_list'
|
517
|
-
end
|
518
|
-
__attribute_list__
|
519
|
-
end
|
520
|
-
end
|
521
|
-
end
|
522
|
-
|
523
|
-
%w( __attributes__ __attribute__ attribute ).each{|dst| alias_method dst, 'attributes'}
|
524
|
-
end
|
525
|
-
|
526
|
-
class Object
|
527
|
-
def attributes *a, &b
|
528
|
-
sc =
|
529
|
-
class << self
|
530
|
-
self
|
531
|
-
end
|
532
|
-
sc.attributes *a, &b
|
533
|
-
end
|
534
|
-
%w( __attributes__ __attribute__ attribute ).each{|dst| alias_method dst, 'attributes'}
|
535
|
-
end
|
536
|
-
|
537
|
-
class Module
|
538
|
-
include Attributes
|
539
|
-
end #--}}}
|
540
|
-
|
541
|
-
# cbc.rb Richard Kernahan <kernighan_rich@rubyforge.org>
|
542
|
-
module Crypt #--{{{
|
543
|
-
module CBC
|
544
|
-
|
545
|
-
require 'stringio'
|
546
|
-
#require 'crypt/stringxor'
|
547
|
-
|
548
|
-
ULONG = 0x100000000
|
549
|
-
|
550
|
-
# When this module is mixed in with an encryption class, the class
|
551
|
-
# must provide three methods: encrypt_block(block) and decrypt_block(block)
|
552
|
-
# and block_size()
|
553
|
-
|
554
|
-
|
555
|
-
def generate_initialization_vector(words)
|
556
|
-
srand(Time.now.to_i)
|
557
|
-
vector = ""
|
558
|
-
words.times {
|
559
|
-
vector << [rand(ULONG)].pack('N')
|
560
|
-
}
|
561
|
-
return(vector)
|
562
|
-
end
|
563
|
-
|
564
|
-
|
565
|
-
def encrypt_stream(plainStream, cryptStream)
|
566
|
-
# Cypher-block-chain mode
|
567
|
-
|
568
|
-
initVector = generate_initialization_vector(block_size() / 4)
|
569
|
-
chain = encrypt_block(initVector)
|
570
|
-
cryptStream.write(chain)
|
571
|
-
|
572
|
-
while ((block = plainStream.read(block_size())) && (block.length == block_size()))
|
573
|
-
block = block ^ chain
|
574
|
-
encrypted = encrypt_block(block)
|
575
|
-
cryptStream.write(encrypted)
|
576
|
-
chain = encrypted
|
577
|
-
end
|
578
|
-
|
579
|
-
# write the final block
|
580
|
-
# At most block_size()-1 bytes can be part of the message.
|
581
|
-
# That means the final byte can be used to store the number of meaningful
|
582
|
-
# bytes in the final block
|
583
|
-
block = '' if block.nil?
|
584
|
-
buffer = block.split('')
|
585
|
-
remainingMessageBytes = buffer.length
|
586
|
-
# we use 7-bit characters to avoid possible strange behavior on the Mac
|
587
|
-
remainingMessageBytes.upto(block_size()-2) { buffer << rand(128).chr }
|
588
|
-
buffer << remainingMessageBytes.chr
|
589
|
-
block = buffer.join('')
|
590
|
-
block = block ^ chain
|
591
|
-
encrypted = encrypt_block(block)
|
592
|
-
cryptStream.write(encrypted)
|
593
|
-
end
|
594
|
-
|
595
|
-
|
596
|
-
def decrypt_stream(cryptStream, plainStream)
|
597
|
-
# Cypher-block-chain mode
|
598
|
-
chain = cryptStream.read(block_size())
|
599
|
-
|
600
|
-
while (block = cryptStream.read(block_size()))
|
601
|
-
decrypted = decrypt_block(block)
|
602
|
-
plainText = decrypted ^ chain
|
603
|
-
plainStream.write(plainText) unless cryptStream.eof?
|
604
|
-
chain = block
|
605
|
-
end
|
606
|
-
|
607
|
-
# write the final block, omitting the padding
|
608
|
-
buffer = plainText.split('')
|
609
|
-
remainingMessageBytes = buffer.last.unpack('C').first
|
610
|
-
remainingMessageBytes.times { plainStream.write(buffer.shift) }
|
611
|
-
end
|
612
|
-
|
613
|
-
|
614
|
-
def carefully_open_file(filename, mode)
|
615
|
-
begin
|
616
|
-
aFile = File.new(filename, mode)
|
617
|
-
rescue
|
618
|
-
puts "Sorry. There was a problem opening the file <#{filename}>."
|
619
|
-
aFile.close() unless aFile.nil?
|
620
|
-
raise
|
621
|
-
end
|
622
|
-
return(aFile)
|
623
|
-
end
|
624
|
-
|
625
|
-
|
626
|
-
def encrypt_file(plainFilename, cryptFilename)
|
627
|
-
plainFile = carefully_open_file(plainFilename, 'rb')
|
628
|
-
cryptFile = carefully_open_file(cryptFilename, 'wb+')
|
629
|
-
encrypt_stream(plainFile, cryptFile)
|
630
|
-
plainFile.close unless plainFile.closed?
|
631
|
-
cryptFile.close unless cryptFile.closed?
|
632
|
-
end
|
633
|
-
|
634
|
-
|
635
|
-
def decrypt_file(cryptFilename, plainFilename)
|
636
|
-
cryptFile = carefully_open_file(cryptFilename, 'rb')
|
637
|
-
plainFile = carefully_open_file(plainFilename, 'wb+')
|
638
|
-
decrypt_stream(cryptFile, plainFile)
|
639
|
-
cryptFile.close unless cryptFile.closed?
|
640
|
-
plainFile.close unless plainFile.closed?
|
641
|
-
end
|
642
|
-
|
643
|
-
|
644
|
-
def encrypt_string(plainText)
|
645
|
-
plainStream = StringIO.new(plainText)
|
646
|
-
cryptStream = StringIO.new('')
|
647
|
-
encrypt_stream(plainStream, cryptStream)
|
648
|
-
cryptText = cryptStream.string
|
649
|
-
return(cryptText)
|
650
|
-
end
|
651
|
-
|
652
|
-
|
653
|
-
def decrypt_string(cryptText)
|
654
|
-
cryptStream = StringIO.new(cryptText)
|
655
|
-
plainStream = StringIO.new('')
|
656
|
-
decrypt_stream(cryptStream, plainStream)
|
657
|
-
plainText = plainStream.string
|
658
|
-
return(plainText)
|
659
|
-
end
|
660
|
-
|
661
|
-
end
|
662
|
-
end #--}}}
|
663
|
-
|
664
|
-
# blowfish-tables.rb Richard Kernahan <kernighan_rich@rubyforge.org>
|
665
|
-
module Crypt #--{{{
|
666
|
-
module BlowfishTables
|
667
|
-
|
668
|
-
INITIALPARRAY = [
|
669
|
-
0x243f6a88, 0x85a308d3, 0x13198a2e, 0x03707344, 0xa4093822, 0x299f31d0,
|
670
|
-
0x082efa98, 0xec4e6c89, 0x452821e6, 0x38d01377, 0xbe5466cf, 0x34e90c6c,
|
671
|
-
0xc0ac29b7, 0xc97c50dd, 0x3f84d5b5, 0xb5470917, 0x9216d5d9, 0x8979fb1b
|
672
|
-
]
|
673
|
-
|
674
|
-
INITIALSBOXES = [[
|
675
|
-
0xd1310ba6, 0x98dfb5ac, 0x2ffd72db, 0xd01adfb7, 0xb8e1afed, 0x6a267e96,
|
676
|
-
0xba7c9045, 0xf12c7f99, 0x24a19947, 0xb3916cf7, 0x0801f2e2, 0x858efc16,
|
677
|
-
0x636920d8, 0x71574e69, 0xa458fea3, 0xf4933d7e, 0x0d95748f, 0x728eb658,
|
678
|
-
0x718bcd58, 0x82154aee, 0x7b54a41d, 0xc25a59b5, 0x9c30d539, 0x2af26013,
|
679
|
-
0xc5d1b023, 0x286085f0, 0xca417918, 0xb8db38ef, 0x8e79dcb0, 0x603a180e,
|
680
|
-
0x6c9e0e8b, 0xb01e8a3e, 0xd71577c1, 0xbd314b27, 0x78af2fda, 0x55605c60,
|
681
|
-
0xe65525f3, 0xaa55ab94, 0x57489862, 0x63e81440, 0x55ca396a, 0x2aab10b6,
|
682
|
-
0xb4cc5c34, 0x1141e8ce, 0xa15486af, 0x7c72e993, 0xb3ee1411, 0x636fbc2a,
|
683
|
-
0x2ba9c55d, 0x741831f6, 0xce5c3e16, 0x9b87931e, 0xafd6ba33, 0x6c24cf5c,
|
684
|
-
0x7a325381, 0x28958677, 0x3b8f4898, 0x6b4bb9af, 0xc4bfe81b, 0x66282193,
|
685
|
-
0x61d809cc, 0xfb21a991, 0x487cac60, 0x5dec8032, 0xef845d5d, 0xe98575b1,
|
686
|
-
0xdc262302, 0xeb651b88, 0x23893e81, 0xd396acc5, 0x0f6d6ff3, 0x83f44239,
|
687
|
-
0x2e0b4482, 0xa4842004, 0x69c8f04a, 0x9e1f9b5e, 0x21c66842, 0xf6e96c9a,
|
688
|
-
0x670c9c61, 0xabd388f0, 0x6a51a0d2, 0xd8542f68, 0x960fa728, 0xab5133a3,
|
689
|
-
0x6eef0b6c, 0x137a3be4, 0xba3bf050, 0x7efb2a98, 0xa1f1651d, 0x39af0176,
|
690
|
-
0x66ca593e, 0x82430e88, 0x8cee8619, 0x456f9fb4, 0x7d84a5c3, 0x3b8b5ebe,
|
691
|
-
0xe06f75d8, 0x85c12073, 0x401a449f, 0x56c16aa6, 0x4ed3aa62, 0x363f7706,
|
692
|
-
0x1bfedf72, 0x429b023d, 0x37d0d724, 0xd00a1248, 0xdb0fead3, 0x49f1c09b,
|
693
|
-
0x075372c9, 0x80991b7b, 0x25d479d8, 0xf6e8def7, 0xe3fe501a, 0xb6794c3b,
|
694
|
-
0x976ce0bd, 0x04c006ba, 0xc1a94fb6, 0x409f60c4, 0x5e5c9ec2, 0x196a2463,
|
695
|
-
0x68fb6faf, 0x3e6c53b5, 0x1339b2eb, 0x3b52ec6f, 0x6dfc511f, 0x9b30952c,
|
696
|
-
0xcc814544, 0xaf5ebd09, 0xbee3d004, 0xde334afd, 0x660f2807, 0x192e4bb3,
|
697
|
-
0xc0cba857, 0x45c8740f, 0xd20b5f39, 0xb9d3fbdb, 0x5579c0bd, 0x1a60320a,
|
698
|
-
0xd6a100c6, 0x402c7279, 0x679f25fe, 0xfb1fa3cc, 0x8ea5e9f8, 0xdb3222f8,
|
699
|
-
0x3c7516df, 0xfd616b15, 0x2f501ec8, 0xad0552ab, 0x323db5fa, 0xfd238760,
|
700
|
-
0x53317b48, 0x3e00df82, 0x9e5c57bb, 0xca6f8ca0, 0x1a87562e, 0xdf1769db,
|
701
|
-
0xd542a8f6, 0x287effc3, 0xac6732c6, 0x8c4f5573, 0x695b27b0, 0xbbca58c8,
|
702
|
-
0xe1ffa35d, 0xb8f011a0, 0x10fa3d98, 0xfd2183b8, 0x4afcb56c, 0x2dd1d35b,
|
703
|
-
0x9a53e479, 0xb6f84565, 0xd28e49bc, 0x4bfb9790, 0xe1ddf2da, 0xa4cb7e33,
|
704
|
-
0x62fb1341, 0xcee4c6e8, 0xef20cada, 0x36774c01, 0xd07e9efe, 0x2bf11fb4,
|
705
|
-
0x95dbda4d, 0xae909198, 0xeaad8e71, 0x6b93d5a0, 0xd08ed1d0, 0xafc725e0,
|
706
|
-
0x8e3c5b2f, 0x8e7594b7, 0x8ff6e2fb, 0xf2122b64, 0x8888b812, 0x900df01c,
|
707
|
-
0x4fad5ea0, 0x688fc31c, 0xd1cff191, 0xb3a8c1ad, 0x2f2f2218, 0xbe0e1777,
|
708
|
-
0xea752dfe, 0x8b021fa1, 0xe5a0cc0f, 0xb56f74e8, 0x18acf3d6, 0xce89e299,
|
709
|
-
0xb4a84fe0, 0xfd13e0b7, 0x7cc43b81, 0xd2ada8d9, 0x165fa266, 0x80957705,
|
710
|
-
0x93cc7314, 0x211a1477, 0xe6ad2065, 0x77b5fa86, 0xc75442f5, 0xfb9d35cf,
|
711
|
-
0xebcdaf0c, 0x7b3e89a0, 0xd6411bd3, 0xae1e7e49, 0x00250e2d, 0x2071b35e,
|
712
|
-
0x226800bb, 0x57b8e0af, 0x2464369b, 0xf009b91e, 0x5563911d, 0x59dfa6aa,
|
713
|
-
0x78c14389, 0xd95a537f, 0x207d5ba2, 0x02e5b9c5, 0x83260376, 0x6295cfa9,
|
714
|
-
0x11c81968, 0x4e734a41, 0xb3472dca, 0x7b14a94a, 0x1b510052, 0x9a532915,
|
715
|
-
0xd60f573f, 0xbc9bc6e4, 0x2b60a476, 0x81e67400, 0x08ba6fb5, 0x571be91f,
|
716
|
-
0xf296ec6b, 0x2a0dd915, 0xb6636521, 0xe7b9f9b6, 0xff34052e, 0xc5855664,
|
717
|
-
0x53b02d5d, 0xa99f8fa1, 0x08ba4799, 0x6e85076a], [
|
718
|
-
0x4b7a70e9, 0xb5b32944,
|
719
|
-
0xdb75092e, 0xc4192623, 0xad6ea6b0, 0x49a7df7d, 0x9cee60b8, 0x8fedb266,
|
720
|
-
0xecaa8c71, 0x699a17ff, 0x5664526c, 0xc2b19ee1, 0x193602a5, 0x75094c29,
|
721
|
-
0xa0591340, 0xe4183a3e, 0x3f54989a, 0x5b429d65, 0x6b8fe4d6, 0x99f73fd6,
|
722
|
-
0xa1d29c07, 0xefe830f5, 0x4d2d38e6, 0xf0255dc1, 0x4cdd2086, 0x8470eb26,
|
723
|
-
0x6382e9c6, 0x021ecc5e, 0x09686b3f, 0x3ebaefc9, 0x3c971814, 0x6b6a70a1,
|
724
|
-
0x687f3584, 0x52a0e286, 0xb79c5305, 0xaa500737, 0x3e07841c, 0x7fdeae5c,
|
725
|
-
0x8e7d44ec, 0x5716f2b8, 0xb03ada37, 0xf0500c0d, 0xf01c1f04, 0x0200b3ff,
|
726
|
-
0xae0cf51a, 0x3cb574b2, 0x25837a58, 0xdc0921bd, 0xd19113f9, 0x7ca92ff6,
|
727
|
-
0x94324773, 0x22f54701, 0x3ae5e581, 0x37c2dadc, 0xc8b57634, 0x9af3dda7,
|
728
|
-
0xa9446146, 0x0fd0030e, 0xecc8c73e, 0xa4751e41, 0xe238cd99, 0x3bea0e2f,
|
729
|
-
0x3280bba1, 0x183eb331, 0x4e548b38, 0x4f6db908, 0x6f420d03, 0xf60a04bf,
|
730
|
-
0x2cb81290, 0x24977c79, 0x5679b072, 0xbcaf89af, 0xde9a771f, 0xd9930810,
|
731
|
-
0xb38bae12, 0xdccf3f2e, 0x5512721f, 0x2e6b7124, 0x501adde6, 0x9f84cd87,
|
732
|
-
0x7a584718, 0x7408da17, 0xbc9f9abc, 0xe94b7d8c, 0xec7aec3a, 0xdb851dfa,
|
733
|
-
0x63094366, 0xc464c3d2, 0xef1c1847, 0x3215d908, 0xdd433b37, 0x24c2ba16,
|
734
|
-
0x12a14d43, 0x2a65c451, 0x50940002, 0x133ae4dd, 0x71dff89e, 0x10314e55,
|
735
|
-
0x81ac77d6, 0x5f11199b, 0x043556f1, 0xd7a3c76b, 0x3c11183b, 0x5924a509,
|
736
|
-
0xf28fe6ed, 0x97f1fbfa, 0x9ebabf2c, 0x1e153c6e, 0x86e34570, 0xeae96fb1,
|
737
|
-
0x860e5e0a, 0x5a3e2ab3, 0x771fe71c, 0x4e3d06fa, 0x2965dcb9, 0x99e71d0f,
|
738
|
-
0x803e89d6, 0x5266c825, 0x2e4cc978, 0x9c10b36a, 0xc6150eba, 0x94e2ea78,
|
739
|
-
0xa5fc3c53, 0x1e0a2df4, 0xf2f74ea7, 0x361d2b3d, 0x1939260f, 0x19c27960,
|
740
|
-
0x5223a708, 0xf71312b6, 0xebadfe6e, 0xeac31f66, 0xe3bc4595, 0xa67bc883,
|
741
|
-
0xb17f37d1, 0x018cff28, 0xc332ddef, 0xbe6c5aa5, 0x65582185, 0x68ab9802,
|
742
|
-
0xeecea50f, 0xdb2f953b, 0x2aef7dad, 0x5b6e2f84, 0x1521b628, 0x29076170,
|
743
|
-
0xecdd4775, 0x619f1510, 0x13cca830, 0xeb61bd96, 0x0334fe1e, 0xaa0363cf,
|
744
|
-
0xb5735c90, 0x4c70a239, 0xd59e9e0b, 0xcbaade14, 0xeecc86bc, 0x60622ca7,
|
745
|
-
0x9cab5cab, 0xb2f3846e, 0x648b1eaf, 0x19bdf0ca, 0xa02369b9, 0x655abb50,
|
746
|
-
0x40685a32, 0x3c2ab4b3, 0x319ee9d5, 0xc021b8f7, 0x9b540b19, 0x875fa099,
|
747
|
-
0x95f7997e, 0x623d7da8, 0xf837889a, 0x97e32d77, 0x11ed935f, 0x16681281,
|
748
|
-
0x0e358829, 0xc7e61fd6, 0x96dedfa1, 0x7858ba99, 0x57f584a5, 0x1b227263,
|
749
|
-
0x9b83c3ff, 0x1ac24696, 0xcdb30aeb, 0x532e3054, 0x8fd948e4, 0x6dbc3128,
|
750
|
-
0x58ebf2ef, 0x34c6ffea, 0xfe28ed61, 0xee7c3c73, 0x5d4a14d9, 0xe864b7e3,
|
751
|
-
0x42105d14, 0x203e13e0, 0x45eee2b6, 0xa3aaabea, 0xdb6c4f15, 0xfacb4fd0,
|
752
|
-
0xc742f442, 0xef6abbb5, 0x654f3b1d, 0x41cd2105, 0xd81e799e, 0x86854dc7,
|
753
|
-
0xe44b476a, 0x3d816250, 0xcf62a1f2, 0x5b8d2646, 0xfc8883a0, 0xc1c7b6a3,
|
754
|
-
0x7f1524c3, 0x69cb7492, 0x47848a0b, 0x5692b285, 0x095bbf00, 0xad19489d,
|
755
|
-
0x1462b174, 0x23820e00, 0x58428d2a, 0x0c55f5ea, 0x1dadf43e, 0x233f7061,
|
756
|
-
0x3372f092, 0x8d937e41, 0xd65fecf1, 0x6c223bdb, 0x7cde3759, 0xcbee7460,
|
757
|
-
0x4085f2a7, 0xce77326e, 0xa6078084, 0x19f8509e, 0xe8efd855, 0x61d99735,
|
758
|
-
0xa969a7aa, 0xc50c06c2, 0x5a04abfc, 0x800bcadc, 0x9e447a2e, 0xc3453484,
|
759
|
-
0xfdd56705, 0x0e1e9ec9, 0xdb73dbd3, 0x105588cd, 0x675fda79, 0xe3674340,
|
760
|
-
0xc5c43465, 0x713e38d8, 0x3d28f89e, 0xf16dff20, 0x153e21e7, 0x8fb03d4a,
|
761
|
-
0xe6e39f2b, 0xdb83adf7], [
|
762
|
-
0xe93d5a68, 0x948140f7, 0xf64c261c, 0x94692934,
|
763
|
-
0x411520f7, 0x7602d4f7, 0xbcf46b2e, 0xd4a20068, 0xd4082471, 0x3320f46a,
|
764
|
-
0x43b7d4b7, 0x500061af, 0x1e39f62e, 0x97244546, 0x14214f74, 0xbf8b8840,
|
765
|
-
0x4d95fc1d, 0x96b591af, 0x70f4ddd3, 0x66a02f45, 0xbfbc09ec, 0x03bd9785,
|
766
|
-
0x7fac6dd0, 0x31cb8504, 0x96eb27b3, 0x55fd3941, 0xda2547e6, 0xabca0a9a,
|
767
|
-
0x28507825, 0x530429f4, 0x0a2c86da, 0xe9b66dfb, 0x68dc1462, 0xd7486900,
|
768
|
-
0x680ec0a4, 0x27a18dee, 0x4f3ffea2, 0xe887ad8c, 0xb58ce006, 0x7af4d6b6,
|
769
|
-
0xaace1e7c, 0xd3375fec, 0xce78a399, 0x406b2a42, 0x20fe9e35, 0xd9f385b9,
|
770
|
-
0xee39d7ab, 0x3b124e8b, 0x1dc9faf7, 0x4b6d1856, 0x26a36631, 0xeae397b2,
|
771
|
-
0x3a6efa74, 0xdd5b4332, 0x6841e7f7, 0xca7820fb, 0xfb0af54e, 0xd8feb397,
|
772
|
-
0x454056ac, 0xba489527, 0x55533a3a, 0x20838d87, 0xfe6ba9b7, 0xd096954b,
|
773
|
-
0x55a867bc, 0xa1159a58, 0xcca92963, 0x99e1db33, 0xa62a4a56, 0x3f3125f9,
|
774
|
-
0x5ef47e1c, 0x9029317c, 0xfdf8e802, 0x04272f70, 0x80bb155c, 0x05282ce3,
|
775
|
-
0x95c11548, 0xe4c66d22, 0x48c1133f, 0xc70f86dc, 0x07f9c9ee, 0x41041f0f,
|
776
|
-
0x404779a4, 0x5d886e17, 0x325f51eb, 0xd59bc0d1, 0xf2bcc18f, 0x41113564,
|
777
|
-
0x257b7834, 0x602a9c60, 0xdff8e8a3, 0x1f636c1b, 0x0e12b4c2, 0x02e1329e,
|
778
|
-
0xaf664fd1, 0xcad18115, 0x6b2395e0, 0x333e92e1, 0x3b240b62, 0xeebeb922,
|
779
|
-
0x85b2a20e, 0xe6ba0d99, 0xde720c8c, 0x2da2f728, 0xd0127845, 0x95b794fd,
|
780
|
-
0x647d0862, 0xe7ccf5f0, 0x5449a36f, 0x877d48fa, 0xc39dfd27, 0xf33e8d1e,
|
781
|
-
0x0a476341, 0x992eff74, 0x3a6f6eab, 0xf4f8fd37, 0xa812dc60, 0xa1ebddf8,
|
782
|
-
0x991be14c, 0xdb6e6b0d, 0xc67b5510, 0x6d672c37, 0x2765d43b, 0xdcd0e804,
|
783
|
-
0xf1290dc7, 0xcc00ffa3, 0xb5390f92, 0x690fed0b, 0x667b9ffb, 0xcedb7d9c,
|
784
|
-
0xa091cf0b, 0xd9155ea3, 0xbb132f88, 0x515bad24, 0x7b9479bf, 0x763bd6eb,
|
785
|
-
0x37392eb3, 0xcc115979, 0x8026e297, 0xf42e312d, 0x6842ada7, 0xc66a2b3b,
|
786
|
-
0x12754ccc, 0x782ef11c, 0x6a124237, 0xb79251e7, 0x06a1bbe6, 0x4bfb6350,
|
787
|
-
0x1a6b1018, 0x11caedfa, 0x3d25bdd8, 0xe2e1c3c9, 0x44421659, 0x0a121386,
|
788
|
-
0xd90cec6e, 0xd5abea2a, 0x64af674e, 0xda86a85f, 0xbebfe988, 0x64e4c3fe,
|
789
|
-
0x9dbc8057, 0xf0f7c086, 0x60787bf8, 0x6003604d, 0xd1fd8346, 0xf6381fb0,
|
790
|
-
0x7745ae04, 0xd736fccc, 0x83426b33, 0xf01eab71, 0xb0804187, 0x3c005e5f,
|
791
|
-
0x77a057be, 0xbde8ae24, 0x55464299, 0xbf582e61, 0x4e58f48f, 0xf2ddfda2,
|
792
|
-
0xf474ef38, 0x8789bdc2, 0x5366f9c3, 0xc8b38e74, 0xb475f255, 0x46fcd9b9,
|
793
|
-
0x7aeb2661, 0x8b1ddf84, 0x846a0e79, 0x915f95e2, 0x466e598e, 0x20b45770,
|
794
|
-
0x8cd55591, 0xc902de4c, 0xb90bace1, 0xbb8205d0, 0x11a86248, 0x7574a99e,
|
795
|
-
0xb77f19b6, 0xe0a9dc09, 0x662d09a1, 0xc4324633, 0xe85a1f02, 0x09f0be8c,
|
796
|
-
0x4a99a025, 0x1d6efe10, 0x1ab93d1d, 0x0ba5a4df, 0xa186f20f, 0x2868f169,
|
797
|
-
0xdcb7da83, 0x573906fe, 0xa1e2ce9b, 0x4fcd7f52, 0x50115e01, 0xa70683fa,
|
798
|
-
0xa002b5c4, 0x0de6d027, 0x9af88c27, 0x773f8641, 0xc3604c06, 0x61a806b5,
|
799
|
-
0xf0177a28, 0xc0f586e0, 0x006058aa, 0x30dc7d62, 0x11e69ed7, 0x2338ea63,
|
800
|
-
0x53c2dd94, 0xc2c21634, 0xbbcbee56, 0x90bcb6de, 0xebfc7da1, 0xce591d76,
|
801
|
-
0x6f05e409, 0x4b7c0188, 0x39720a3d, 0x7c927c24, 0x86e3725f, 0x724d9db9,
|
802
|
-
0x1ac15bb4, 0xd39eb8fc, 0xed545578, 0x08fca5b5, 0xd83d7cd3, 0x4dad0fc4,
|
803
|
-
0x1e50ef5e, 0xb161e6f8, 0xa28514d9, 0x6c51133c, 0x6fd5c7e7, 0x56e14ec4,
|
804
|
-
0x362abfce, 0xddc6c837, 0xd79a3234, 0x92638212, 0x670efa8e, 0x406000e0], [
|
805
|
-
0x3a39ce37, 0xd3faf5cf, 0xabc27737, 0x5ac52d1b, 0x5cb0679e, 0x4fa33742,
|
806
|
-
0xd3822740, 0x99bc9bbe, 0xd5118e9d, 0xbf0f7315, 0xd62d1c7e, 0xc700c47b,
|
807
|
-
0xb78c1b6b, 0x21a19045, 0xb26eb1be, 0x6a366eb4, 0x5748ab2f, 0xbc946e79,
|
808
|
-
0xc6a376d2, 0x6549c2c8, 0x530ff8ee, 0x468dde7d, 0xd5730a1d, 0x4cd04dc6,
|
809
|
-
0x2939bbdb, 0xa9ba4650, 0xac9526e8, 0xbe5ee304, 0xa1fad5f0, 0x6a2d519a,
|
810
|
-
0x63ef8ce2, 0x9a86ee22, 0xc089c2b8, 0x43242ef6, 0xa51e03aa, 0x9cf2d0a4,
|
811
|
-
0x83c061ba, 0x9be96a4d, 0x8fe51550, 0xba645bd6, 0x2826a2f9, 0xa73a3ae1,
|
812
|
-
0x4ba99586, 0xef5562e9, 0xc72fefd3, 0xf752f7da, 0x3f046f69, 0x77fa0a59,
|
813
|
-
0x80e4a915, 0x87b08601, 0x9b09e6ad, 0x3b3ee593, 0xe990fd5a, 0x9e34d797,
|
814
|
-
0x2cf0b7d9, 0x022b8b51, 0x96d5ac3a, 0x017da67d, 0xd1cf3ed6, 0x7c7d2d28,
|
815
|
-
0x1f9f25cf, 0xadf2b89b, 0x5ad6b472, 0x5a88f54c, 0xe029ac71, 0xe019a5e6,
|
816
|
-
0x47b0acfd, 0xed93fa9b, 0xe8d3c48d, 0x283b57cc, 0xf8d56629, 0x79132e28,
|
817
|
-
0x785f0191, 0xed756055, 0xf7960e44, 0xe3d35e8c, 0x15056dd4, 0x88f46dba,
|
818
|
-
0x03a16125, 0x0564f0bd, 0xc3eb9e15, 0x3c9057a2, 0x97271aec, 0xa93a072a,
|
819
|
-
0x1b3f6d9b, 0x1e6321f5, 0xf59c66fb, 0x26dcf319, 0x7533d928, 0xb155fdf5,
|
820
|
-
0x03563482, 0x8aba3cbb, 0x28517711, 0xc20ad9f8, 0xabcc5167, 0xccad925f,
|
821
|
-
0x4de81751, 0x3830dc8e, 0x379d5862, 0x9320f991, 0xea7a90c2, 0xfb3e7bce,
|
822
|
-
0x5121ce64, 0x774fbe32, 0xa8b6e37e, 0xc3293d46, 0x48de5369, 0x6413e680,
|
823
|
-
0xa2ae0810, 0xdd6db224, 0x69852dfd, 0x09072166, 0xb39a460a, 0x6445c0dd,
|
824
|
-
0x586cdecf, 0x1c20c8ae, 0x5bbef7dd, 0x1b588d40, 0xccd2017f, 0x6bb4e3bb,
|
825
|
-
0xdda26a7e, 0x3a59ff45, 0x3e350a44, 0xbcb4cdd5, 0x72eacea8, 0xfa6484bb,
|
826
|
-
0x8d6612ae, 0xbf3c6f47, 0xd29be463, 0x542f5d9e, 0xaec2771b, 0xf64e6370,
|
827
|
-
0x740e0d8d, 0xe75b1357, 0xf8721671, 0xaf537d5d, 0x4040cb08, 0x4eb4e2cc,
|
828
|
-
0x34d2466a, 0x0115af84, 0xe1b00428, 0x95983a1d, 0x06b89fb4, 0xce6ea048,
|
829
|
-
0x6f3f3b82, 0x3520ab82, 0x011a1d4b, 0x277227f8, 0x611560b1, 0xe7933fdc,
|
830
|
-
0xbb3a792b, 0x344525bd, 0xa08839e1, 0x51ce794b, 0x2f32c9b7, 0xa01fbac9,
|
831
|
-
0xe01cc87e, 0xbcc7d1f6, 0xcf0111c3, 0xa1e8aac7, 0x1a908749, 0xd44fbd9a,
|
832
|
-
0xd0dadecb, 0xd50ada38, 0x0339c32a, 0xc6913667, 0x8df9317c, 0xe0b12b4f,
|
833
|
-
0xf79e59b7, 0x43f5bb3a, 0xf2d519ff, 0x27d9459c, 0xbf97222c, 0x15e6fc2a,
|
834
|
-
0x0f91fc71, 0x9b941525, 0xfae59361, 0xceb69ceb, 0xc2a86459, 0x12baa8d1,
|
835
|
-
0xb6c1075e, 0xe3056a0c, 0x10d25065, 0xcb03a442, 0xe0ec6e0e, 0x1698db3b,
|
836
|
-
0x4c98a0be, 0x3278e964, 0x9f1f9532, 0xe0d392df, 0xd3a0342b, 0x8971f21e,
|
837
|
-
0x1b0a7441, 0x4ba3348c, 0xc5be7120, 0xc37632d8, 0xdf359f8d, 0x9b992f2e,
|
838
|
-
0xe60b6f47, 0x0fe3f11d, 0xe54cda54, 0x1edad891, 0xce6279cf, 0xcd3e7e6f,
|
839
|
-
0x1618b166, 0xfd2c1d05, 0x848fd2c5, 0xf6fb2299, 0xf523f357, 0xa6327623,
|
840
|
-
0x93a83531, 0x56cccd02, 0xacf08162, 0x5a75ebb5, 0x6e163697, 0x88d273cc,
|
841
|
-
0xde966292, 0x81b949d0, 0x4c50901b, 0x71c65614, 0xe6c6c7bd, 0x327a140a,
|
842
|
-
0x45e1d006, 0xc3f27b9a, 0xc9aa53fd, 0x62a80f00, 0xbb25bfe2, 0x35bdd2f6,
|
843
|
-
0x71126905, 0xb2040222, 0xb6cbcf7c, 0xcd769c2b, 0x53113ec0, 0x1640e3d3,
|
844
|
-
0x38abbd60, 0x2547adf0, 0xba38209c, 0xf746ce76, 0x77afa1c5, 0x20756060,
|
845
|
-
0x85cbfe4e, 0x8ae88dd8, 0x7aaaf9b0, 0x4cf9aa7e, 0x1948c25c, 0x02fb8a8c,
|
846
|
-
0x01c36ae4, 0xd6ebe1f9, 0x90d4f869, 0xa65cdea0, 0x3f09252d, 0xc208e69f,
|
847
|
-
0xb74e6132, 0xce77e25b, 0x578fdfe3, 0x3ac372e6]
|
848
|
-
]
|
849
|
-
|
850
|
-
|
851
|
-
end
|
852
|
-
end #--}}}
|
853
|
-
|
854
|
-
# blowfish.rb Richard Kernahan <kernighan_rich@rubyforge.org>
|
855
|
-
#
|
856
|
-
# Blowfish algorithm by Bruce Schneider
|
857
|
-
# Ported by Richard Kernahan from the reference C code
|
858
|
-
module Crypt #--{{{
|
859
|
-
class Blowfish
|
860
|
-
|
861
|
-
#require 'crypt/cbc'
|
862
|
-
include Crypt::CBC
|
863
|
-
|
864
|
-
#require 'crypt/blowfish-tables'
|
865
|
-
include Crypt::BlowfishTables
|
866
|
-
|
867
|
-
ULONG = 0x100000000
|
868
|
-
|
869
|
-
def block_size
|
870
|
-
return(8)
|
871
|
-
end
|
872
|
-
|
873
|
-
|
874
|
-
def initialize(key)
|
875
|
-
@key = key
|
876
|
-
raise "Bad key length: the key must be 1-56 bytes." unless (key.length.between?(1,56))
|
877
|
-
@pArray = []
|
878
|
-
@sBoxes = []
|
879
|
-
setup_blowfish()
|
880
|
-
end
|
881
|
-
|
882
|
-
|
883
|
-
def f(x)
|
884
|
-
a, b, c, d = [x].pack('N').unpack('CCCC')
|
885
|
-
y = (@sBoxes[0][a] + @sBoxes[1][b]) % ULONG
|
886
|
-
y = (y ^ @sBoxes[2][c]) % ULONG
|
887
|
-
y = (y + @sBoxes[3][d]) % ULONG
|
888
|
-
return(y)
|
889
|
-
end
|
890
|
-
|
891
|
-
|
892
|
-
def setup_blowfish()
|
893
|
-
@sBoxes = Array.new(4) { |i| INITIALSBOXES[i].clone }
|
894
|
-
@pArray = INITIALPARRAY.clone
|
895
|
-
keypos = 0
|
896
|
-
0.upto(17) { |i|
|
897
|
-
data = 0
|
898
|
-
4.times {
|
899
|
-
data = ((data << 8) | @key[keypos]) % ULONG
|
900
|
-
keypos = (keypos.next) % @key.length
|
901
|
-
}
|
902
|
-
@pArray[i] = (@pArray[i] ^ data) % ULONG
|
903
|
-
}
|
904
|
-
l = 0
|
905
|
-
r = 0
|
906
|
-
0.step(17, 2) { |i|
|
907
|
-
l, r = encrypt_pair(l, r)
|
908
|
-
@pArray[i] = l
|
909
|
-
@pArray[i+1] = r
|
910
|
-
}
|
911
|
-
0.upto(3) { |i|
|
912
|
-
0.step(255, 2) { |j|
|
913
|
-
l, r = encrypt_pair(l, r)
|
914
|
-
@sBoxes[i][j] = l
|
915
|
-
@sBoxes[i][j+1] = r
|
916
|
-
}
|
917
|
-
}
|
918
|
-
end
|
919
|
-
|
920
|
-
def encrypt_pair(xl, xr)
|
921
|
-
0.upto(15) { |i|
|
922
|
-
xl = (xl ^ @pArray[i]) % ULONG
|
923
|
-
xr = (xr ^ f(xl)) % ULONG
|
924
|
-
xl, xr = [xl, xr].reverse
|
925
|
-
}
|
926
|
-
xl, xr = [xl, xr].reverse
|
927
|
-
xr = (xr ^ @pArray[16]) % ULONG
|
928
|
-
xl = (xl ^ @pArray[17]) % ULONG
|
929
|
-
return([xl, xr])
|
930
|
-
end
|
931
|
-
|
932
|
-
|
933
|
-
def decrypt_pair(xl, xr)
|
934
|
-
17.downto(2) { |i|
|
935
|
-
xl = (xl ^ @pArray[i]) % ULONG
|
936
|
-
xr = (xr ^ f(xl)) % ULONG
|
937
|
-
xl, xr = [xl, xr].reverse
|
938
|
-
}
|
939
|
-
xl, xr = [xl, xr].reverse
|
940
|
-
xr = (xr ^ @pArray[1]) % ULONG
|
941
|
-
xl = (xl ^ @pArray[0]) % ULONG
|
942
|
-
return([xl, xr])
|
943
|
-
end
|
944
|
-
|
945
|
-
|
946
|
-
def encrypt_block(block)
|
947
|
-
xl, xr = block.unpack('NN')
|
948
|
-
xl, xr = encrypt_pair(xl, xr)
|
949
|
-
encrypted = [xl, xr].pack('NN')
|
950
|
-
return(encrypted)
|
951
|
-
end
|
952
|
-
|
953
|
-
|
954
|
-
def decrypt_block(block)
|
955
|
-
xl, xr = block.unpack('NN')
|
956
|
-
xl, xr = decrypt_pair(xl, xr)
|
957
|
-
decrypted = [xl, xr].pack('NN')
|
958
|
-
return(decrypted)
|
959
|
-
end
|
960
|
-
|
961
|
-
end
|
962
|
-
end #--}}}
|
963
|
-
|
964
|
-
# gost.rb
|
965
|
-
# Adapted by Richard Kernahan <kernighan_rich@rubyforge.org>
|
966
|
-
# from C++ code written by Wei Dai
|
967
|
-
# of the Crypto++ project http://www.eskimo.com/~weidai/cryptlib.html
|
968
|
-
module Crypt #--{{{
|
969
|
-
class Gost
|
970
|
-
|
971
|
-
#require 'crypt/cbc'
|
972
|
-
include CBC
|
973
|
-
|
974
|
-
ULONG = 0x100000000
|
975
|
-
|
976
|
-
def block_size
|
977
|
-
return(8)
|
978
|
-
end
|
979
|
-
|
980
|
-
|
981
|
-
def initialize(userKey)
|
982
|
-
|
983
|
-
# These are the S-boxes given in Applied Cryptography 2nd Ed., p. 333
|
984
|
-
@sBox = [
|
985
|
-
[4, 10, 9, 2, 13, 8, 0, 14, 6, 11, 1, 12, 7, 15, 5, 3],
|
986
|
-
[14, 11, 4, 12, 6, 13, 15, 10, 2, 3, 8, 1, 0, 7, 5, 9],
|
987
|
-
[5, 8, 1, 13, 10, 3, 4, 2, 14, 15, 12, 7, 6, 0, 9, 11],
|
988
|
-
[7, 13, 10, 1, 0, 8, 9, 15, 14, 4, 6, 12, 11, 2, 5, 3],
|
989
|
-
[6, 12, 7, 1, 5, 15, 13, 8, 4, 10, 9, 14, 0, 3, 11, 2],
|
990
|
-
[4, 11, 10, 0, 7, 2, 1, 13, 3, 6, 8, 5, 9, 12, 15, 14],
|
991
|
-
[13, 11, 4, 1, 3, 15, 5, 9, 0, 10, 14, 7, 6, 8, 2, 12],
|
992
|
-
[1, 15, 13, 0, 5, 7, 10, 4, 9, 2, 3, 14, 6, 11, 8, 12]
|
993
|
-
]
|
994
|
-
|
995
|
-
# These are the S-boxes given in the GOST source code listing in Applied
|
996
|
-
# Cryptography 2nd Ed., p. 644. They appear to be from the DES S-boxes
|
997
|
-
# [13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7 ],
|
998
|
-
# [ 4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1 ],
|
999
|
-
# [12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11 ],
|
1000
|
-
# [ 2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9 ],
|
1001
|
-
# [ 7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15 ],
|
1002
|
-
# [10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8 ],
|
1003
|
-
# [15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10 ],
|
1004
|
-
# [14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7 ]
|
1005
|
-
|
1006
|
-
# precalculate the S table
|
1007
|
-
@sTable = precalculate_S_table()
|
1008
|
-
|
1009
|
-
# derive the 32-byte key from the user-supplied key
|
1010
|
-
userKeyLength = userKey.length
|
1011
|
-
@key = userKey[0..31].unpack('C'*32)
|
1012
|
-
if (userKeyLength < 32)
|
1013
|
-
userKeyLength.upto(31) { @key << 0 }
|
1014
|
-
end
|
1015
|
-
end
|
1016
|
-
|
1017
|
-
|
1018
|
-
def precalculate_S_table()
|
1019
|
-
sTable = [[], [], [], []]
|
1020
|
-
0.upto(3) { |i|
|
1021
|
-
0.upto(255) { |j|
|
1022
|
-
t = @sBox[2*i][j % 16] | (@sBox[2*i+1][j/16] << 4)
|
1023
|
-
u = (8*i + 11) % 32
|
1024
|
-
v = (t << u) | (t >> (32-u))
|
1025
|
-
sTable[i][j] = (v % ULONG)
|
1026
|
-
}
|
1027
|
-
}
|
1028
|
-
return(sTable)
|
1029
|
-
end
|
1030
|
-
|
1031
|
-
|
1032
|
-
def f(longWord)
|
1033
|
-
longWord = longWord % ULONG
|
1034
|
-
a, b, c, d = [longWord].pack('L').unpack('CCCC')
|
1035
|
-
return(@sTable[3][d] ^ @sTable[2][c] ^ @sTable[1][b] ^ @sTable[0][a])
|
1036
|
-
end
|
1037
|
-
|
1038
|
-
|
1039
|
-
def encrypt_pair(xl, xr)
|
1040
|
-
3.times {
|
1041
|
-
xr ^= f(xl+@key[0])
|
1042
|
-
xl ^= f(xr+@key[1])
|
1043
|
-
xr ^= f(xl+@key[2])
|
1044
|
-
xl ^= f(xr+@key[3])
|
1045
|
-
xr ^= f(xl+@key[4])
|
1046
|
-
xl ^= f(xr+@key[5])
|
1047
|
-
xr ^= f(xl+@key[6])
|
1048
|
-
xl ^= f(xr+@key[7])
|
1049
|
-
}
|
1050
|
-
xr ^= f(xl+@key[7])
|
1051
|
-
xl ^= f(xr+@key[6])
|
1052
|
-
xr ^= f(xl+@key[5])
|
1053
|
-
xl ^= f(xr+@key[4])
|
1054
|
-
xr ^= f(xl+@key[3])
|
1055
|
-
xl ^= f(xr+@key[2])
|
1056
|
-
xr ^= f(xl+@key[1])
|
1057
|
-
xl ^= f(xr+@key[0])
|
1058
|
-
return([xr, xl])
|
1059
|
-
end
|
1060
|
-
|
1061
|
-
|
1062
|
-
def decrypt_pair(xl, xr)
|
1063
|
-
xr ^= f(xl+@key[0])
|
1064
|
-
xl ^= f(xr+@key[1])
|
1065
|
-
xr ^= f(xl+@key[2])
|
1066
|
-
xl ^= f(xr+@key[3])
|
1067
|
-
xr ^= f(xl+@key[4])
|
1068
|
-
xl ^= f(xr+@key[5])
|
1069
|
-
xr ^= f(xl+@key[6])
|
1070
|
-
xl ^= f(xr+@key[7])
|
1071
|
-
3.times {
|
1072
|
-
xr ^= f(xl+@key[7])
|
1073
|
-
xl ^= f(xr+@key[6])
|
1074
|
-
xr ^= f(xl+@key[5])
|
1075
|
-
xl ^= f(xr+@key[4])
|
1076
|
-
xr ^= f(xl+@key[3])
|
1077
|
-
xl ^= f(xr+@key[2])
|
1078
|
-
xr ^= f(xl+@key[1])
|
1079
|
-
xl ^= f(xr+@key[0])
|
1080
|
-
}
|
1081
|
-
return([xr, xl])
|
1082
|
-
end
|
1083
|
-
|
1084
|
-
|
1085
|
-
def encrypt_block(block)
|
1086
|
-
xl, xr = block.unpack('NN')
|
1087
|
-
xl, xr = encrypt_pair(xl, xr)
|
1088
|
-
encrypted = [xl, xr].pack('NN')
|
1089
|
-
return(encrypted)
|
1090
|
-
end
|
1091
|
-
|
1092
|
-
|
1093
|
-
def decrypt_block(block)
|
1094
|
-
xl, xr = block.unpack('NN')
|
1095
|
-
xl, xr = decrypt_pair(xl, xr)
|
1096
|
-
decrypted = [xl, xr].pack('NN')
|
1097
|
-
return(decrypted)
|
1098
|
-
end
|
1099
|
-
|
1100
|
-
|
1101
|
-
end
|
1102
|
-
end #--}}}
|
1103
|
-
|
1104
|
-
# idea.rb Richard Kernahan <kernighan_rich@rubyforge.org>
|
1105
|
-
# IDEA (International Data Encryption Algorithm) by
|
1106
|
-
# Xuejia Lai and James Massey (1992). Refer to license info at end.
|
1107
|
-
# Ported by Richard Kernahan 2005
|
1108
|
-
module Crypt #--{{{
|
1109
|
-
class IDEA
|
1110
|
-
|
1111
|
-
#require 'crypt/cbc'
|
1112
|
-
include Crypt::CBC
|
1113
|
-
|
1114
|
-
require 'digest/md5'
|
1115
|
-
|
1116
|
-
ULONG = 0x100000000
|
1117
|
-
USHORT = 0x10000
|
1118
|
-
|
1119
|
-
ENCRYPT = 0
|
1120
|
-
DECRYPT = 1
|
1121
|
-
|
1122
|
-
|
1123
|
-
def block_size
|
1124
|
-
return(8)
|
1125
|
-
end
|
1126
|
-
|
1127
|
-
|
1128
|
-
def initialize(key128, mode)
|
1129
|
-
# IDEA is subject to attack unless the key is sufficiently random, so we
|
1130
|
-
# take an MD5 digest of a variable-length passphrase to ensure a solid key
|
1131
|
-
if (key128.class == String)
|
1132
|
-
digest = Digest::MD5.new(key128).digest
|
1133
|
-
key128 = digest.unpack('n'*8)
|
1134
|
-
end
|
1135
|
-
raise "Key must be 128 bits (8 words)" unless (key128.class == Array) && (key128.length == 8)
|
1136
|
-
raise "Mode must be IDEA::ENCRYPT or IDEA::DECRYPT" unless ((mode == ENCRYPT) | (mode == DECRYPT))
|
1137
|
-
if (mode == ENCRYPT)
|
1138
|
-
@subkeys = generate_encryption_subkeys(key128)
|
1139
|
-
else (mode == DECRYPT)
|
1140
|
-
@subkeys = generate_decryption_subkeys(key128)
|
1141
|
-
end
|
1142
|
-
end
|
1143
|
-
|
1144
|
-
|
1145
|
-
def mul(a, b)
|
1146
|
-
modulus = 0x10001
|
1147
|
-
return((1 - b) % USHORT) if (a == 0)
|
1148
|
-
return((1 - a) % USHORT) if (b == 0)
|
1149
|
-
return((a * b) % modulus)
|
1150
|
-
end
|
1151
|
-
|
1152
|
-
|
1153
|
-
def mulInv(x)
|
1154
|
-
modulus = 0x10001
|
1155
|
-
x = x.to_i % USHORT
|
1156
|
-
return(x) if (x <= 1)
|
1157
|
-
t1 = USHORT / x
|
1158
|
-
y = modulus % x
|
1159
|
-
if (y == 1)
|
1160
|
-
inv = (1 - t1) & 0xFFFF
|
1161
|
-
return(inv)
|
1162
|
-
end
|
1163
|
-
t0 = 1
|
1164
|
-
while (y != 1)
|
1165
|
-
q = x / y
|
1166
|
-
x = x % y
|
1167
|
-
t0 = t0 + (q * t1)
|
1168
|
-
return(t0) if (x == 1)
|
1169
|
-
q = y / x
|
1170
|
-
y = y % x
|
1171
|
-
t1 = t1 + (q * t0)
|
1172
|
-
end
|
1173
|
-
inv = (1 - t1) & 0xFFFF
|
1174
|
-
return(inv)
|
1175
|
-
end
|
1176
|
-
|
1177
|
-
|
1178
|
-
def generate_encryption_subkeys(key)
|
1179
|
-
encrypt_keys = []
|
1180
|
-
encrypt_keys[0..7] = key.dup
|
1181
|
-
8.upto(51) { |i|
|
1182
|
-
a = ((i + 1) % 8 > 0) ? (i-7) : (i-15)
|
1183
|
-
b = ((i + 2) % 8 < 2) ? (i-14) : (i-6)
|
1184
|
-
encrypt_keys[i] = ((encrypt_keys[a] << 9) | (encrypt_keys[b] >> 7)) % USHORT
|
1185
|
-
}
|
1186
|
-
return(encrypt_keys)
|
1187
|
-
end
|
1188
|
-
|
1189
|
-
|
1190
|
-
def generate_decryption_subkeys(key)
|
1191
|
-
encrypt_keys = generate_encryption_subkeys(key)
|
1192
|
-
decrypt_keys = []
|
1193
|
-
decrypt_keys[48] = mulInv(encrypt_keys.shift)
|
1194
|
-
decrypt_keys[49] = (-encrypt_keys.shift) % USHORT
|
1195
|
-
decrypt_keys[50] = (-encrypt_keys.shift) % USHORT
|
1196
|
-
decrypt_keys[51] = mulInv(encrypt_keys.shift)
|
1197
|
-
42.step(0, -6) { |i|
|
1198
|
-
decrypt_keys[i+4] = encrypt_keys.shift % USHORT
|
1199
|
-
decrypt_keys[i+5] = encrypt_keys.shift % USHORT
|
1200
|
-
decrypt_keys[i] = mulInv(encrypt_keys.shift)
|
1201
|
-
if (i ==0)
|
1202
|
-
decrypt_keys[1] = (-encrypt_keys.shift) % USHORT
|
1203
|
-
decrypt_keys[2] = (-encrypt_keys.shift) % USHORT
|
1204
|
-
else
|
1205
|
-
decrypt_keys[i+2] = (-encrypt_keys.shift) % USHORT
|
1206
|
-
decrypt_keys[i+1] = (-encrypt_keys.shift) % USHORT
|
1207
|
-
end
|
1208
|
-
decrypt_keys[i+3] = mulInv(encrypt_keys.shift)
|
1209
|
-
}
|
1210
|
-
return(decrypt_keys)
|
1211
|
-
end
|
1212
|
-
|
1213
|
-
|
1214
|
-
def crypt_pair(l, r)
|
1215
|
-
word = [l, r].pack('NN').unpack('nnnn')
|
1216
|
-
k = @subkeys[0..51]
|
1217
|
-
8.downto(1) { |i|
|
1218
|
-
word[0] = mul(word[0], k.shift)
|
1219
|
-
word[1] = (word[1] + k.shift) % USHORT
|
1220
|
-
word[2] = (word[2] + k.shift) % USHORT
|
1221
|
-
word[3] = mul(word[3], k.shift)
|
1222
|
-
t2 = word[0] ^ word[2]
|
1223
|
-
t2 = mul(t2, k.shift)
|
1224
|
-
t1 = (t2 + (word[1] ^ word[3])) % USHORT
|
1225
|
-
t1 = mul(t1, k.shift)
|
1226
|
-
t2 = (t1 + t2) % USHORT
|
1227
|
-
word[0] ^= t1
|
1228
|
-
word[3] ^= t2
|
1229
|
-
t2 ^= word[1]
|
1230
|
-
word[1] = word[2] ^ t1
|
1231
|
-
word[2] = t2
|
1232
|
-
}
|
1233
|
-
result = []
|
1234
|
-
result << mul(word[0], k.shift)
|
1235
|
-
result << (word[2] + k.shift) % USHORT
|
1236
|
-
result << (word[1] + k.shift) % USHORT
|
1237
|
-
result << mul(word[3], k.shift)
|
1238
|
-
twoLongs = result.pack('nnnn').unpack('NN')
|
1239
|
-
return(twoLongs)
|
1240
|
-
end
|
1241
|
-
|
1242
|
-
def encrypt_block(block)
|
1243
|
-
xl, xr = block.unpack('NN')
|
1244
|
-
xl, xr = crypt_pair(xl, xr)
|
1245
|
-
encrypted = [xl, xr].pack('NN')
|
1246
|
-
return(encrypted)
|
1247
|
-
end
|
1248
|
-
|
1249
|
-
|
1250
|
-
def decrypt_block(block)
|
1251
|
-
xl, xr = block.unpack('NN')
|
1252
|
-
xl, xr = crypt_pair(xl, xr)
|
1253
|
-
decrypted = [xl, xr].pack('NN')
|
1254
|
-
return(decrypted)
|
1255
|
-
end
|
1256
|
-
|
1257
|
-
|
1258
|
-
end
|
1259
|
-
end #--}}}
|
1260
|
-
|
1261
|
-
# LICENSE INFORMATION
|
1262
|
-
#
|
1263
|
-
# This software product contains the IDEA algorithm as described and claimed in
|
1264
|
-
# US patent 5,214,703, EPO patent 0482154 (covering Austria, France, Germany,
|
1265
|
-
# Italy, the Netherlands, Spain, Sweden, Switzerland, and the UK), and Japanese
|
1266
|
-
# patent application 508119/1991, "Device for the conversion of a digital block
|
1267
|
-
# and use of same" (hereinafter referred to as "the algorithm"). Any use of
|
1268
|
-
# the algorithm for commercial purposes is thus subject to a license from Ascom
|
1269
|
-
# Systec Ltd. of CH-5506 Maegenwil (Switzerland), being the patentee and sole
|
1270
|
-
# owner of all rights, including the trademark IDEA.
|
1271
|
-
#
|
1272
|
-
# Commercial purposes shall mean any revenue generating purpose including but
|
1273
|
-
# not limited to:
|
1274
|
-
#
|
1275
|
-
# i) Using the algorithm for company internal purposes (subject to a site
|
1276
|
-
# license).
|
1277
|
-
#
|
1278
|
-
# ii) Incorporating the algorithm into any software and distributing such
|
1279
|
-
# software and/or providing services relating thereto to others (subject to
|
1280
|
-
# a product license).
|
1281
|
-
#
|
1282
|
-
# iii) Using a product containing the algorithm not covered by an IDEA license
|
1283
|
-
# (subject to an end user license).
|
1284
|
-
#
|
1285
|
-
# All such end user license agreements are available exclusively from Ascom
|
1286
|
-
# Systec Ltd and may be requested via the WWW at http://www.ascom.ch/systec or
|
1287
|
-
# by email to idea@ascom.ch.
|
1288
|
-
#
|
1289
|
-
# Use other than for commercial purposes is strictly limited to non-revenue
|
1290
|
-
# generating data transfer between private individuals. The use by government
|
1291
|
-
# agencies, non-profit organizations, etc is considered as use for commercial
|
1292
|
-
# purposes but may be subject to special conditions. Any misuse will be
|
1293
|
-
# prosecuted.
|
1294
|
-
|
1295
|
-
# crypt/rattle.rb Richard Kernahan <kernighan_rich@rubyforge.org>
|
1296
|
-
|
1297
|
-
# add_noise - take a message and intersperse noise to make a new noisy message of given byte-length
|
1298
|
-
# remove_noise - take a noisy message and extract the message
|
1299
|
-
module Crypt #--{{{
|
1300
|
-
module Noise
|
1301
|
-
|
1302
|
-
def add_noise(newLength)
|
1303
|
-
message = self
|
1304
|
-
usableNoisyMessageLength = newLength / 9 * 8
|
1305
|
-
bitmapSize = newLength / 9
|
1306
|
-
remainingBytes = newLength - usableNoisyMessageLength - bitmapSize
|
1307
|
-
if (message.length > usableNoisyMessageLength)
|
1308
|
-
minimumNewLength = (message.length / 8.0).ceil * 9
|
1309
|
-
puts "For a clear text of #{message.length} bytes, the minimum obscured length"
|
1310
|
-
puts "is #{minimumNewLength} bytes which allows for no noise in the message."
|
1311
|
-
puts "You should choose an obscured length of at least double the clear text"
|
1312
|
-
puts "length, such as #{message.length / 8 * 32} bytes"
|
1313
|
-
raise "Insufficient length for noisy message"
|
1314
|
-
end
|
1315
|
-
bitmap = []
|
1316
|
-
usableNoisyMessageLength.times { bitmap << false }
|
1317
|
-
srand(Time.now.to_i)
|
1318
|
-
positionsSelected = 0
|
1319
|
-
while (positionsSelected < message.length)
|
1320
|
-
positionTaken = rand(usableNoisyMessageLength)
|
1321
|
-
if bitmap[positionTaken]
|
1322
|
-
next
|
1323
|
-
else
|
1324
|
-
bitmap[positionTaken] = true
|
1325
|
-
positionsSelected = positionsSelected.next
|
1326
|
-
end
|
1327
|
-
end
|
1328
|
-
|
1329
|
-
noisyMessage = ""
|
1330
|
-
0.upto(bitmapSize-1) { |byte|
|
1331
|
-
c = 0
|
1332
|
-
0.upto(7) { |bit|
|
1333
|
-
c = c + (1<<bit) if bitmap[byte * 8 + bit]
|
1334
|
-
}
|
1335
|
-
noisyMessage << c.chr
|
1336
|
-
}
|
1337
|
-
posInMessage = 0
|
1338
|
-
0.upto(usableNoisyMessageLength-1) { |pos|
|
1339
|
-
if bitmap[pos]
|
1340
|
-
meaningfulByte = message[posInMessage]
|
1341
|
-
noisyMessage << meaningfulByte
|
1342
|
-
posInMessage = posInMessage.next
|
1343
|
-
else
|
1344
|
-
noiseByte = rand(256).chr
|
1345
|
-
noisyMessage << noiseByte
|
1346
|
-
end
|
1347
|
-
}
|
1348
|
-
remainingBytes.times {
|
1349
|
-
noiseByte = rand(256).chr
|
1350
|
-
noisyMessage << noiseByte
|
1351
|
-
}
|
1352
|
-
return(noisyMessage)
|
1353
|
-
end
|
1354
|
-
|
1355
|
-
|
1356
|
-
def remove_noise
|
1357
|
-
noisyMessage = self
|
1358
|
-
bitmapSize = noisyMessage.length / 9
|
1359
|
-
actualMessageLength = bitmapSize * 8
|
1360
|
-
|
1361
|
-
actualMessageStart = bitmapSize
|
1362
|
-
actualMessageFinish = bitmapSize + actualMessageLength - 1
|
1363
|
-
actualMessage = noisyMessage[actualMessageStart..actualMessageFinish]
|
1364
|
-
|
1365
|
-
bitmap = []
|
1366
|
-
0.upto(bitmapSize - 1) { |byte|
|
1367
|
-
c = noisyMessage[byte]
|
1368
|
-
0.upto(7) { |bit|
|
1369
|
-
bitmap[byte * 8 + bit] = (c[bit] == 1)
|
1370
|
-
}
|
1371
|
-
}
|
1372
|
-
clearMessage = ""
|
1373
|
-
0.upto(actualMessageLength) { |pos|
|
1374
|
-
meaningful = bitmap[pos]
|
1375
|
-
if meaningful
|
1376
|
-
clearMessage << actualMessage[pos]
|
1377
|
-
end
|
1378
|
-
}
|
1379
|
-
return(clearMessage)
|
1380
|
-
end
|
1381
|
-
|
1382
|
-
end
|
1383
|
-
end
|
1384
|
-
|
1385
|
-
class String
|
1386
|
-
include Crypt::Noise
|
1387
|
-
end #--}}}
|
1388
|
-
|
1389
|
-
|
1390
|
-
# Thanks to Binky DaClown who wrote this pure-ruby implementation
|
1391
|
-
# http://rubyforge.org/projects/prstringio/
|
1392
|
-
# Apparently CBC does not work well with the C-based stringio
|
1393
|
-
module Crypt #--{{{
|
1394
|
-
class PureRubyStringIO
|
1395
|
-
|
1396
|
-
include Enumerable
|
1397
|
-
|
1398
|
-
SEEK_CUR = IO::SEEK_CUR
|
1399
|
-
SEEK_END = IO::SEEK_END
|
1400
|
-
SEEK_SET = IO::SEEK_SET
|
1401
|
-
|
1402
|
-
@@relayMethods = [:<<, :all?, :any?, :binmode, :close, :close_read, :close_write, :closed?, :closed_read?,
|
1403
|
-
:closed_write?, :collect, :detect, :each, :each_byte, :each_line, :each_with_index,
|
1404
|
-
:entries, :eof, :eof?, :fcntl, :fileno, :find, :find_all, :flush, :fsync, :getc, :gets,
|
1405
|
-
:grep, :include?, :inject, :isatty, :length, :lineno, :lineno=, :map, :max, :member?,
|
1406
|
-
:min, :partition, :path, :pid, :pos, :pos=, :print, :printf, :putc, :puts, :read,
|
1407
|
-
:readchar, :readline, :readlines, :reject, :rewind, :seek, :select, :size, :sort,
|
1408
|
-
:sort_by, :string, :string=, :sync, :sync=, :sysread, :syswrite, :tell, :truncate, :tty?,
|
1409
|
-
:ungetc, :write, :zip]
|
1410
|
-
|
1411
|
-
def self.open(string="", mode="r+")
|
1412
|
-
if block_given? then
|
1413
|
-
sio = new(string, mode)
|
1414
|
-
rc = yield(sio)
|
1415
|
-
sio.close
|
1416
|
-
rc
|
1417
|
-
else
|
1418
|
-
new(string, mode)
|
1419
|
-
end
|
1420
|
-
end
|
1421
|
-
|
1422
|
-
def <<(obj)
|
1423
|
-
requireWritable
|
1424
|
-
write obj
|
1425
|
-
self
|
1426
|
-
end
|
1427
|
-
|
1428
|
-
def binmode
|
1429
|
-
self
|
1430
|
-
end
|
1431
|
-
|
1432
|
-
def close
|
1433
|
-
requireOpen
|
1434
|
-
@sio_closed_read = true
|
1435
|
-
@sio_closed_write = true
|
1436
|
-
self
|
1437
|
-
end
|
1438
|
-
|
1439
|
-
def close_read
|
1440
|
-
raise IOError, "closing non-duplex IO for reading", caller if closed_read?
|
1441
|
-
@sio_closed_read = true
|
1442
|
-
self
|
1443
|
-
end
|
1444
|
-
|
1445
|
-
def close_write
|
1446
|
-
raise IOError, "closing non-duplex IO for writing", caller if closed_write?
|
1447
|
-
@sio_closed_read = true
|
1448
|
-
self
|
1449
|
-
end
|
1450
|
-
|
1451
|
-
def closed?
|
1452
|
-
closed_read? && closed_write?
|
1453
|
-
end
|
1454
|
-
|
1455
|
-
def closed_read?
|
1456
|
-
@sio_closed_read
|
1457
|
-
end
|
1458
|
-
|
1459
|
-
def closed_write?
|
1460
|
-
@sio_closed_write
|
1461
|
-
end
|
1462
|
-
|
1463
|
-
def each(sep_string=$/, &block)
|
1464
|
-
requireReadable
|
1465
|
-
@sio_string.each(sep_string, &block)
|
1466
|
-
@sio_pos = @sio_string.length
|
1467
|
-
end
|
1468
|
-
|
1469
|
-
def each_byte(&block)
|
1470
|
-
requireReadable
|
1471
|
-
@sio_string.each_byte(&block)
|
1472
|
-
@sio_pos = @sio_string.length
|
1473
|
-
end
|
1474
|
-
|
1475
|
-
def eof
|
1476
|
-
requireReadable { @sio_pos >= @sio_string.length }
|
1477
|
-
end
|
1478
|
-
|
1479
|
-
def fcntl(integer_cmd, arg)
|
1480
|
-
raise NotImplementedError, "The fcntl() function is unimplemented on this machine", caller
|
1481
|
-
end
|
1482
|
-
|
1483
|
-
def fileno
|
1484
|
-
nil
|
1485
|
-
end
|
1486
|
-
|
1487
|
-
def flush
|
1488
|
-
self
|
1489
|
-
end
|
1490
|
-
|
1491
|
-
def fsync
|
1492
|
-
0
|
1493
|
-
end
|
1494
|
-
|
1495
|
-
def getc
|
1496
|
-
requireReadable
|
1497
|
-
char = @sio_string[@sio_pos]
|
1498
|
-
@sio_pos += 1 unless char.nil?
|
1499
|
-
char
|
1500
|
-
end
|
1501
|
-
|
1502
|
-
def gets(sep_string=$/)
|
1503
|
-
requireReadable
|
1504
|
-
@sio_lineno += 1
|
1505
|
-
pstart = @sio_pos
|
1506
|
-
@sio_pos = @sio_string.index(sep_string, @sio_pos) || [@sio_string.length, @sio_pos].max
|
1507
|
-
@sio_string[pstart..@sio_pos]
|
1508
|
-
end
|
1509
|
-
|
1510
|
-
def initialize(string="", mode="r+")
|
1511
|
-
@sio_string = string.to_s
|
1512
|
-
@sio_lineno = 0
|
1513
|
-
@mode = mode
|
1514
|
-
@relay = nil
|
1515
|
-
case mode.delete("b")
|
1516
|
-
when "r"
|
1517
|
-
@sio_closed_read = false
|
1518
|
-
@sio_closed_write = true
|
1519
|
-
@sio_pos = 0
|
1520
|
-
when "r+"
|
1521
|
-
@sio_closed_read = false
|
1522
|
-
@sio_closed_write = false
|
1523
|
-
@sio_pos = 0
|
1524
|
-
when "w"
|
1525
|
-
@sio_closed_read = true
|
1526
|
-
@sio_closed_write = false
|
1527
|
-
@sio_pos = 0
|
1528
|
-
@sio_string.replace("")
|
1529
|
-
when "w+"
|
1530
|
-
@sio_closed_read = false
|
1531
|
-
@sio_closed_write = false
|
1532
|
-
@sio_pos = 0
|
1533
|
-
@sio_string.replace("")
|
1534
|
-
when "a"
|
1535
|
-
@sio_closed_read = true
|
1536
|
-
@sio_closed_write = false
|
1537
|
-
@sio_pos = @sio_string.length
|
1538
|
-
when "a+"
|
1539
|
-
@sio_closed_read = false
|
1540
|
-
@sio_closed_write = false
|
1541
|
-
@sio_pos = @sio_string.length
|
1542
|
-
else
|
1543
|
-
raise ArgumentError, "illegal access mode #{mode}", caller
|
1544
|
-
end
|
1545
|
-
end
|
1546
|
-
|
1547
|
-
def isatty
|
1548
|
-
flase
|
1549
|
-
end
|
1550
|
-
|
1551
|
-
def length
|
1552
|
-
@sio_string.length
|
1553
|
-
end
|
1554
|
-
|
1555
|
-
def lineno
|
1556
|
-
@sio_lineno
|
1557
|
-
end
|
1558
|
-
|
1559
|
-
def lineno=(integer)
|
1560
|
-
@sio_lineno = integer
|
1561
|
-
end
|
1562
|
-
|
1563
|
-
def path
|
1564
|
-
nil
|
1565
|
-
end
|
1566
|
-
|
1567
|
-
def pid
|
1568
|
-
nil
|
1569
|
-
end
|
1570
|
-
|
1571
|
-
def pos
|
1572
|
-
@sio_pos
|
1573
|
-
end
|
1574
|
-
|
1575
|
-
def pos=(integer)
|
1576
|
-
raise Errno::EINVAL, "Invalid argument", caller if integer < 0
|
1577
|
-
@sio_pos = integer
|
1578
|
-
end
|
1579
|
-
|
1580
|
-
def print(*args)
|
1581
|
-
requireWritable
|
1582
|
-
args.unshift($_) if args.empty
|
1583
|
-
args.each { |obj| write(obj) }
|
1584
|
-
write($\) unless $\.nil?
|
1585
|
-
nil
|
1586
|
-
end
|
1587
|
-
|
1588
|
-
def printf(format_string, *args)
|
1589
|
-
requireWritable
|
1590
|
-
write format(format_string, *args)
|
1591
|
-
nil
|
1592
|
-
end
|
1593
|
-
|
1594
|
-
def putc(obj)
|
1595
|
-
requireWritable
|
1596
|
-
write(obj.is_a?(Numeric) ? sprintf("%c", obj) : obj.to_s[0..0])
|
1597
|
-
obj
|
1598
|
-
end
|
1599
|
-
|
1600
|
-
def puts(*args)
|
1601
|
-
requireWritable
|
1602
|
-
args.unshift("") if args.empty?
|
1603
|
-
args.each { |obj|
|
1604
|
-
write obj
|
1605
|
-
write $/
|
1606
|
-
}
|
1607
|
-
nil
|
1608
|
-
end
|
1609
|
-
|
1610
|
-
def read(length=nil, buffer=nil)
|
1611
|
-
requireReadable
|
1612
|
-
len = length || [@sio_string.length - @sio_pos, 0].max
|
1613
|
-
raise ArgumentError, "negative length #{len} given", caller if len < 0
|
1614
|
-
buffer ||= ""
|
1615
|
-
pstart = @sio_pos
|
1616
|
-
@sio_pos += len
|
1617
|
-
buffer.replace(@sio_string[pstart..@sio_pos])
|
1618
|
-
buffer.empty? && !length.nil? ? nil : buffer
|
1619
|
-
end
|
1620
|
-
|
1621
|
-
def readchar
|
1622
|
-
requireReadable
|
1623
|
-
raise EOFError, "End of file reached", caller if eof?
|
1624
|
-
getc
|
1625
|
-
end
|
1626
|
-
|
1627
|
-
def readline
|
1628
|
-
requireReadable
|
1629
|
-
raise EOFError, "End of file reached", caller if eof?
|
1630
|
-
gets
|
1631
|
-
end
|
1632
|
-
|
1633
|
-
def readlines(sep_string=$/)
|
1634
|
-
requireReadable
|
1635
|
-
raise EOFError, "End of file reached", caller if eof?
|
1636
|
-
rc = []
|
1637
|
-
until eof
|
1638
|
-
rc << gets(sep_string)
|
1639
|
-
end
|
1640
|
-
rc
|
1641
|
-
end
|
1642
|
-
|
1643
|
-
def reopen(string, mode=nil)
|
1644
|
-
if string.is_a?(self.class) then
|
1645
|
-
raise ArgumentError, "wrong number of arguments (2 for 1)", caller if !mode.nil?
|
1646
|
-
@relay = string
|
1647
|
-
instance_eval(%Q{
|
1648
|
-
class << self
|
1649
|
-
@@relayMethods.each { |name|
|
1650
|
-
define_method(name, ObjectSpace._id2ref(#{@relay.object_id}).method(("original_" + name.to_s).to_sym).to_proc)
|
1651
|
-
}
|
1652
|
-
end
|
1653
|
-
})
|
1654
|
-
else
|
1655
|
-
raise ArgumentError, "wrong number of arguments (1 for 2)", caller if mode.nil?
|
1656
|
-
class << self
|
1657
|
-
@@relayMethods.each { |name|
|
1658
|
-
alias_method(name, "original_#{name}".to_sym)
|
1659
|
-
public name
|
1660
|
-
}
|
1661
|
-
@relay = nil
|
1662
|
-
end unless @relay.nil?
|
1663
|
-
@sio_string = string.to_s
|
1664
|
-
@mode = mode
|
1665
|
-
end
|
1666
|
-
end
|
1667
|
-
|
1668
|
-
def rewind
|
1669
|
-
@sio_pos = 0
|
1670
|
-
@sio_lineno = 0
|
1671
|
-
end
|
1672
|
-
|
1673
|
-
def seek(amount, whence=SEEK_SET)
|
1674
|
-
if whence == SEEK_CUR then
|
1675
|
-
offset += @sio_pos
|
1676
|
-
elsif whence == SEEK_END then
|
1677
|
-
offset += size
|
1678
|
-
end
|
1679
|
-
@sio_pos = offset
|
1680
|
-
end
|
1681
|
-
|
1682
|
-
def string
|
1683
|
-
@sio_string
|
1684
|
-
end
|
1685
|
-
|
1686
|
-
def string=(newstring)
|
1687
|
-
@sio_string = newstring
|
1688
|
-
end
|
1689
|
-
|
1690
|
-
def sync
|
1691
|
-
true
|
1692
|
-
end
|
1693
|
-
|
1694
|
-
def sync=(boolean)
|
1695
|
-
boolean
|
1696
|
-
end
|
1697
|
-
|
1698
|
-
def sysread(length=nil, buffer=nil)
|
1699
|
-
requireReadable
|
1700
|
-
raise EOFError, "End of file reached", caller if eof?
|
1701
|
-
read(length, buffer)
|
1702
|
-
end
|
1703
|
-
|
1704
|
-
def syswrite(string)
|
1705
|
-
requireWritable
|
1706
|
-
addition = "\000" * (@sio_string.length - @sio_pos) + string.to_s
|
1707
|
-
@sio_string[@sio_pos..(addition.length - 1)] = addition
|
1708
|
-
@sio_pos += addition.size
|
1709
|
-
addition.size
|
1710
|
-
end
|
1711
|
-
|
1712
|
-
#In ruby 1.8.4 truncate differs from the docs in two ways.
|
1713
|
-
#First, if an integer greater that the length is given then the string is expanded to the new integer
|
1714
|
-
#length. As this expansion seems to contain junk characters instead of nulls I suspect this may be a
|
1715
|
-
#flaw in the C code which could cause a core dump if abused/used.
|
1716
|
-
#Second, the documentation states that truncate returns 0. It returns the integer instead.
|
1717
|
-
#This implementation follows the documentation in the first instance as I suspect this will be fixed
|
1718
|
-
#in the C code. In the second instance, it follows the actions of the C code instead of the docs.
|
1719
|
-
#This was decided as it causes no immedeate harm and this ruby implentation is to be as compatable
|
1720
|
-
#as possible with the C version. Should the C version change to match the docs the ruby version
|
1721
|
-
#will be simple to update as well.
|
1722
|
-
def truncate(integer)
|
1723
|
-
requireWritable
|
1724
|
-
raise Errno::EINVAL, "Invalid argument - negative length", caller if integer < 0
|
1725
|
-
@sio_string[[integer, @sio_string.length].max..-1] = ""
|
1726
|
-
integer
|
1727
|
-
end
|
1728
|
-
|
1729
|
-
def ungetc(integer)
|
1730
|
-
requireWritable
|
1731
|
-
if @sio_pos > 0 then
|
1732
|
-
@sio_pos -= 1
|
1733
|
-
putc(integer)
|
1734
|
-
@sio_pos -= 1
|
1735
|
-
end
|
1736
|
-
end
|
1737
|
-
|
1738
|
-
alias :each_line :each
|
1739
|
-
alias :eof? :eof
|
1740
|
-
alias :size :length
|
1741
|
-
alias :tty? :isatty
|
1742
|
-
alias :tell :pos
|
1743
|
-
alias :write :syswrite
|
1744
|
-
|
1745
|
-
protected
|
1746
|
-
@@relayMethods.each { |name|
|
1747
|
-
alias_method("original_#{name}".to_sym, name)
|
1748
|
-
protected "original_#{name}".to_sym
|
1749
|
-
}
|
1750
|
-
|
1751
|
-
private
|
1752
|
-
|
1753
|
-
def requireReadable
|
1754
|
-
raise IOError, "not opened for reading", caller[1..-1] if @sio_closed_read
|
1755
|
-
end
|
1756
|
-
|
1757
|
-
def requireWritable
|
1758
|
-
raise IOError, "not opened for writing", caller[1..-1] if @sio_closed_write
|
1759
|
-
end
|
1760
|
-
|
1761
|
-
def requireOpen
|
1762
|
-
raise IOError, "closed stream", caller[1..-1] if @sio_closed_read && @sio_closed_write
|
1763
|
-
end
|
1764
|
-
|
1765
|
-
end
|
1766
|
-
end #--}}}
|
1767
|
-
|
1768
|
-
# rijndael-tables.rb Richard Kernahan <kernighan_rich@rubyforge.org>
|
1769
|
-
module Crypt #--{{{
|
1770
|
-
module RijndaelTables
|
1771
|
-
|
1772
|
-
LogTable = [
|
1773
|
-
0, 0, 25, 1, 50, 2, 26, 198, 75, 199, 27, 104, 51, 238, 223, 3,
|
1774
|
-
100, 4, 224, 14, 52, 141, 129, 239, 76, 113, 8, 200, 248, 105, 28, 193,
|
1775
|
-
125, 194, 29, 181, 249, 185, 39, 106, 77, 228, 166, 114, 154, 201, 9, 120,
|
1776
|
-
101, 47, 138, 5, 33, 15, 225, 36, 18, 240, 130, 69, 53, 147, 218, 142,
|
1777
|
-
150, 143, 219, 189, 54, 208, 206, 148, 19, 92, 210, 241, 64, 70, 131, 56,
|
1778
|
-
102, 221, 253, 48, 191, 6, 139, 98, 179, 37, 226, 152, 34, 136, 145, 16,
|
1779
|
-
126, 110, 72, 195, 163, 182, 30, 66, 58, 107, 40, 84, 250, 133, 61, 186,
|
1780
|
-
43, 121, 10, 21, 155, 159, 94, 202, 78, 212, 172, 229, 243, 115, 167, 87,
|
1781
|
-
175, 88, 168, 80, 244, 234, 214, 116, 79, 174, 233, 213, 231, 230, 173, 232,
|
1782
|
-
44, 215, 117, 122, 235, 22, 11, 245, 89, 203, 95, 176, 156, 169, 81, 160,
|
1783
|
-
127, 12, 246, 111, 23, 196, 73, 236, 216, 67, 31, 45, 164, 118, 123, 183,
|
1784
|
-
204, 187, 62, 90, 251, 96, 177, 134, 59, 82, 161, 108, 170, 85, 41, 157,
|
1785
|
-
151, 178, 135, 144, 97, 190, 220, 252, 188, 149, 207, 205, 55, 63, 91, 209,
|
1786
|
-
83, 57, 132, 60, 65, 162, 109, 71, 20, 42, 158, 93, 86, 242, 211, 171,
|
1787
|
-
68, 17, 146, 217, 35, 32, 46, 137, 180, 124, 184, 38, 119, 153, 227, 165,
|
1788
|
-
103, 74, 237, 222, 197, 49, 254, 24, 13, 99, 140, 128, 192, 247, 112, 7
|
1789
|
-
]
|
1790
|
-
|
1791
|
-
AlogTable = [
|
1792
|
-
1, 3, 5, 15, 17, 51, 85, 255, 26, 46, 114, 150, 161, 248, 19, 53,
|
1793
|
-
95, 225, 56, 72, 216, 115, 149, 164, 247, 2, 6, 10, 30, 34, 102, 170,
|
1794
|
-
229, 52, 92, 228, 55, 89, 235, 38, 106, 190, 217, 112, 144, 171, 230, 49,
|
1795
|
-
83, 245, 4, 12, 20, 60, 68, 204, 79, 209, 104, 184, 211, 110, 178, 205,
|
1796
|
-
76, 212, 103, 169, 224, 59, 77, 215, 98, 166, 241, 8, 24, 40, 120, 136,
|
1797
|
-
131, 158, 185, 208, 107, 189, 220, 127, 129, 152, 179, 206, 73, 219, 118, 154,
|
1798
|
-
181, 196, 87, 249, 16, 48, 80, 240, 11, 29, 39, 105, 187, 214, 97, 163,
|
1799
|
-
254, 25, 43, 125, 135, 146, 173, 236, 47, 113, 147, 174, 233, 32, 96, 160,
|
1800
|
-
251, 22, 58, 78, 210, 109, 183, 194, 93, 231, 50, 86, 250, 21, 63, 65,
|
1801
|
-
195, 94, 226, 61, 71, 201, 64, 192, 91, 237, 44, 116, 156, 191, 218, 117,
|
1802
|
-
159, 186, 213, 100, 172, 239, 42, 126, 130, 157, 188, 223, 122, 142, 137, 128,
|
1803
|
-
155, 182, 193, 88, 232, 35, 101, 175, 234, 37, 111, 177, 200, 67, 197, 84,
|
1804
|
-
252, 31, 33, 99, 165, 244, 7, 9, 27, 45, 119, 153, 176, 203, 70, 202,
|
1805
|
-
69, 207, 74, 222, 121, 139, 134, 145, 168, 227, 62, 66, 198, 81, 243, 14,
|
1806
|
-
18, 54, 90, 238, 41, 123, 141, 140, 143, 138, 133, 148, 167, 242, 13, 23,
|
1807
|
-
57, 75, 221, 124, 132, 151, 162, 253, 28, 36, 108, 180, 199, 82, 246, 1
|
1808
|
-
]
|
1809
|
-
|
1810
|
-
S = [
|
1811
|
-
99, 124, 119, 123, 242, 107, 111, 197, 48, 1, 103, 43, 254, 215, 171, 118,
|
1812
|
-
202, 130, 201, 125, 250, 89, 71, 240, 173, 212, 162, 175, 156, 164, 114, 192,
|
1813
|
-
183, 253, 147, 38, 54, 63, 247, 204, 52, 165, 229, 241, 113, 216, 49, 21,
|
1814
|
-
4, 199, 35, 195, 24, 150, 5, 154, 7, 18, 128, 226, 235, 39, 178, 117,
|
1815
|
-
9, 131, 44, 26, 27, 110, 90, 160, 82, 59, 214, 179, 41, 227, 47, 132,
|
1816
|
-
83, 209, 0, 237, 32, 252, 177, 91, 106, 203, 190, 57, 74, 76, 88, 207,
|
1817
|
-
208, 239, 170, 251, 67, 77, 51, 133, 69, 249, 2, 127, 80, 60, 159, 168,
|
1818
|
-
81, 163, 64, 143, 146, 157, 56, 245, 188, 182, 218, 33, 16, 255, 243, 210,
|
1819
|
-
205, 12, 19, 236, 95, 151, 68, 23, 196, 167, 126, 61, 100, 93, 25, 115,
|
1820
|
-
96, 129, 79, 220, 34, 42, 144, 136, 70, 238, 184, 20, 222, 94, 11, 219,
|
1821
|
-
224, 50, 58, 10, 73, 6, 36, 92, 194, 211, 172, 98, 145, 149, 228, 121,
|
1822
|
-
231, 200, 55, 109, 141, 213, 78, 169, 108, 86, 244, 234, 101, 122, 174, 8,
|
1823
|
-
186, 120, 37, 46, 28, 166, 180, 198, 232, 221, 116, 31, 75, 189, 139, 138,
|
1824
|
-
112, 62, 181, 102, 72, 3, 246, 14, 97, 53, 87, 185, 134, 193, 29, 158,
|
1825
|
-
225, 248, 152, 17, 105, 217, 142, 148, 155, 30, 135, 233, 206, 85, 40, 223,
|
1826
|
-
140, 161, 137, 13, 191, 230, 66, 104, 65, 153, 45, 15, 176, 84, 187, 22
|
1827
|
-
]
|
1828
|
-
|
1829
|
-
Si = [
|
1830
|
-
82, 9, 106, 213, 48, 54, 165, 56, 191, 64, 163, 158, 129, 243, 215, 251,
|
1831
|
-
124, 227, 57, 130, 155, 47, 255, 135, 52, 142, 67, 68, 196, 222, 233, 203,
|
1832
|
-
84, 123, 148, 50, 166, 194, 35, 61, 238, 76, 149, 11, 66, 250, 195, 78,
|
1833
|
-
8, 46, 161, 102, 40, 217, 36, 178, 118, 91, 162, 73, 109, 139, 209, 37,
|
1834
|
-
114, 248, 246, 100, 134, 104, 152, 22, 212, 164, 92, 204, 93, 101, 182, 146,
|
1835
|
-
108, 112, 72, 80, 253, 237, 185, 218, 94, 21, 70, 87, 167, 141, 157, 132,
|
1836
|
-
144, 216, 171, 0, 140, 188, 211, 10, 247, 228, 88, 5, 184, 179, 69, 6,
|
1837
|
-
208, 44, 30, 143, 202, 63, 15, 2, 193, 175, 189, 3, 1, 19, 138, 107,
|
1838
|
-
58, 145, 17, 65, 79, 103, 220, 234, 151, 242, 207, 206, 240, 180, 230, 115,
|
1839
|
-
150, 172, 116, 34, 231, 173, 53, 133, 226, 249, 55, 232, 28, 117, 223, 110,
|
1840
|
-
71, 241, 26, 113, 29, 41, 197, 137, 111, 183, 98, 14, 170, 24, 190, 27,
|
1841
|
-
252, 86, 62, 75, 198, 210, 121, 32, 154, 219, 192, 254, 120, 205, 90, 244,
|
1842
|
-
31, 221, 168, 51, 136, 7, 199, 49, 177, 18, 16, 89, 39, 128, 236, 95,
|
1843
|
-
96, 81, 127, 169, 25, 181, 74, 13, 45, 229, 122, 159, 147, 201, 156, 239,
|
1844
|
-
160, 224, 59, 77, 174, 42, 245, 176, 200, 235, 187, 60, 131, 83, 153, 97,
|
1845
|
-
23, 43, 4, 126, 186, 119, 214, 38, 225, 105, 20, 99, 85, 33, 12, 125,
|
1846
|
-
]
|
1847
|
-
|
1848
|
-
IG = [
|
1849
|
-
[0x0e, 0x09, 0x0d, 0x0b],
|
1850
|
-
[0x0b, 0x0e, 0x09, 0x0d],
|
1851
|
-
[0x0d, 0x0b, 0x0e, 0x09],
|
1852
|
-
[0x09, 0x0d, 0x0b, 0x0e]
|
1853
|
-
]
|
1854
|
-
|
1855
|
-
Rcon = [
|
1856
|
-
0x01, 0x02, 0x04, 0x08, 0x10, 0x20,
|
1857
|
-
0x40, 0x80, 0x1b, 0x36, 0x6c, 0xd8,
|
1858
|
-
0xab, 0x4d, 0x9a, 0x2f, 0x5e, 0xbc,
|
1859
|
-
0x63, 0xc6, 0x97, 0x35, 0x6a, 0xd4,
|
1860
|
-
0xb3, 0x7d, 0xfa, 0xef, 0xc5, 0x91
|
1861
|
-
]
|
1862
|
-
|
1863
|
-
Shifts = [
|
1864
|
-
[
|
1865
|
-
[0, 0],
|
1866
|
-
[1, 3],
|
1867
|
-
[2, 2],
|
1868
|
-
[3, 1]
|
1869
|
-
], [
|
1870
|
-
[0, 0],
|
1871
|
-
[1, 5],
|
1872
|
-
[2, 4],
|
1873
|
-
[3, 3]
|
1874
|
-
], [
|
1875
|
-
[0, 0],
|
1876
|
-
[1, 7],
|
1877
|
-
[3, 5],
|
1878
|
-
[4, 4]
|
1879
|
-
]
|
1880
|
-
]
|
1881
|
-
|
1882
|
-
end
|
1883
|
-
end #--}}}
|
1884
|
-
|
1885
|
-
# rijndael.rb Richard Kernahan <kernighan_rich@rubyforge.org>
|
1886
|
-
# Adapted from the reference C implementation:
|
1887
|
-
# rijndael-alg-ref.c v2.2 March 2002
|
1888
|
-
# Reference ANSI C code
|
1889
|
-
# authors: Paulo Barreto and Vincent Rijmen
|
1890
|
-
# This code is placed in the public domain.
|
1891
|
-
module Crypt #--{{{
|
1892
|
-
class Rijndael
|
1893
|
-
|
1894
|
-
#require 'crypt/cbc'
|
1895
|
-
include Crypt::CBC
|
1896
|
-
|
1897
|
-
#require 'crypt/rijndael-tables'
|
1898
|
-
include Crypt::RijndaelTables
|
1899
|
-
|
1900
|
-
|
1901
|
-
def initialize(userKey, keyBits = 256, blockBits = 128)
|
1902
|
-
case keyBits
|
1903
|
-
when 128
|
1904
|
-
@keyWords = 4
|
1905
|
-
when 192
|
1906
|
-
@keyWords = 6
|
1907
|
-
when 256
|
1908
|
-
@keyWords = 8
|
1909
|
-
else raise "The key must be 128, 192, or 256 bits long."
|
1910
|
-
end
|
1911
|
-
|
1912
|
-
case (keyBits >= blockBits) ? keyBits : blockBits
|
1913
|
-
when 128
|
1914
|
-
@rounds = 10
|
1915
|
-
when 192
|
1916
|
-
@rounds = 12
|
1917
|
-
when 256
|
1918
|
-
@rounds = 14
|
1919
|
-
else raise "The key and block sizes must be 128, 192, or 256 bits long."
|
1920
|
-
end
|
1921
|
-
|
1922
|
-
case blockBits
|
1923
|
-
when 128
|
1924
|
-
@blockSize = 16
|
1925
|
-
@blockWords = 4
|
1926
|
-
@shiftIndex = 0
|
1927
|
-
when 192
|
1928
|
-
@blockSize = 24
|
1929
|
-
@blockWords = 6
|
1930
|
-
@shiftIndex = 1
|
1931
|
-
when 256
|
1932
|
-
@blockSize = 32
|
1933
|
-
@blockWords = 8
|
1934
|
-
@shiftIndex = 2
|
1935
|
-
else raise "The block size must be 128, 192, or 256 bits long."
|
1936
|
-
end
|
1937
|
-
|
1938
|
-
uk = userKey.unpack('C'*userKey.length)
|
1939
|
-
maxUsefulSizeOfUserKey = (keyBits/8)
|
1940
|
-
uk = uk[0..maxUsefulSizeOfUserKey-1] # truncate
|
1941
|
-
padding = 0
|
1942
|
-
if (userKey.length < keyBits/8)
|
1943
|
-
shortfallInUserKey = (keyBits/8 - userKey.length)
|
1944
|
-
shortfallInUserKey.times { uk << padding }
|
1945
|
-
end
|
1946
|
-
@key = [[], [], [], []]
|
1947
|
-
0.upto(uk.length-1) { |pos|
|
1948
|
-
@key[pos % 4][pos / 4] = uk[pos]
|
1949
|
-
}
|
1950
|
-
@roundKeys = generate_key_schedule(@key, keyBits, blockBits)
|
1951
|
-
end
|
1952
|
-
|
1953
|
-
|
1954
|
-
def block_size
|
1955
|
-
return(@blockSize) # needed for CBC
|
1956
|
-
end
|
1957
|
-
|
1958
|
-
|
1959
|
-
def mul(a, b)
|
1960
|
-
if ((a ==0) | (b == 0))
|
1961
|
-
result = 0
|
1962
|
-
else
|
1963
|
-
result = AlogTable[(LogTable[a] + LogTable[b]) % 255]
|
1964
|
-
end
|
1965
|
-
return(result)
|
1966
|
-
end
|
1967
|
-
|
1968
|
-
|
1969
|
-
def add_round_key(blockArray, roundKey)
|
1970
|
-
0.upto(3) { |i|
|
1971
|
-
0.upto(@blockWords) { |j|
|
1972
|
-
blockArray[i][j] ^= roundKey[i][j]
|
1973
|
-
}
|
1974
|
-
}
|
1975
|
-
return(blockArray)
|
1976
|
-
end
|
1977
|
-
|
1978
|
-
|
1979
|
-
def shift_rows(blockArray, direction)
|
1980
|
-
tmp = []
|
1981
|
-
1.upto(3) { |i| # row zero remains unchanged
|
1982
|
-
0.upto(@blockWords-1) { |j|
|
1983
|
-
tmp[j] = blockArray[i][(j + Shifts[@shiftIndex][i][direction]) % @blockWords]
|
1984
|
-
}
|
1985
|
-
0.upto(@blockWords-1) { |j|
|
1986
|
-
blockArray[i][j] = tmp[j]
|
1987
|
-
}
|
1988
|
-
}
|
1989
|
-
return(blockArray)
|
1990
|
-
end
|
1991
|
-
|
1992
|
-
|
1993
|
-
def substitution(blockArray, sBox)
|
1994
|
-
# replace every byte of the input with the byte at that position in the S-box
|
1995
|
-
0.upto(3) { |i|
|
1996
|
-
0.upto(@blockWords-1) { |j|
|
1997
|
-
blockArray[i][j] = sBox[blockArray[i][j]]
|
1998
|
-
}
|
1999
|
-
}
|
2000
|
-
return(blockArray)
|
2001
|
-
end
|
2002
|
-
|
2003
|
-
|
2004
|
-
def mix_columns(blockArray)
|
2005
|
-
mixed = [[], [], [], []]
|
2006
|
-
0.upto(@blockWords-1) { |j|
|
2007
|
-
0.upto(3) { |i|
|
2008
|
-
mixed[i][j] = mul(2,blockArray[i][j]) ^
|
2009
|
-
mul(3,blockArray[(i + 1) % 4][j]) ^
|
2010
|
-
blockArray[(i + 2) % 4][j] ^
|
2011
|
-
blockArray[(i + 3) % 4][j]
|
2012
|
-
}
|
2013
|
-
}
|
2014
|
-
return(mixed)
|
2015
|
-
end
|
2016
|
-
|
2017
|
-
|
2018
|
-
def inverse_mix_columns(blockArray)
|
2019
|
-
unmixed = [[], [], [], []]
|
2020
|
-
0.upto(@blockWords-1) { |j|
|
2021
|
-
0.upto(3) { |i|
|
2022
|
-
unmixed[i][j] = mul(0xe, blockArray[i][j]) ^
|
2023
|
-
mul(0xb, blockArray[(i + 1) % 4][j]) ^
|
2024
|
-
mul(0xd, blockArray[(i + 2) % 4][j]) ^
|
2025
|
-
mul(0x9, blockArray[(i + 3) % 4][j])
|
2026
|
-
}
|
2027
|
-
}
|
2028
|
-
return(unmixed)
|
2029
|
-
end
|
2030
|
-
|
2031
|
-
|
2032
|
-
def generate_key_schedule(k, keyBits, blockBits)
|
2033
|
-
tk = k[0..3][0..@keyWords-1] # using slice to get a copy instead of a reference
|
2034
|
-
keySched = []
|
2035
|
-
(@rounds + 1).times { keySched << [[], [], [], []] }
|
2036
|
-
t = 0
|
2037
|
-
j = 0
|
2038
|
-
while ((j < @keyWords) && (t < (@rounds+1)*@blockWords))
|
2039
|
-
0.upto(3) { |i|
|
2040
|
-
keySched[t / @blockWords][i][t % @blockWords] = tk[i][j]
|
2041
|
-
}
|
2042
|
-
j += 1
|
2043
|
-
t += 1
|
2044
|
-
end
|
2045
|
-
# while not enough round key material collected, calculate new values
|
2046
|
-
rconIndex = 0
|
2047
|
-
while (t < (@rounds+1)*@blockWords)
|
2048
|
-
0.upto(3) { |i|
|
2049
|
-
tk[i][0] ^= S[tk[(i + 1) % 4][@keyWords - 1]]
|
2050
|
-
}
|
2051
|
-
tk[0][0] ^= Rcon[rconIndex]
|
2052
|
-
rconIndex = rconIndex.next
|
2053
|
-
if (@keyWords != 8)
|
2054
|
-
1.upto(@keyWords - 1) { |j|
|
2055
|
-
0.upto(3) { |i|
|
2056
|
-
tk[i][j] ^= tk[i][j-1];
|
2057
|
-
}
|
2058
|
-
}
|
2059
|
-
else
|
2060
|
-
1.upto(@keyWords/2 - 1) { |j|
|
2061
|
-
0.upto(3) { |i|
|
2062
|
-
tk[i][j] ^= tk[i][j-1]
|
2063
|
-
}
|
2064
|
-
}
|
2065
|
-
0.upto(3) { |i|
|
2066
|
-
tk[i][@keyWords/2] ^= S[tk[i][@keyWords/2 - 1]]
|
2067
|
-
}
|
2068
|
-
(@keyWords/2 + 1).upto(@keyWords - 1) { |j|
|
2069
|
-
0.upto(3) { |i|
|
2070
|
-
tk[i][j] ^= tk[i][j-1]
|
2071
|
-
}
|
2072
|
-
}
|
2073
|
-
end
|
2074
|
-
j = 0
|
2075
|
-
while ((j < @keyWords) && (t < (@rounds+1) * @blockWords))
|
2076
|
-
0.upto(3) { |i|
|
2077
|
-
keySched[t / @blockWords][i][t % @blockWords] = tk[i][j]
|
2078
|
-
}
|
2079
|
-
j += 1
|
2080
|
-
t += 1
|
2081
|
-
end
|
2082
|
-
end
|
2083
|
-
return(keySched)
|
2084
|
-
end
|
2085
|
-
|
2086
|
-
|
2087
|
-
def encrypt_byte_array(blockArray)
|
2088
|
-
blockArray = add_round_key(blockArray, @roundKeys[0])
|
2089
|
-
1.upto(@rounds - 1) { |round|
|
2090
|
-
blockArray = substitution(blockArray, S)
|
2091
|
-
blockArray = shift_rows(blockArray, 0)
|
2092
|
-
blockArray = mix_columns(blockArray)
|
2093
|
-
blockArray = add_round_key(blockArray, @roundKeys[round])
|
2094
|
-
}
|
2095
|
-
# special round without mix_columns
|
2096
|
-
blockArray = substitution(blockArray,S)
|
2097
|
-
blockArray = shift_rows(blockArray,0)
|
2098
|
-
blockArray = add_round_key(blockArray, @roundKeys[@rounds])
|
2099
|
-
return(blockArray)
|
2100
|
-
end
|
2101
|
-
|
2102
|
-
|
2103
|
-
def encrypt_block(block)
|
2104
|
-
raise "block must be #{@blockSize} bytes long" if (block.length() != @blockSize)
|
2105
|
-
blockArray = [[], [], [], []]
|
2106
|
-
0.upto(@blockSize - 1) { |pos|
|
2107
|
-
blockArray[pos % 4][pos / 4] = block[pos]
|
2108
|
-
}
|
2109
|
-
encryptedBlock = encrypt_byte_array(blockArray)
|
2110
|
-
encrypted = ""
|
2111
|
-
0.upto(@blockSize - 1) { |pos|
|
2112
|
-
encrypted << encryptedBlock[pos % 4][pos / 4]
|
2113
|
-
}
|
2114
|
-
return(encrypted)
|
2115
|
-
end
|
2116
|
-
|
2117
|
-
|
2118
|
-
def decrypt_byte_array(blockArray)
|
2119
|
-
# first special round without inverse_mix_columns
|
2120
|
-
# add_round_key is an involution - applying it a second time returns the original result
|
2121
|
-
blockArray = add_round_key(blockArray, @roundKeys[@rounds])
|
2122
|
-
blockArray = substitution(blockArray,Si) # using inverse S-box
|
2123
|
-
blockArray = shift_rows(blockArray,1)
|
2124
|
-
(@rounds-1).downto(1) { |round|
|
2125
|
-
blockArray = add_round_key(blockArray, @roundKeys[round])
|
2126
|
-
blockArray = inverse_mix_columns(blockArray)
|
2127
|
-
blockArray = substitution(blockArray, Si)
|
2128
|
-
blockArray = shift_rows(blockArray, 1)
|
2129
|
-
}
|
2130
|
-
blockArray = add_round_key(blockArray, @roundKeys[0])
|
2131
|
-
return(blockArray)
|
2132
|
-
end
|
2133
|
-
|
2134
|
-
|
2135
|
-
def decrypt_block(block)
|
2136
|
-
raise "block must be #{@blockSize} bytes long" if (block.length() != @blockSize)
|
2137
|
-
blockArray = [[], [], [], []]
|
2138
|
-
0.upto(@blockSize - 1) { |pos|
|
2139
|
-
blockArray[pos % 4][pos / 4] = block[pos]
|
2140
|
-
}
|
2141
|
-
decryptedBlock = decrypt_byte_array(blockArray)
|
2142
|
-
decrypted = ""
|
2143
|
-
0.upto(@blockSize - 1) { |pos|
|
2144
|
-
decrypted << decryptedBlock[pos % 4][pos / 4]
|
2145
|
-
}
|
2146
|
-
return(decrypted)
|
2147
|
-
end
|
2148
|
-
|
2149
|
-
|
2150
|
-
end
|
2151
|
-
end #--}}}
|
2152
|
-
|
2153
|
-
# stringxor.rb Richard Kernahan <kernighan_rich@rubyforge.org>
|
2154
|
-
module Crypt #--{{{
|
2155
|
-
module StringXor
|
2156
|
-
|
2157
|
-
|
2158
|
-
def ^(aString)
|
2159
|
-
a = self.unpack('C'*(self.length))
|
2160
|
-
b = aString.unpack('C'*(aString.length))
|
2161
|
-
if (b.length < a.length)
|
2162
|
-
(a.length - b.length).times { b << 0 }
|
2163
|
-
end
|
2164
|
-
xor = ""
|
2165
|
-
0.upto(a.length-1) { |pos|
|
2166
|
-
x = a[pos] ^ b[pos]
|
2167
|
-
xor << x.chr()
|
2168
|
-
}
|
2169
|
-
return(xor)
|
2170
|
-
end
|
2171
|
-
|
2172
|
-
|
2173
|
-
end
|
2174
|
-
end
|
2175
|
-
|
2176
|
-
class String
|
2177
|
-
include Crypt::StringXor
|
2178
|
-
end #--}}}
|
2179
|
-
#--}}}
|
2180
|
-
}
|
2181
|
-
|
2182
|
-
__END__
|
2183
|
-
class RaptchaController < ApplicationController
|
2184
|
-
def index # the image responder
|
2185
|
-
Raptcha.render self, params
|
2186
|
-
end
|
2187
|
-
|
2188
|
-
def form # sample on how to use
|
2189
|
-
render :inline => <<-html
|
2190
|
-
<html>
|
2191
|
-
<body>
|
2192
|
-
<hr>
|
2193
|
-
<em>valid</em>:#{ Raptcha.valid? params }
|
2194
|
-
<hr>
|
2195
|
-
<form method=post>
|
2196
|
-
#{ Raptcha.input }
|
2197
|
-
<hr>
|
2198
|
-
<input type=submit name=submit value=submit />
|
2199
|
-
<hr>
|
2200
|
-
<a href="#{ request.request_uri }">new</a>
|
2201
|
-
</form>
|
2202
|
-
</body>
|
2203
|
-
</html>
|
2204
|
-
html
|
2205
|
-
end
|
2206
|
-
|
2207
|
-
def inline # does not work in older internet exploders
|
2208
|
-
render :inline => <<-html
|
2209
|
-
<html>
|
2210
|
-
<body>
|
2211
|
-
<hr>
|
2212
|
-
<em>valid</em>:#{ Raptcha.valid? params }
|
2213
|
-
<hr>
|
2214
|
-
<form method=post>
|
2215
|
-
#{ Raptcha.input :inline => true }
|
2216
|
-
<hr>
|
2217
|
-
<input type=submit name=submit value=submit />
|
2218
|
-
<hr>
|
2219
|
-
<a href="#{ request.request_uri }">new</a>
|
2220
|
-
</form>
|
2221
|
-
</body>
|
2222
|
-
</html>
|
2223
|
-
html
|
2224
|
-
end
|
2225
|
-
end
|