40
41
42
43
44
45
46
47
48
49
50
51
52
53
|
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
|
+
|
#ifdef __EMX__
typedef int socklen_t;
#endif
#include <time.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <netdb.h>
#include "cgi.h"
#if INTERFACE
/*
** Shortcuts for cgi_parameter. P("x") returns the value of query parameter
** or cookie "x", or NULL if there is no such parameter or cookie. PD("x","y")
** does the same except "y" is returned in place of NULL if there is not match.
|
1117
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
|
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
|
+
+
+
+
+
+
+
+
+
+
+
|
zInput++;
while( fossil_isspace(*zInput) ){ zInput++; }
}
if( zLeftOver ){ *zLeftOver = zInput; }
return zResult;
}
/*
** All possible forms of an IP address. Needed to work around GCC strict
** aliasing rules.
*/
typedef union {
struct sockaddr sa; /* Abstract superclass */
struct sockaddr_in sa4; /* IPv4 */
struct sockaddr_in6 sa6; /* IPv6 */
struct sockaddr_storage sas; /* Should be the maximum of the above 3 */
} address;
/*
** This routine handles a single HTTP request which is coming in on
** standard input and which replies on standard output.
**
** The HTTP request is read from standard input and is used to initialize
** environment variables as per CGI. The cgi_init() routine to complete
** the setup. Once all the setup is finished, this procedure returns
|
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
1170
1171
1172
1173
|
1167
1168
1169
1170
1171
1172
1173
1174
1175
1176
1177
1178
1179
1180
1181
1182
1183
1184
1185
1186
1187
1188
1189
|
-
-
-
-
-
+
+
+
+
+
+
+
+
+
|
malformed_request();
}
cgi_setenv("REQUEST_URI", zToken);
for(i=0; zToken[i] && zToken[i]!='?'; i++){}
if( zToken[i] ) zToken[i++] = 0;
cgi_setenv("PATH_INFO", zToken);
cgi_setenv("QUERY_STRING", &zToken[i]);
if( zIpAddr==0 &&
getpeername(fileno(g.httpIn), (struct sockaddr*)&remoteName,
&size)>=0
){
zIpAddr = inet_ntoa(remoteName.sin_addr);
if( zIpAddr==0 ){
address remoteAddr;
unsigned int size = sizeof(remoteAddr);
char zHost[NI_MAXHOST];
if( getpeername(fileno(g.httpIn), &remoteAddr.sa, &size)>=0 ){
getnameinfo(&remoteAddr.sa, size, zHost, sizeof(zHost), 0, 0,
NI_NUMERICHOST);
zIpAddr = mprintf("%s", zHost);
}
}
if( zIpAddr ){
cgi_setenv("REMOTE_ADDR", zIpAddr);
g.zIpAddr = mprintf("%s", zIpAddr);
}
/* Get all the optional fields that follow the first line.
|