Friday, November 23, 2012

Simple Script to Update All of Your Ubuntu Machines Securely Over SSH from One Central Location

First configure certificate-based authentication with no password on the server that will manage the updates for the rest of your hosts:

$ ssh-keygen -t rsa
Generating public/private rsa key pair.
Enter file in which to save the key (/home/<YOURUSERNAME>/.ssh/id_rsa): <ENTER>
Enter passphrase (empty for no passphrase): <ENTER>
Enter same passphrase again: <ENTER>
Your identification has been saved in /home/<YOURUSERNAME>/.ssh/id_rsa.
Your public key has been saved in /home/<YOURUSERNAME>/.ssh/id_rsa.pub.
The key fingerprint is:
82:ef:d2:3a:b3:5f:9d:bc:41:ac:10:42:8f:a3:24:02 <YOURUSERNAME>@<THE_UPDATE_SERVER>
The key's randomart image is:
+--[ RSA 2048]----+
|    E.. .        |
|       o o       |
|      . = o      |
|       + + . .   |
|      o S .   o  |
|     .  .  . = . |
|     ...    o =  |
|    . . +  .   o |
|     .. .=.   .  |
+-----------------+

This will generate ~/.ssh/id_rsa.pub - copy the contents of this file into ~/.ssh/authorized_keys on every host you'd like to update (~/.ssh/authorized_keys should be the home folder of the user that will be used to ssh into the host that will obtain an update).

Once you can ssh into each host from the server without entering a password, create the file /usr/local/etc/update_da_boxen.config on the update server:

$ sudo touch /usr/local/etc/update_da_boxen.config

Next include one username@host_to_update entry on each line within /usr/local/etc/update_da_boxen.config:

johndoe@firsthosttoupdate
jackie@seconfdhosttoupdate
janedee@thirdhosttoupdate

Save your changes and ensure the file is only readable by root:

chmod 600 /usr/local/etc/update_da_boxen.config && chown root:root /usr/local/etc/update_da_boxen.config

Next create /usr/local/scripts/update_da_boxen.rb:

#!/usr/bin/env ruby
target_user_at_hosts_file = '/usr/local/etc/update_da_boxen.config'
File.read(target_user_at_hosts_file).each_line do |l|
  user_at_host = l.strip.chomp
  system("ssh #{user_at_host} 'sudo apt-get update'")
  system("ssh #{user_at_host} 'sudo apt-get upgrade --assume-yes'")
  system("ssh #{user_at_host} 'sudo apt-get dist-upgrade --assume-yes'")
end

Save your changes and make /usr/local/scripts/update_da_boxen.rb executable:

$ sudo chmod 700 /usr/local/scripts/update_da_boxen.rb && sudo chown root:root /usr/local/scripts/update_da_boxen.rb

To ensure the example script above works, your remote SSH user must be added as a sudoer on the client host that will be included in the update pool:

# visudo

If you don't want to have to type a password to obtain sudo authorization, enter the following:

<YOURUSERNAME> ALL=(ALL:ALL) NOPASSWD:ALL

Replace <YOURUSERNAME> with the SSH user of the host that will be updated.

Cheers! 

Thursday, November 22, 2012

Install the Latest Oracle Java JDK in Ubuntu with Ruby


#!/usr/bin/env ruby
# Download Files at: http://www.oracle.com/technetwork/java/javase/downloads/java-se-jdk-7-download-432154.html
if ARGV[0].nil?
  puts "Usage #{$0} <path of downloaded oracle tgz file>"
else
  update_file = ARGV[0]
  if File.extname(update_file) == ".tgz" || File.basename(update_file)[-6..-1] == "tar.gz"
    java_root = `tar -tzf #{update_file}`.split("\/")[0]
    update_root = "/usr/lib/jvm"
    system("tar -xzvf #{update_file}") unless Dir.exists?("#{update_root}/#{java_root}")
    first_time_installing_java = false
    unless Dir.exists?("/usr/lib/jvm") 
      `mkdir /usr/lib/jvm`
      first_time_installing_java = true
    end
    `mv #{java_root} #{update_root}` unless Dir.exists?("#{update_root}/#{java_root}")
    if first_time_installing_java
      system("update-alternatives --install '/usr/bin/java' 'java' '#{update_root}/#{java_root}/bin/java' 1")
      system("update-alternatives --install '/usr/bin/javac' 'javac' '#{update_root}/#{java_root}/bin/javac' 1")
      system("update-alternatives --install '/usr/bin/javaws' 'javaws' '#{update_root}/#{java_root}/bin/javaws' 1")
    else
      system("update-alternatives --config java")
      system("update-alternatives --config javac")
      system("update-alternatives --config javaws")
    end
    print "Populate Username that Will Use the Mozilla Firefox Java Plugin: "
    username = STDIN.gets.chomp
    if username != "root"
      mozilla_java_plugin_dir = "/home/#{username}"
    else
      mozilla_java_plugin_dir = "/root/.mozilla/plugins"
    end
    puts "MOZILLA PLUGIN HOME DIR = #{mozilla_java_plugin_dir}/libnpjp2.so"
    `mkdir #{mozilla_java_plugin_dir}` unless Dir.exists?(mozilla_java_plugin_dir)
    `ln -sf #{update_root}/#{java_root}/jre/lib/amd64/libnpjp2.so #{mozilla_java_plugin_dir}`
    `ln -sf #{update_root}/#{java_root}`
  else
    puts "ERROR!!! This script only support .tgz or tar.gz Oracle Java files..."
    exit
  end
end

Friday, August 31, 2012

Installing the "curb" Ruby Gem in Windows



Download the Ruby DevKit and Extract into C:\Devkit:
https://github.com/downloads/oneclick/rubyinstaller/DevKit-tdm-32-4.5.2-20111229-1559-sfx.exe

Type the following command from a command prompt:
cd \Devkit
devkitvars.bat

Download this file and extract it into C:\Windows\Sytem32:
http://curl.haxx.se/gknw.net/7.27.0/dist-w32/curl-7.27.0-rtmp-ssh2-ssl-sspi-zlib-idn-static-bin-w32.zip

Download this file and extract it into C:\
http://curl.haxx.se/gknw.net/7.27.0/dist-w32/curl-7.27.0-devel-mingw32.zip

Finally, from the same command prompt, run the following command:
gem install curb -- --with-curl-lib=C:\curl-7.27.0-devel-mingw32\bin --with-curl-include=C:\curl-7.27.0-devel-mingw32\include

Friday, August 10, 2012

Wild Kill...Yeee-Haaah!!!

#!/bin/bash
ps -ef | grep $1 | awk '{print $2}' | while read pid; do kill -15 $pid; done

Save the script as wildkill.sh, make it executable:

chmod 755 wildkill.sh

and run it like this:

./wildkill.sh firefox

This will kill any process that contains the name firefox...be sure you know what you're killing because this script can be wild!

Yeee-Haaah!


Tuesday, July 17, 2012

haxor_android: streamlining monotonous mobile preparation prior to a security engagement



Periodic element class for security engagements on Android devices...requires the Anroid SDK. This package also requires a rooted device.
Create your own rendition of this class based on the README at: https://github.com/ninp0/kore_kit/tree/master/lib/kore_kit/telecom/mobile/android
Please note: You'll need to download and unzip extraxt dex2jar separately. Once extracted, create a symlink/shortcut to dex2jar.sh/dex2jar.bat (depending on your OS) CALLED "dex2jar" (NO EXTENSION) and place it in your PATH.

Cheers!

Tuesday, July 3, 2012

Introducing watirfall - An Automated Human Approach for Very Surgical Web Engagements


Decided to start working on a "smart" web-based class capable of behaving as if it were human.  This class can be used when a "surgical approach" is preferable during web security engagements.  This class currently works with the Firefox and Chrome browsers under both Linux and MacOSX.  It will allow you to drive a browser automatically, taking advantage of the built-in JavaScript engines found in the most popular browsers.  The following is an example of how to use it.

#!/usr/bin/env ruby
require './watirfall_config'
require './watirfall'

watirfall_config = WatirfallConfig.new
watirfall_config.as_firefox
wf = Watirfall.new(watirfall_config)
browser = wf.startup
browser.goto("http://www.ksl.com")
browser.text_field(:id => 'search_keyword').click
wf.type_as_human("watirfall") {|char| browser.text_field(:id => 'search_keyword').send_keys char}
browser.text_field(:id => 'search_keyword').send_keys :enter

If you feel you'd like to give this code a go, you can find it at https://github.com/ninp0/kore_kit/tree/master/lib/kore_kit/web/watirfall

For more information around driving this browser, the real sauce is found within watir-webdriver.

Cheers!

Wednesday, June 20, 2012

num_jenny - A Versatile Number Generator for the Security Mindset


A helpful ruby class for all sorts of security projects...this class is a member of my periodic table of classes.  Get it here:

https://github.com/ninp0/num_jenny 

It's pretty cool since this ruby class can be invoked to produce all types of numbers!

require './num_jenny'
# Only needed for last example
require 'creditcard'

n = NumJenny.new
puts n.range(:start_with => 0, :end_with => 10)

n.range(:start_with => 0, :end_with => 9999, :pad => true).each do |pin|
  puts "Attempting: #{pin}"
end

puts n.range(:start_with => 0, :end_with => 10, :random => true)

puts n.range(:start_with => 0, :end_with => 10, :pad => true, :random => true)

puts n.range(:start_with => 10, :end_with => 20, :pad => true)

n.range(:start_with => '1-493-555-0000', :end_with => '1-493-555-9999', :random => true).each do |phoneno|
  puts "ATDT#{phoneno}"
end

n.range(:start_with => "344543800000000", :end_with => "344543800999999", :random => true).each do |ccno|
  puts "Valid #{ccno.creditcard_type} Card Found: #{ccno}" if ccno.creditcard?
end


Cheers!

Thursday, June 14, 2012

Streamlining the Evolution of Application Development by Developing a Periodic Table of Classes


"The best designs are those that mimic life."

Remember the aforementioned statement, as it's critically important to reflect upon this statement as you read further.

Now, when we begin to imagine how the  building blocks of life interact and bond with one another at a sub-atomic >> atomic >> molecular level to form more self-aware and complex forms of life, it's easy to consider how those building blocks of life provide an excellent model to approach object oriented design within applications we write for ourselves and others.  "Phew, that was a long run-on sentence to consume..."  Run through it again.

Atoms, when bound with other atoms, produce various compounds (molecules).  For example, two Hydrogen atoms and one Oxygen atom when bound, form a single water molecule.  Now stay with me here, there's a point to all of this...that is if you haven't already started to understand why this is such a beautiful mindset to develop when designing applications.

When new programmers design code (and I've certainly been guilty of this as well), it's pretty common to write an application top-to-bottom...in one file.  Cool, it works...at least for the time being.  We do this because we have deadlines and we believe it's the fastest way to accomplish our goal or the goal of our employers.  It's time to think differently now that we're stepping back a bit further, thinking deeper, and really wrapping our minds around the bigger picture (all in the spirit of supporting maintainability, scalability, re-usability, interoperability, and my favorite collaboritive code to share with one another).  While we're here, let's ask ourselves...aren't we sick of copying and pasting code or worse yet, sick of writing the same code snippets over and over?  Me too.

An application can become harder and harder to manage over time as change presents itself.  Change is inevitable and this is especially true over longer periods of time - more folks depend on your application because hey, it makes their life easier right?  As a result, new requirements also present themselves - life never seems easy enough for most.  This is perfectly okay because it's this fundamental desire that can drive innovation and the progression within all of us.

Unfortunately, the top-to-bottom evolution process likely results in hundreds, if not thousands of lines of code all managed in a single file (or a small collections of files).  It's likely we can all agree that wrapping our minds around the logic contained within hundreds, if not thousands of lines of code in aggregate simply becomes...a huge pain in the ass.  In simpler terms this approach could be described as the, "Dodo Bird Approach" to development - a development design mindset that can't adapt to it's ever-changing and demanding environment - ultimately leading to its extinction.

Now, back to life's approach to design - particularly at the atomic/elemental level.  Looking at the periodic table of elements we start to notice a pattern - all elements/atoms contain certain properties that define how they behave.  For the context of this post, we will assert that the properties of an element/atom are synonymous to the methods/functions/subroutines found within a particular "elemental/atomic class."

What this means from the perspective of a developer is the need to create our own "periodic table of classes" - each with their own specific properties (public/private methods) small enough to share and use interchangeably to streamline the application development process.  The classes only focus on accomplishing a specific task and should only focus on that task.  An example of this may be an "element" designed to connect and interact with various types of databases.  We instantiate a collection of various "elemental/atomic classes" to create a complex organism (the application), capable of evolving in a manner that makes it more efficient through its evolution process.

In essence, when we think of object oriented design in this context we are actually thinking about how to design code in way that is meant to be shared, providing an opportunity to learn from one another.  This in turn promotes innovation, an efficient evolution process to support the ever-changing demands of our environment, and ultimately a means to present a better quality of life for one another.  Big things start really small and as a person smarter than Myself once said, simply put...the best designs are those that mimic life.

An excellent book around more design patterns is called, "Design Patterns: Elements of Reusable Object-Oriented Software"

I hope this mindset helps you as it's certainly helped me...

To see code using this design methodology check out this git repo:
https://github.com/ninp0/kore_kit

Cheers!


Thursday, May 31, 2012

Find all Plist Files in a Directory and Convert Contents into XML Files


Works on MacOSX Boxes:

#!/bin/bash
# Cheers!
find $1 -iname "*.plist" | while read f; do
  xml_file=`echo $f | sed "s/\.plist/\.xml/g"`
  echo "Found $f"

  echo -n "Converting to XML..."

  /usr/libexec/PlistBuddy -c 'Print' $f > $xml_file

  echo "complete."

  echo "XML file resides in: $xml_file"
done

Sunday, May 13, 2012

haxor_mailer.rb Class


# Send eMail from Many Different Mail Providers...cheers!

class HaxorMailer
  require 'pony'
  require 'highline/import'

  def populate_mail_password(user_name)
    mail_pass = HighLine.new.ask("#{user_name} password: ") {|q| q.echo = "\*" }
    return mail_pass.chomp
  end

  def pony_express(opts={})
    from = opts[:from]
    to = opts[:to]
    cc = opts[:cc]
    bcc = opts[:bcc]
    subject = opts[:subject]
    html_body = opts[:html_body]
    txt_body = opts[:txt_body] # If HTML is NOT supported or desired
    attachments_hash = {}
    opts[:attachments_hash].each do |attachment_name, attachment_path|
      attachments_hash[attachment_name] = File.binread(attachment_path)
    end

    debug = opts[:debug]

    address = opts[:address]
    port = opts[:port]
    user_name = opts[:user_name]
    if ! user_name.nil? && opts[:password].nil?
      password = self.populate_mail_password(user_name)
    else
      password = opts[:password]
    end

    if debug == true
      puts "DEBUG ENABLED: from=>#{from.inspect}, to=>#{to.inspect}, cc=>#{cc.inspect}, bcc=>#{bcc.inspect}, subject=>#{subject.inspect}, html_body=>#{html_body.inspect}, txt_body=>#{txt_body.inspect}, attachments=>#{attachments_hash.inspect}, address=>#{address.inspect}, port=>#{port.inspect}, user_name=>#{user_name.inspect}"
    end
    begin
      Pony.mail({
        :to => to,
        :cc => cc,
        :bcc => bcc,
        :from => from,
        :subject => subject,
        :html_body => html_body,
        :txt_body => txt_body,
        :attachments => attachments_hash,
        :via => :smtp,
        :via_options => {
          :address => address,
          :port => port,
          :enable_starttls_auto => true,
          :user_name => user_name,
          :password => password,
          :authentication => :plain,
          :domain => 'localhost.localdomain'
        }
      })
    rescue => e
      puts "ERROR!!! #{e.class} #{e} #{e.backtrace}"
    end
  end

  def gmail(opts={})
    opts[:address] = 'smtp.gmail.com'
    opts[:port] = 587
    self.pony_express(opts)
  end

  def hotmail(opts={})
    opts[:address] = 'smtp.live.com'
    opts[:port] = 587
    self.pony_express(opts)
  end

  def spoof(opts={})
    self.pony_express(opts)
  end

  def yahoo(opts={})
    opts[:address] = 'smtp.mail.yahoo.com'
    opts[:port] = 587
    self.pony_express(opts)
  end
end


Yeeesss! \o/ Here's how you instantiate the class:

require './haxor_mailer'
mail = HaxorMailer.new


# A quick way to use the supported/builtin methods to the class...
puts mail.gmail(:from => 'some.user@gmail.com', :to => 'some.other.user@some-email.com', :subject => 'Check this Out!', :html_body => '<!DOCTYPE HTML><html><head></head><body><div><a href="http://www.google.com">Google Rocks!</a></div></body></html>', :txt_body => 'Google Rocks! Navigate to: http://www.google.com with Your Internet Browser', :user_name => 'jake.hoopes@gmail.com', :attachments_hash => { 'mail1.txt' => './mail1.txt', 'mail2.txt' => './mail2.txt' }, :debug => true)

puts mail.hotmail(
:password=>'my_optional_passed_in_password', :from => 'some.user@hotmail.com', :to => 'some.other.user@some-email.com', :subject => 'Check this Out!', :html_body => '<!DOCTYPE HTML><html><head></head><body><div><a href="http://www.google.com">Google Rocks!</a></div></body></html>', :txt_body => 'Google Rocks! Navigate to: http://www.google.com with Your Internet Browser', :user_name => 'hoopes9@hotmail.com', :attachments_hash => { 'mail1.txt' => './mail1.txt', 'mail2.txt' => './mail2.txt' }, :debug => true)

puts mail.yahoo(:password=>'my_optional_passed_in_password', :from => '
some.user@yahoo.com', :to => 'some.other.user@some-email.com', :subject => 'Check this Out!', :html_body => '<!DOCTYPE HTML><html><head></head><body><div><a href="http://www.google.com">Google Rocks!</a></div></body></html>', :txt_body => 'Google Rocks! Navigate to: http://www.google.com with Your Internet Browser', :user_name => 'jake.hoopes@yahoo.com', :attachments_hash => { 'mail1.txt' => './mail1.txt', 'mail2.txt' => './mail2.txt' }, :debug => true)

puts mail.spoof(:from => 'spoof_mail_from@mailrelay.com', :to => '
some.other.user@some-email.com', :subject => 'Check this Out!', :html_body => '<!DOCTYPE HTML><html><head></head><body><div><a href="http://www.google.com">Google Rocks!</a></div></body></html>', :txt_body => 'Google Rocks! Navigate to: http://www.google.com with Your Internet Browser', :address => '127.0.0.1', :port => 25, :attachments_hash => { 'mail1.txt' => './mail1.txt', 'mail2.txt' => './mail2.txt' }, :debug => true)

Wednesday, March 28, 2012

Example: Simple Banner-Grabbing Modem Dialer Class Object (Using GNU Screen Wrapped in Ruby Goodness)


Here's an example of a class that can be leveraged to interact with modems in an effort to retrieve banners:

class AtHayesScreenDialer
  def initialize(screen_session_name, tty_dev_path, at_init_str="AT S7=45 S0=0 L1 V1 X4 &c1 E1 Q0")
    @screen_session_name = "#{screen_session_name}_#{rand(36**8).to_s(36)}"
    @screen_session_rc_file = "/tmp/screenrc_#{@screen_session_name}"
    @screen_session_log_file = "/tmp/screen_#{@screen_session_name}.log"
    @press_enter = sprintf("\r")
    @screen_cmd = "screen -p 0 -S #{@screen_session_name} -X stuff"

    begin
       # Setup GNU screen session's flushing of logfile buffer to be real-time
      File.open(@screen_session_rc_file, 'w') do |f|
        f.puts "logfile '#{@screen_session_log_file}'"
        f.puts "logfile flush 0"
      end
      # Custom rc file, log, and start in deteached mode with session name
      `screen -c #{@screen_session_rc_file} -L -d -m -S #{@screen_session_name} #{tty_dev_path}`
      sleep 3 # Let's wait a bit to ensure our screen session is ready...
      puts "\nIntializing Screen Session: #{@screen_session_name}"
      print "Sent '#{at_init_str}' Command..."
      `#{@screen_cmd} "#{at_init_str}#{@press_enter}"`
      sleep 1
      puts self.check_response
      return 0
    rescue => e
      puts "ERROR!!! #{e.class} #{e} #{e.backtrace}"
      self.close
      return 1
    end
  end

  def dump
    begin
      return File.read(@screen_session_log_file, :encoding=>"BINARY")
    rescue => e
      puts "ERROR!!! #{e.class} #{e} #{e.backtrace}"
      self.close
      return 1
    end
  end

  def close
    begin
      `screen -S #{@screen_session_name} -X quit`
      File.unlink(@screen_session_rc_file)
      File.unlink(@screen_session_log_file)
      return 0
    rescue => e
      puts "ERROR!!! #{e.class} #{e} #{e.backtrace}"
      return 1
    end
  end

  # Pass in 0 as param for key_delay_seconds if no key delay is desired...
  def press_key(key,times=1,key_delay_seconds=1)
    (1..times).each do
      printf("%s", key)
      sleep key_delay_seconds
    end
    return
  end

  def check_response
    serial_output = File.read(@screen_session_log_file, :encoding=>"BINARY")
    if serial_output.nil?
      response = nil
    else 
      response = serial_output.split(/\r\n/)[-1]
      unless response.nil?
        response = response.strip.chomp
      end
    end
    case response
      when "OK"
        return :OK
      when /CONNECT (9600|38400|115200)/
        return response
      when "ERROR"
        return :ERROR
      when /ATDT[0-9],[0-9]/
        return 0
      when "NO CARRIER"
        return :NO_CARRIER
      when "BUSY"
        return :BUSY
      when "VOICE"
        return :VOICE
    end
  end

  def command_mode
    begin
      `#{@screen_cmd} "+++"`
      sleep 1
      return 0
    rescue => e
      puts "ERROR!!! #{e.class} #{e} #{e.backtrace}"
      self.close
      return 1
    end
  end

  def data_mode
    begin
      `#{@screen_cmd} "ATO#{@press_enter}"`
      sleep 1
      return 0
    rescue => e
      puts "ERROR!!! #{e.class} #{e} #{e.backtrace}"
      self.close
      return 1
    end
  end

  def hangup
    begin
      print "\nHanging Up.  Sending 'ATH' Command..."
      `#{@screen_cmd} "ATH#{@press_enter}"`
      sleep 1
      puts self.check_response
      return 0
    rescue => e
      puts "ERROR!!! #{e.class} #{e} #{e.backtrace}"
      self.close
      return 1
    end
  end

  def reset
    begin
      print "\nHanging Up.  Sending 'ATH' Command..."
      `#{@screen_cmd} "ATZ#{@press_enter}"`
      sleep 1
      puts self.check_response
      return 0
    rescue => e
      puts "ERROR!!! #{e.class} #{e} #{e.backtrace}"
      self.close
      return 1
    end
  end

  def dial(phone_num, call_length_seconds, dial_prefix=nil, banner_grap=true)
    begin
      call_started = Time.now
      call_length_status = Time.now - call_started
      unless dial_prefix.nil?
        print "Dialing #{dial_prefix},#{phone_num} for a duration of #{call_length_seconds} seconds..."
        `#{@screen_cmd} "ATDT#{dial_prefix},#{phone_num}#{@press_enter}"`
      else
        print "Dialing #{phone_num} for a duration of #{call_length_seconds} seconds"
        `#{@screen_cmd} "ATDT#{phone_num}#{@press_enter}"`
      end
      until call_length_status > call_length_seconds
        current_response = self.check_response
        # If we get a CONNECT response, pass a few carriage returns to get a banner response...
        if current_response =~ /CONNECT (9600|38400|115200)/
          puts current_response
          `#{@screen_cmd} #{@press_enter}`
          sleep 1
          `#{@screen_cmd} #{@press_enter}`
          sleep 1
          `#{@screen_cmd} #{@press_enter}`
          `#{@screen_cmd} #{@press_enter}`
          `#{@screen_cmd} #{@press_enter}`
          sleep 3
          if banner_grap == true
            self.command_mode
            self.hangup 
            self.reset
            return 0
          #else
            #jack with the remote session
          end
        end
        print "."
        call_length_status = Time.now - call_started
        sleep 1
      end
      puts "CALL LENGTH MET (#{call_length_seconds} seconds)."
      self.command_mode
      self.hangup
      puts self.check_response
      return 0
    rescue => e
      puts "ERROR!!! #{e.class} #{e} #{e.backtrace}"
      self.close
      return 1
    end
  end
end