Skip to content

Instantly share code, notes, and snippets.

@chrahunt
Created May 7, 2014 17:05
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save chrahunt/89bd596fdb8485556c64 to your computer and use it in GitHub Desktop.
Save chrahunt/89bd596fdb8485556c64 to your computer and use it in GitHub Desktop.
Segmentation Fault Example
module Net; module SSH
# A general exception class, to act as the ancestor of all other Net::SSH
# exception classes.
class Exception < ::RuntimeError; end
# This exception is raised when authentication fails (whether it be
# public key authentication, password authentication, or whatever).
class AuthenticationFailed < Exception; end
# This exception is raised when a connection attempt times out.
class ConnectionTimeout < Exception; end
# This exception is raised when the remote host has disconnected
# unexpectedly.
class Disconnect < Exception; end
# This exception is primarily used internally, but if you have a channel
# request handler (see Net::SSH::Connection::Channel#on_request) that you
# want to fail in such a way that the server knows it failed, you can
# raise this exception in the handler and Net::SSH will translate that into
# a "channel failure" message.
class ChannelRequestFailed < Exception; end
# This is exception is primarily used internally, but if you have a channel
# open handler (see Net::SSH::Connection::Session#on_open_channel) and you
# want to fail in such a way that the server knows it failed, you can
# raise this exception in the handler and Net::SSH will translate that into
# a "channel open failed" message.
class ChannelOpenFailed < Exception
attr_reader :code, :reason
def initialize(code, reason)
@code, @reason = code, reason
super "#{reason} (#{code})"
end
end
# Base class for host key exceptions. When rescuing this exception, you can
# inspect the key fingerprint and, if you want to proceed anyway, simply call
# the remember_host! method on the exception, and then retry.
class HostKeyError < Exception
# the callback to use when #remember_host! is called
attr_writer :callback #:nodoc:
# situation-specific data describing the host (see #host, #port, etc.)
attr_writer :data #:nodoc:
# An accessor for getting at the data that was used to look up the host
# (see also #fingerprint, #host, #port, #ip, and #key).
def [](key)
@data && @data[key]
end
# Returns the fingerprint of the key for the host, which either was not
# found or did not match.
def fingerprint
@data && @data[:fingerprint]
end
# Returns the host name for the remote host, as reported by the socket.
def host
@data && @data[:peer] && @data[:peer][:host]
end
# Returns the port number for the remote host, as reported by the socket.
def port
@data && @data[:peer] && @data[:peer][:port]
end
# Returns the IP address of the remote host, as reported by the socket.
def ip
@data && @data[:peer] && @data[:peer][:ip]
end
# Returns the key itself, as reported by the remote host.
def key
@data && @data[:key]
end
# Tell Net::SSH to record this host and key in the known hosts file, so
# that subsequent connections will remember them.
def remember_host!
@callback.call
end
end
# Raised when the cached key for a particular host does not match the
# key given by the host, which can be indicative of a man-in-the-middle
# attack. When rescuing this exception, you can inspect the key fingerprint
# and, if you want to proceed anyway, simply call the remember_host!
# method on the exception, and then retry.
class HostKeyMismatch < HostKeyError; end
# Raised when there is no cached key for a particular host, which probably
# means that the host has simply not been seen before.
# When rescuing this exception, you can inspect the key fingerprint and, if
# you want to proceed anyway, simply call the remember_host! method on the
# exception, and then retry.
class HostKeyUnknown < HostKeyError; end
end; end
require 'dl/import'
require 'dl/types'
require 'dl'
require_relative 'errors'
module Pageant
# From Putty pageant.c
AGENT_MAX_MSGLEN = 8192
AGENT_COPYDATA_ID = 0x804e50ba
# The definition of the Windows methods and data structures used in
# communicating with the pageant process.
module Win
extend DL::Importer
dlload 'user32','kernel32','advapi32'
include DL::Win32Types
SIZEOF_DWORD = DL::SIZEOF_LONG
typealias("LPCTSTR", "char *") # From winnt.h
typealias("LPVOID", "void *") # From winnt.h
typealias("LPCVOID", "const void *") # From windef.h
typealias("LRESULT", "long") # From windef.h
typealias("WPARAM", "unsigned int *") # From windef.h
typealias("LPARAM", "long *") # From windef.h
typealias("PDWORD_PTR", "long *") # From basetsd.h
typealias("USHORT", "unsigned short") # From windef.h
# From winbase.h, winnt.h
INVALID_HANDLE_VALUE = -1
NULL = nil
PAGE_READWRITE = 0x0004
FILE_MAP_WRITE = 2
WM_COPYDATA = 74
#SMTO_NORMAL = 0 # From winuser.h
# args: lpClassName, lpWindowName
extern 'HWND FindWindow(LPCTSTR, LPCTSTR)'
# args: none
extern 'DWORD GetCurrentThreadId()'
# args: hFile, (ignored), flProtect, dwMaximumSizeHigh,
# dwMaximumSizeLow, lpName
extern 'HANDLE CreateFileMappingW(HANDLE, void *, DWORD, DWORD, ' +
'DWORD, LPCTSTR)'
# args: hFileMappingObject, dwDesiredAccess, dwFileOffsetHigh,
# dwfileOffsetLow, dwNumberOfBytesToMap
extern 'LPVOID MapViewOfFile(HANDLE, DWORD, DWORD, DWORD, DWORD)'
# args: lpBaseAddress
extern 'BOOL UnmapViewOfFile(LPCVOID)'
# args: hObject
extern 'BOOL CloseHandle(HANDLE)'
# args: hWnd, Msg, wParam, lParam, fuFlags, uTimeout, lpdwResult
extern 'LRESULT SendMessageTimeout(HWND, UINT, WPARAM, LPARAM, ' +
'UINT, UINT, PDWORD_PTR)'
# args: none
extern 'DWORD GetLastError()'
# args: none
extern 'HANDLE GetCurrentProcess()'
# args: hProcessHandle, dwDesiredAccess, (out) phNewTokenHandle
extern 'BOOL OpenProcessToken(HANDLE, DWORD, PHANDLE)'
# args: hTokenHandle, uTokenInformationClass,
# (out) lpTokenInformation, dwTokenInformationLength
# (out) pdwInfoReturnLength
extern 'BOOL GetTokenInformation(HANDLE, UINT, LPVOID, DWORD, ' +
'PDWORD)'
# args: (out) lpSecurityDescriptor, dwRevisionLevel
extern 'BOOL InitializeSecurityDescriptor(LPVOID, DWORD)'
# args: (out) lpSecurityDescriptor, lpOwnerSid, bOwnerDefaulted
extern 'BOOL SetSecurityDescriptorOwner(LPVOID, LPVOID, BOOL)'
# args: pSecurityDescriptor
extern 'BOOL IsValidSecurityDescriptor(LPVOID)'
extern 'void AuditFree(PVOID)'
# Constants needed for security attribute retrieval.
# Specifies the access mask corresponding to the desired access
# rights.
TOKEN_QUERY = 0x8
# The value of TOKEN_USER from the TOKEN_INFORMATION_CLASS enum.
TOKEN_USER_INFORMATION_CLASS = 1
# The initial revision level assigned to the security descriptor.
REVISION = 1
# Structs for security attribute functions.
TOKEN_USER = struct ['void * SID', 'DWORD ATTRIBUTES']
SECURITY_ATTRIBUTES = struct ['DWORD nLength',
'LPVOID lpSecurityDescriptor',
'BOOL bInheritHandle']
SECURITY_DESCRIPTOR = struct ['UCHAR Revision', 'UCHAR Sbz1',
'USHORT Control', 'LPVOID Owner',
'LPVOID Group', 'LPVOID Sacl',
'LPVOID Dacl']
def self.open_process_token
token_handle = DL::CPtr.malloc(DL::SIZEOF_VOIDP, DL::RUBY_FREE)
OpenProcessToken(Win.GetCurrentProcess, 0x8, token_handle.ref)
end
def self.raise_error_if_zero(result)
if result == 0
raise "Windows error: #{Win.GetLastError}"
end
end
end
end
require_relative 'mwe'
Pageant::Win.open_process_token
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment