source: src/router/httpd/modules/upgrade.c @ 31701

Last change on this file since 31701 was 31701, checked in by brainslayer, 7 days ago

not sure if this is correct

File size: 19.2 KB
Line 
1
2/*
3 * Broadcom Home Gateway Reference Design
4 * Web Page Configuration Support Routines
5 *
6 * Copyright 2001-2003, Broadcom Corporation
7 * All Rights Reserved.
8 *
9 * THIS SOFTWARE IS OFFERED "AS IS", AND BROADCOM GRANTS NO WARRANTIES OF ANY
10 * KIND, EXPRESS OR IMPLIED, BY STATUTE, COMMUNICATION OR OTHERWISE. BROADCOM
11 * SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS
12 * FOR A SPECIFIC PURPOSE OR NONINFRINGEMENT CONCERNING THIS SOFTWARE.
13 * $Id: upgrade.c,v 1.4 2005/11/30 11:53:42 seg Exp $
14 */
15
16#include <stdio.h>
17#include <string.h>
18#include <fcntl.h>
19#include <errno.h>
20#include <signal.h>
21#include <sys/stat.h>
22#include <stdlib.h>
23#include <unistd.h>
24#include <sys/wait.h>
25
26#include <broadcom.h>
27#include <cyutils.h>
28#include <shutils.h>
29#include <byteswap.h>
30#include <endian.h>             /* for __BYTE_ORDER */
31
32#if (__BYTE_ORDER == __LITTLE_ENDIAN)
33#  define HOST_TO_BE32(x)       bswap_32(x)
34#  define HOST_TO_BE16(x)       bswap_16(x)
35#else
36#  define HOST_TO_BE32(x)       (x)
37#  define HOST_TO_BE16(x)       (x)
38#endif
39
40#ifndef HAVE_MICRO
41#define MIN_BUF_SIZE    65536
42#else
43#define MIN_BUF_SIZE    4096
44#endif
45#define CODE_PATTERN_ERROR 9999
46static int upgrade_ret;
47
48void set_upgrade_ret(int result)
49{
50        if (result != 0) {
51                upgrade_ret = result;
52        } else {
53                upgrade_ret = NULL;
54        }
55}
56
57void
58// do_upgrade_cgi(char *url, FILE *stream)
59do_upgrade_cgi(struct mime_handler *handler, char *url, webs_t stream, char *query)     // jimmy, https,
60                                                        // 8/6/2003
61{
62#ifndef ANTI_FLASH
63
64        fprintf(stderr, "[UPGRADE] ret: %d\n", upgrade_ret);
65        if (upgrade_ret) {
66                do_ej(handler, "Fail_u_s.asp", stream, NULL);
67                killall("ledtool", SIGTERM);
68                led_control(LED_DIAG, LED_OFF);
69        } else {
70                do_ej(handler, "Success_u_s.asp", stream, NULL);
71        }
72        websDone(stream, 200);
73
74        /*
75         * Reboot if successful
76         */
77        if (upgrade_ret == 0) {
78                // sleep (10);
79                sys_reboot();
80        }
81#else
82
83        do_ej(handler, "Fail_u_s.asp", stream, NULL);
84        websDone(stream, 200);
85
86#endif
87}
88
89typedef struct {
90        char magic[8];          // "FIRMWARE"
91        char ver_inter[4];
92        char ver_outer[4];
93        char model[24];
94        unsigned int len;
95        unsigned int crc32;
96} ralink_firmware_header;
97
98static char *allmagics[] = {
99        CODE_PATTERN_WRT54G,
100        CODE_PATTERN_WRT54GS,
101        CODE_PATTERN_WRH54G,
102        CODE_PATTERN_WRT150N,
103        CODE_PATTERN_WRT160N,
104        CODE_PATTERN_WRT300N,
105        CODE_PATTERN_WRT300NV11,
106        CODE_PATTERN_WRT310N,
107        CODE_PATTERN_WRT350N,
108        CODE_PATTERN_WRTSL54GS,
109        CODE_PATTERN_WRT54G3G,
110        CODE_PATTERN_WRT54G3GV,
111        CODE_PATTERN_WRT610N,
112        CODE_PATTERN_WRT54GSV4,
113        CODE_PATTERN_WRT320N,
114        CODE_PATTERN_VALET_M10,
115        CODE_PATTERN_VALET_M20,
116        CODE_PATTERN_E900,
117        CODE_PATTERN_E800,
118        CODE_PATTERN_E1000,
119        CODE_PATTERN_E1200V1,
120        CODE_PATTERN_E1200V2,
121        CODE_PATTERN_E1500,
122        CODE_PATTERN_E1550,
123        CODE_PATTERN_E2000,
124        CODE_PATTERN_E2500,
125        CODE_PATTERN_E3000,
126        CODE_PATTERN_E3200,
127        CODE_PATTERN_E4200,
128        CODE_PATTERN_NV60K,
129        CODE_PATTERN_NV64K,
130        NULL
131};
132
133static char *nv60k[] = {
134        CODE_PATTERN_E1550,
135        CODE_PATTERN_E2000,
136        CODE_PATTERN_E2500,
137        CODE_PATTERN_E3000,
138        CODE_PATTERN_E3200,
139        CODE_PATTERN_E4200,
140        CODE_PATTERN_NV60K,
141        NULL
142};
143
144static char *nv64k[] = {
145        CODE_PATTERN_E900,
146        CODE_PATTERN_E800,
147        CODE_PATTERN_E1200V1,
148        CODE_PATTERN_E1200V2,
149        CODE_PATTERN_E1500,
150        CODE_PATTERN_NV64K,
151        NULL
152};
153
154static int checkmagic(char *magic, char *check[])
155{
156        int cnt = 0;
157        while (check[cnt]) {
158                if (!memcmp(magic, check[cnt], 4))
159                        return 0;
160                cnt++;
161        }
162        return -1;
163}
164
165int
166// sys_upgrade(char *url, FILE *stream, int *total)
167sys_upgrade(char *url, webs_t stream, int *total, int type)     // jimmy,
168                                                                // https,
169                                                                // 8/6/2003
170{
171
172        int brand = getRouterBrand();
173
174#ifndef ANTI_FLASH
175        char upload_fifo[] = "/tmp/uploadXXXXXX";
176        FILE *fifo = NULL;
177        char *write_argv[4];
178        pid_t pid;
179        char *buf = NULL;
180        int count, ret = 0;
181        long flags = -1;
182        int size = BUFSIZ;
183        int i = 0;
184#if (defined(HAVE_FONERA) || defined(HAVE_WHRAG108) || defined(HAVE_MERAKI) || defined(HAVE_TW6600) || defined(HAVE_PB42) || defined(HAVE_LS5) || defined(HAVE_USR5453)) && \
185(!defined(HAVE_DIR400) && !defined(HAVE_WRT54G2) && !defined(HAVE_GWMF54G2) && !defined(HAVE_FONERA2200) && !defined(HAVE_MR3202A) && !defined(HAVE_CA8PRO) &&  \
186!defined(HAVE_CA8) && !defined(HAVE_RT2880) && !defined(HAVE_LS2) && !defined(HAVE_WRK54G) && !defined(HAVE_ADM5120) && !defined(HAVE_DIR300) && !defined(HAVE_DLM101) && \
187!defined(HAVE_MERAKI) && !defined(HAVE_SOLO51) && !defined(HAVE_RTG32) && !defined(HAVE_EOC5610) && !defined(HAVE_NP25G))
188#define WRITEPART "rootfs"
189#else
190#define WRITEPART "linux"
191#endif
192
193        write_argv[0] = "write";
194        write_argv[1] = upload_fifo;
195        write_argv[2] = WRITEPART;
196        write_argv[3] = NULL;
197        eval("fischecksum");
198        if (url)
199                return eval("write", url, WRITEPART);
200        // diag_led(DIAG, START_LED); // blink the diag led
201        C_led(1);
202#ifdef HAVE_HTTPS
203        if (do_ssl)
204                ACTION("ACT_WEBS_UPGRADE");
205        else
206#endif
207                ACTION("ACT_WEB_UPGRADE");
208        int uploadcount = 0;
209
210        /*
211         * Set nonblock on the socket so we can timeout
212         */
213#ifdef HAVE_HTTPS
214        if (!do_ssl) {
215#endif
216                if ((flags = fcntl(fileno(stream->fp), F_GETFL)) < 0 || fcntl(fileno(stream->fp), F_SETFL, flags | O_NONBLOCK) < 0) {
217                        ret = errno;
218                        goto err;
219                }
220#ifdef HAVE_HTTPS
221        }
222#endif
223
224        /*
225         ** The buffer must be at least as big as what the stream file is
226         ** using so that it can read all the data that has been buffered
227         ** in the stream file. Otherwise it would be out of sync with fn
228         ** select specially at the end of the data stream in which case
229         ** the select tells there is no more data available but there in
230         ** fact is data buffered in the stream file's buffer. Since no
231         ** one has changed the default stream file's buffer size, let's
232         ** use the constant BUFSIZ until someone changes it.
233         **/
234
235        if (size < MIN_BUF_SIZE)
236                size = MIN_BUF_SIZE;
237        fprintf(stderr, "use buffer size %d\n", size);
238        if ((buf = safe_malloc(size)) == NULL) {
239                ret = ENOMEM;
240                goto err;
241        }
242        eval("ledtool", "500");
243        /*
244         * Pipe the rest to the FIFO
245         */
246        cprintf("Upgrading\n");
247        int lastblock = 0;
248        while (total && *total) {
249#ifdef HAVE_HTTPS
250                if (do_ssl) {
251                        if (size > *total)
252                                size = *total;
253                        count = wfread(buf, 1, size, stream);
254                } else
255#endif
256                {
257                        if (waitfor(fileno(stream->fp), 5) <= 0) {
258                                lastblock = 1;
259                        }
260                        count = safe_fread(buf, 1, size, stream->fp);
261                        if (!count && (ferror(stream->fp) || feof(stream->fp))) {
262                                break;
263                        }
264                }
265
266                if (i == 0) {   // check code pattern, the first data must
267#ifdef HAVE_VENTANA
268                        if (!strncmp(buf, "UBI#", 4)) { // check for "UBI#"
269                                eval("mount", "-o", "remount,ro", "/");
270                                char *write_argv_buf[8];
271                                fprintf(stderr, "erase nandflash\n");
272                                eval("mtd", "erase", "rootfs");
273                                sleep(10);
274                                write_argv_buf[0] = "mtd";
275                                write_argv_buf[1] = "-f";
276                                write_argv_buf[2] = "write";
277                                write_argv_buf[3] = upload_fifo;
278                                write_argv_buf[4] = "rootfs";
279                                write_argv_buf[5] = NULL;
280                                if (!mktemp(upload_fifo) || mkfifo(upload_fifo, S_IRWXU) < 0 || (ret = _evalpid(write_argv_buf, NULL, 0, &pid))
281                                    || !(fifo = fopen(upload_fifo, "w"))) {
282                                        if (!ret)
283                                                ret = errno;
284                                        goto err;
285                                }
286                                goto write_data;
287                        }
288#endif
289//0x1200000 0x70000 RN67
290#ifdef HAVE_IPQ806X
291
292#define _WEB_HEADER_ "RN67"
293#define FW_HEADER                       ((char *)"CSYS")
294#define DWORD_SWAP(v)   ((((v&0xff)<<24)&0xff000000) | \
295                                                ((((v>>8)&0xff)<<16)&0xff0000) | \
296                                                ((((v>>16)&0xff)<<8)&0xff00) | \
297                                                (((v>>24)&0xff)&0xff) )
298
299                        typedef struct img_header {
300                                unsigned char signature[4];
301                                unsigned int startAddr __attribute__((packed));
302                                unsigned int burnAddr __attribute__((packed));
303                                unsigned char modTag[4];
304                                unsigned int len __attribute__((packed));
305                        } __attribute__((packed)) img_header_t;
306                        if (brand == ROUTER_ASROCK_G10) {
307                                img_header_t *header = (img_header_t *) buf;
308                                if (!memcmp(header->signature, FW_HEADER, 4) && !memcmp(header->modTag, _WEB_HEADER_, 4)) {
309                                        fprintf(stderr, "found valid ASROCK-G10 Image\n");
310                                        sysprintf("startservice bootprimary");
311                                //      sysprintf("startservice finishupgrade");
312                                        count -= sizeof(struct img_header);
313                                        memcpy(buf, buf + sizeof(struct img_header), count);
314                                        char *write_argv_buf[8];
315                                        write_argv_buf[0] = "mtd";
316                                        write_argv_buf[1] = "-e";
317                                        write_argv_buf[2] = "linux";
318                                        write_argv_buf[3] = "-f";
319                                        write_argv_buf[4] = "write";
320                                        write_argv_buf[5] = upload_fifo;
321                                        write_argv_buf[6] = "linux";
322                                        write_argv_buf[7] = NULL;
323                                        if (!mktemp(upload_fifo) || mkfifo(upload_fifo, S_IRWXU) < 0 || (ret = _evalpid(write_argv_buf, NULL, 0, &pid))
324                                            || !(fifo = fopen(upload_fifo, "w"))) {
325                                                if (!ret)
326                                                        ret = errno;
327                                                goto err;
328                                        }
329                                        goto write_data;
330                                }
331                        }
332#endif
333#if defined(HAVE_DIR860) || defined(HAVE_DIR859)
334#define SEAMA_MAGIC             0x5EA3A417
335
336                        typedef struct seama_hdr seamahdr_t;
337                        struct seama_hdr {
338                                unsigned int magic;     /* should always be SEAMA_MAGIC. */
339                                unsigned short reserved;        /* reserved for  */
340                                unsigned short metasize;        /* size of the META data */
341                                unsigned int size;      /* size of the image */
342                        } __attribute__((packed));
343                        seamahdr_t *seama = (seamahdr_t *) buf;
344
345                        if (seama->magic == HOST_TO_BE32(SEAMA_MAGIC)) {
346                                unsigned int skip = HOST_TO_BE16(seama->metasize) + sizeof(seamahdr_t);
347                                fprintf(stderr, "found seama header, skip seal header of %d bytes\n", skip);
348                                if (skip > count)
349                                        goto err;
350#ifdef HAVE_DIR869
351#define signature "signature=wrgac54_dlink.2015_dir869"
352#elif HAVE_DIR859
353#define signature "signature=wrgac37_dlink.2013gui_dir859"
354#else
355#define signature "signature=wrgac13_dlink.2013gui_dir860lb"
356#endif
357                                if (memcmp(buf + sizeof(seamahdr_t), signature, sizeof(signature))) {
358                                        fprintf(stderr, "firmware signature must be %s\n", signature);
359                                        goto err;
360                                }
361
362                                count -= skip;
363                                memcpy(buf, buf + skip, count);
364                                char *write_argv_buf[8];
365                                write_argv_buf[0] = "mtd";
366                                write_argv_buf[1] = "-f";
367                                write_argv_buf[2] = "write";
368                                write_argv_buf[3] = upload_fifo;
369                                write_argv_buf[4] = "linux";
370                                write_argv_buf[5] = NULL;
371                                if (!mktemp(upload_fifo) || mkfifo(upload_fifo, S_IRWXU) < 0 || (ret = _evalpid(write_argv_buf, NULL, 0, &pid))
372                                    || !(fifo = fopen(upload_fifo, "w"))) {
373                                        if (!ret)
374                                                ret = errno;
375                                        goto err;
376                                }
377                                goto write_data;
378
379                        }
380#endif
381#if defined(HAVE_DIR862)
382                        unsigned int *uboot_magic = (unsigned int *)buf;
383                        if (*uboot_magic == HOST_TO_BE32(0x27051956)) {
384                                char *write_argv_buf[8];
385                                write_argv_buf[0] = "mtd";
386                                write_argv_buf[1] = "-f";
387                                write_argv_buf[2] = "write";
388                                write_argv_buf[3] = upload_fifo;
389                                write_argv_buf[4] = "linux";
390                                write_argv_buf[5] = NULL;
391                                if (!mktemp(upload_fifo) || mkfifo(upload_fifo, S_IRWXU) < 0 || (ret = _evalpid(write_argv_buf, NULL, 0, &pid))
392                                    || !(fifo = fopen(upload_fifo, "w"))) {
393                                        if (!ret)
394                                                ret = errno;
395                                        goto err;
396                                }
397                                goto write_data;
398                        }
399#endif
400#if defined(HAVE_DAP2230) || defined(HAVE_DAP2330) || defined(HAVE_DAP2660) || defined(HAVE_DAP3662) || defined(HAVE_DAP3320)
401#ifdef HAVE_DAP2660
402#define MAGIC "wapac09_dkbs_dap2660"
403#elif HAVE_DAP2330
404#define MAGIC "wapn24_dkbs_dap2330"
405#elif HAVE_DAP3662
406#define MAGIC "wapac11_dkbs_dap3662"
407#elif HAVE_DAP3320
408#define MAGIC "wapn29_dkbs_dap3320"
409#elif HAVE_DAP2230
410#define MAGIC "wapn31_dkbs_dap2230"
411#endif
412                        if (!strncmp(buf, MAGIC, strlen(MAGIC))) {
413                                char *write_argv_buf[8];
414                                write_argv_buf[0] = "mtd";
415                                write_argv_buf[1] = "-f";
416                                write_argv_buf[2] = "write";
417                                write_argv_buf[3] = upload_fifo;
418                                write_argv_buf[4] = "linux";
419                                write_argv_buf[5] = NULL;
420                                if (!mktemp(upload_fifo) || mkfifo(upload_fifo, S_IRWXU) < 0 || (ret = _evalpid(write_argv_buf, NULL, 0, &pid))
421                                    || !(fifo = fopen(upload_fifo, "w"))) {
422                                        if (!ret)
423                                                ret = errno;
424                                        goto err;
425                                }
426                                goto write_data;
427                        }
428#endif
429#if defined(HAVE_BUFFALO) || defined(HAVE_IDEXX)
430                        ralink_firmware_header fh;
431                        memcpy(&fh, buf, sizeof(fh));
432                        char *str;
433                        str = (char *)&fh;
434                        unsigned char ch, temp;
435                        int idx, index;
436                        ch = 0xff;
437                        index = sizeof(fh) - 1;
438                        for (idx = 0; idx < sizeof(fh) / 2; idx++) {
439                                temp = str[idx];
440                                str[idx] = str[index - idx];
441                                str[index - idx] = temp;
442                        }
443                        for (idx = 0; idx < sizeof(fh); idx++)
444                                str[idx] ^= ch;
445                        if (!strncmp(buf, "bgn", 3) || !strncmp(buf, "WZR", 3)
446                            || !strncmp(buf, "WHR", 3)
447                            || !strncmp(buf, "WLA", 3)
448                            ) {
449                                char *write_argv_buf[4];
450                                write_argv_buf[0] = "buffalo_flash";
451                                write_argv_buf[1] = upload_fifo;
452#if defined(HAVE_IDEXX) || defined(HAVE_IDEXX_SIGNATUR)
453                                write_argv_buf[2] = "verify";
454                                write_argv_buf[3] = NULL;
455#else
456                                write_argv_buf[2] = NULL;
457#endif
458                                if (!mktemp(upload_fifo) || mkfifo(upload_fifo, S_IRWXU) < 0 || (ret = _evalpid(write_argv_buf, NULL, 0, &pid))
459                                    || !(fifo = fopen(upload_fifo, "w"))) {
460                                        if (!ret)
461                                                ret = errno;
462                                        goto err;
463                                }
464                                goto write_data;
465                        } else if (!strncmp(fh.magic, "FIRMWARE", 8)) { // check for "FIRMWARE"
466                                char *write_argv_buf[4];
467                                write_argv_buf[0] = "buffalo_flash";
468                                write_argv_buf[1] = upload_fifo;
469                                write_argv_buf[2] = "ralink";
470#if defined(HAVE_IDEXX) || defined(HAVE_IDEXX_SIGNATUR)
471                                write_argv_buf[3] = "verify";
472                                write_argv_buf[4] = NULL;
473#else
474                                write_argv_buf[3] = NULL;
475#endif
476                                if (!mktemp(upload_fifo) || mkfifo(upload_fifo, S_IRWXU) < 0 || (ret = _evalpid(write_argv_buf, NULL, 0, &pid))
477                                    || !(fifo = fopen(upload_fifo, "w"))) {
478                                        if (!ret)
479                                                ret = errno;
480                                        goto err;
481                                }
482                                goto write_data;
483                        } else {
484#ifdef HAVE_IDEXX_SIGNATUR
485                                goto err;
486#endif
487                                if (!mktemp(upload_fifo) || mkfifo(upload_fifo, S_IRWXU) < 0 || (ret = _evalpid(write_argv, NULL, 0, &pid))
488                                    || !(fifo = fopen(upload_fifo, "w"))) {
489                                        if (!ret)
490                                                ret = errno;
491                                        goto err;
492                                }
493
494                        }
495
496#else
497                        /*
498                         * Feed write from a temporary FIFO
499                         */
500                        if (!mktemp(upload_fifo) || mkfifo(upload_fifo, S_IRWXU) < 0 || (ret = _evalpid(write_argv, NULL, 0, &pid)) || !(fifo = fopen(upload_fifo, "w"))) {
501                                if (!ret)
502                                        ret = errno;
503                                goto err;
504                        }
505#endif
506                        // have code pattern
507                        char ver[40];
508                        long ver1, ver2, ver3;
509                        snprintf(ver, sizeof(ver), "v%d.%d.%d", buf[11], buf[12], buf[13]);
510                        ver1 = convert_ver(ver);
511                        ver2 = convert_ver(INTEL_FLASH_SUPPORT_VERSION_FROM);
512                        ver3 = convert_ver(BCM4712_CHIP_SUPPORT_VERSION_FROM);
513                        fprintf(stderr, "upgrade_ver[%s] upgrade_ver[%ld] intel_ver[%ld] 4712_ver[%ld]\n", ver, ver1, ver2, ver3);
514#if defined(HAVE_WIKINGS) || defined(HAVE_ESPOD)
515#ifdef HAVE_WIKINGS
516#ifdef HAVE_SUB3
517#define V "XMED"
518#elif HAVE_SUB6
519#define V "XMIN"
520#else
521#define V "XMAX"
522#endif
523#endif
524#ifdef HAVE_ESPOD
525#ifdef HAVE_SUB3
526#define V "EPMN"
527#elif HAVE_SUB6
528#define V "EPMD"
529#else
530#define V "EPMX"
531#endif
532#endif
533                        if (memcmp(&buf[0], V, 4)) {
534                                fprintf(stderr, "code pattern error!\n");
535                                goto write_data;        // must be there, otherwise fail here
536                                //goto err;     // must be there, otherwise fail here
537                        }
538#undef V
539#endif
540
541#if defined(HAVE_WIKINGS) || defined(HAVE_ESPOD)
542#else
543#ifdef HAVE_WRT160NL
544                        if (memcmp(&buf[0], &CODE_PATTERN_WRT160NL, 4)
545                            && memcmp(&buf[0], &CODE_PATTERN_E2100L, 4)) {
546                                cprintf("code pattern error!\n");
547                                goto err;       // must be there, otherwise fail here
548                        }
549#else
550
551#ifndef HAVE_80211AC
552                        if (brand == ROUTER_LINKSYS_E1550 || (brand == ROUTER_WRT320N && nvram_match("boardrev", "0x1307"))     //E2000
553                            || brand == ROUTER_LINKSYS_E2500 || (brand == ROUTER_WRT610NV2 && nvram_match("boot_hw_model", "E300"))     //E3000
554                            || brand == ROUTER_LINKSYS_E3200 || brand == ROUTER_LINKSYS_E4200) {
555                                if (checkmagic(&buf[0], nv60k)) {
556                                        cprintf("image not compatible with nv60k router!\n");
557                                        goto err;       // must be there, otherwise fail here
558                                }
559                        } else if (brand == ROUTER_NETGEAR_WNDR4000 || brand == ROUTER_NETGEAR_WNDR3400 || brand == ROUTER_LINKSYS_E900 || brand == ROUTER_LINKSYS_E800 || brand == ROUTER_LINKSYS_E1500) {
560                                if (checkmagic(&buf[0], nv64k)) {
561                                        cprintf("image not compatible with nv64k router!\n");
562                                        goto err;       // must be there, otherwise fail here
563                                }
564                        } else {
565                                if (memcmp(&buf[0], &CODE_PATTERN_NV60K, 4) == 0 || memcmp(&buf[0], &CODE_PATTERN_NV64K, 4) == 0) {
566                                        cprintf("image not compatible with your router!\n");
567                                        goto err;       // fail here                           
568                                }
569                        }
570#endif
571                        if (checkmagic(&buf[0], allmagics)) {
572                                cprintf("code pattern error!\n");
573                                goto write_data;
574                        }
575#endif
576#endif
577
578                        if (check_hw_type() == BCM4712_CHIP && ver1 < ver3) {
579                                fprintf(stderr, "The old firmware version can't support bcm4712 chipset\n");
580                                fprintf(stderr, "Can't downgrade to this old firmware version (%s), must be above %s(included)\n", ver, BCM4712_CHIP_SUPPORT_VERSION_FROM);
581                                goto write_data;
582                        }
583
584                        fprintf(stderr, "code pattern correct!\n");
585                        *total -= count;
586#ifdef HAVE_WRT160NL
587                        safe_fwrite(buf, 1, count, fifo);       // we have to write the whole header to flash too
588#else
589                        safe_fwrite(&buf[sizeof(struct code_header)], 1, count - sizeof(struct code_header), fifo);
590#endif
591                        i++;
592                        continue;
593                }
594
595              write_data:
596                *total -= count;
597                safe_fwrite(buf, 1, count, fifo);
598                uploadcount += count;
599                fprintf(stderr, "uploading [%d]\r", uploadcount);
600                if (lastblock)
601                        break;
602                i++;
603        }
604
605        fprintf(stderr, "uploading [%d]\n", uploadcount);
606        fclose(fifo);
607        fifo = NULL;
608        /*
609         * Wait for write to terminate
610         */
611        waitpid(pid, &ret, 0);
612        cprintf("done\n");
613#ifdef HAVE_HTTPS
614        if (!do_ssl) {
615#endif
616                /*
617                 * Reset nonblock on the socket
618                 */
619                if (fcntl(fileno(stream->fp), F_SETFL, flags) < 0) {
620                        ret = errno;
621                        goto err;
622                }
623#ifdef HAVE_HTTPS
624        }
625#endif
626
627err:
628        if (buf)
629                free(buf);
630        if (fifo)
631                fclose(fifo);
632        unlink(upload_fifo);
633        // diag_led(DIAG, STOP_LED);
634        C_led(0);
635        ACTION("ACT_IDLE");
636        return ret;
637#else
638        return 0;
639#endif
640}
641
642void
643// do_upgrade_post(char *url, FILE *stream, int len, char *boundary)
644do_upgrade_post(char *url, webs_t stream, int len, char *boundary)      // jimmy,
645                                                                        // https,
646                                                                        // 8/6/2003
647{
648        killall("udhcpc", SIGKILL);
649
650#ifndef ANTI_FLASH
651        int type = 0;
652        char *buf = malloc(1024);
653        upgrade_ret = EINVAL;
654
655        /*
656         * Look for our part
657         */
658        while (len > 0) {
659                if (!wfgets(buf, MIN(len + 1, 1024), stream)) {
660                        free(buf);
661                        return;
662                }
663
664                len -= strlen(buf);
665                if (!strncasecmp(buf, "Content-Disposition:", 20)) {
666                        if (strstr(buf, "name=\"erase\"")) {
667                                while (len > 0 && strcmp(buf, "\n")
668                                       && strcmp(buf, "\r\n")) {
669                                        if (!wfgets(buf, MIN(len + 1, 1024), stream)) {
670                                                free(buf);
671                                                return;
672                                        }
673
674                                        len -= strlen(buf);
675                                }
676                                if (!wfgets(buf, MIN(len + 1, 1024), stream)) {
677                                        free(buf);
678                                        return;
679                                }
680                                len -= strlen(buf);
681                                buf[1] = '\0';  // we only want the 1st digit
682                                nvram_set("sv_restore_defaults", buf);
683                                nvram_commit();
684                        } else if (strstr(buf, "name=\"file\"")) {      // upgrade image
685                                type = 0;
686                                break;
687                        }
688                }
689        }
690
691        /*
692         * Skip boundary and headers
693         */
694        while (len > 0) {
695                if (!wfgets(buf, MIN(len + 1, 1024), stream)) {
696                        free(buf);
697                        return;
698                }
699
700                len -= strlen(buf);
701                if (!strcmp(buf, "\n") || !strcmp(buf, "\r\n"))
702                        break;
703        }
704
705        upgrade_ret = sys_upgrade(NULL, stream, &len, type);
706
707        /*
708         * Restore factory original settings if told to. This will also cause a
709         * restore defaults on reboot of a Sveasoft firmware.
710         */
711#ifdef HAVE_BUFFALO_SA
712        int region_sa = 0;
713        if (nvram_default_match("region", "SA", ""))
714                region_sa = 1;
715#endif
716        if (nvram_matchi("sv_restore_defaults", 1)) {
717                eval("erase", "nvram");
718#ifdef HAVE_BUFFALO_SA
719                nvram_seti("sv_restore_defaults", 1);
720                if (region_sa)
721                        nvram_set("region", "SA");
722#endif
723        }
724        sys_commit();
725
726        /*
727         * Slurp anything remaining in the request
728         */
729
730        wfgets(buf, len, stream);
731        free(buf);
732#endif
733}
Note: See TracBrowser for help on using the repository browser.