]> rtime.felk.cvut.cz Git - fpga/plasma.git/blob - kernel/http.c
Local copy of Plasma MIPS project.
[fpga/plasma.git] / kernel / http.c
1 /*--------------------------------------------------------------------
2  * TITLE: Plasma TCP/IP HTTP Server
3  * AUTHOR: Steve Rhoads (rhoadss@yahoo.com)
4  * DATE CREATED: 4/22/06
5  * FILENAME: http.c
6  * PROJECT: Plasma CPU core
7  * COPYRIGHT: Software placed into the public domain by the author.
8  *    Software 'as is' without warranty.  Author liable for nothing.
9  * DESCRIPTION:
10  *    Plasma TCP/IP HTTP Server
11  *--------------------------------------------------------------------*/
12 #ifdef WIN32
13 #include <stdio.h>
14 #include <stdlib.h>
15 #include <string.h>
16 #include <ctype.h>
17 #define _LIBC
18 #endif
19 #include "rtos.h"
20 #include "tcpip.h"
21 #ifdef WIN32
22 #define UartPrintf printf
23 #define OS_MQueueCreate(A,B,C) 0
24 #define OS_MQueueGet(A,B,C) 0
25 #define OS_ThreadCreate(A,B,C,D,E) 0
26 #endif
27
28 static const char pageGif[]=
29 {
30    "HTTP/1.0 200 OK\r\n"
31    "Content-Length: %d\r\n"
32    "Content-Type: binary/gif\r\n\r\n"
33 };
34 static const char pageGif2[]=
35 {
36    "HTTP/1.0 200 OK\r\n"
37    "Content-Type: binary/gif\r\n\r\n"
38 };
39 static const char pageBinary[]=
40 {
41    "HTTP/1.0 200 OK\r\n"
42    "Content-Length: %d\r\n"
43    "Content-Type: binary/binary\r\n\r\n"
44 };
45 static const char pageBinary2[]=
46 {
47    "HTTP/1.0 200 OK\r\n"
48    "Content-Type: binary/binary\r\n\r\n"
49 };
50 static const char pageHtml[]={
51    "HTTP/1.0 200 OK\r\n"
52    "Content-Length: %d\r\n"
53    "Content-Type: text/html\r\n\r\n"
54 };
55 static const char pageHtml2[]={
56    "HTTP/1.0 200 OK\r\n"
57    "Content-Type: text/html\r\n\r\n"
58 };
59 static const char pageText[]={
60    "HTTP/1.0 200 OK\r\n"
61    "Content-Length: %d\r\n"
62    "Content-Type: text/text\r\n\r\n"
63 };
64 static const char pageEmpty[]=
65 {
66    "HTTP/1.0 404 OK\r\n"
67    "Content-Length: 0\r\n"
68    "Content-Type: text/html\r\n\r\n"
69 };
70
71 static const PageEntry_t *HtmlPages;
72 static int HtmlFiles;
73
74
75 void HttpServer(IPSocket *socket)
76 {
77    uint8 buf[600];
78    char filename[80];
79    int bytes, i, length, len, needFooter;
80    char *name=NULL, *page=NULL;
81    const char *header, *header2;
82
83    if(socket == NULL)
84       return;
85    if(socket->funcPtr != HttpServer && socket->funcPtr)
86    {
87       socket->funcPtr(socket);
88       return;
89    }
90    bytes = IPRead(socket, buf, sizeof(buf)-1);
91    if(bytes)
92    {
93       buf[bytes] = 0;
94       if(strncmp((char*)buf, "GET /", 5) == 0)
95       {
96          for(i = 0; ; ++i)
97          {
98             length = HtmlPages[i].length;
99             if(length == -1)
100                break;
101             name = (char*)HtmlPages[i].name;
102             page = (char*)HtmlPages[i].page;
103             len = (int)strlen(name);
104             if(strncmp((char*)buf+4, name, len) == 0)
105                break;
106          }
107 #if defined(WIN32) || defined(INCLUDE_FILESYS)
108          if(length == HTML_LENGTH_LIST_END && HtmlFiles)
109          {
110             FILE *file;
111             char *ptr;
112
113             name = (char*)buf + 5;
114             ptr = strstr(name, " ");
115             if(ptr)
116                *ptr = 0;
117             strcpy(filename, "/web/");
118             strncat(filename, name, 60);
119             file = fopen(filename, "rb");
120             if(file == NULL)
121             {
122                strcpy(filename, "/flash/web/");
123                strncat(filename, name, 60);
124                file = fopen(filename, "rb");
125             }
126             if(file)
127             {
128                if(strstr(name, ".htm"))
129                   IPWrite(socket, (uint8*)pageHtml2, sizeof(pageHtml2)-1);
130                else if(strstr(name, ".gif"))
131                   IPWrite(socket, (uint8*)pageGif2, sizeof(pageGif2)-1);
132                else
133                   IPWrite(socket, (uint8*)pageBinary2, sizeof(pageBinary2)-1);
134                for(;;)
135                {
136                   len = fread(buf, 1, sizeof(buf), file);
137                   if(len == 0)
138                      break;
139                   IPWrite(socket, (uint8*)buf, len);
140                }
141                fclose(file);
142                IPWriteFlush(socket);
143                IPClose(socket);
144                return;
145             }
146          }
147 #endif
148          if(length != HTML_LENGTH_LIST_END)
149          {
150             if(length == HTML_LENGTH_CALLBACK)
151             {
152                IPFuncPtr funcPtr = (IPFuncPtr)(uint32)page;
153                funcPtr(socket, buf, bytes);
154                return;
155             }
156             if(length == 0)
157                length = (int)strlen(page);
158             needFooter = 0;
159             header2 = NULL;
160             if(strstr(name, ".html"))
161                header = pageHtml;
162             else if(strstr(name, ".htm") || strcmp(name, "/ ") == 0)
163             {
164                header = pageHtml;
165                header2 = HtmlPages[0].page;
166                needFooter = 1;
167             }
168             else if(strstr(HtmlPages[i].name, ".gif"))
169                header = pageGif;
170             else
171                header = pageBinary;
172             len = 0;
173             if(header2)
174                len += (int)strlen(header2) + (int)strlen(HtmlPages[1].page);
175             sprintf((char*)buf, header, length + len);
176             IPWrite(socket, buf, (int)strlen((char*)buf));
177             if(header2)
178                IPWrite(socket, (uint8*)header2, (int)strlen(header2));
179             IPWrite(socket, (uint8*)page, length);
180             if(needFooter)
181                IPWrite(socket, (uint8*)HtmlPages[1].page, (int)strlen(HtmlPages[1].page));
182          }
183          else
184          {
185             IPWrite(socket, (uint8*)pageEmpty, (int)strlen(pageEmpty));
186          }
187          IPClose(socket);
188       }
189    }
190 }
191
192
193 void HttpInit(const PageEntry_t *Pages, int UseFiles)
194 {
195    HtmlPages = Pages;
196    HtmlFiles = UseFiles;
197    IPOpen(IP_MODE_TCP, 0, 80, HttpServer);
198    IPOpen(IP_MODE_TCP, 0, 8080, HttpServer);
199 }
200
201
202 #ifdef EXAMPLE_HTML
203 //Example test code
204 static void MyProg(IPSocket *socket, char *request, int bytes)
205 {
206    char *text="HTTP/1.0 200 OK\r\nContent-Type: text/html\r\n\r\n"
207               "<html><body>Hello World!</body></html>";
208    (void)request; (void)bytes;
209    IPWrite(socket, (uint8*)text, (int)strlen(text));
210    IPClose(socket);
211 }
212 static const PageEntry_t pageEntry[]=
213 {  //name, length, htmlText
214    {"/Header", 0, "<HTML><HEAD><TITLE>Plasma CPU</TITLE></HEAD>\n<BODY>"},
215    {"/Footer", 0, "</BODY></HTML>"},
216    {"/ ", 0, "<h2>Home Page</h2>Welcome!  <a href='/other.htm'>Other</a>"
217              " <a href='/cgi/myprog'>myprog</a>"},
218    {"/other.htm ", 0, "<h2>Other</h2>Other."},
219    //{"/binary/plasma.gif ", 1945, PlasmaGif},
220    {"/cgi/myprog", HTML_LENGTH_CALLBACK, (char*)MyProg},
221    {"", HTML_LENGTH_LIST_END, NULL}
222 };
223 void HtmlInit(int UseFiles)
224 {
225    (void)UseFiles;
226    HttpInit(pageEntry, 1);
227 }
228 #endif
229
230