--- /dev/null
+package HTTP::Body;
+
+use strict;
+
+use Carp qw[ ];
+use List::Util qw[ first ];
+use Scalar::Util qw[ blessed ];
+
+our $PARSERS = {
+ 'application/octet-stream' => 'HTTP::Body::Octetstream',
+ 'application/x-www-form-urlencoded' => 'HTTP::Body::Urlencoded',
+ 'multipart/form-data' => 'HTTP::Body::Multipart'
+};
+
+sub new {
+ my ( $class, $content_type, $content_length ) = @_;
+
+ unless ( @_ == 3 ) {
+ Carp::croak( $class, '->new( $content_type, $content_length )' );
+ }
+
+ my $type = first { index( lc($content_type), $_ ) >= 0 } keys %{ $PARSERS };
+ my $body = $PARSERS->{ $type || 'application/octet-stream' };
+
+ eval "require $body";
+
+ if ( $@ ) {
+ die $@;
+ }
+
+ my $self = {
+ buffer => '',
+ content_length => $content_length,
+ content_type => $content_type,
+ param => { },
+ upload => { }
+ };
+
+ bless( $self, $body );
+
+ return $self->init;
+}
+
+sub add {
+ Carp::croak('Define abstract method add() in implementation');
+}
+
+sub init {
+ return $_[0];
+}
+
+sub body {
+ my $self = shift;
+ $self->{body} = shift if @_;
+ return $self->{body};
+}
+
+sub content_length {
+ return shift->{content_length};
+}
+
+sub content_type {
+ return shift->{content_type};
+}
+
+sub param {
+ my $self = shift;
+
+ if ( @_ == 2 ) {
+
+ my ( $name, $value ) = @_;
+
+ if ( exists $self->{param}->{$name} ) {
+ for ( $self->{param}->{$name} ) {
+ $_ = [$_] unless ref($_) eq "ARRAY";
+ push( @$_, $value );
+ }
+ }
+ else {
+ $self->{param}->{$name} = $value;
+ }
+ }
+
+ return $self->{param};
+}
+
+sub upload {
+ my $self = shift;
+
+ if ( @_ == 2 ) {
+
+ my ( $name, $upload ) = @_;
+
+ if ( exists $self->{upload}->{$name} ) {
+ for ( $self->{upload}->{$name} ) {
+ $_ = [$_] unless ref($_) eq "ARRAY";
+ push( @$_, $upload );
+ }
+ }
+ else {
+ $self->{upload}->{$name} = $upload;
+ }
+ }
+
+ return $self->{upload};
+}
+
+1;
package HTTP::Body::Multipart;
use strict;
-use base 'HTTP::Body::Multipart::Parser';
+use base 'HTTP::Body';
+use bytes;
use File::Temp 0.14;
-sub new {
- my $class = shift;
-
- my $self = $class->SUPER::new(@_);
- $self->{param} = {};
- $self->{upload} = {};
+sub init {
+ my $self = shift;
+
+ unless ( $self->content_type =~ /boundary=\"?([^\";,]+)\"?/ ) {
+ my $content_type = $self->content_type;
+ Carp::croak("Invalid boudrary in content_type: '$content_type'");
+ }
+
+ $self->{boundary} = $1;
+ $self->{state} = 'preamble';
+ $self->{length} = $self->content_length - $self->content_length * 2;
return $self;
}
-sub handler {
- my ( $self, $part ) = @_;
+sub add {
+ my ( $self, $buffer ) = @_;
- if ( $part->{done} && $part->{size} == 0 ) {
+ unless ( defined $buffer ) {
+ $buffer = '';
+ }
+
+ $self->{buffer} .= $buffer;
+ $self->{length} += length($buffer);
+
+ while (1) {
+
+ if ( $self->{state} eq 'done' ) {
+ return 0;
+ }
+
+ elsif ( $self->{state} =~ /^(preamble|boundary|header|body)$/ ) {
+ my $method = "parse_$1";
+ return $self->{length} unless $self->$method;
+ }
+
+ else {
+ Carp::croak('Unknown state');
+ }
+ }
+}
+
+sub boundary {
+ my $self = shift;
+ $self->{boundary} = shift if @_;
+ return $self->{boundary};
+}
+
+sub boundary_begin {
+ return "--" . shift->boundary;
+}
+
+sub boundary_end {
+ return shift->boundary_begin . "--";
+}
+
+sub crlf {
+ return "\x0d\x0a";
+}
+
+sub delimiter_begin {
+ my $self = shift;
+ return $self->crlf . $self->boundary_begin;
+}
+
+sub delimiter_end {
+ my $self = shift;
+ return $self->crlf . $self->boundary_end;
+}
+
+sub parse_preamble {
+ my $self = shift;
+
+ my $index = index( $self->{buffer}, $self->boundary_begin );
+
+ unless ( $index >= 0 ) {
return 0;
}
- unless ( $self->{seen}->{"$part"}++ ) {
+ # replace preamble with CRLF so we can match dash-boundary as delimiter
+ substr( $self->{buffer}, 0, $index, $self->crlf );
- my $disposition = $part->{headers}->{'Content-Disposition'};
- my ($name) = $disposition =~ / name="?([^\";]+)"?"/;
- my ($filename) = $disposition =~ / filename="?([^\"]+)"?/;
+ $self->{state} = 'boundary';
- $part->{name} = $name;
- $part->{filename} = $filename;
+ return 1;
+}
- if ($filename) {
+sub parse_boundary {
+ my $self = shift;
- my $fh = File::Temp->new( UNLINK => 0 );
+ if ( index( $self->{buffer}, $self->delimiter_begin . $self->crlf ) == 0 ) {
- $part->{fh} = $fh;
- $part->{tempname} = $fh->filename;
- }
+ substr( $self->{buffer}, 0, length( $self->delimiter_begin ) + 2, '' );
+ $self->{current} = {};
+ $self->{state} = 'header';
+
+ return 1;
}
- if ( $part->{filename} ) {
- $part->{fh}->write( delete $part->{data} );
+ if ( index( $self->{buffer}, $self->delimiter_end . $self->crlf ) == 0 ) {
+ $self->{current} = {};
+ $self->{state} = 'done';
+ return 0;
+ }
+
+ return 0;
+}
+
+sub parse_header {
+ my $self = shift;
+
+ my $crlf = $self->crlf;
+ my $index = index( $self->{buffer}, $crlf . $crlf );
+
+ unless ( $index >= 0 ) {
+ return 0;
}
- if ( $part->{done} ) {
+ my $header = substr( $self->{buffer}, 0, $index );
- if ( $part->{filename} ) {
- $self->upload( $part->{name}, $part );
- }
+ substr( $self->{buffer}, 0, $index + 4, '' );
+ my @headers;
+ for ( split /$crlf/, $header ) {
+ if (s/^[ \t]+//) {
+ $headers[-1] .= $_;
+ }
else {
- $self->param( $part->{name}, $part->{data} );
+ push @headers, $_;
}
}
-}
-sub param {
- my $self = shift;
+ my $token = qr/[^][\x00-\x1f\x7f()<>@,;:\\"\/?={} \t]+/;
- if ( @_ == 2 ) {
+ for my $header (@headers) {
- my ( $name, $value ) = @_;
+ $header =~ s/^($token):[\t ]*//;
- if ( exists $self->{param}->{$name} ) {
- for ( $self->{param}->{$name} ) {
+ ( my $field = $1 ) =~ s/\b(\w)/uc($1)/eg;
+
+ if ( exists $self->{current}->{headers}->{$field} ) {
+ for ( $self->{current}->{headers}->{$field} ) {
$_ = [$_] unless ref($_) eq "ARRAY";
- push( @$_, $value );
+ push( @$_, $header );
}
}
else {
- $self->{param}->{$name} = $value;
+ $self->{current}->{headers}->{$field} = $header;
}
}
- return $self->{param};
+ $self->{state} = 'body';
+
+ return 1;
}
-sub upload {
+sub parse_body {
my $self = shift;
- if ( @_ == 2 ) {
+ my $index = index( $self->{buffer}, $self->delimiter_begin );
- my ( $name, $upload ) = @_;
+ if ( $index < 0 ) {
- if ( exists $self->{upload}->{$name} ) {
- for ( $self->{upload}->{$name} ) {
- $_ = [$_] unless ref($_) eq "ARRAY";
- push( @$_, $upload );
- }
+ # make sure we have enough buffer to detect end delimiter
+ my $length = length( $self->{buffer} ) - ( length( $self->delimiter_end ) + 2 );
+
+ unless ( $length > 0 ) {
+ return 0;
}
- else {
- $self->{upload}->{$name} = $upload;
+
+ $self->{current}->{data} .= substr( $self->{buffer}, 0, $length, '' );
+ $self->{current}->{size} += $length;
+ $self->{current}->{done} = 0;
+
+ $self->handler( $self->{current} );
+
+ return 0;
+ }
+
+ $self->{current}->{data} .= substr( $self->{buffer}, 0, $index, '' );
+ $self->{current}->{size} += $index;
+ $self->{current}->{done} = 1;
+
+ $self->handler( $self->{current} );
+
+ $self->{state} = 'boundary';
+
+ return 1;
+}
+
+sub handler {
+ my ( $self, $part ) = @_;
+
+ if ( $part->{done} && $part->{size} == 0 ) {
+ return 0;
+ }
+
+ unless ( $self->{seen}->{"$part"}++ ) {
+
+ my $disposition = $part->{headers}->{'Content-Disposition'};
+ my ($name) = $disposition =~ / name="?([^\";]+)"?"/;
+ my ($filename) = $disposition =~ / filename="?([^\"]+)"?/;
+
+ $part->{name} = $name;
+ $part->{filename} = $filename;
+
+ if ($filename) {
+
+ my $fh = File::Temp->new( UNLINK => 0 );
+
+ $part->{fh} = $fh;
+ $part->{tempname} = $fh->filename;
}
}
- return $self->{upload};
+ if ( $part->{filename} ) {
+ $part->{fh}->write( delete $part->{data} );
+ }
+
+ if ( $part->{done} ) {
+
+ if ( $part->{filename} ) {
+
+ my $fh = delete $part->{fh};
+ $fh->close;
+
+ $self->upload( $part->{name}, $part );
+ }
+
+ else {
+ $self->param( $part->{name}, $part->{data} );
+ }
+ }
}
1;
--- /dev/null
+package HTTP::Body::Octetstream;
+
+use strict;
+use base 'HTTP::Body';
+use bytes;
+
+use File::Temp 0.14;
+
+1;
--- /dev/null
+package HTTP::Body::Urlencoded;
+
+use strict;
+use base 'HTTP::Body';
+use bytes;
+
+1;
--- /dev/null
+------------0xKhTmLbOuNdArY\r
+Content-Disposition: form-data; name="text1"\r
+\r
+Ratione accusamus aspernatur aliquam\r
+------------0xKhTmLbOuNdArY\r
+Content-Disposition: form-data; name="text2"\r
+\r
+\r
+------------0xKhTmLbOuNdArY\r
+Content-Disposition: form-data; name="select"\r
+\r
+A\r
+------------0xKhTmLbOuNdArY\r
+Content-Disposition: form-data; name="select"\r
+\r
+B\r
+------------0xKhTmLbOuNdArY\r
+Content-Disposition: form-data; name="textarea"\r
+\r
+Voluptatem cumque voluptate sit recusandae at. Et quas facere rerum unde esse. Sit est et voluptatem. Vel temporibus velit neque odio non.\r
+\r
+Molestias rerum ut sapiente facere repellendus illo. Eum nulla quis aut. Quidem voluptas vitae ipsam officia voluptatibus eveniet. Aspernatur cupiditate ratione aliquam quidem corrupti. Eos sunt rerum non optio culpa.\r
+------------0xKhTmLbOuNdArY\r
+Content-Disposition: form-data; name="upload"; filename="hello.pl"\r
+Content-Type: application/octet-stream\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+------------0xKhTmLbOuNdArY\r
+Content-Disposition: form-data; name="upload"; filename="hello.pl"\r
+Content-Type: application/octet-stream\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+------------0xKhTmLbOuNdArY\r
+Content-Disposition: form-data; name="upload1"; filename=""\r
+\r
+\r
+------------0xKhTmLbOuNdArY\r
+Content-Disposition: form-data; name="upload2"; filename="hello.pl"\r
+Content-Type: application/octet-stream\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+------------0xKhTmLbOuNdArY--\r
--- /dev/null
+---
+Content-Length: 1559
+Content-Type: multipart/form-data; boundary=----------0xKhTmLbOuNdArY
+User-Agent: 'Mozilla/5.0 (Macintosh; U; PPC Mac OS X; en) AppleWebKit/312.1 (KHTML, like Gecko) Safari/312'
--- /dev/null
+--LYNX\r
+Content-Disposition: form-data; name="text1"\r
+Content-Type: text/plain; charset=utf-8\r
+\r
+Ratione accusamus aspernatur aliquam\r
+--LYNX\r
+Content-Disposition: form-data; name="text2"\r
+Content-Type: text/plain; charset=utf-8\r
+\r
+\r
+--LYNX\r
+Content-Disposition: form-data; name="select"\r
+Content-Type: text/plain; charset=utf-8\r
+\r
+A\r
+--LYNX\r
+Content-Disposition: form-data; name="select"\r
+Content-Type: text/plain; charset=utf-8\r
+\r
+B\r
+--LYNX\r
+Content-Disposition: form-data; name="textarea"\r
+Content-Type: text/plain; charset=utf-8\r
+\r
+Voluptatem cumque voluptate sit recusandae at. Et quas facere rerum unde esse. Sit est et voluptatem. Vel temporibus velit neque odio non.\r
+\r
+Molestias rerum ut sapiente facere repellendus illo. Eum nulla quis aut. Quidem voluptas vitae ipsam officia voluptatibus eveniet. Aspernatur cupiditate ratione aliquam quidem corrupti. Eos sunt rerum non optio culpa.\r
+\r
+--LYNX\r
+Content-Disposition: form-data; name="upload"; filename="/Users/chansen/hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+--LYNX\r
+Content-Disposition: form-data; name="upload"; filename="/Users/chansen/hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+--LYNX\r
+Content-Disposition: form-data; name="upload1"; filename=""\r
+Content-Type: text/plain\r
+\r
+\r
+--LYNX\r
+Content-Disposition: form-data; name="upload2"; filename="/Users/chansen/hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+--LYNX--\r
--- /dev/null
+---
+Content-Length: 1585
+Content-Type: multipart/form-data; boundary=LYNX
+User-Agent: Lynx/2.8.5rel.2 libwww-FM/2.14
--- /dev/null
+--00000000000000000000000000000000\r
+Content-Disposition: form-data; name="text1"\r
+\r
+Ratione accusamus aspernatur aliquam\r
+--00000000000000000000000000000000\r
+Content-Disposition: form-data; name="text2"\r
+\r
+\r
+--00000000000000000000000000000000\r
+Content-Disposition: form-data; name="select"\r
+\r
+A\r
+--00000000000000000000000000000000\r
+Content-Disposition: form-data; name="select"\r
+\r
+B\r
+--00000000000000000000000000000000\r
+Content-Disposition: form-data; name="textarea"\r
+\r
+Voluptatem cumque voluptate sit recusandae at. Et quas facere rerum unde esse. Sit est et voluptatem. Vel temporibus velit neque odio non.
+
+Molestias rerum ut sapiente facere repellendus illo. Eum nulla quis aut. Quidem voluptas vitae ipsam officia voluptatibus eveniet. Aspernatur cupiditate ratione aliquam quidem corrupti. Eos sunt rerum non optio culpa.\r
+--00000000000000000000000000000000\r
+Content-Disposition: form-data; name="upload"; filename="hello.pl"\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+--00000000000000000000000000000000\r
+Content-Disposition: form-data; name="upload"; filename="hello.pl"\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+--00000000000000000000000000000000\r
+Content-Disposition: form-data; name="upload1"; filename=""\r
+\r
+\r
+--00000000000000000000000000000000\r
+Content-Disposition: form-data; name="upload2"; filename="hello.pl"\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+--00000000000000000000000000000000--\r
--- /dev/null
+---
+Content-Length: 1507
+Content-Type: multipart/form-data; boundary=00000000000000000000000000000000
+User-Agent: ELinks/0.9.2 (textmode; Darwin 7.9.0 Power Macintosh; 167x36)
--- /dev/null
+-----------------------------168071508944249\r
+Content-Disposition: form-data; name="text1"\r
+Content-Type: text/plain; charset="utf-8"\r
+\r
+Ratione accusamus aspernatur aliquam\r
+-----------------------------168071508944249\r
+Content-Disposition: form-data; name="text2"\r
+Content-Type: text/plain; charset="utf-8"\r
+\r
+\r
+-----------------------------168071508944249\r
+Content-Disposition: form-data; name="select"\r
+Content-Type: text/plain; charset="utf-8"\r
+\r
+A\r
+-----------------------------168071508944249\r
+Content-Disposition: form-data; name="select"\r
+Content-Type: text/plain; charset="utf-8"\r
+\r
+B\r
+-----------------------------168071508944249\r
+Content-Disposition: form-data; name="textarea"\r
+Content-Type: text/plain; charset="utf-8"\r
+\r
+Voluptatem cumque voluptate sit recusandae at. Et quas facere rerum unde esse. Sit est et voluptatem. Vel temporibus velit neque odio non.\r
+\r
+Molestias rerum ut sapiente facere repellendus illo. Eum nulla quis aut. Quidem voluptas vitae ipsam officia voluptatibus eveniet. Aspernatur cupiditate ratione aliquam quidem corrupti. Eos sunt rerum non optio culpa.\r
+-----------------------------168071508944249\r
+Content-Disposition: form-data; name="upload"; filename="hello.pl"\r
+Content-Type: application/octet-stream\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------168071508944249\r
+Content-Disposition: form-data; name="upload"; filename="hello.pl"\r
+Content-Type: application/octet-stream\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------168071508944249\r
+Content-Disposition: form-data; name="upload1"; filename=""\r
+Content-Type: text/plain; charset="utf-8"\r
+\r
+\r
+-----------------------------168071508944249\r
+Content-Disposition: form-data; name="upload2"; filename="hello.pl"\r
+Content-Type: application/octet-stream\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------168071508944249--\r
--- /dev/null
+---
+Content-Length: 1987
+Content-Type: multipart/form-data; boundary=---------------------------168071508944249
+User-Agent: Mozilla/4.0 (compatible; MSIE 5.23; Mac_PowerPC)
--- /dev/null
+-----------------------------168072824752491622650073\r
+Content-Disposition: form-data; name="text1"\r
+\r
+Ratione accusamus aspernatur aliquam\r
+-----------------------------168072824752491622650073\r
+Content-Disposition: form-data; name="text2"\r
+\r
+\r
+-----------------------------168072824752491622650073\r
+Content-Disposition: form-data; name="select"\r
+\r
+A\r
+-----------------------------168072824752491622650073\r
+Content-Disposition: form-data; name="select"\r
+\r
+B\r
+-----------------------------168072824752491622650073\r
+Content-Disposition: form-data; name="textarea"\r
+\r
+Voluptatem cumque voluptate sit recusandae at. Et quas facere rerum unde esse. Sit est et voluptatem. Vel temporibus velit neque odio non.\r
+\r
+Molestias rerum ut sapiente facere repellendus illo. Eum nulla quis aut. Quidem voluptas vitae ipsam officia voluptatibus eveniet. Aspernatur cupiditate ratione aliquam quidem corrupti. Eos sunt rerum non optio culpa.\r
+-----------------------------168072824752491622650073\r
+Content-Disposition: form-data; name="upload"; filename="hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------168072824752491622650073\r
+Content-Disposition: form-data; name="upload"; filename="hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------168072824752491622650073\r
+Content-Disposition: form-data; name="upload1"; filename=""\r
+Content-Type: application/octet-stream\r
+\r
+\r
+-----------------------------168072824752491622650073\r
+Content-Disposition: form-data; name="upload2"; filename="hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------168072824752491622650073--\r
--- /dev/null
+---
+Content-Length: 1817
+Content-Type: multipart/form-data; boundary=---------------------------168072824752491622650073
+User-Agent: Mozilla/5.0 (Macintosh; U; PPC Mac OS X Mach-O; en-US; rv:1.7.8) Gecko/20050511 Firefox/1.0.4
--- /dev/null
+-----------------------------7d53c2922c\r
+Content-Disposition: form-data; name="text1"\r
+\r
+Ratione accusamus aspernatur aliquam\r
+-----------------------------7d53c2922c\r
+Content-Disposition: form-data; name="text2"\r
+\r
+\r
+-----------------------------7d53c2922c\r
+Content-Disposition: form-data; name="select"\r
+\r
+A\r
+-----------------------------7d53c2922c\r
+Content-Disposition: form-data; name="select"\r
+\r
+B\r
+-----------------------------7d53c2922c\r
+Content-Disposition: form-data; name="textarea"\r
+\r
+Voluptatem cumque voluptate sit recusandae at. Et quas facere rerum unde esse. Sit est et voluptatem. Vel temporibus velit neque odio non.\r
+\r
+Molestias rerum ut sapiente facere repellendus illo. Eum nulla quis aut. Quidem voluptas vitae ipsam officia voluptatibus eveniet. Aspernatur cupiditate ratione aliquam quidem corrupti. Eos sunt rerum non optio culpa.\r
+-----------------------------7d53c2922c\r
+Content-Disposition: form-data; name="upload"; filename="C:\WINDOWS\Skrivbord\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d53c2922c\r
+Content-Disposition: form-data; name="upload"; filename="C:\WINDOWS\Skrivbord\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d53c2922c\r
+Content-Disposition: form-data; name="upload1"; filename=""\r
+Content-Type: application/octet-stream\r
+\r
+\r
+-----------------------------7d53c2922c\r
+Content-Disposition: form-data; name="upload2"; filename="C:\WINDOWS\Skrivbord\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d53c2922c--\r
--- /dev/null
+---
+Content-Length: 1740
+Content-Type: multipart/form-data; boundary=---------------------------7d53c2922c
+User-Agent: Mozilla/4.0 (compatible; MSIE 4.01; Windows 98)
--- /dev/null
+------------Bv684bhJBhreYbdRAUxHhF\r
+Content-Disposition: form-data; name="text1"\r
+\r
+Ratione accusamus aspernatur aliquam\r
+------------Bv684bhJBhreYbdRAUxHhF\r
+Content-Disposition: form-data; name="text2"\r
+\r
+\r
+------------Bv684bhJBhreYbdRAUxHhF\r
+Content-Disposition: form-data; name="select"\r
+\r
+A\r
+------------Bv684bhJBhreYbdRAUxHhF\r
+Content-Disposition: form-data; name="select"\r
+\r
+B\r
+------------Bv684bhJBhreYbdRAUxHhF\r
+Content-Disposition: form-data; name="textarea"\r
+\r
+Voluptatem cumque voluptate sit recusandae at. Et quas facere rerum unde esse. Sit est et voluptatem. Vel temporibus velit neque odio non.\r
+\r
+Molestias rerum ut sapiente facere repellendus illo. Eum nulla quis aut. Quidem voluptas vitae ipsam officia voluptatibus eveniet. Aspernatur cupiditate ratione aliquam quidem corrupti. Eos sunt rerum non optio culpa.\r
+------------Bv684bhJBhreYbdRAUxHhF\r
+Content-Disposition: form-data; name="upload"; filename="hello.pl"\r
+Content-Type: application/octet-stream\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+------------Bv684bhJBhreYbdRAUxHhF\r
+Content-Disposition: form-data; name="upload"; filename="hello.pl"\r
+Content-Type: application/octet-stream\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+------------Bv684bhJBhreYbdRAUxHhF\r
+Content-Disposition: form-data; name="upload1"; filename=""\r
+\r
+\r
+------------Bv684bhJBhreYbdRAUxHhF\r
+Content-Disposition: form-data; name="upload2"; filename="hello.pl"\r
+Content-Type: application/octet-stream\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+------------Bv684bhJBhreYbdRAUxHhF--\r
--- /dev/null
+---
+Content-Length: 1629
+Content-Type: multipart/form-data; boundary=----------Bv684bhJBhreYbdRAUxHhF
+User-Agent: Mozilla/4.0 (compatible; MSIE 6.0; Mac_PowerPC Mac OS X; en) Opera 8.01
--- /dev/null
+-----------------------------7d52bc247fc\r
+Content-Disposition: form-data; name="text1"\r
+\r
+Ratione accusamus aspernatur aliquam\r
+-----------------------------7d52bc247fc\r
+Content-Disposition: form-data; name="text2"\r
+\r
+\r
+-----------------------------7d52bc247fc\r
+Content-Disposition: form-data; name="select"\r
+\r
+A\r
+-----------------------------7d52bc247fc\r
+Content-Disposition: form-data; name="select"\r
+\r
+B\r
+-----------------------------7d52bc247fc\r
+Content-Disposition: form-data; name="textarea"\r
+\r
+Voluptatem cumque voluptate sit recusandae at. Et quas facere rerum unde esse. Sit est et voluptatem. Vel temporibus velit neque odio non.\r
+\r
+Molestias rerum ut sapiente facere repellendus illo. Eum nulla quis aut. Quidem voluptas vitae ipsam officia voluptatibus eveniet. Aspernatur cupiditate ratione aliquam quidem corrupti. Eos sunt rerum non optio culpa.\r
+-----------------------------7d52bc247fc\r
+Content-Disposition: form-data; name="upload"; filename="C:\WINDOWS\Skrivbord\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d52bc247fc\r
+Content-Disposition: form-data; name="upload"; filename="C:\WINDOWS\Skrivbord\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d52bc247fc\r
+Content-Disposition: form-data; name="upload1"; filename=""\r
+Content-Type: application/octet-stream\r
+\r
+\r
+-----------------------------7d52bc247fc\r
+Content-Disposition: form-data; name="upload2"; filename="C:\WINDOWS\Skrivbord\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d52bc247fc--\r
--- /dev/null
+---
+Content-Length: 1750
+Content-Type: multipart/form-data; boundary=---------------------------7d52bc247fc
+User-Agent: Mozilla/4.0 (compatible; MSIE 4.01; Windows 98)
--- /dev/null
+-----------------------------7d53941f40118\r
+Content-Disposition: form-data; name="text1"\r
+\r
+Ratione accusamus aspernatur aliquam\r
+-----------------------------7d53941f40118\r
+Content-Disposition: form-data; name="text2"\r
+\r
+\r
+-----------------------------7d53941f40118\r
+Content-Disposition: form-data; name="select"\r
+\r
+A\r
+-----------------------------7d53941f40118\r
+Content-Disposition: form-data; name="select"\r
+\r
+B\r
+-----------------------------7d53941f40118\r
+Content-Disposition: form-data; name="textarea"\r
+\r
+Voluptatem cumque voluptate sit recusandae at. Et quas facere rerum unde esse. Sit est et voluptatem. Vel temporibus velit neque odio non.\r
+\r
+Molestias rerum ut sapiente facere repellendus illo. Eum nulla quis aut. Quidem voluptas vitae ipsam officia voluptatibus eveniet. Aspernatur cupiditate ratione aliquam quidem corrupti. Eos sunt rerum non optio culpa.\r
+-----------------------------7d53941f40118\r
+Content-Disposition: form-data; name="upload"; filename="C:\Documents and Settings\Administrator\Desktop\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d53941f40118\r
+Content-Disposition: form-data; name="upload"; filename="C:\Documents and Settings\Administrator\Desktop\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d53941f40118\r
+Content-Disposition: form-data; name="upload1"; filename=""\r
+Content-Type: application/octet-stream\r
+\r
+\r
+-----------------------------7d53941f40118\r
+Content-Disposition: form-data; name="upload2"; filename="C:\Documents and Settings\Administrator\Desktop\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d53941f40118--\r
--- /dev/null
+---
+Content-Length: 1851
+Content-Type: multipart/form-data; boundary=---------------------------7d53941f40118
+User-Agent: Mozilla/4.0 (compatible; MSIE 5.01; Windows NT 5.0)
--- /dev/null
+-----------------------------7d561c5012e\r
+Content-Disposition: form-data; name="text1"\r
+\r
+Ratione accusamus aspernatur aliquam\r
+-----------------------------7d561c5012e\r
+Content-Disposition: form-data; name="text2"\r
+\r
+\r
+-----------------------------7d561c5012e\r
+Content-Disposition: form-data; name="select"\r
+\r
+A\r
+-----------------------------7d561c5012e\r
+Content-Disposition: form-data; name="select"\r
+\r
+B\r
+-----------------------------7d561c5012e\r
+Content-Disposition: form-data; name="textarea"\r
+\r
+Voluptatem cumque voluptate sit recusandae at. Et quas facere rerum unde esse. Sit est et voluptatem. Vel temporibus velit neque odio non.\r
+\r
+Molestias rerum ut sapiente facere repellendus illo. Eum nulla quis aut. Quidem voluptas vitae ipsam officia voluptatibus eveniet. Aspernatur cupiditate ratione aliquam quidem corrupti. Eos sunt rerum non optio culpa.\r
+-----------------------------7d561c5012e\r
+Content-Disposition: form-data; name="upload"; filename="C:\Documents and Settings\Administrator\Desktop\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d561c5012e\r
+Content-Disposition: form-data; name="upload"; filename=""\r
+Content-Type: application/octet-stream\r
+\r
+\r
+-----------------------------7d561c5012e\r
+Content-Disposition: form-data; name="upload1"; filename="C:\Documents and Settings\Administrator\Desktop\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d561c5012e\r
+Content-Disposition: form-data; name="upload2"; filename="C:\Documents and Settings\Administrator\Desktop\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d561c5012e--\r
--- /dev/null
+---
+Content-Length: 1831
+Content-Type: multipart/form-data; boundary=---------------------------7d561c5012e
+User-Agent: Mozilla/4.0 (compatible; MSIE 5.5; Windows NT 5.0)
--- /dev/null
+-----------------------------7d534d1d60150\r
+Content-Disposition: form-data; name="text1"\r
+\r
+Ratione accusamus aspernatur aliquam\r
+-----------------------------7d534d1d60150\r
+Content-Disposition: form-data; name="text2"\r
+\r
+\r
+-----------------------------7d534d1d60150\r
+Content-Disposition: form-data; name="select"\r
+\r
+A\r
+-----------------------------7d534d1d60150\r
+Content-Disposition: form-data; name="select"\r
+\r
+B\r
+-----------------------------7d534d1d60150\r
+Content-Disposition: form-data; name="textarea"\r
+\r
+Voluptatem cumque voluptate sit recusandae at. Et quas facere rerum unde esse. Sit est et voluptatem. Vel temporibus velit neque odio non.\r
+\r
+Molestias rerum ut sapiente facere repellendus illo. Eum nulla quis aut. Quidem voluptas vitae ipsam officia voluptatibus eveniet. Aspernatur cupiditate ratione aliquam quidem corrupti. Eos sunt rerum non optio culpa.\r
+-----------------------------7d534d1d60150\r
+Content-Disposition: form-data; name="upload"; filename="C:\Documents and Settings\Administrator\Desktop\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d534d1d60150\r
+Content-Disposition: form-data; name="upload"; filename=""\r
+Content-Type: application/octet-stream\r
+\r
+\r
+-----------------------------7d534d1d60150\r
+Content-Disposition: form-data; name="upload1"; filename="C:\Documents and Settings\Administrator\Desktop\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d534d1d60150\r
+Content-Disposition: form-data; name="upload2"; filename="C:\Documents and Settings\Administrator\Desktop\hello.pl"\r
+Content-Type: text/plain\r
+\r
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+
+print "Hello World :)\n";
+
+\r
+-----------------------------7d534d1d60150--\r
--- /dev/null
+---
+Content-Length: 1851
+Content-Type: multipart/form-data; boundary=---------------------------7d534d1d60150
+User-Agent: Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.0)
use lib './lib';
use Data::Dumper;
-use HTTP::Body::Multipart;
+use HTTP::Body;
use IO::File;
use YAML qw[LoadFile];
my $test = shift(@ARGV) || 1;
-my $headers = LoadFile( sprintf( "t/data/%.3d-headers.yml", $test ) );
-my $content = IO::File->new( sprintf( "t/data/%.3d-content.dat", $test ), O_RDONLY );
-my $parser = HTTP::Body::Multipart->new( $headers->{'Content-Type'}, $headers->{'Content-Length'} );
+my $headers = LoadFile( sprintf( "t/data/multipart/%.3d-headers.yml", $test ) );
+my $content = IO::File->new( sprintf( "t/data/multipart/%.3d-content.dat", $test ), O_RDONLY );
+my $parser = HTTP::Body->new( $headers->{'Content-Type'}, $headers->{'Content-Length'} );
+
+warn ref($parser);
binmode $content;
last if $parser->add($buffer) == 0;
}
-warn "length : $parser->{length}\n";
-warn "state : $parser->{state}\n";
+warn "length : $parser->{length}\n";
+warn "state : $parser->{state}\n";
warn Dumper( $parser->param );
warn Dumper( $parser->upload );