Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place.
Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place.
Path: blob/master/lib/rex/proto/nuuo/client.rb
Views: 11704
# -*- coding: binary -*-12require 'rex/socket'34module Rex5module Proto6module Nuuo7# This class is a representation of a nuuo client8class Client9# @!attribute host10# @return [String] The nuuo server host11attr_accessor :host12# @!attribute port13# @return [Integer] The nuuo server port14attr_accessor :port15# @!attribute timeout16# @return [Integer] The connect/read timeout17attr_accessor :timeout18# @!attribute connection19# @return [IO] The connection established through Rex sockets20attr_accessor :connection21# @!attribute context22# @return [Hash] The Msf context where the connection belongs to23attr_accessor :context24# @!attribute ncs_version25# @return [String] NCS version used in session26attr_accessor :ncs_version27# @!attribute username28# @return [String] Username for NCS29attr_accessor :username30# @!attribute password31# @return [String] Password for NCS user32attr_accessor :password33# @!attribute user_session34# @return [String] ID for the user session35attr_accessor :user_session36# @!attribute config37# @return [Hash] ClientRequest configuration options38attr_accessor :config3940def initialize(opts = {})41self.host = opts[:host]42self.port = opts[:port] || 518043self.timeout = opts[:timeout] || 1044self.context = opts[:context] || {}45self.username = opts[:username]46self.password = opts[:password]47self.user_session = opts[:user_session]4849self.config = Nuuo::ClientRequest::DefaultConfig50end5152# Creates a connection through a Rex socket53#54# @return [Rex::Socket::Tcp]55def connect(temp: false)56return connection if connection && !temp57return create_tcp_connection(temp: temp)58end5960# Closes the connection61def close62if connection63connection.shutdown64connection.close unless connection.closed?65end6667self.connection = nil68end6970def send_recv(req, conn=nil, t=-1)71send_request(req, conn)72read_response(conn, t)73end7475def send_request(req, conn=nil)76conn ? conn.put(req.to_s) : connect.put(req.to_s)77end7879def read_response(conn=nil, t=-1)80res = Response.new81conn = connection unless conn8283return res if not t84Timeout.timeout((t < 0) ? nil : t) do85parse_status = nil86while (!conn.closed? &&87parse_status != Response::ParseCode::Completed &&88parse_status != Response::ParseCode::Error89)90begin91buff = conn.get_once92parse_status = res.parse(buff || '')93rescue ::Errno::EPIPE, ::EOFError, ::IOError94case res.state95when Response::ParseState::ProcessingHeader96res = nil97when Response::ParseState::ProcessingBody98res.error = :truncated99end100break101end102end103end104105res106end107108def user_session_header(opts)109val = nil110if opts['user_session']111val = opts['user_session']112elsif self.user_session113val = self.user_session114end115end116117def request_ping(opts={})118opts = self.config.merge(opts)119opts['headers'] ||= {}120opts['method'] = 'PING'121session = user_session_header(opts)122opts['headers']['User-Session-No'] = session if session123124ClientRequest.new(opts)125end126127def request_sendlicfile(opts={})128opts = self.config.merge(opts)129opts['headers'] ||= {}130opts['method'] = 'SENDLICFILE'131132session = user_session_header(opts)133opts['headers']['User-Session-No'] = session if session134opts['data'] = '' unless opts['data']135136opts['headers']['FileName'] = opts['file_name']137opts['headers']['Content-Length'] = opts['data'].length138139ClientRequest.new(opts)140end141142# GETCONFIG143# FileName:144# FileType: 1145# User-Session-No: <session-no>146# @return [ClientRequest]147def request_getconfig(opts={})148opts = self.config.merge(opts)149opts['headers'] ||= {}150opts['method'] = 'GETCONFIG'151152opts['headers']['FileName'] = opts['file_name']153opts['headers']['FileType'] = opts['file_type'] || 1154session = user_session_header(opts)155opts['headers']['User-Session-No'] = session if session156157ClientRequest.new(opts)158end159160# COMMITCONFIG161# FileName:162# FileType: 1163# Content-Length164# User-Session-No: <session-no>165#166# <data> filedata167# @return [ClientRequest]168def request_commitconfig(opts={})169opts = self.config.merge(opts)170opts['headers'] ||= {}171opts['method'] = 'COMMITCONFIG'172173opts['headers']['FileName'] = opts['file_name']174opts['headers']['FileType'] = opts['file_type'] || 1175176session = user_session_header(opts)177opts['headers']['User-Session-No'] = session if session178179opts['data'] = '' unless opts['data']180opts['headers']['Content-Length'] = opts['data'].length181182ClientRequest.new(opts)183end184185# USERLOGIN186# Version:187# Username:188# Password-Length:189# TimeZone-Length: 0190#191# <data> password192# @return [ClientRequest]193def request_userlogin(opts={})194opts = self.config.merge(opts)195opts['headers'] ||= {}196opts['method'] = 'USERLOGIN'197198# Account for version...199opts['headers']['Version'] = opts['server_version']200201username = nil202if opts['username'] && opts['username'] != ''203username = opts['username']204elsif self.username && self.username != ''205username = self.username206end207208opts['headers']['Username'] = username209210password = ''211if opts['password'] && opts['password'] != ''212password = opts['password']213elsif self.password && self.password != ''214password = self.password215end216opts['data'] = password217opts['headers']['Password-Length'] = password.length218219# Need to verify if this is needed220opts['headers']['TimeZone-Length'] = '0'221222ClientRequest.new(opts)223end224225# GETOPENALARM NUCM/1.0226# DeviceID: <number>227# SourceServer: <server-id>228# LastOne: <number>229# @return [ClientRequest]230def request_getopenalarm(opts={})231opts = self.config.merge(opts)232opts['headers'] ||= {}233opts['method'] = 'GETOPENALARM'234235opts['headers']['DeviceID'] = opts['device_id'] || 1236opts['headers']['SourceServer'] = opts['source_server'] || 1237opts['headers']['LastOne'] = opts['last_one'] || 1238239ClientRequest.new(opts)240end241242243private244245# Creates a TCP connection using Rex::Socket::Tcp246#247# @return [Rex::Socket::Tcp]248def create_tcp_connection(temp: false)249tcp_connection = Rex::Socket::Tcp.create(250'PeerHost' => host,251'PeerPort' => port.to_i,252'Context' => context,253'Timeout' => timeout254)255self.connection = tcp_connection unless temp256tcp_connection257end258259end260end261end262end263264265