I'm trying to use HLA to program CGI's. I can write stuff to the screen using stdout.put, and figured out how to read environment variables using _GetEnvironmentVariableA@12, but I'm stuck on reading input from a POST method (I suppose if I wanted I could use GET, but now that I'm stuck I'm stubborn as a mule ;) )...I tried stdin.get, but it didn't work (I suspect maybe it's waiting for the enter key?). After searching the archives here I tried importing MASM's stdin routine and adapting someone else's code, but that didn't work either. Then I tried something else I found in the archives using a few windows procedures (GetStdHandle, SetConsoleMode, ReadFile). It still doesn't work.
I checked the windows procedures' returns...GetStdHandle successfully returns something, but SetConsoleMode and ReadFile are returning 0 in EAX.
For any of you who know HLA here's my current code:
Any help would be appreciated...I'm still learning HLA, and I don't know hardly any MASM, but if anyone has any ideas...
P.S. - those of you not used to HLA, the instructions are backwards of MASM... mov(eax, ebx) is equivalent to mov ebx, eax (I think...)
I checked the windows procedures' returns...GetStdHandle successfully returns something, but SetConsoleMode and ReadFile are returning 0 in EAX.
For any of you who know HLA here's my current code:
program CGItest;
#include("stdlib.hhf");
#include("win32.hhf");
#include("win32more.hhf"); // additional windows procedures
#include("masm.hhf"); // (attempted) MASM import
#asm
includelib \hla\hlalib\masm32.lib
#endasm
/**********************************************************
Main Program
**********************************************************/
static
env_buffer: string;
env_var: string;
blah: uns32;
begin CGItest;
stralloc(256);
mov(eax, env_buffer);
stralloc(80);
mov(eax, env_var);
stdout.put("Content-type: text/html",nl,nl);
stdout.put("<HTML>",nl,"<BODY TEXT=""FFFFFF"" BGCOLOR=""000000"">",nl);
mov(env_buffer,ebx);
str.cpy("REQUEST_METHOD", env_var);
winmore.GetEnv(256,ebx,env_var);
mov(eax, (type dword [ebx-4]));
str.eq(ebx, "POST");
if (eax == 0) then
stdout.put(" Error: Method must be ""POST"".<BR>",nl," ");
stdout.puts(env_buffer);
stdout.put("<BR><BR>",nl,nl);
// jmp endtest;
endif;
str.cpy("CONTENT_TYPE", env_var);
winmore.GetEnv(256,ebx,env_var);
mov(eax, (type dword [ebx-4]));
str.cpy("application/x-www-form-urlencoded", env_var);
str.eq(ebx, env_var);
if (eax == 0) then
stdout.put(" Error: This CGI must be accessed from a form.<BR>",nl," ");
stdout.puts(env_buffer);
stdout.put("<BR><BR>",nl,nl);
// jmp endtest;
endif;
str.cpy("CONTENT_LENGTH", env_var);
winmore.GetEnv(256,ebx,env_var);
mov(eax, (type dword [ebx-4]));
stdout.put("Content length: ");
stdout.puts(ebx);
stdout.put("<BR><BR>",nl,nl);
mov(0,ecx);
mov(0,eax);
while(ecx < (type dword [ebx-4])) do
mov(eax, edx);
shl(1,eax);
shl(3,edx);
add(edx,eax);
add((type dword (type byte [ebx])), eax);
sub('0',eax);
inc(ecx);
endwhile;
mov(0,ecx);
mov(eax,edx);
inc(eax);
mov(env_buffer, ebx);
mov(eax,(type dword [ebx-4]));
stdout.put(eax, " ");
masm.StdIn(ebx,eax);
stdout.put(eax, " ");
winmore.GetStdHandle(winmore.STD_INPUT_HANDLE);
stdout.put(eax, " ");
push(eax);
winmore.SetConsoleMode(eax,winmore.ENABLE_LINE_INPUT | winmore.ENABLE_ECHO_INPUT | winmore.ENABLE_PROCESSED_INPUT);
stdout.put(eax, " ");
pop(eax);
winmore.ReadFile(eax,env_buffer,eax,&blah,0);
stdout.put(eax, " ");
stdout.put(blah, " ");
mov(0, (type byte [ebx+ecx]));
stdout.put(" Content: ");
stdout.puts(env_buffer);
stdout.put("<BR><BR>",nl,nl);
endtest:
stdout.put(" End of test CGI.",nl);
stdout.put("</BODY>",nl,"</HTML>");
strfree(env_var);
strfree(env_buffer);
end CGItest;
Any help would be appreciated...I'm still learning HLA, and I don't know hardly any MASM, but if anyone has any ideas...
P.S. - those of you not used to HLA, the instructions are backwards of MASM... mov(eax, ebx) is equivalent to mov ebx, eax (I think...)
first, is the filehandle (always) equal to the content-length?
Second, does stdout.put, and the other calls, preserve eax,ebx, etc?
I don't know the specifics of HLA, but most functions in other languages will return values, include success flags in eax. You should probably grab a value and save it into a well labeled memory location, that way your code will be more readable as a side effect.
winmore.ReadFile(eax,env_buffer,eax,&blah,0);
Maybe the second eax is supposec to be ebx?
Second, does stdout.put, and the other calls, preserve eax,ebx, etc?
winmore.GetStdHandle(winmore.STD_INPUT_HANDLE);
stdout.put(eax, " ");
push(eax);
I don't know the specifics of HLA, but most functions in other languages will return values, include success flags in eax. You should probably grab a value and save it into a well labeled memory location, that way your code will be more readable as a side effect.
I figured it out (partially). The way I had my loop for extracting the content length from the env_buffer string, I wasn't zero-extending each character's value, giving me lengths of +/- 2 billion :eek:
I'm also getting some text from stdin now (before I got nothing), so I think I'm almost set.
Thanks a lot for the help...I'll try using variables more like you said, eet...Faster programs aren't any good if they dont run, right? ;)
Does anyone know if HLA has a string-to-number function? It'd probably be more reliable than my code...
I'm also getting some text from stdin now (before I got nothing), so I think I'm almost set.
Thanks a lot for the help...I'll try using variables more like you said, eet...Faster programs aren't any good if they dont run, right? ;)
Does anyone know if HLA has a string-to-number function? It'd probably be more reliable than my code...
Ok, I've got it mostly figured out now. The only problem I have is that 2 bytes of stdin data get cut off, and it adds an <ENTER> character...so, for example:
"testtxt=test...&submit=Subm", CRLF
-or-
"submit=Submit&testtxt=test.",CRLF
Is there any way to retrieve the last two characters or should I just add an unimportant "filler" value at the end of my form?
(BTW, I did a test and apparently stdout.put doesn't modify EAX...)
"testtxt=test...&submit=Subm", CRLF
-or-
"submit=Submit&testtxt=test.",CRLF
Is there any way to retrieve the last two characters or should I just add an unimportant "filler" value at the end of my form?
(BTW, I did a test and apparently stdout.put doesn't modify EAX...)
program CGItest;
#include("stdlib.hhf");
#include("win32.hhf");
#include("win32more.hhf");
#include("masm.hhf");
#asm
includelib \hla\hlalib\masm32.lib
#endasm
/**********************************************************
Main Program
**********************************************************/
static
env_buffer: string;
env_var: string;
blah: uns32;
begin CGItest;
stralloc(256);
mov(eax, env_buffer);
stralloc(80);
mov(eax, env_var);
stdout.put("Content-type: text/html",nl,nl);
stdout.put("<HTML>",nl,"<BODY TEXT=""FFFFFF"" BGCOLOR=""000000"">",nl);
/* stdout.put(" <I>", nl);
mov(1,ebx);
while(ebx < 5) do
stdout.put(" 1<BR>");
stdout.put(nl);
inc(ebx);
endwhile;*/
mov(env_buffer,ebx);
str.cpy("REQUEST_METHOD", env_var);
winmore.GetEnv(256,ebx,env_var);
mov(eax, (type dword [ebx-4]));
str.eq(ebx, "POST");
if (eax == 0) then
stdout.put(" Error: Method must be ""POST"".<BR>",nl," ");
stdout.puts(env_buffer);
stdout.put("<BR><BR>",nl,nl);
// jmp endtest;
endif;
str.cpy("CONTENT_TYPE", env_var);
winmore.GetEnv(256,ebx,env_var);
mov(eax, (type dword [ebx-4]));
str.cpy("application/x-www-form-urlencoded", env_var);
str.eq(ebx, env_var);
if (eax == 0) then
stdout.put(" Error: This CGI must be accessed from a form.<BR>",nl," ");
stdout.puts(env_buffer);
stdout.put("<BR><BR>",nl,nl);
// jmp endtest;
endif;
str.cpy("CONTENT_LENGTH", env_var);
winmore.GetEnv(256,ebx,env_var);
mov(eax, (type dword [ebx-4]));
stdout.put("Content length: ");
stdout.puts(ebx);
stdout.put("<BR>",nl);
mov(0,ecx);
mov(0,eax);
while(ecx < (type dword [ebx-4])) do
mov(eax, edx);
shl(1,eax);
shl(3,edx);
add(edx,eax);
movzx((type byte [ebx+ecx]),edx);
add(edx, eax);
sub('0',eax);
inc(ecx);
endwhile;
stdout.put("Extracted Content Length: ", (type int32 eax),"<BR><BR>",nl,nl);
mov(env_buffer, ebx);
mov(0, (type byte [ebx+eax]));
dec(eax);
dec(eax);
mov(eax,(type dword [ebx-4]));
stdout.put("Stdin: ");
mov(0,ecx);
while((type int32 ecx) < (type int32 eax)) do
push(eax);
stdin.getc();
mov(al, (type byte [ebx+ecx]));
stdout.put((type char al));
inc(ecx);
pop(eax);
endwhile;
stdout.put("<BR><BR>",nl,nl);
stdout.put(" Content: ");
stdout.puts(env_buffer);
stdout.put("<BR><BR>",nl,nl);
endtest:
stdout.put(" End of test CGI.",nl);
stdout.put("</BODY>",nl,"</HTML>");
strfree(env_var);
strfree(env_buffer);
mov(0,eax);
end CGItest;
sirchess2,
I would try for an answer from Randy Hyde on this one as he is the author. I don't think Randy has posted in this forum as yet but I know he posts in the alt lang asm newsgroup so you may have some success there.
Regards,
hutch@movsd.com
I would try for an answer from Randy Hyde on this one as he is the author. I don't think Randy has posted in this forum as yet but I know he posts in the alt lang asm newsgroup so you may have some success there.
Regards,
hutch@movsd.com
Forgive my idiocity, but what's a newsgroup, and how does one subscribe/browse to it? :o
Network News is a web application that has thread forums, like this HTTP forum, but it has it's own protocal NNTP. A quick google, tucows, etc for a News Reader/Browser should find the app you're looking for. Most ISPs provide NNTP servers. You can also do a google for servers.