8
8
#include < WiFiClient.h>
9
9
#include < WebServer.h>
10
10
11
+ #include < ESPmDNS.h>
12
+ #include < DNSServer.h>
13
+
11
14
#include " webUI/index.h"
12
15
13
16
#include " src/utils.h"
@@ -24,82 +27,175 @@ WebServer server(80);
24
27
TaskHandle_t webapp;
25
28
TaskHandle_t nuggweb;
26
29
27
- void getPayloads () {
28
- String* payloadPaths = RubberNugget::allPayloadPaths ();
30
+ void getPayloads ()
31
+ {
32
+ String *payloadPaths = RubberNugget::allPayloadPaths ();
29
33
Serial.printf (" [SERVER][getPayloads] %s\n " , payloadPaths->c_str ());
30
34
server.send (200 , " text/plain" , *payloadPaths);
31
35
}
32
36
33
- void handleRoot () {
37
+ void handleRoot ()
38
+ {
34
39
Serial.println (" handling root!" );
35
40
server.send (200 , " text/html" , String (INDEX));
36
41
}
37
42
38
- void delpayload () {
43
+ void delpayload ()
44
+ {
39
45
String path (server.arg (" path" ));
40
46
FRESULT res = f_unlink (path.c_str ());
41
- if (res == FR_OK){
47
+ if (res == FR_OK)
48
+ {
42
49
server.send (200 );
43
- } else {
50
+ }
51
+ else
52
+ {
44
53
server.send (500 );
45
54
}
46
55
}
47
56
48
- void websave () {
49
- fileOp decodeOp = base64Decode (server.arg (" payloadText" ));
50
- if (!decodeOp.ok ){
51
- server.send (500 , " text/plain" , decodeOp.result );
57
+ void websave ()
58
+ {
59
+ // path should be corrected, i.e. by index.html's pathCorrector function
60
+ // Each path should start with '/' and not end with '/'
61
+ String path = (server.arg (" path" ));
62
+ const char *constPath = path.c_str ();
63
+
64
+ // construct directories as needed
65
+ FILINFO filinfo;
66
+ int pathSoFarIdx = 1 ;
67
+ while (true )
68
+ {
69
+ int nextDir = path.indexOf (" /" , pathSoFarIdx);
70
+ if (nextDir == -1 )
71
+ {
72
+ break ;
73
+ }
74
+ String pathSoFar = path.substring (0 , nextDir);
75
+ if (FR_OK != f_stat (pathSoFar.c_str (), &filinfo))
76
+ {
77
+ if (f_mkdir (pathSoFar.c_str ()) != FR_OK)
78
+ {
79
+ server.send (500 , " text/plain" , " Could not create directory" );
80
+ return ;
81
+ }
82
+ }
83
+ pathSoFarIdx = nextDir + 1 ;
84
+ }
85
+
86
+ // Create file
87
+ FIL file;
88
+ if (FR_OK != f_open (&file, constPath, FA_WRITE | FA_CREATE_ALWAYS))
89
+ {
90
+ server.send (500 , " text/plain" , " Could not open file for writing" );
52
91
return ;
53
92
}
54
- fileOp saveOp = saveFile (server.arg (" path" ), decodeOp.result );
55
- if (!saveOp.ok ){
56
- server.send (500 , " text/plain" , saveOp.result );
93
+
94
+ // Write to file
95
+ String content = (server.arg (" payloadText" ));
96
+ content.replace (" " , " /" ); // why
97
+ const char *contentBase64 = content.c_str ();
98
+ size_t payloadLength = BASE64::decodeLength (contentBase64);
99
+ uint8_t payloadContent[payloadLength];
100
+ BASE64::decode (contentBase64, payloadContent);
101
+ UINT written = 0 ;
102
+ if (FR_OK != f_write (&file, payloadContent, payloadLength, &written))
103
+ {
104
+ server.send (500 , " text/plain" , " Could not write to file" );
105
+ f_close (&file);
57
106
return ;
58
107
}
59
- server.send (200 , " text/plain" , " payload saved successfully" );
108
+ f_close (&file);
109
+ server.send (200 , " text/plain" , " Payload created successfully" );
110
+ }
111
+
112
+ // decode base64 and run
113
+ void webrunlive ()
114
+ {
115
+ server.send (200 , " text/plain" , " Running payload..." );
116
+ if (server.hasArg (" plain" ))
117
+ {
118
+ Serial.print (" Decoding: " );
119
+ String decoded = (server.arg (" plain" ));
120
+ char tab2[decoded.length () + 1 ];
121
+ strcpy (tab2, decoded.c_str ());
122
+
123
+ for (int i = 0 ; i < decoded.length (); i++)
124
+ {
125
+ Serial.print (tab2[i]);
126
+ }
127
+
128
+ Serial.println ();
129
+ Serial.println (decoded.length ());
130
+ Serial.println (" -------" );
131
+
132
+ uint8_t raw[BASE64::decodeLength (tab2)];
133
+ Serial.println (BASE64::decodeLength (tab2));
134
+ BASE64::decode (tab2, raw);
135
+
136
+ String meow = (char *)raw;
137
+ meow = meow.substring (0 , (int )BASE64::decodeLength (tab2));
138
+ RubberNugget::runLivePayload (meow);
139
+ Serial.println ();
140
+ Serial.println (" -------" );
141
+ }
60
142
}
61
143
62
- void webget () {
144
+ void webget ()
145
+ {
146
+ FRESULT fr;
147
+ FIL file;
148
+ uint16_t size;
149
+ UINT bytesRead;
150
+
63
151
String path = server.arg (" path" );
64
- fileOp op = readFile (path);
65
- if (!op.ok ) {
66
- // TODO: send 500/4XX depending on file existence vs internal error
67
- server.send (500 , " text/plain" , String (" error getting payload: " ) + op.result );
152
+ fr = f_open (&file, path.c_str (), FA_READ);
153
+
154
+ if (fr != FR_OK)
155
+ {
156
+ // TODO: most likely file not found, but we need to check why fr != OK.
157
+ // Marking 500 until resolved
158
+ server.send (500 , " plain/text" , String (" Error loading script" ));
68
159
return ;
69
160
}
70
- String payload = base64::encode (op.result );
71
- server.send (200 , " text/plain" , payload);
161
+
162
+ size = f_size (&file);
163
+ char *data = NULL ;
164
+
165
+ data = (char *)malloc (size);
166
+
167
+ fr = f_read (&file, data, (UINT)size, &bytesRead);
168
+ if (fr == FR_OK)
169
+ {
170
+ String payload = String (data);
171
+ payload = payload.substring (0 , bytesRead);
172
+ payload = base64::encode (payload);
173
+ server.send (200 , " plain/text" , payload);
174
+ }
175
+ else
176
+ {
177
+ server.send (500 , " plain/text" , String (" Error reading script" ));
178
+ }
179
+ f_close (&file);
72
180
}
73
181
74
182
NuggetInterface* nuggetInterface;
75
183
76
184
// run payload with get request path
77
- void webrun () {
78
- fileOp op = readFile (server.arg (" path" ));
79
- if (op.ok ) {
80
- server.send (200 , " text/html" , " Running payload..." );
81
- NuggetScreen* runner = new ScriptRunnerScreen (op.result );
82
- bool ok = nuggetInterface->injectScreen (runner);
83
- return ;
84
- }
85
- server.send (500 , " text/html" , " couldn't run payload: " + op.result );
185
+ void webrun ()
186
+ {
187
+ server.send (200 , " text/html" , " Running payload..." );
188
+ String path = server.arg (" path" );
189
+ RubberNugget::runPayload (path.c_str (), 1 ); // provide parameter triggered from webpage
86
190
}
87
191
88
- void webrunlive () {
89
- // TODO: use server.arg "content" or "payload" instead of "plain"
90
- fileOp op = base64Decode (server.arg (" plain" ));
91
- if (op.ok ) {
92
- server.send (200 , " text/plain" , " running live payload" );
93
- NuggetScreen* runner = new ScriptRunnerScreen (op.result );
94
- bool ok = nuggetInterface->injectScreen (runner);
95
- // TODO: send 503 when device is busy
96
- return ;
97
- }
98
- server.send (500 , " text/html" , " Device busy" );
99
- }
192
+ DNSServer dns;
100
193
101
- void webserverInit (void *p) {
102
- while (1 ) {
194
+ void webserverInit (void *p)
195
+ {
196
+ while (1 )
197
+ {
198
+ dns.processNextRequest ();
103
199
server.handleClient ();
104
200
vTaskDelay (2 );
105
201
}
@@ -108,27 +204,44 @@ void webserverInit(void *p) {
108
204
extern String netPassword;
109
205
extern String networkName;
110
206
111
- void setup () {
207
+
208
+
209
+ void setup ()
210
+ {
211
+ pinMode (12 , OUTPUT);
212
+ strip.begin ();
213
+ delay (500 );
214
+
112
215
Serial.begin (115200 );
113
216
114
217
RubberNugget::init ();
115
-
116
- if (networkName.length () >0 ) {
218
+
219
+ if (networkName.length () > 0 )
220
+ {
117
221
Serial.println (networkName);
118
- const char * c = networkName.c_str ();
119
- ssid= c;
222
+ const char *c = networkName.c_str ();
223
+ ssid = c;
120
224
}
121
- if (netPassword.length () >=8 ) {
225
+ if (netPassword.length () >= 8 )
226
+ {
122
227
Serial.println (netPassword);
123
- const char * d = netPassword.c_str ();
124
- password= d;
228
+ const char *d = netPassword.c_str ();
229
+ password = d;
125
230
}
126
231
127
232
WiFi.softAP (ssid, password);
233
+ // }
128
234
IPAddress myIP = WiFi.softAPIP ();
129
235
Serial.print (" AP IP address: " );
130
236
Serial.println (myIP);
131
237
238
+
239
+ dns.setErrorReplyCode (DNSReplyCode::NoError);
240
+ dns.start (53 , " *" , myIP);
241
+
242
+ MDNS.begin (" usb.nugg" );
243
+ Serial.println (" mDNS responder started" );
244
+
132
245
server.on (" /" , handleRoot);
133
246
server.on (" /payloads" , getPayloads);
134
247
server.on (" /savepayload" , HTTP_POST, websave);
@@ -139,6 +252,14 @@ void setup() {
139
252
140
253
server.begin ();
141
254
255
+ MDNS.addService (" http" , " tcp" , 80 );
256
+ strip.clear ();
257
+ strip.setPixelColor (0 , strip.Color (0 , 0 , 0 ));
258
+ strip.show ();
259
+ strip.show ();
260
+
261
+ // initialize & launch payload selector
262
+
142
263
xTaskCreate (webserverInit, " webapptask" , 12 * 1024 , NULL , 5 , &webapp); // create task priority 1
143
264
nuggetInterface = new NuggetInterface;
144
265
NuggetScreen* dirScreen = new DirScreen (" /" );
0 commit comments