You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Note: I made a ninja edit to this on 19/2/24 to change the proposed fix.
When developing an exploit module that targets ARCH_JAVA for several platforms (win, linux, osx) that are not the java platform, i.e the exploit wants to execute a JSP payload, I noticed several problems occurring in the command shell payload.
The Issue(s)
Issue 1
The session has the wrong platform reported, it will always default to linux as that is the first platform listed in the JSP payload:
# ~/git/metasploit-framework/modules/payloads/singles/java/jsp_shell_reverse_tcp.rbdefinitialize(info={})super(merge_info(info,'Name'=>'Java JSP Command Shell, Reverse TCP Inline','Description'=>'Connect back to attacker and spawn a command shell','Author'=>['sf'],'License'=>MSF_LICENSE,'Platform'=>%w{linuxosxsolarisunixwin},'Arch'=>ARCH_JAVA,
And then later in Msf::Sessions::CommandShellOptions this happens:
defon_session(session)super# Configure input/output to match the payloadsession.user_input=self.user_inputifself.user_inputsession.user_output=self.user_outputifself.user_outputplatform=nilifself.platformandself.platform.kind_of?Msf::Module::PlatformListplatform=self.platform.platforms.first.realname.downcaseendifself.platformandself.platform.kind_of?Msf::Module::Platformplatform=self.platform.realname.downcaseend# a blank platform is *all* platforms and used by the generic modules, in that case only set this instance if it was# not previously set to a more specific value through some meanssession.platform=platformunlessplatform.blank? && !session.platform.blank?
Causing session.platform to always be set to linux (because of self.platform.platforms.first being used). So after my exploit gets a session, I see this:
msf6 exploit(multi/http/redacted) > sessions -l
Active sessions
===============
Id Name Type Information Connection
-- ---- ---- ----------- ----------
1 shell java/linux Shell Banner: Microsoft Windows [Version 10.0.20348.1547 192.168.86.42:4444 -> redacted
] (c) Microsoft Corp...
We can see the session type is java/linux but the banner clearly shows we have Windows shell session.
Issue 2
The code above that updates the session.platform is called after the FileDropper mixin runs, because of the call to super at the start of on_session.
So if we update the session.platform in CommandShellOptions::on_session, then FileDropper will have already run, and it needed to know the session platform to run correctly.
So if the session.platform is to be updated, it should occur before the call to super
Issue 3
This looks like a logic bug, I expect this was the intended behavior:
This works for me and could be the basis of resolving the issues mentioned above.
For a shell session with no platform, where the platform would have been selected as the first platform in a list of supported platforms, we can grep the banner and determine if it is Windows. This will enable FileDropper mixin to run, as well as the session being reported as the correct platform
We move the logic that updates the session platform/arch above the call to super, so things like FileDropper can benefit from the platform being correct.
What seems like a logic bug is resolved to ensure the platform is not overwritten if we did set one.
--- a/lib/msf/base/sessions/command_shell_options.rb+++ b/lib/msf/base/sessions/command_shell_options.rb@@ -32,7 +32,6 @@ module CommandShellOptions
end
def on_session(session)
- super
# Configure input/output to match the payload
session.user_input = self.user_input if self.user_input
@@ -40,7 +39,25 @@ module CommandShellOptions
platform = nil
if self.platform and self.platform.kind_of? Msf::Module::PlatformList
- platform = self.platform.platforms.first.realname.downcase++ # Update a sessions platform if we can, based on the shell's banner.+ # Do this before the call to super, so other on_session methods (like FileDropper.on_new_session called via+ # Payload.on_session) can benefit from the session platform being known.+ unless session.banner.blank?+ [+ 'Microsoft Windows [Version ', # Server 2022, 11, 10, 7, Vista+ 'Microsoft Windows XP [Version ', # XP+ 'Copyright Microsoft Corp', # 95, 98+ 'Microsoft(R) Windows NT(TM)', # NT4+ ].each do |windows_banner|+ if session.banner.include? windows_banner+ platform = 'windows'+ break+ end+ end+ end++ platform = self.platform.platforms.first.realname.downcase if platform.nil?
end
if self.platform and self.platform.kind_of? Msf::Module::Platform
platform = self.platform.realname.downcase
@@ -49,7 +66,7 @@ module CommandShellOptions
# a blank platform is *all* platforms and used by the generic modules, in that case only set this instance if it was
# not previously set to a more specific value through some means
- session.platform = platform unless platform.blank? && !session.platform.blank?+ session.platform = platform unless platform.blank? || !session.platform.blank?
if self.arch
if self.arch.kind_of?(Array)
@@ -59,6 +76,7 @@ module CommandShellOptions
end
end
+ super
end
end
Finally, if I run my exploit with this fix (and the pull request from #18844 to address a separate issue in the FileDropper mixin). I see the session correctly reported as java/windows:
msf6 exploit(multi/http/redacted) > sessions -l
Active sessions
===============
Id Name Type Information Connection
-- ---- ---- ----------- ----------
1 shell java/windows Shell Banner: Microsoft Windows [Version 10.0.20348.154 192.168.86.42:4444 -> redacted
7] (c) Microsoft Corp...
And the FileDropper mixin now correctly deletes the files I was expecting it to (because it now knowns the session is for windows).
Open question(s)
Dumping some final thoughts I had when looking into this:
Can we identify other platforms by grepping their banners too?
The text was updated successfully, but these errors were encountered:
This issue has been left open with no activity for a while now.
We get a lot of issues, so we currently close issues after 60 days of inactivity. It’s been at least 30 days since the last update here.
If we missed this issue or if you want to keep it open, please reply here. You can also add the label "not stale" to keep this issue open!
As a friendly reminder: the best way to see this issue, or any other, fixed is to open a Pull Request.
Note: I made a ninja edit to this on 19/2/24 to change the proposed fix.
When developing an exploit module that targets
ARCH_JAVA
for several platforms (win, linux, osx) that are not the java platform, i.e the exploit wants to execute a JSP payload, I noticed several problems occurring in the command shell payload.The Issue(s)
Issue 1
The session has the wrong platform reported, it will always default to
linux
as that is the first platform listed in the JSP payload:And then later in
Msf::Sessions::CommandShellOptions
this happens:Causing
session.platform
to always be set tolinux
(because ofself.platform.platforms.first
being used). So after my exploit gets a session, I see this:We can see the session type is
java/linux
but the banner clearly shows we have Windows shell session.Issue 2
The code above that updates the
session.platform
is called after theFileDropper
mixin runs, because of the call tosuper
at the start ofon_session
.So if we update the
session.platform
inCommandShellOptions::on_session
, thenFileDropper
will have already run, and it needed to know the session platform to run correctly.So if the session.platform is to be updated, it should occur before the call to
super
Issue 3
This looks like a logic bug, I expect this was the intended behavior:
Proposed Fix
This works for me and could be the basis of resolving the issues mentioned above.
FileDropper
mixin to run, as well as the session being reported as the correct platformsuper
, so things likeFileDropper
can benefit from the platform being correct.Finally, if I run my exploit with this fix (and the pull request from #18844 to address a separate issue in the
FileDropper
mixin). I see the session correctly reported asjava/windows
:And the
FileDropper
mixin now correctly deletes the files I was expecting it to (because it now knowns the session is for windows).Open question(s)
Dumping some final thoughts I had when looking into this:
The text was updated successfully, but these errors were encountered: