#include <sys/types.h>
#include <sys/socket.h>
#include <sys/un.h>
#include <stdio.h>
#include <netinet/in.h>

#define ADDRESS     "mysocket"  /* addr to connect */
#define BUFLEN 2048

serve_line(int s, char* line){
	send(s, line, strlen(line), 0);
}

serve_page1(int s){
	serve_line (s, "Content-type: text/html\n\n");
    serve_line (s, "<b>Web Server Demo by Sandy Dunlop</b><br><br>\n");
    serve_line (s, "This is a test.<br><br>\n");
    serve_line (s, "<a href=\"/main.html\">click here</a>\n");
}

serve_page2(int s){
	serve_line (s, "Content-type: text/html\n\n");
    serve_line (s, "<b>Web Server Demo by Sandy Dunlop</b><br><br>\n");
    serve_line (s, "Page 2.\n");
}

main()
{
    char c;
    FILE *fp;
    int fromlen;
    register int i, s, len;
    struct sockaddr_in from;

    char* hostname = (char*) NULL;
    struct sockaddr_in sin;
    int n=0, b=0;
    long addr;
    struct hostent *rmthost;
    char hostidstr[1024];
    char buf[BUFLEN];
    char* url;
    char* u;
    char* proto;
    int header_line;
    int request_type;
	int arg;
    int child;

    sin.sin_family = AF_INET;
    sin.sin_port = htons(1000);
    sin.sin_addr.s_addr = INADDR_ANY;

    if ((s = socket(AF_INET, SOCK_STREAM, 0)) < 0) {
        perror("server: socket");
        exit(1);
    }

   /*
     * Conditionally reuse address. This option is intended to allow the
     * server to run even though there are dead connections still in place.
     */
	arg = 1;
	if (setsockopt(s, SOL_SOCKET, SO_REUSEADDR, (char *)&arg,
		 sizeof arg) < 0) {
	    perror("Unable to set socket option");
	    exit(6);
	}

    /*
     * Set SO_KEEPALIVE option on socket so that the TCP connection should
     * eventually clean itself up if anything untoward happens.
     */
	arg = 1;
	if (setsockopt(s, SOL_SOCKET, SO_KEEPALIVE, (char *)&arg,
		       sizeof arg) < 0) {
	    /*
	     * Don't consider this to be critical error if it cannot be set
	     * so use logstat() and don't exit.
	     */
	    perror("Unable to set socket SO_KEEPALIVE option");
	}

    if (bind(s, (struct sockaddr *)&sin, sizeof sin) < 0){
        perror("server: bind");
        exit(1);
    }

    if (listen(s, 5) < 0) {
        perror("server: listen");
        exit(1);
    }

    
    while(1){
        n = accept(s, (struct sockaddr *)&from, &fromlen);
        if (n < 0) {
            perror("server: accept");
            exit(1);
        }c=='\r' ||
        printf ("\nConnection accepted\n");

        /* TODO: Fork() here */

        child = fork();
        switch(child){

            case 0:
                fp = fdopen(n, "rw");

                header_line=0;
                request_type=0;
                while (c!=EOF){
                    b=0;
                    while ((c = fgetc(fp)) != EOF) {
                        if (b<BUFLEN-1){
                            buf[b++]=c;
                        }else{
                        }
                        if (c=='\0' || c=='\n'){
                            /* end of string*/
                            if (c=='\n')
                                buf[b-1]='\0'; /* ensire it ends with NULL*/
                            break;
                        }
                    }
                    buf[b]='\0';
                    if (b<=2)
                        c=EOF;
                    /*
                    printf ("GOT: %s\n", buf);
                    */

                    if (header_line==0){
                        /* initial request */
                        buf[3]='\0';
                        u=buf+4;
                        proto = strchr(u,' ');
                        u[proto-u] = '\0';
                        proto++;
                        if (!strcmp(buf, "GET")){
                            request_type = 1;
                            url = strdup(u);
                        }
                        if (!strcmp(buf, "PUT")){
                            printf ("HTTP PUT\n");
                        }
                    }

                    header_line++;
                }
                if (request_type==1){
                	printf ("HTTP GET: %s.\n", url);
                	if (!strcmp(url, "/main.html")){
                    	serve_page2(n);
                    }else{
                    	serve_page1(n);
                    }
                    free(url);
                }
                shutdown (n,2);
                exit(0);
            default:  /*parent*/
                break;
		}/* end of switch*/
	}
    close(s);
    exit(0);
}
