[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

HOWTO send large amounts of form data to ISAPI/CGI, Upload files to Pi3Web



Hi all,

I tested again with large amounts of form data with ISAPI and Standard CGI
(Perl) and here are the facts:

1.) ISAPI
=========

Take good care of reading exact the pECB.cbTotalBytes of data. If you read
less bytes than indicated in pECB.cbTotalBytes a 'Connection reset by peer'
error occurs in the browser. If you try to read more bytes ReadClient never
returns.

Problem:
The pECB.cbTotalBytes holds possibly 2 bytes less than required.
If I sent a small block (all data available from pECB) the pECB.cbTotalBytes
member is always 2 bytes smaller than the pECB.cbAvailable field.

The below example code fragment shows how to make it with Delphi 3:

function HttpExtensionProc (var pECB: EXTENSION_CONTROL_BLOCK) : DWORD; export;
stdcall;
var
  Data     : Array[0..4096] of Char;
  Response : Array[0..8] of Char;
  dwLen, ToRead : DWord;
begin
  .
  .
  .
  // Do something with the pECB.cbAvailable Bytes in pECB.lpbData
  .
  .
  .
  // Possibly a bug - cbTotalBytes seems to be 2 bytes less then required
  pECB.cbTotalBytes := pECB.cbTotalBytes + 2;

  // How many bytes left to read? 
  ToRead:=pECB.cbTotalBytes - pECB.cbAvailable;

  // Our data buffer is limited to 4kByte - dwLen is set to it or the rest
  if ToRead > 4096 then dwLen := 4096 else dwLen := ToRead;

  // Call ReadClient until all Bytes are read
  while (ToRead > 0) and pECB.ReadClient(pECB.ConnID, @Data, @dwLen) do begin
    .
    .
    .
    // Do something with the dwLen Bytes in Data
    .
    .
    .
    // dwLen now contains the read count
    Dec(ToRead, dwLen);

    // Set dwLen again for the next read request
    if ToRead > 4096 then dwLen := 4096 else dwLen := ToRead;
  end;

  // Initialize the response header
  StrPCopy(Response, '200 OK');
  pECB.ServerSupportFunction(pECB.ConnID, HSE_REQ_SEND_RESPONSE_HEADER,
@Response, nil, nil);

  // We've done it
  result := HSE_STATUS_SUCCESS;
end;

Debugging ISAPI extension DLL's with Delphi 3/C++ builder
=========================================================
Menu Start|Parameters:
    host application  C:\Pi3Web\bin\enhpi3.exe
    command line      /START C:\Pi3Web\Conf\Config.pi3


2.) Standard CGI (Perl)
=======================
The problem is similar to ISAPI if there are to much data the standard

read(STDIN, $buf, $ENV{CONTENT_LENGTH});

fails also with a 'Connection reset by peer'. Maybe Perl can't allocate
sufficient bytes for $buf or the read function can't read CONTENT_LENGTH
bytes per call, don't know.

The below example code fragment shows how to make it with Perl:

#!/usr/bin/perl

# we work with an input buffer of 4 kByte
my $inbufsize = 4096;
my $count = int($ENV{CONTENT_LENGTH} / $inbufsize);
my $rest = $ENV{CONTENT_LENGTH} % $inbufsize;
my i;
for ($i = 0; $i < $count; $i++) {
  read(STDIN, $inbuf, $inbufsize);
  # do something with $inbuf
};
read(STDIN, $inbuf, $rest);
# do something with $inbuf

3.) File upload with HTML-form and CGI
======================================

Make a simple HTML-form:

<form method='POST' enctype='multipart/form-data' action='/cgi-bin/fupload.pl'>
File to upload: <input type=file name=upfile><br>
Notes about the file: <input type=text name=note><br>
<br>
<input type=submit value=Press> to upload the file!
</form>

Now make a smart script to parse the contents and rebuild the file.
Have a look at the CGI input data:

-----------------------------2224084169055
Content-Disposition: form-data; name="upfile"; filename="c:\rfc\rfc2068.html"
Content-Type: text/html

.
.
.
-----------------------------2224084169055
Content-Disposition: form-data; name="note"


-----------------------------2224084169055--



I made some forms and scripts for basic testing. Ask me if you're interested.

-- 
with regards
Holger

---------------------------------------------------------
Holger 'Zimpel' Zimmermann    Contact me:
---------------------------------------------------------
Wendishain                    tel./fax company: on demand
Germany                       tel./fax private: on demand
---------------------------------------------------------
homepage: http://home.t-online.de/home/zimpel@t-online.de
web server: surf to it from my homepage (online every
            Sunday 20:00-24:00 GMT, start 1. Jule 1998)
e-Mail:     zimpel@t-online.de
--------------------------------------------------------

test2.pl

Title: File Upload Form

File Upload Form

Please fill in the file-upload form:

File to upload:
Notes about the file:

to upload the file!