Use CGI environment variables and symbolic links to reduce CGI program volume

1. Cause
There is an application with a very large CGI program, and each program has a size of nearly 1MB after the strip. The flash space is limited, so consider The method of reducing the program deployment space without changing the external interface program.
2. Analysis
< span style="font-family: Microsoft Yahei">1.cgi main program code is very similar, the difference is the type of xml. The type here is hard-coded. If the http request type can be dynamically obtained in the cgi program, and the xml type is determined, these programs can be integrated.
2. The original design is that different types of xml correspond to different URLs. After the integration, there is one URL, which can also be used, but unlike the interface design, both sides of the interface must modify the program. Linux has a symbolic link mechanism, which can create symbolic links of the same file with different names. With this mechanism, the cgi program is split into five different programs.
3. Implementation
1.cgi obtains context information through environment variables. Whenever the server loads an instance of the script, the following environment variables are set, and are private and specific to the instance:
The following is reproduced from http://www.voidcn.com/article/p-ttlxyhbj-bex.html

  • AUTH_TYPE
    [If the server supports basic authentication and if the script is protected, this variable provides the authentication type. This information is specific to the protocol and server. An example of AUTH_TYPE is BASIC.
  • CONTENT_LENGTH
    If the request includes data via the POST method, this variable is set to provide the length of the legal data in bytes passed through STDIN—for example, 72.
  • CONTENT_TYPE
    If the request includes data, this variable specifies the data type as a MIME header. For example, application/x-www-form-urlencoded
  • GATEWAY_INTERFACE
    it Provide the version number of the CGI interface supported by the server, the format is CGI/version number: such as CGI/1.1.
  • HTTP_ACCEPT
    Provide a list of MIME types separated by commas and acceptable by the client server, such as image/gif, image/x-xbitmap, image/jpeg, image/pjpeg and */*. This list actually comes from the browser itself, and the server just passes it to the CGI script.
  • HTTP_USER_AGENT
    Provide the client browser name that may contain the version number or other proprietary data, such as Mozilla/2.0b3 (Win NT;I).
  • PATH_INFO
    Display any additional path information provided by the customer and attached to the end of the virtual path. It is usually used as a parameter of the script. For example, in the URL
    http://www.yourcompany.com/cgi-bin/myscript.pl/dir1/dir2, the script is myscript.pl and PATH_INFO is /dirl/dlr2.
  • PATH_TRANSLATED
    Only supported by some servers, this variable contains the conversion from the virtual path to the executed script (ie virtual path to physical path Mapping). For example, if the absolute path to the root of your web server is /usr/local/etc/httpd/htdocs, and your cgi-bin folder is at the root level of the web server (i.e., http://www.mycorp. com/cgi-bin), a script with URL http://www.mycorp.com/cgi-bin/search.cgi sets the variable PATH_TRANSLATED to /usr/local/etc/httpd/htdocs/cgi-bin/search .cgi.
  • QUERY_STRING
    Display any additional information provided by the customer attached to the end of the URL and separated from the script name by a question mark. For example, name=joe&id=45 in
    htt p://www.yourcompany.com/hello.html?name=joe&id=id=45 is QUERY_STRING.
  • REMOTE_ADDR
    It provides the IP address of the requesting client—for example, 199.1.166.171. This information is always available.
  • REMOTE_HOST
    It provides the hostname of the requesting client that has been resolved. Such as dial-up102.abc.def.com. This information is usually unavailable due to two reasons: the caller’s IP cannot be correctly mapped to a hostname through DNS, or the web administrator of your site has blocked the IP lookup. The web administrator usually closes the lookup because They mean that the server has to perform additional steps after each connection, which will reduce the efficiency of the server.
  • EMOTE_IDENT
    If the server and client support RFC931, this variable will contain the identification information provided by the remote user’s computer. Few servers and clients still support this protocol. This information is also of little value, because users can set this information to whatever they want. Do not use this variable even if your server supports it.
  • REMOTE_USER
    If AUTH_TYPE is set, this variable will contain the username provided by the user and confirmed by the server.
    Note
    AUTH_TYPE and REMOTE_USER are only set after the user has successfully authenticated their identity on the server (usually by username and password). Therefore, these variables are only set when a restricted area is established and only in this area Useful.
  • REQUEST_METHOD
    It provides the method by which the script is called. For scripts using HTTP/1.0 protocol, only GET and POST are meaningful.
  • SCRIPT_NAME
    This is the name of the called script file. It is useful for self-referencing scripts. For example, this variable can be used to generate a URL of a script called by the GET method to generate and output a form, and the same script is called by the POST method when the form is submitted. It is easier to maintain by using this variable instead of hard-coding the script name or location-for example, /cgi-bin/myscript.exe. When you move or rename the script, when you reconfigure the server to change the cgi-bin directory, or when you install the script on another machine, you don’t need to change the code.
  • SERVER_NAME
    This is the host name, alias or IP address of your web server. It is reliable for generating URLs that point to the server at runtime—for example, www.ourcompany.com.
  • SERVER_PORT
    This is the port number of this connection—for example, 80.
  • SERVER_PROTOCOL
    This is the name/version of the protocol used in this request. For example, HTTP/1.0.
  • SERVER一S0FTWARE
    This is the name/version of the HTTP server running the script. For example, HTTPS/1.1.

The above three environment variables marked in red can get the request url After testing, only SCRIPT_NAME is valid. For example: request 192.168.56.101/cgi-bin/capture, SCRIPT_NAME is /cgi-bin/capture. In cgic, the environment variable SCRIPT_NAME is stored in the global variable cgiScriptName, and the code is modified to:

  1. static cgiFormResultType zXmlCgiRespond(char *ptypename);
  2. const char * gScriptName[] = {
  3. “CONFIGTIMERES” ,
  4. ……
  5. ……
  6. NULL
  7. }
  8. int gzXmlResult[] = {
  9. CONFIGTIMERES,
  10. ……
  11. }
  12. zXmlType zXmlCgiScriptNametozXmlType(char * ptypename) {
  13. int index = 0;
  14. for (i = 0; gScriptName[i] != NULL; i++) {< br>
  15. if(!strcmp(ptypename, gScriptName) {
  16. index = i;
  17. break;
  18. li>

  19. }
  20. }
  21. return gzXmlResult[index];
  22. }
  23. static cgiFormResultType zXmlCgiRespon d(char *ptypename) {
  24. zXmlError res;
  25. cgiFormResultType formres;
  26. char content[HTTP_POST_LEN] = { 0};
  27. char resxml[ZXML_RESPOND_LEN] = {0};
  28. zXmlType type = zXmlCgiScriptNametozXmlType(ptypename);
  29. Int length = (HTTP_POST_LEN
  30. cgiHeaderContentType(“text/plain”);
  31. formres = cgiFormString(“xml” , content, length);
  32. if (formres != cgiFormSuccess) {
  33. return formres;
  34. }
  35. res = zXmlParseAndMakeRespond(resxml, type, length, content);
  36. fprintf(cgiOut, “%s”, resxml);
  37. return cgiFormSuccess;
  38. }
  39. int cgiMain() {
  40. < li> cgiFormResultType res =;

  41. char * ptypename = (char *)malloc(strlen(cgiScriptName));
  42. if (ptypename != NULL) {
  43. strcpy(ptypename, cgiScriptName);
  44. res = zXmlCgiRespond(basename(pytpename));
  45. free(ptypename);
  46. } else {
  47. res = cgiFormMemory;
  48. }
  49. return res;
  50. }

Copy code

2. Assuming that the cgi program is cgizxml.org, add a symbolic link in the cgi-bin file, ln -s path/to/cgizxml.org xxx.cgi, etc.

  1. static cgiFormResultType zXmlCgiRespond(char *ptypename);
  2. const char * gScriptName[] = {
  3. “CONFIGTIMERES”,
  4. ……
  5. ……
  6. NULL
  7. }
  8. int gzXmlResult[] = {
  9. CONFIGTIMERES,
  10. ……< br>
  11. }
  12. zXmlType zXmlCgiScriptNametozXmlType(char * ptypename) {
  13. int index = 0;
  14. for (i = 0; gScriptName[i] != NULL; i++) {
  15. if(!strcmp(ptypename, gScriptName) {
  16. index = i;
  17. break;
  18. }
  19. }
  20. return gzXmlResult [index];
  21. }
  22. static cgiFormResultType zXmlCgiRespond(char *ptypename) {
  23. zXmlError res;
  24. cgiFormResultType formres;
  25. Char content[HTTP_POST_LEN] = {0};
  26. char resxml[ZXML_RESPOND_LEN] = {0};
  27. zXmlType type = zXmlCgiScriptNametozXmlType(ptypename);< br>
  28. int length = (HTTP_POST_LEN
  29. cgiHeaderContentType(“text/plain”);
  30. Formres = cgiFormString(“xml”, content, length);
  31. if (formres != cgiFormSuccess) {
  32. return formres;
  33. }
  34. res = zXmlParseAndMakeRespond(resxml, type, length, content);
  35. fprintf(cgiOut, “%s”, resxml) ;
  36. return cgiFormSuccess;
  37. }
  38. int cgiMain() {
  39. cgiFormResultType res =;
  40. char * ptypename = (char *)malloc(strlen(cgiScriptName));
  41. if (ptypename != NULL) {
  42. strcpy(ptypename, cgiScriptName);
  43. res = zXmlCgiRe spond(basename(pytpename));

  44. free(ptypename);
  45. } else {
  46. res = cgiFormMemory;
  47. }
  48. return res;
  49. }

Copy code

  1. static cgiFormResultType zXmlCgiRespond(char *ptypename);
  2. const char * gScriptName[] = {
  3. “CONFIGTIMERES”,
  4. ……
  5. … …
  6. NULL
  7. }
  8. int gzXmlResult[] = {
  9. CONFIGTIMERES ,
  10. ……
  11. }
  12. zXmlType zXmlCgiScriptNametozXmlType(char * ptypename) {
  13. int index = 0;

  14. for (i = 0; gScriptName[i] != NULL; i++) {
  15. if(!strcmp(ptypename, gScriptName) {
  16. index = i;
  17. Break;
  18. }
  19. }< br>
  20. return gzXmlResult[in dex];
  21. }
  22. static cgiFormResultType zXmlCgiRespond(char * ptypename) {
  23. zXmlError res;
  24. cgiFormResultType formres;
  25. char content[HTTP_POST_LEN] = {0};< br>
  26. char resxml[ZXML_RESPOND_LEN] = {0};
  27. zXmlType type = zXmlCgiScriptNametozXmlType(ptypename);
  28. int length = (HTTP_POST_LEN
  29. cgiHeaderContentType(“text/plain”);
  30. formres = cgiFormString(“xml”, content, length );
  31. if (formres != cgiFormSuccess) {
  32. return formres;
  33. }
  34. res = zXmlParseAndMakeRespond(resxml, type, length, content);
  35. fprintf(cgiOut, “%s”, resxml);
  36. < br>
  37. return cgiFormSuccess;
  38. }
  39. int cgiMain() {
  40. cgiFormResultType res =;
  41. char * ptypename = (char *)malloc(strlen(cgiScriptName));
  42. if (ptypename != NULL) {
  43. strcpy(ptypename, cgiScriptName) ;
  44. res = zXmlCgiRespond(basename(pytpename));
  45. free(ptypename);
  46. } else {< br>
  47. res = cgiFormMemory;
  48. }
  49. return res;
  50. }

Leave a Comment

Your email address will not be published.