bitreich-httpd.c - bitreich-httpd - Bitreich HTTPD service
HTML git clone git://bitreich.org/bitreich-httpd git://enlrupgkhuxnvlhsf6lc3fziv5h2hhfrinws65d7roiv6bfj7d652fid.onion/bitreich-httpd
DIR Log
DIR Files
DIR Refs
DIR Tags
DIR README
DIR LICENSE
---
bitreich-httpd.c (9297B)
---
1 /*
2 * Copy me if you can.
3 * by 20h
4 */
5
6 #include <unistd.h>
7 #include <stdio.h>
8 #include <stdlib.h>
9 #include <time.h>
10 #include <sys/types.h>
11 #include <sys/stat.h>
12 #include <fcntl.h>
13 #include <string.h>
14 #include <strings.h>
15 #include <sys/socket.h>
16 #include <sys/wait.h>
17 #include <netdb.h>
18 #include <time.h>
19
20 void *
21 xmalloc(size_t size)
22 {
23 void *p;
24
25 if (!(p = malloc(size))) {
26 perror("malloc");
27 exit(1);
28 }
29
30 return p;
31 }
32
33 void
34 print404(void)
35 {
36 printf("HTTP/1.1 404 Google Broke The Web\r\n");
37 printf("\r\n");
38 }
39
40 void
41 printheaders(char *ctype)
42 {
43 time_t t;
44 char fortunecookie[512];
45 FILE *fcstdout;
46 int fclen = 0;
47
48 bzero(fortunecookie, sizeof(fortunecookie));
49 fcstdout = popen("/home/annna/bin/fortune-cookie", "r");
50 if (fcstdout != NULL) {
51 fread(fortunecookie, sizeof(fortunecookie)-1, 1, fcstdout);
52 pclose(fcstdout);
53 fclen = strlen(fortunecookie);
54 if (fclen > 0) {
55 if (fortunecookie[fclen-1] == '\n')
56 fortunecookie[fclen-1] = '\0';
57 }
58 }
59
60 t = time(NULL);
61 if (t > 0)
62 printf("Date: %s", asctime(gmtime(&t)));
63 printf("X-Future: Gopher ftw!\r\n");
64 if (fclen > 0)
65 printf("X-Fortune-Cookie: %s\r\n", fortunecookie);
66 printf("Content-Type: %s\r\n", ctype);
67 printf("X-Irritate: Be irritated.\r\n");
68 printf("X-Use-Gopher: gophers://bitreich.org\r\n");
69 printf("If-By-Whiskey: Terrorist\r\n");
70 printf("X-Powered-By: love\r\n");
71 printf("Permission-Policy: interest-cohort=()\r\n");
72 printf("Fuck-Off: Google\r\n");
73 printf("Server: bitreich-httpd/2.0\r\n");
74 printf("X-Alarm: <script>window.alert(\"Turn off Javascript, it hurts me.\");</script>\r\n");
75 printf("X-Goat-0: (_(\r\n");
76 printf("X-Goat-1: /_/'_____/)\r\n");
77 printf("X-Goat-2: \" | |\r\n");
78 printf("X-Goat-3: |\"\"\"\"\"\"| \r\n");
79 printf("Host: bitreich.org\r\n");
80 printf("Connection: close\r\n");
81 /* Have some fun with the websters. */
82 printf("X-Fun-Begins: Yes!\r\n");
83 printf("Content-Security: secure\r\n");
84 printf("X-Cachwall-Reason: no reason\r\n");
85 printf("X-Powered-By: binarysec\r\n");
86 printf("X-Here-We-Match: squid\r\n");
87 printf("aessecure-code: Kot\r\n");
88 printf("X-CDN: jup\r\n");
89 printf("X-Backside-Trans: ok\r\n");
90 printf("X-dotDefender-denied: 1\r\n");
91 printf("X-ASPNET-Version: got me\r\n");
92 printf("X-Powered-By-360wzb: Of course!\r\n");
93 printf("asp-id: here I am\r\n");
94 printf("X-Not-Here: cloudfront\r\n");
95 printf("WZWS-RAY: anyu yuuuuu\r\n");
96 printf("Strict-Transport: Prussian\r\n");
97 printf("X-Sucuri-Block: We are sucur!\r\n");
98 printf("gladius_blockchain_driven_cyber_protection_network_session: oi!\r\n");
99 printf("GW-Server: grey.wizard\r\n");
100 printf("X-Cache: wt696969696969cdn\r\n");
101 printf("X-Cache: YUNDUN\r\n");
102 printf("X-Arrested: dosarrest\r\n");
103 printf("X-Instart-Request-ID: dadadadada\r\n");
104 printf("Via: 1.1 varnish\r\n");
105 printf("X-Cachwall-Action: ACTION! SET!\r\n");
106 printf("X-st8id33133: yeah\r\n");
107 printf("X-Sucuri-ID: Curry is tasty.\r\n");
108 printf("X-Varnish: 37337\r\n");
109 printf("X-Powered-By: waf1337\r\n");
110 printf("X-Instart-CacheKeyMod: ahahahahaha\r\n");
111 }
112
113 int
114 servefile(char *path, char *ctype, int sock)
115 {
116 struct stat st;
117 char *sendb, *sendi;
118 size_t bufsiz = BUFSIZ;
119 int len, sent, fd;
120
121 fd = open(path, O_RDONLY);
122 if (fd < 0) {
123 print404();
124 return 1;
125 }
126
127 printf("HTTP/1.1 200 OK\r\n");
128 printheaders(ctype);
129
130 if (fstat(fd, &st) >= 0)
131 if ((bufsiz = st.st_blksize) < BUFSIZ)
132 bufsiz = BUFSIZ;
133
134 printf("Content-Length: %ld\r\n", st.st_size);
135 printf("\r\n");
136 fflush(stdout);
137
138 sendb = xmalloc(bufsiz);
139 while ((len = read(fd, sendb, bufsiz)) > 0) {
140 sendi = sendb;
141 while (len > 0) {
142 if ((sent = write(sock, sendi, len)) < 0) {
143 free(sendb);
144 return 1;
145 }
146 len -= sent;
147 sendi += sent;
148 }
149 }
150 free(sendb);
151
152 return 0;
153 }
154
155 char *
156 read_line(int fd, int *len, int maxread)
157 {
158 char *buf;
159 int r, rbytes;
160
161 buf = xmalloc(maxread+1);
162 memset(buf, 0, maxread+1);
163
164 rbytes = 0;
165 while (rbytes < maxread) {
166 r = read(fd, &buf[rbytes], 1);
167 if (r < 0) {
168 free(buf);
169 return NULL;
170 }
171 if (r == 0)
172 break;
173 if (buf[rbytes] == '\n') {
174 buf[rbytes] = '\0';
175 break;
176 }
177 rbytes += r;
178 }
179
180 *len = rbytes;
181 return buf;
182 }
183
184 int
185 main(int argc, char *argv[])
186 {
187 char *wwwbase, *wwwindex, *request, *ctype, *path, *le_file,
188 *le_base, clienth[NI_MAXHOST], clientp[NI_MAXSERV], *zuccbase,
189 *requested, *header, *headerval, *hosthdr;
190 int rlen, i, user_agent_script_pid, isxfirefoxai, flags;
191 struct sockaddr_storage clt;
192 socklen_t cltlen = sizeof(clt);
193 time_t tim;
194
195 hosthdr = NULL;
196 user_agent_script_pid = -1;
197
198 wwwbase = "/bitreich/www";
199 wwwindex = "index.html";
200
201 le_base = "/br/www/uacme";
202 zuccbase = "/br/www/zuccless";
203
204 /*
205 * Try to set keepalive in case we have some socket on stdin.
206 */
207 flags = 1;
208 setsockopt(0, SOL_SOCKET, SO_KEEPALIVE, (void *)&flags, sizeof(flags));
209
210 if (!getpeername(0, (struct sockaddr *)&clt, &cltlen)) {
211 if (getnameinfo((struct sockaddr *)&clt, cltlen, clienth,
212 sizeof(clienth), clientp, sizeof(clientp),
213 NI_NUMERICHOST|NI_NUMERICSERV)) {
214 clienth[0] = clientp[0] = '\0';
215 }
216 if (!strncmp(clienth, "::ffff:", 7))
217 memmove(clienth, clienth+7, strlen(clienth)-6);
218 } else {
219 clienth[0] = clientp[0] = '\0';
220 }
221
222 request = read_line(0, &rlen, 512);
223 if (request == NULL)
224 return 1;
225 if (request[rlen-1] == '\r')
226 request[rlen-1] = '\0';
227
228 /* Header parsing. */
229 /* At max read 16 headers. Do not allow DDoS. */
230 isxfirefoxai = 0;
231 for (i = 0; i < 16; i++) {
232 header = read_line(0, &rlen, 512);
233 if (header == NULL || rlen == 0)
234 break;
235 if (header[rlen-1] == '\r') {
236 header[rlen-1] = '\0';
237 if (rlen == 1) {
238 free(header);
239 break;
240 }
241 }
242 headerval = strchr(header, ':');
243 if (headerval == NULL) {
244 free(header);
245 continue;
246 }
247 *headerval = '\0';
248 headerval += 2;
249 if (headerval > (header + rlen)) {
250 free(header);
251 continue;
252 }
253 if (!strcasecmp(header, "user-agent")) {
254 user_agent_script_pid = fork();
255 switch (user_agent_script_pid) {
256 case -1:
257 perror("fork");
258 return 1;
259 case 0:
260 return execl("add-user-agent.sh",
261 "/home/annna/bin/modules/http-user-agent/add-user-agent.sh",
262 headerval, 0);
263 }
264 }
265 if (!strcasecmp(header, "host")) {
266 rlen = strlen(headerval);
267 hosthdr = xmalloc(rlen+1);
268 memset(hosthdr, 0, rlen+1);
269 strncpy(hosthdr, headerval, rlen);
270 }
271 if (!strcasecmp(header, "x-firefox-ai")) {
272 isxfirefoxai = 1;
273 ctype = "video/webm";
274 asprintf(&path, "%s/s/aiaiaiai.webm", wwwbase);
275 }
276 free(header);
277 }
278
279 if (strncmp(request, "GET ", 4))
280 return 1;
281
282 if (isxfirefoxai) {
283 } else if (strstr(request, "s/bitreich.sh")) {
284 asprintf(&path, "%s/s/bitreich.sh", wwwbase);
285 ctype = "text/plain";
286 } else if (strstr(request, "favicon.gif")) {
287 asprintf(&path, "%s/s/favicon.gif", wwwbase);
288 ctype = "image/gif";
289 } else if (strstr(request, "deep-thinker.gif")) {
290 asprintf(&path, "%s/s/deep-thinker.gif", wwwbase);
291 ctype = "image/gif";
292 } else if (strstr(request, "startup.mp3")) {
293 asprintf(&path, "%s/s/startup.mp3", wwwbase);
294 ctype = "audio/mpeg";
295 } else if (strstr(request, "padme-hum.mp3")) {
296 asprintf(&path, "%s/s/padme-hum.mp3", wwwbase);
297 ctype = "audio/mpeg";
298 } else if (strstr(request, "dickbutt")) {
299 asprintf(&path,
300 "/home/annna/bin/locate-cake-hater \"%s\" \"%s\"",
301 clienth, clientp);
302 system(path);
303 free(path);
304 asprintf(&path, "%s/s/dickbutt.jpg", wwwbase);
305 ctype = "image/jpeg";
306 } else if (strstr(request, "bitreich.css")) {
307 asprintf(&path, "%s/s/bitreich.css", wwwbase);
308 ctype = "text/css";
309 } else if (strstr(request, "neko.png")) {
310 asprintf(&path, "%s/s/neko.png", wwwbase);
311 ctype = "image/png";
312 } else if (strstr(request, "snow.js")) {
313 asprintf(&path, "%s/s/snow.js", wwwbase);
314 ctype = "text/javascript";
315 } else if (strstr(request, "fluid.js")) {
316 asprintf(&path, "%s/s/fluid.js", wwwbase);
317 ctype = "text/javascript";
318 } else if (strstr(request, "ads-prebid-wp-ads-banner.js")) {
319 asprintf(&path, "%s/s/ads-prebid-wp-ads-banner.js", wwwbase);
320 ctype = "text/javascript";
321 } else if (strstr(request, "yolo-css-")) {
322 /* We hate CSS in here. */
323 sleep(1);
324 asprintf(&path, "%s/s/yolo-css.css", wwwbase);
325 ctype = "text/css";
326 } else if ((le_file = strstr(request, ".well-known/acme-challenge/"))) {
327 /* Setup for Letsencrypt */
328 le_file += strlen(".well-known/acme-challenge/");
329 requested = strtok(le_file, " ");
330 if (strchr(requested, '/') != NULL) {
331 /* Get Zucced, no path exploitation. */
332 asprintf(&path, "%s/zucc-job.webm", zuccbase);
333 ctype = "video/webm";
334 } else {
335 /* Seems legit. */
336 asprintf(&path, "%s/%s", le_base, requested);
337 ctype = "text/plain";
338 }
339 } else {
340 if (hosthdr != NULL && strstr(hosthdr, "zuccless.org")) {
341 tim = time(NULL);
342 srandom(tim);
343 wwwbase = zuccbase;
344 switch (random() % 3) {
345 case 0:
346 asprintf(&path, "%s/zucc-job.webm", zuccbase);
347 break;
348 default:
349 asprintf(&path, "%s/zucc-meat.webm", zuccbase);
350 break;
351 }
352 ctype = "video/webm";
353 } else {
354 asprintf(&path, "%s/%s", wwwbase, wwwindex);
355 ctype = "text/html";
356 }
357 }
358 if (hosthdr != NULL)
359 free(hosthdr);
360 free(request);
361
362 rlen = servefile(path, ctype, 1);
363 free(path);
364
365 if (user_agent_script_pid != -1) {
366 if (waitpid(user_agent_script_pid, NULL, 0) < 0) {
367 perror("waitpid");
368 return 1;
369 }
370 }
371
372 return rlen;
373 }
374