Skip to content

Commit 85be0f3

Browse files
earlephilhowerigrr
authored andcommitted
Move MIME type table into PROGMEM to save RAM (#3475)
The extension -> MIME type routine uses lots of constant strings which end up in the RODATA segment of RAM. Refactor the comparison to use a table of strings stored in PMMEM instead, freeing ~370 bytes for the heap.
1 parent 4bed115 commit 85be0f3

File tree

1 file changed

+38
-23
lines changed

1 file changed

+38
-23
lines changed

libraries/ESP8266WebServer/src/detail/RequestHandlersImpl.h

+38-23
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,32 @@
33

44
#include "RequestHandler.h"
55

6+
// Table of extension->MIME strings stored in PROGMEM, needs to be global due to GCC section typing rules
7+
static const struct {const char endsWith[16]; const char mimeType[32];} mimeTable[] ICACHE_RODATA_ATTR = {
8+
{ ".html", "text/html" },
9+
{ ".htm", "text/html" },
10+
{ ".css", "text/css" },
11+
{ ".txt", "text/plain" },
12+
{ ".js", "application/javascript" },
13+
{ ".json", "application/json" },
14+
{ ".png", "image/png" },
15+
{ ".gif", "image/gif" },
16+
{ ".jpg", "image/jpeg" },
17+
{ ".ico", "image/x-icon" },
18+
{ ".svg", "image/svg+xml" },
19+
{ ".ttf", "application/x-font-ttf" },
20+
{ ".otf", "application/x-font-opentype" },
21+
{ ".woff", "application/font-woff" },
22+
{ ".woff2", "application/font-woff2" },
23+
{ ".eot", "application/vnd.ms-fontobject" },
24+
{ ".sfnt", "application/font-sfnt" },
25+
{ ".xml", "text/xml" },
26+
{ ".pdf", "application/pdf" },
27+
{ ".zip", "application/zip" },
28+
{ ".gz", "application/x-gzip" },
29+
{ ".appcache", "text/cache-manifest" },
30+
{ "", "application/octet-stream" } };
31+
632
class FunctionRequestHandler : public RequestHandler {
733
public:
834
FunctionRequestHandler(ESP8266WebServer::THandlerFunction fn, ESP8266WebServer::THandlerFunction ufn, const String &uri, HTTPMethod method)
@@ -116,29 +142,18 @@ class StaticRequestHandler : public RequestHandler {
116142
}
117143

118144
static String getContentType(const String& path) {
119-
if (path.endsWith(".html")) return "text/html";
120-
else if (path.endsWith(".htm")) return "text/html";
121-
else if (path.endsWith(".css")) return "text/css";
122-
else if (path.endsWith(".txt")) return "text/plain";
123-
else if (path.endsWith(".js")) return "application/javascript";
124-
else if (path.endsWith(".json")) return "application/json";
125-
else if (path.endsWith(".png")) return "image/png";
126-
else if (path.endsWith(".gif")) return "image/gif";
127-
else if (path.endsWith(".jpg")) return "image/jpeg";
128-
else if (path.endsWith(".ico")) return "image/x-icon";
129-
else if (path.endsWith(".svg")) return "image/svg+xml";
130-
else if (path.endsWith(".ttf")) return "application/x-font-ttf";
131-
else if (path.endsWith(".otf")) return "application/x-font-opentype";
132-
else if (path.endsWith(".woff")) return "application/font-woff";
133-
else if (path.endsWith(".woff2")) return "application/font-woff2";
134-
else if (path.endsWith(".eot")) return "application/vnd.ms-fontobject";
135-
else if (path.endsWith(".sfnt")) return "application/font-sfnt";
136-
else if (path.endsWith(".xml")) return "text/xml";
137-
else if (path.endsWith(".pdf")) return "application/pdf";
138-
else if (path.endsWith(".zip")) return "application/zip";
139-
else if(path.endsWith(".gz")) return "application/x-gzip";
140-
else if (path.endsWith(".appcache")) return "text/cache-manifest";
141-
return "application/octet-stream";
145+
char buff[sizeof(mimeTable[0].mimeType)];
146+
// Check all entries but last one for match, return if found
147+
for (size_t i=0; i < sizeof(mimeTable)/sizeof(mimeTable[0])-1; i++) {
148+
strcpy_P(buff, mimeTable[i].endsWith);
149+
if (path.endsWith(buff)) {
150+
strcpy_P(buff, mimeTable[i].mimeType);
151+
return String(buff);
152+
}
153+
}
154+
// Fall-through and just return default type
155+
strcpy_P(buff, mimeTable[sizeof(mimeTable)/sizeof(mimeTable[0])-1].mimeType);
156+
return String(buff);
142157
}
143158

144159
protected:

0 commit comments

Comments
 (0)