blob: 92a50d647459b3ea0d6e0164c7410ddb75099d99 [file] [log] [blame]
adamdunkels5ca13272003-08-06 22:57:05 +00001/*
2 * Copyright (c) 2002, Adam Dunkels.
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above
11 * copyright notice, this list of conditions and the following
12 * disclaimer in the documentation and/or other materials provided
13 * with the distribution.
14 * 3. All advertising materials mentioning features or use of this
15 * software must display the following acknowledgement:
16 * This product includes software developed by Adam Dunkels.
17 * 4. The name of the author may not be used to endorse or promote
18 * products derived from this software without specific prior
19 * written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
22 * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
23 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
25 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE
27 * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
28 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
29 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
30 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
31 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32 *
33 * This file is part of the Contiki desktop environment
34 *
adamdunkels7cde6092003-08-24 22:35:22 +000035 * $Id: configedit.c,v 1.7 2003/08/24 22:35:22 adamdunkels Exp $
adamdunkels5ca13272003-08-06 22:57:05 +000036 *
37 */
38
39#include "uip_main.h"
40#include "uip.h"
41#include "uip_arp.h"
42#include "resolv.h"
43#include "ctk.h"
44#include "ctk-draw.h"
45#include "dispatcher.h"
46
47#include "uip-signal.h"
48
49#include "program-handler.h"
50
51#include "c64-fs.h"
52
53#include "loader.h"
54
adamdunkels93d8ea72003-08-09 23:27:57 +000055#include <stdio.h>
56
adamdunkels5ca13272003-08-06 22:57:05 +000057/* TCP/IP configuration window. */
58static struct ctk_window window;
59
adamdunkels93d8ea72003-08-09 23:27:57 +000060#define LABELMAXWIDTH 12
61
adamdunkels5ca13272003-08-06 22:57:05 +000062static struct ctk_label themelabel =
adamdunkels93d8ea72003-08-09 23:27:57 +000063 {CTK_LABEL(0, 1, LABELMAXWIDTH, 1, "CTK theme")};
adamdunkels5ca13272003-08-06 22:57:05 +000064static char theme[25];
65static struct ctk_textentry themetextentry =
adamdunkels93d8ea72003-08-09 23:27:57 +000066 {CTK_TEXTENTRY(LABELMAXWIDTH + 1, 1, 16, 1, theme, 24)};
adamdunkels5ca13272003-08-06 22:57:05 +000067
68static struct ctk_label driverlabel =
adamdunkels93d8ea72003-08-09 23:27:57 +000069 {CTK_LABEL(0, 3, LABELMAXWIDTH, 1, "Net driver")};
adamdunkels5ca13272003-08-06 22:57:05 +000070static char driver[25];
71static struct ctk_textentry drivertextentry =
adamdunkels93d8ea72003-08-09 23:27:57 +000072 {CTK_TEXTENTRY(LABELMAXWIDTH + 1, 3, 16, 1, driver, 24)};
73
74static struct ctk_label screensaverlabel =
75 {CTK_LABEL(0, 5, LABELMAXWIDTH, 1, "Screensaver")};
76static char screensaver[25];
77static struct ctk_textentry screensavertextentry =
78 {CTK_TEXTENTRY(LABELMAXWIDTH + 1, 5, 16, 1, screensaver, 24)};
adamdunkels5ca13272003-08-06 22:57:05 +000079
80
81static struct ctk_label ipaddrlabel =
adamdunkels93d8ea72003-08-09 23:27:57 +000082 {CTK_LABEL(0, 7, LABELMAXWIDTH, 1, "IP address")};
adamdunkels5ca13272003-08-06 22:57:05 +000083static char ipaddr[25];
84static struct ctk_textentry ipaddrtextentry =
adamdunkels93d8ea72003-08-09 23:27:57 +000085 {CTK_TEXTENTRY(LABELMAXWIDTH + 1, 7, 16, 1, ipaddr, 24)};
adamdunkels5ca13272003-08-06 22:57:05 +000086static struct ctk_label netmasklabel =
adamdunkels93d8ea72003-08-09 23:27:57 +000087 {CTK_LABEL(0, 9, LABELMAXWIDTH, 1, "Netmask")};
adamdunkels5ca13272003-08-06 22:57:05 +000088static char netmask[25];
89static struct ctk_textentry netmasktextentry =
adamdunkels93d8ea72003-08-09 23:27:57 +000090 {CTK_TEXTENTRY(LABELMAXWIDTH + 1, 9, 16, 1, netmask, 24)};
adamdunkels5ca13272003-08-06 22:57:05 +000091static struct ctk_label gatewaylabel =
adamdunkels93d8ea72003-08-09 23:27:57 +000092 {CTK_LABEL(0, 11, LABELMAXWIDTH, 1, "Gateway")};
adamdunkels5ca13272003-08-06 22:57:05 +000093static char gateway[25];
94static struct ctk_textentry gatewaytextentry =
adamdunkels93d8ea72003-08-09 23:27:57 +000095 {CTK_TEXTENTRY(LABELMAXWIDTH + 1, 11, 16, 1, gateway, 24)};
adamdunkels5ca13272003-08-06 22:57:05 +000096static struct ctk_label dnsserverlabel =
adamdunkels93d8ea72003-08-09 23:27:57 +000097 {CTK_LABEL(0, 13, LABELMAXWIDTH, 1, "DNS server")};
adamdunkels5ca13272003-08-06 22:57:05 +000098static char dnsserver[25];
99static struct ctk_textentry dnsservertextentry =
adamdunkels93d8ea72003-08-09 23:27:57 +0000100 {CTK_TEXTENTRY(LABELMAXWIDTH + 1, 13, 16, 1, dnsserver, 24)};
adamdunkels5ca13272003-08-06 22:57:05 +0000101
adamdunkelsa8a50ab2003-08-20 19:51:47 +0000102static struct ctk_button cancelbutton =
103 {CTK_BUTTON(0, 15, 6, "Cancel")};
104
105
adamdunkels5ca13272003-08-06 22:57:05 +0000106static struct ctk_button savebutton =
adamdunkelsa8a50ab2003-08-20 19:51:47 +0000107 {CTK_BUTTON(18, 15, 12, "Save & close")};
adamdunkels5ca13272003-08-06 22:57:05 +0000108
109static DISPATCHER_SIGHANDLER(configedit_sighandler, s, data);
110static struct dispatcher_proc p =
111 {DISPATCHER_PROC("Config editor", NULL, configedit_sighandler, NULL)};
112static ek_id_t id;
113
114
115
116
117/*-----------------------------------------------------------------------------------*/
118struct ptentry {
119 char c;
120 char * (* pfunc)(char *str);
121};
122
123/*-----------------------------------------------------------------------------------*/
124static char *
125parse(char *str, struct ptentry *t)
126{
127 struct ptentry *p;
128
129 /* Loop over the parse table entries in t in order to find one that
130 matches the first character in str. */
131 for(p = t; p->c != 0; ++p) {
132 if(*str == p->c) {
133 /* Skip rest of the characters up to the first space. */
134 while(*str != ' ') {
135 ++str;
136 }
137
138 /* Skip all spaces.*/
139 while(*str == ' ') {
140 ++str;
141 }
142
143 /* Call parse table entry function and return. */
144 return p->pfunc(str);
145 }
146 }
147
148 /* Did not find matching entry in parse table. We just call the
149 default handler supplied by the caller and return. */
150 return p->pfunc(str);
151}
152/*-----------------------------------------------------------------------------------*/
153static char *
154skipnewline(char *str)
155{
156 /* Skip all characters until the newline. */
157 while(*str != '\n') {
158 ++str;
159 }
160
161 /* Return a pointer to the first character after the newline. */
162 return str + 1;
163}
164/*-----------------------------------------------------------------------------------*/
165static char *
166nullterminate(char *str)
167{
168 char *nt;
169
170 /* Nullterminate string. Start with finding newline character. */
171 for(nt = str; *nt != '\r' &&
172 *nt != '\n'; ++nt);
173
174 /* Replace newline with a null char. */
175 *nt = 0;
176
adamdunkelsa8a50ab2003-08-20 19:51:47 +0000177 /* Remove trailing spaces. */
178 while(nt > str && *(nt - 1) == ' ') {
179 *(nt - 1) = 0;
180 --nt;
181 }
182
adamdunkels5ca13272003-08-06 22:57:05 +0000183 /* Return pointer to null char. */
184 return nt;
185}
186/*-----------------------------------------------------------------------------------*/
adamdunkels93d8ea72003-08-09 23:27:57 +0000187static char * __fastcall__
188copystr(char *dst, char *src, int len)
189{
190 char *nt = nullterminate(src);
191 strncpy(dst, src, len);
192 return nt + 1;
193}
194/*-----------------------------------------------------------------------------------*/
adamdunkels5ca13272003-08-06 22:57:05 +0000195static char *
196loaddriver(char *str)
197{
adamdunkels93d8ea72003-08-09 23:27:57 +0000198 return copystr(driver, str, sizeof(driver));
adamdunkels5ca13272003-08-06 22:57:05 +0000199}
200/*-----------------------------------------------------------------------------------*/
201static char *
202loadtheme(char *str)
203{
adamdunkels93d8ea72003-08-09 23:27:57 +0000204 return copystr(theme, str, sizeof(theme));
adamdunkels5ca13272003-08-06 22:57:05 +0000205}
206/*-----------------------------------------------------------------------------------*/
207static char *
adamdunkels1f982712003-08-09 23:40:17 +0000208loadscreensaver(char *str)
209{
210 return copystr(screensaver, str, sizeof(screensaver));
211}
212/*-----------------------------------------------------------------------------------*/
213static char *
adamdunkels5ca13272003-08-06 22:57:05 +0000214ipaddrconf(char *str)
215{
adamdunkels93d8ea72003-08-09 23:27:57 +0000216 return copystr(ipaddr, str, sizeof(ipaddr));
adamdunkels5ca13272003-08-06 22:57:05 +0000217}
218/*-----------------------------------------------------------------------------------*/
219static char *
220netmaskconf(char *str)
221{
adamdunkels93d8ea72003-08-09 23:27:57 +0000222 return copystr(netmask, str, sizeof(netmask));
adamdunkels5ca13272003-08-06 22:57:05 +0000223}
224/*-----------------------------------------------------------------------------------*/
225static char *
226drconf(char *str)
227{
adamdunkels93d8ea72003-08-09 23:27:57 +0000228 return copystr(gateway, str, sizeof(gateway));
adamdunkels5ca13272003-08-06 22:57:05 +0000229}
230/*-----------------------------------------------------------------------------------*/
231static char *
232dnsconf(char *str)
233{
adamdunkels93d8ea72003-08-09 23:27:57 +0000234 return copystr(dnsserver, str, sizeof(dnsserver));
adamdunkels5ca13272003-08-06 22:57:05 +0000235}
236/*-----------------------------------------------------------------------------------*/
237static struct ptentry initparsetab[] =
adamdunkelsa8a50ab2003-08-20 19:51:47 +0000238 {{'n', loaddriver},
adamdunkels5ca13272003-08-06 22:57:05 +0000239 {'t', loadtheme},
adamdunkels1f982712003-08-09 23:40:17 +0000240 {'s', loadscreensaver},
adamdunkels5ca13272003-08-06 22:57:05 +0000241 {'i', ipaddrconf},
adamdunkelsa8a50ab2003-08-20 19:51:47 +0000242 {'m', netmaskconf},
adamdunkels5ca13272003-08-06 22:57:05 +0000243 {'r', drconf},
adamdunkels5ca13272003-08-06 22:57:05 +0000244 {'d', dnsconf},
adamdunkels5ca13272003-08-06 22:57:05 +0000245 {'#', skipnewline},
246
247 /* Default action */
248 {0, skipnewline}};
249static void
250initscript(void)
251{
252 char line[40], *lineptr;
253 struct c64_fs_file f;
254
adamdunkelse89927e2003-08-06 23:14:20 +0000255 if(c64_fs_open("config.cfg", &f) == -1) {
adamdunkels5ca13272003-08-06 22:57:05 +0000256 return;
257 }
258 line[0] = ' ';
259 while(line[0] != '.' &&
260 line[0] != 0) {
261 lineptr = line;
262 do {
263 if(c64_fs_read(&f, lineptr, 1) != 1) {
264 c64_fs_close(&f);
265 return;
266 }
267 ++lineptr;
268 } while(*(lineptr - 1) != '\n' &&
269 *(lineptr - 1) != '\r');
270
271 *lineptr = 0;
272
273 if(line[0] != '.' &&
274 line[0] != 0) {
275 parse(line, initparsetab);
276 }
277
278 }
279 c64_fs_close(&f);
280 return;
281}
282/*-----------------------------------------------------------------------------------*/
adamdunkels81780132003-08-15 18:44:26 +0000283static int
284makeline(char *line, char c, char *str)
285{
286 int len;
287
288 len = strlen(str);
289
290 line[0] = c;
291 line[1] = ' ';
292 strcpy(&line[2], str);
293 line[2 + len] = '\n';
294 line[3 + len] = 0;
295 return len + 3;
296}
297/*-----------------------------------------------------------------------------------*/
adamdunkels5ca13272003-08-06 22:57:05 +0000298static void
299savescript(void)
300{
301 char line[40];
302 struct c64_fs_file f;
adamdunkels5ca13272003-08-06 22:57:05 +0000303
adamdunkelse89927e2003-08-06 23:14:20 +0000304 if(c64_fs_open("config.cfg", &f) == -1) {
adamdunkels5ca13272003-08-06 22:57:05 +0000305 return;
306 }
307 if(theme[0] != 0) {
adamdunkels81780132003-08-15 18:44:26 +0000308 c64_fs_write(&f, line, makeline(line, 't', theme));
adamdunkels5ca13272003-08-06 22:57:05 +0000309 }
310 if(driver[0] != 0) {
adamdunkelsa8a50ab2003-08-20 19:51:47 +0000311 c64_fs_write(&f, line, makeline(line, 'n', driver));
adamdunkels5ca13272003-08-06 22:57:05 +0000312 }
313 if(ipaddr[0] != 0) {
adamdunkels81780132003-08-15 18:44:26 +0000314 c64_fs_write(&f, line, makeline(line, 'i', ipaddr));
adamdunkels5ca13272003-08-06 22:57:05 +0000315 }
316 if(netmask[0] != 0) {
adamdunkelsa8a50ab2003-08-20 19:51:47 +0000317 c64_fs_write(&f, line, makeline(line, 'm', netmask));
adamdunkels5ca13272003-08-06 22:57:05 +0000318 }
319 if(gateway[0] != 0) {
adamdunkels81780132003-08-15 18:44:26 +0000320 c64_fs_write(&f, line, makeline(line, 'r', gateway));
adamdunkels5ca13272003-08-06 22:57:05 +0000321 }
322 if(dnsserver[0] != 0) {
adamdunkels81780132003-08-15 18:44:26 +0000323 c64_fs_write(&f, line, makeline(line, 'd', dnsserver));
adamdunkels93d8ea72003-08-09 23:27:57 +0000324 }
325
326 if(screensaver[0] != 0) {
adamdunkels81780132003-08-15 18:44:26 +0000327 c64_fs_write(&f, line, makeline(line, 's', screensaver));
adamdunkels5ca13272003-08-06 22:57:05 +0000328 }
329
adamdunkels81780132003-08-15 18:44:26 +0000330 strcpy(line, ".\n\0\n\n\n");
adamdunkels93d8ea72003-08-09 23:27:57 +0000331 c64_fs_write(&f, line, strlen(line));
adamdunkels5ca13272003-08-06 22:57:05 +0000332
333 c64_fs_close(&f);
334
335}
336/*-----------------------------------------------------------------------------------*/
adamdunkels7cde6092003-08-24 22:35:22 +0000337LOADER_INIT_FUNC(configedit_init, arg)
adamdunkels5ca13272003-08-06 22:57:05 +0000338{
adamdunkels7cde6092003-08-24 22:35:22 +0000339 arg_free(arg);
340
adamdunkels5ca13272003-08-06 22:57:05 +0000341 if(id == EK_ID_NONE) {
342 id = dispatcher_start(&p);
343
344 /* Create window. */
adamdunkels93d8ea72003-08-09 23:27:57 +0000345 ctk_window_new(&window, 32, 16, "Config editor");
adamdunkels5ca13272003-08-06 22:57:05 +0000346
347 CTK_WIDGET_ADD(&window, &themelabel);
348 CTK_WIDGET_ADD(&window, &themetextentry);
349
350 CTK_WIDGET_ADD(&window, &driverlabel);
351 CTK_WIDGET_ADD(&window, &drivertextentry);
352
adamdunkels93d8ea72003-08-09 23:27:57 +0000353 CTK_WIDGET_ADD(&window, &screensaverlabel);
354 CTK_WIDGET_ADD(&window, &screensavertextentry);
355
adamdunkels5ca13272003-08-06 22:57:05 +0000356 CTK_WIDGET_ADD(&window, &ipaddrlabel);
357 CTK_WIDGET_ADD(&window, &ipaddrtextentry);
358 CTK_WIDGET_ADD(&window, &netmasklabel);
359 CTK_WIDGET_ADD(&window, &netmasktextentry);
360 CTK_WIDGET_ADD(&window, &gatewaylabel);
361 CTK_WIDGET_ADD(&window, &gatewaytextentry);
362 CTK_WIDGET_ADD(&window, &dnsserverlabel);
363 CTK_WIDGET_ADD(&window, &dnsservertextentry);
364
adamdunkelsa8a50ab2003-08-20 19:51:47 +0000365 CTK_WIDGET_ADD(&window, &cancelbutton);
adamdunkels5ca13272003-08-06 22:57:05 +0000366 CTK_WIDGET_ADD(&window, &savebutton);
adamdunkels5ca13272003-08-06 22:57:05 +0000367
368 CTK_WIDGET_FOCUS(&window, &themetextentry);
369
370 /* Fill the configuration strings with values from the current
371 configuration */
372 initscript();
373
374 dispatcher_listen(ctk_signal_button_activate);
375 dispatcher_listen(ctk_signal_window_close);
376 }
377 ctk_window_open(&window);
378}
379/*-----------------------------------------------------------------------------------*/
380
381/*-----------------------------------------------------------------------------------*/
382static void
383configedit_quit(void)
384{
385 dispatcher_exit(&p);
386 id = EK_ID_NONE;
387 LOADER_UNLOAD();
388}
389/*-----------------------------------------------------------------------------------*/
390static
391DISPATCHER_SIGHANDLER(configedit_sighandler, s, data)
392{
393 DISPATCHER_SIGHANDLER_ARGS(s, data);
394
395 if(s == ctk_signal_button_activate) {
396 if(data == (ek_data_t)&savebutton) {
397 savescript();
398 ctk_window_close(&window);
adamdunkelsa8a50ab2003-08-20 19:51:47 +0000399 configedit_quit();
adamdunkels7cde6092003-08-24 22:35:22 +0000400 program_handler_load("config.prg", NULL);
adamdunkelsa8a50ab2003-08-20 19:51:47 +0000401 } else if(data == (ek_data_t)&cancelbutton) {
adamdunkels5ca13272003-08-06 22:57:05 +0000402 ctk_window_close(&window);
403 configedit_quit();
adamdunkels5ca13272003-08-06 22:57:05 +0000404 }
405 } else if(s == ctk_signal_window_close ||
406 s == dispatcher_signal_quit) {
407 ctk_window_close(&window);
408 configedit_quit();
409 }
410}
411/*-----------------------------------------------------------------------------------*/