CGI principle parsing Series 3-how to obtain complete WEB Server Data Using CGI-cgi
// Simulates the process of starting cgi by the httpd process on the server,
// The get and post methods are fully displayed.
// Gcc-g httpd_all.c-o httpd_all.ums;
# Include <stdio. h>
# Include <string. h>
# Include <unistd. h>
# Include <sys/wait. h>
# Include <stdlib. h>
# Define CGI_NAME "get_post.ums"
# Define REQUEST_METHOD "REQUEST_METHOD = POST"
# Define REQUEST_PARAMETER "myname = huangzhihui"
Int main (int argc, char * argv [])
{
Int parent [2], child [2];
If (pipe (parent) <0)
{
Printf ("create pipe fail. \ n ");
}
If (pipe (child) <0)
{
Close (parent [0]);
Close (parent [1]);
Printf ("create pipe fail. \ n ");
}
Pid_t pid;
If (pid = fork () <0)
{
Printf ("fork fail. \ n ");
}
Else if (pid> 0)
{
/* Parent */
// Close unnecessary handles to construct a single read/write Channel
Close (parent [0]);
Close (child [1]);
// Simulate data transfer to CGI
Ssize_t length = strlen (REQUEST_PARAMETER );
If (write (parent [1], REQUEST_PARAMETER, length )! = Length)
{
Printf ("write error to pipe \ n ");
}
Close (parent [1]);
// Wait until the CGI sub-process completely reads the data and writes the data,
// Select or epoll listeners are used.
// Usleep (1000 );
// Simulate receiving CGI response data
Char buff [256] = {0 };
Length = read (child [0], buff, sizeof (buff ));
If (length <= 0)
{
Printf ("read error from pipe \ n ");
}
Else
{
Printf ("pid % d read data = % u \ n % s", getpid (), length, buff );
}
Close (child [0]);
If (waitpid (pid, NULL, 0) <0)
{
Printf ("waitpid error \ n ");
}
Exit (0 );
}
Else
{
/* Child */
// Close unnecessary handles to construct a single read/write Channel
Close (parent [1]);
Close (child [0]);
// Redirect the input of the MPs queue to the standard input.
If (parent [0]! = STDIN_FILENO)
{
If (dup2 (parent [0], STDIN_FILENO )! = STDIN_FILENO)
{
Printf ("dup2 error to stdin ");
}
Close (parent [0]);
}
// Redirect the output of the MPs queue to the standard output
If (child [1]! = STDOUT_FILENO)
{
If (dup2 (child [1], STDOUT_FILENO )! = STDOUT_FILENO)
{
Printf ("dup2 error to stdout ");
}
Close (child [1]);
}
// Overwrite the process space and set CGI Environment Variables
Char content_length [128] = {0 };
Sprintf (content_length, "CONTENT_LENGTH = % u", strlen (REQUEST_PARAMETER ));
Char * exec_argv [3] = {REQUEST_METHOD, content_length };
If (execve (CGI_NAME, argv, exec_argv) <0)
{
Printf ("execl error for % s", CGI_NAME );
}
Exit (0 );
}
Exit (0 );
}