Using Ruby to fuzz FTP Server - ruby

Hey, I'm new to Ruby and trying to learn by porting some progs from one language to another. Right now I'm working on an FTP fuzzer in Ruby that mirrors this perl script:
use Net::FTP;
$target = "192.168.37.128";
$buffer = "A\x20";
$buffer .= "A" x 512;
$ftp = Net::FTP->new($target, Debug => 0, Timeout => 5)
or die "Cannot connect to $host: $# \n";
$ftp->login("anonymous",'anonymous#nowhere.com')
or die "Couldn't log in: $#\n";
$ftp->list($buffer);
$ftp->quit;
This is my Ruby equivalent:
require 'net/ftp'
buffer = 'A\x20'
buffer = (buffer + ('A'*512))
ftp = Net::FTP.open('127.0.0.1','anonymous','anonymous')
ftp.login
ftp.list(buffer)
ftp.quit
When I run the program I get the following error:
C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:241:in `readline': end of file reached (EOF
Error)
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:241:in `getline'
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:251:in `getmultiline'
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:265:in `getresp'
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:281:in `voidresp'
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:304:in `block in voidcmd'
from C:/Ruby192/lib/ruby/1.9.1/monitor.rb:201:in `mon_synchronize'
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:302:in `voidcmd'
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:155:in `send_type_command'
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:149:in `binary='
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:168:in `ensure in with_binary'
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:168:in `with_binary'
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:440:in `block in retrlines'
from C:/Ruby192/lib/ruby/1.9.1/monitor.rb:201:in `mon_synchronize'
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:439:in `retrlines'
from C:/Ruby192/lib/ruby/1.9.1/net/ftp.rb:682:in `list'
from ftpcrash.rb:10:in `<main>'
I've traced the issue to the ftp.list(buffer) line, but can't come up with a Ruby solution that will accomplish what $ftp->list($buffer) does in the perl one.
Suggestions?

The buffer is unnecessary. #list takes an optional argument like '*n', not a buffer, and it returns an array.
require 'net/ftp'
ftp = Net::FTP.open('ftp.gnu.org','anonymous','')
puts ftp.list
ftp.quit

Judging by net/ftp.rb source code this exception is raised when ftp library is trying to get a response from the server and response is empty.
You should wrap this command in begin/rescue/end (or just rescue) and handle the error accordingly.

Here What you want dude
#!/bin/ruby
require 'socket'
buffer = "A" * 512
host = 'xx.xx.xx.xx'
port = 21
s = TCPSocket.open(host, port)
s.recv(1024)
s.send("USER anonymous\r\n", 0)
s.recv(1024)
s.send("PASS anonymous\r\n", 0)
s.recv(1024)
s.send(buffer + "\r\n", 0)
sleep 0.3
s.close
Stay Secure ;)

Related

ruby - zlib header error when uncompressing tar.gz

I wanted to write a ruby program to unpackage tar.gz files, and I ran into some issues. After reading the documentation on the ruby-doc site, Zlib::GzipReader and Zlib::Inflate. Then I found this Module someone wrote on GitHub, and that didn't work either. So, using the examples from the Ruby page for Zlib::GzipReader, I these were able to run successfully.
irb(main):027:0* File.open('zlib_inflate.tar.gz') do |f|
irb(main):028:1* gz = Zlib::GzipReader.new(f)
irb(main):029:1> print gz.read
irb(main):030:1> gz.close
irb(main):031:1> end
#
#
#
irb(main):023:0* Zlib::GzipReader.open('zlib_inflate.tar.gz') { |gz|
irb(main):024:1* print gz.read
irb(main):025:1> }
Then, when trying to use the Zlib::Inflate options, I kept running into incorrect header check errors.
irb(main):047:0* zstream = Zlib::Inflate.new
=> #<Zlib::Inflate:0x00000002b15790 #dictionaries={}>
irb(main):048:0> buf = zstream.inflate('zlib_inflate.tar.gz')
Zlib::DataError: incorrect header check
from (irb):48:in `inflate'
from (irb):48
from C:/ruby/Ruby200p353/Ruby200-x64/bin/irb:12:in `<main>'
#
#
#
irb(main):049:0> cf = File.open("zlib_inflate.tar.gz")
=> #<File:zlib_inflate.tar.gz>
irb(main):050:0> ucf = File.open("ruby_inflate.rb", "w+")
=> #<File:ruby_inflate.rb>
irb(main):051:0> zi = Zlib::Inflate.new(Zlib::MAX_WBITS)
=> #<Zlib::Inflate:0x00000002c097f0 #dictionaries={}>
irb(main):052:0> ucf << zi.inflate(cf.read)
Zlib::DataError: incorrect header check
from (irb):52:in `inflate'
from (irb):52
from C:/ruby/Ruby200p353/Ruby200-x64/bin/irb:12:in `<main>'
#
#
#
irb(main):057:0* File.open("zlib_inflate.tar.gz") {|cf|
irb(main):058:1* zi = Zlib::Inflate.new
irb(main):059:1> File.open("zlib_inflate.rb", "w+") {|ucf|
irb(main):060:2* ucf << zi.inflate(cf.read)
irb(main):061:2> }
irb(main):062:1> zi.close
irb(main):063:1> }
Zlib::DataError: incorrect header check
from (irb):60:in `inflate'
from (irb):60:in `block (2 levels) in irb_binding'
from (irb):59:in `open'
from (irb):59:in `block in irb_binding'
from (irb):57:in `open'
from (irb):57
from C:/ruby/Ruby200p353/Ruby200-x64/bin/irb:12:in `<main>'
How would I go about taking a tar.gz file, and extract the contents so the files are not null? I did read this other post about Ruby Zlib from here, but that did not work for me as well. What am I doing wrong?

Ruby/SSL:sslv3 alert handshake failure

Please note I have reviewed as many of the articles on here about this issue and the sample/example code I am showing is one of a dozen variations I have tried based on my reading. So please don't RTFM or the like.
I am writing a simple ruby script to log in/logout of a web app. Unfortunately it is https, and in my attempts it seems like ssl is a much harder "easy programming" scenario than I thought.
I am running this script on a stock Kali installation. I am justing Ruby 1.9.1. The error I am getting is:
/usr/lib/ruby/1.9.1/net/http.rb:799:in `connect': SSL_connect returned=1 errno=0 state=SSLv3 read finished A: sslv3 alert handshake failure (OpenSSL::SSL::SSLError)
from /usr/lib/ruby/1.9.1/net/http.rb:799:in `block in connect'
from /usr/lib/ruby/1.9.1/timeout.rb:54:in `timeout'
from /usr/lib/ruby/1.9.1/timeout.rb:99:in `timeout'
from /usr/lib/ruby/1.9.1/net/http.rb:799:in `connect'
from /usr/lib/ruby/1.9.1/net/http.rb:755:in `do_start'
from /usr/lib/ruby/1.9.1/net/http.rb:744:in `start'
from ./capture_ids.rb:27:in `block in <main>'
from ./capture_ids.rb:18:in `each'
from ./capture_ids.rb:18:in `<main>'
Here is my ruby script:
#!/usr/bin/env ruby
require 'net/http'
require 'net/https'
require 'openssl'
puts OpenSSL::OPENSSL_VERSION
puts "SSL_CERT_FILE: %s" % OpenSSL::X509::DEFAULT_CERT_FILE
puts "SSL_CERT_DIR: %s" % OpenSSL::X509::DEFAULT_CERT_DIR
login_str = "https://192.168.0.251/~login_handler?UserName=foo&Password=bar"
logout_str = "https://192.168.0.251/~logout_handler?session_id="
seqids = Array.new
puts "Starting capture..."
puts "Staring loop..."
for num in 0..2 do
puts "doing iteration #{num}"
uri = URI.parse(login_str)
https = Net::HTTP.new(uri.host, uri.port)
https.use_ssl = true
# https.cert_store = OpenSSL::X509::Store.new
# https.cert_store.set_default_paths
https.verify_mode = OpenSSL::SSL::VERIFY_NONE
req = Net::HTTP::Post.new(uri.path)
https.start {
res = https.request(req)
}
# puts "*********** Here is the response ***************"
# puts res
# puts "*********** End of response ********************"
start_pt = res.index("name=")
end_pt = res.index(" src=")
seq_id = res.slice(start_pt, end_pt)
puts "Sequence id is " + seq_id
seqids << seq_id
uri = URI.parse(logout_str)
https = Net::HTTP::new(uri.host, uri.port)
https.use_ssl = true
# https.cert_store = OpenSSL::X509::Store.new
# https.cert_store.set_default_paths
https.verify_mode = OpenSSL::SSL::VERIFY_NONE
req = Net::HTTP::Get.new(uri.path)
https.start {
https.request(req)
}
end
My SSL dir/certs are:
SSL_CERT_FILE: /usr/lib/ssl/cert.pem
SSL_CERT_DIR: /usr/lib/ssl/certs
And yes I have confirmed things are there. I also have tried to download new cert files and ca files and use them and put them in there.
What magic ju ju beads do I have to shake?

Ruby Spreadsheet: Bad file descriptor - test.xls (Errno::EBADF)

I have problem with script that makes simple .xls file and writes data to one cell. Here is simple code:
require 'spreadsheet'
class Filter
def filter
#excel = Spreadsheet::Workbook.new
#sheet = #excel.create_worksheet
#sheet[0, 0] = "test"
#excel.write 'test.xls'
end
end
f = Filter.new
f.filter
But it raises error:
C:/Ruby193/lib/ruby/gems/1.9.1/gems/ruby-ole-1.2.11.5/lib/ole/storage/base.rb:62:in
write_nonblock': Bad file descriptor - test.xls (Errno::EBADF)
from C:/Ruby193/lib/ruby/gems/1.9.1/gems/ruby-ole-1.2.11.5/lib/ole/storage/base.rb:62:in
initialize'
from C:/Ruby193/lib/ruby/gems/1.9.1/gems/ruby-ole-1.2.11.5/lib/ole/storage/base.rb:78:in
new'
from C:/Ruby193/lib/ruby/gems/1.9.1/gems/ruby-ole-1.2.11.5/lib/ole/storage/base.rb:78:in
open'
from C:/Ruby193/lib/ruby/gems/1.9.1/gems/spreadsheet-0.7.4/lib/spreadsheet/excel/writer/workbook.rb:4
53:in write_from_scratch'
from C:/Ruby193/lib/ruby/gems/1.9.1/gems/spreadsheet-0.7.4/lib/spreadsheet/excel/writer/workbook.rb:6
31:inwrite_workbook'
from C:/Ruby193/lib/ruby/gems/1.9.1/gems/spreadsheet-0.7.4/lib/spreadsheet/writer.rb:15:in
block in write'
from C:/Ruby193/lib/ruby/gems/1.9.1/gems/spreadsheet-0.7.4/lib/spreadsheet/writer.rb:14:in
open'
from C:/Ruby193/lib/ruby/gems/1.9.1/gems/spreadsheet-0.7.4/lib/spreadsheet/writer.rb:14:in
write'
from C:/Ruby193/lib/ruby/gems/1.9.1/gems/spreadsheet-0.7.4/lib/spreadsheet/workbook.rb:116:in
write'
from filter.rb:10:in `filter'
from filter.rb:15:in `<main>'
because ruby-ole 1.2.11.5 doesn't support windows platform,
more detail: ruby-ole issue
you can use ruby-ole 1.2.11.4 to avoid this problem.
require 'rubygems'
gem 'ruby-ole','1.2.11.4'
require 'spreadsheet'
I've seen these before. First verify that you can write to that file's location.
My guess is either the file is already open in Excel or your antivirus is blocking the 'threat'.

Ruby Net::FTP gettextfile not able to save files locally

I am trying to retrieve files (.csv) from an ftp site and save them all locally in the same folder. My code looks like this:
#! /usr/bin/ruby
require 'logger'
require 'fileutils'
require 'net/ftp'
require 'rubygems'
require 'mysql2'
require 'roo'
require 'date'
# logging setup
log = Logger.new("/path_to_logs/ftp_log.log", 10, 1024000)
log.level = Logger::INFO
export_ftp_path = '/Receive/results/'
export_work_path ='/Users/pierce/results_exports/'
Net::FTP.open('host', 'username', 'password') do |ftp|
log.info("Logged into FTP")
ftp.passive = true
ftp.chdir("#{export_ftp_path}")
ftp.list.each do |file|
log.info("Found file #{file}")
new_file = file[56..115] #take part of the file name and remove spaces and periods
new_file = new_file.gsub(/[.]+/, "")
new_file = new_file.gsub(/\s/, "0")
ftp.gettextfile(file,"#{new_file}")
log.info("Downloaded file #{new_file}")
end
end
And here is the error I receive:
/Users/pierce/.rbenv/versions/1.9.2-p290/lib/ruby/1.9.1/net/ftp.rb:560:in `initialize': No such file or directory - (Errno::ENOENT)
from /Users/pierce/.rbenv/versions/1.9.2-p290/lib/ruby/1.9.1/net/ftp.rb:560:in `open'
from /Users/pierce/.rbenv/versions/1.9.2-p290/lib/ruby/1.9.1/net/ftp.rb:560:in `gettextfile'
from ftp_test.rb:44:in `block (2 levels) in <main>'
from ftp_test.rb:33:in `each'
from ftp_test.rb:33:in `block in <main>'
from /Users/pierce/.rbenv/versions/1.9.2-p290/lib/ruby/1.9.1/net/ftp.rb:116:in `open'
As suggested, here are the values I have for puts file and puts new_file.
file = -rwxr-xr-x 1 1130419 114727 9546 May 17 08:11 results_Wed. 16 May 2012.csv
new_file = results_Wed0230May02012csv
Any suggestions on what to change in gettextfile or within my script to get the files saved correctly?
You should use nlst instead of list when you just need a list of files in a directory. The output of list needs to be properly parsed otherwise.
When you request the file it has to be the original filename, including all spaces. When you save the file it can be anything you want (including spaces or not). The error was because you were requesting the wrong file. Use nlst in your case instead. It will make it much easier (no conversion or parsing needed).

Ruby FTP sendcmd error

ftp = Net::FTP.new(IPAddress)
ftp.login(UserName, Password)
ftp.sendcmd("prompt")
ftp.sendcmd("mget filename*")
This code returns the following error.
/usr/lib/ruby/1.9.1/net/ftp.rb:261:in `getresp': 500 'PROMPT': command not understood (Net::FTPPermError)
from /usr/lib/ruby/1.9.1/net/ftp.rb:269:in `voidresp'
from /usr/lib/ruby/1.9.1/net/ftp.rb:292:in `block in voidcmd'
from /usr/lib/ruby/1.9.1/monitor.rb:190:in `mon_synchronize'
from /usr/lib/ruby/1.9.1/net/ftp.rb:290:in `voidcmd'
Why is Ruby converting my command to UPPERCASE while I am giving it in lower case.
i don't think sendcmd is used this way. Try this alternative
require 'net/ftp'
user="user"
pass="password"
server="server"
Net::FTP.open(server) do |ftp|
ftp.login(user,pass)
ftp.nlst("filename.*").each do |file|
ftp.getbinaryfile(file,file)
end
ftp.close
end

Resources