39 Commits
Author SHA1 Message Date
Pali Rohár a6ec475a92 Merge branch 'pvc' into legacy 2013-01-14 19:30:10 +01:00
Pali Rohár 783222ed00 Remove code which is not for version 0.5 2012-08-13 11:08:05 +02:00
Pali Rohár f62628bf29 Update fiasco documentation 2012-07-14 09:22:47 +02:00
Pali Rohár 8301455a5b Align also kernel image 2012-07-14 09:21:34 +02:00
Pali Rohár 860d71d18a Fix prepaired new 0xFFFF options 2012-06-24 15:00:52 +02:00
Pali Rohár 48384d4e47 Rename n700 --> 770 2012-06-24 11:43:11 +02:00
Pali Rohár ce177a9588 Update usb device table 2012-06-24 11:42:41 +02:00
Pali Rohár 2421b9f6c2 fiasco - remove dead code 2012-06-23 21:26:30 +02:00
Pali Rohár eac07b18d9 Added option to use only image pieces for specific device / hw revision 2012-06-23 18:49:07 +02:00
Pali Rohár 418f3cfd4b Cold Flasher - Remove duplicate usb code, prepair for flashing form fiasco images 2012-06-23 18:19:08 +02:00
Pali Rohár 3f0d6f85d3 Import my open source tool for Cold Flashing: cold-flasher-rx51.c 2012-06-23 18:17:49 +02:00
Pali Rohár 027a6d9a18 Fix compilation warnings 2012-06-23 17:39:33 +02:00
Pali Rohár 58c0dbe275 Update fiasco documentation, now is on 95% complete 2012-06-23 17:03:25 +02:00
Pali Rohár 2110196958 Fiasco image: Allow to specify device string without hw revision (then image is valid for all hw revisions). Generating images should be complete! 2012-06-23 17:01:48 +02:00
Pali Rohár 9195f3c7da Fixed creating fiasco images, added param version: for specifing sw-ver. Now generated fiasco images are valid for nokia flasher. 2012-06-23 16:54:05 +02:00
Pali Rohár 4f92794cdf Rename fwname to swver 2012-06-23 16:21:28 +02:00
Pali Rohár 535561efbf Fix unpacking fiasco images (check for number of subsections). Now unpacking is complete! 2012-06-23 15:54:13 +02:00
Pali Rohár 5da30a5bc5 Fix memory problems when unpacking fiasco images 2012-06-23 15:01:10 +02:00
Pali Rohár 8fdba437af Unpacking fiasco - added support for FW headers (FW name) 2012-06-23 14:09:33 +02:00
Pali Rohár 583cc8a963 When identifing fiasco image, show all pieces 2012-06-23 13:24:12 +02:00
Pali Rohár 491f06015b Added preview of new 0xFFFF arguments to main.c. This change will be needed to support other flashing modes (cold, MK II, ...) 2012-06-23 13:15:44 +02:00
Pali Rohár 1aca3bef85 Fix creating fiasco images - added support for specifing device, hwrevs, version, mmc layout and auto align mmc images
Format of arguments for adding piece to fiasco image is now:
$ 0xFFFF -p [[[[dev:hw:]ver:]type:]file[%%layout]
2012-06-23 13:11:54 +02:00
Pali Rohár b4575a40fc Rename hwrev to hwrevs and fix unpacking fiasco images. hwrevs do not have to be separated by nullterm if size of hwrev is 8. 2012-06-23 13:09:44 +02:00
Pali Rohár 8bc521f3e5 do_hash_file - align size for mmc images, append chars \xff (nokia flasher needs mmc images alingned) 2012-06-23 13:07:34 +02:00
Pali Rohár b1cfc3181b Prepair flash_image for specifing device and hw revisions 2012-06-23 13:05:46 +02:00
Pali Rohár 1ddf269c69 Prepair piece structure for device & hw revisions 2012-06-23 13:02:52 +02:00
Pali Rohár dc910a5317 Prepair for flashing via MK II protocol (N900 in PC-Suite mode) 2012-06-23 13:00:12 +02:00
pancake 34c8fb057d * Apply Pali Rohár patch - Add support for device and hw revisions specified in hw pieces - Updated documentation - Fixed problems when unpacking - Ready for mmc and cold flashing 2012-06-23 10:43:20 +02:00
pancake 04f9369ace * Apply Pali Rohár patch fixing RX51 Fiasco Image parsing 2011-12-16 16:17:17 +01:00
pancake b0f69c8b6b * Add manpages (thanks sre!) 2010-11-18 16:32:00 +01:00
pancake dc4fd72133 * Fix warning in dump.c * Port GUI to GtkON syntax * Fix build for latest valac
--HG--
rename : src/gui/gui.gtkaml => src/gui/gui.gtkaml.orig
2010-11-18 00:30:13 +01:00
pancake 20eed53d8c * Fix usb initialization link with n900 * minor syntax fixup 2010-04-26 18:29:19 +02:00
pancake e2aaa2cb40 * Add C files of the gui, so it can be built without gtkamlc or valac * Fix build of gui.gtkaml (sync with last vala) * Update version number in gui about dialog * Some syntax cleanup and removed some unnecesary printf calls 2009-12-22 00:08:47 +01:00
pancake 4d7899fa40 * Use /usr/local PREFIX by default * Bump revision to 0.5 2009-12-21 23:16:28 +01:00
pancake@flubox 3f975a93b3 * Fix segmentation fault with -O2 while unpacking (thanks for reporting) * Various random checks to ensure read/write ops are success 2009-12-21 14:40:12 +01:00
pancake@localhost.localdomain 5f4476566d * Fix n900 identification for dump (-e) * Make clean libusb from the root makefile 2009-10-18 21:03:16 +02:00
pancake@localhost.localdomain b7206abf11 * Fix static build 2009-10-17 15:51:00 +02:00
pancake@localhost.localdomain 034b17cef4 * Added support for local n900 nand dump * Do some code cleanup, update headers from 2007 to 2009 :) - Fix warning messages 2009-10-17 15:43:39 +02:00
pancake a6ef73359c * Apply security patches from Erik Hovland - Thanks! 2008-12-19 19:39:27 +01:00
33 changed files with 2556 additions and 404 deletions

No files matched your search

+3
View File
@@ -22,6 +22,7 @@ logot:
clean:
cd src && ${MAKE} clean
cd libusb && ${MAKE} clean
cd logotool && ${MAKE} clean
install:
@@ -31,6 +32,8 @@ install:
-cp src/gui/goxf ${DESTDIR}${PREFIX}/bin
cp logotool/logotool ${DESTDIR}${PREFIX}/bin
cp 0xFFFF.desktop ${DESTDIR}${PREFIX}/share/applications/
mkdir -p ${DESTDIR}${PREFIX}/share/man/man1
cp man/*.1 ${DESTDIR}${PREFIX}/share/man/man1
deinstall:
rm -f ${DESTDIR}${PREFIX}/bin/0xFFFF
+7 -4
View File
@@ -1,10 +1,13 @@
VERSION=0.4.0
PREFIX=/usr
VERSION=0.5
PREFIX=/usr/local
# NetBSD stuff
CFLAGS+=-I/usr/pkg/include -O2
CFLAGS+=-I/usr/pkg/include -g -O2
LDFLAGS+=-L/usr/pkg/lib -Wl,-R/usr/pkg/lib
HAVE_USB=1
HAVE_GUI=1
# For linking against this copy of libusb
#CFLAGS+=-I../libusb
+2 -2
View File
@@ -40,14 +40,14 @@ and sometimes (in the early days often) replacing proprietary software.
The non-free bits in the core infrastructure of the IT OS 2007 are a road block
for efforts to create free operating systems/distributions besides IT OS on the
N770/N800.
770/N800.
The reason for why it is helpful to have other operating system/distribution on
the N800 is simple: There are hundreds of GNU/Linux distributions out there.
Each one exists because there is a userbase that exactly likes their flavor of
GNU/Linux.
For the N770/N800 Internet Tablets there exists only one such distribution: The
For the 770/N800 Internet Tablets there exists only one such distribution: The
Internet Tablet OS. With the sheer amount of GNU/Linux distributions for
desktops/workstations/servers/routers/PDAs on the one hand and the single OS
solution for the Internet Tablets on the other I doubt that it can handle all
+4 -4
View File
@@ -50,7 +50,7 @@ This file tries to collect a bunch of common questions/answers about flashing
flashed together.
On the n800 firmwares, these two pieces are distributed in a single
file, but when flashing a n770, NOLO requires to provide the xloader
file, but when flashing a 770, NOLO requires to provide the xloader
(without commiting) and then the secondary piece.
This piece of software is closed source and is the responsable of
@@ -61,13 +61,13 @@ This file tries to collect a bunch of common questions/answers about flashing
<b>*) How can I identify my device?</b>
Theorically n770 and n800 have different USB device ID, but this is not
Theorically 770 and n800 have different USB device ID, but this is not
true at all. The first series of the n800 comes with the same usb-id
than n770. That's weird!
than 770. That's weird!
So, the only way to identify the device is by asking nolo for the version
information of different pieces of the firmware. This can be faked, because
you can flash n770 stuff on n800 and viceversa, but it's not recommended
you can flash 770 stuff on n800 and viceversa, but it's not recommended
because it wouldn't work :)
+34 -15
View File
@@ -1,3 +1,6 @@
Copyright (C) 2007-2011 pancake <pancake@youterm.com>
Copyright (C) 2011-2012 Pali Rohár <pali.rohar@gmail.com>
SPECS FOR TEH FIASCO FIRMWARE FILE FORMAT ffff!
-----------------------------------------------
@@ -8,23 +11,39 @@ SPECS FOR TEH FIASCO FIRMWARE FILE FORMAT ffff!
FILE HEADER
1 byte = 0xb4 -- signature
4 bytes -- firmware name length (big endian)
6 bytes -- versioning info ( byte 4 is format version )
N-6 bytes -- firmware name (zero fill)
4 bytes -- FW header length (big endian)
PIECE HEADER
FW HEADER
1 byte = 0x54 -- piece signature
6 bytes -- unknown
2 bytes -- checksum for the piece contents (xorpair)
12 bytes -- piece name (first byte is FF if is the last)
4 bytes -- piece size (big endian)
4 bytes -- unknown
4 bytes -- number of FW header blocks (big endian)
block {
1 byte -- if (value '1'-'9') { ..there's a comment.. }
1 byte -- length of comment
N bytes -- comment
1 byte -- type of block
0xE8 - Fiasco name
0x31 - FW name
1 byte -- length of block data
N bytes -- block data
}
N bytes -- piece data
IMAGE
1 byte = 0x54 -- signature
1 byte -- number of subsection blocks + 1
5 bytes -- unknown (always 0x2e 0x19 0x01 0x01 0x00)
2 bytes -- checksum for the image contents (xorpair) (big endian)
12 bytes -- image name type (first byte is FF if is the last image)
4 bytes -- length of image data (big endian)
4 bytes -- unknown (always 0x00 0x00 0x00 0x00)
block {
1 byte -- type of subsection block
'1' - version
'2' - device & hw revisions (separated by char 0x00, max size of device is 16, hw revision 8)
'3' - layout
'4' - unknown
'/' - unknown
1 byte -- length of subsection block
N bytes -- subsection block data
}
1 byte -- unknown (maybe end of subsections?)
N bytes -- image data
+1 -1
View File
@@ -21,4 +21,4 @@ have flashed properly every piece inside the device, but keep in mind
that it is dangerous and you can brick your device.
But feel free to send feedback to provide a full support for local
flashing on n770 and n800.
flashing on 770 and n800.
+1 -1
View File
@@ -37,7 +37,7 @@ Pieces can be automatically identified by using the '-I' flag:
You can dump these pieces from the internal memory of the internet
tablet by using the mtd-utils over /dev/mtd* or just running:
n770$ 0xFFFF -e /media/mmc1
770$ 0xFFFF -e /media/mmc1
There is another way for dumping pieces with extra parameters and options,
read doc/dumping for more information.
+1 -1
View File
@@ -1,7 +1,7 @@
<b>Usage guide</b>
0xFFFF is a free software implementation of the flasher for the Nokia Internet
Tablets (n770 and n800).
Tablets (770 and n800).
<pre>
- flash separated pieces of the firmware.
- retrieve information about the device
+1
View File
@@ -60,6 +60,7 @@ int compress_image(char *srcf, char *dstf, int w, int h)
fdout = open( dstf, O_TRUNC | O_CREAT | O_WRONLY , 0660 );
if (fdout == -1) {
printf("Cannot open file '%s' for writing\n", dstf);
fclose(fd);
return 1;
}
+2
View File
@@ -107,5 +107,7 @@ int rgb2yuv(char *from, char *to, int width, int height)
for ( i = 0 ; i < height ; i+=2 )
for ( j = 0; j < width ; j +=2 )
write ( fout,&dstV[j+(i*width)], 1);
free(dstV); free(dstU); free(dstY); free(src);
return 1;
}
+3 -2
View File
@@ -71,7 +71,7 @@ int uncompress_image(char *srcf, char *dstf)
src = malloc ( fsize );
dst = malloc ( width*height*2 );
deof = dst+width*height*2;
if ((int)src == -1 || (int)dst == -1 ) {
if (src == (void *)-1 || dst == (void *)-1 ) {
printf("Cannot malloc\n");
return 1;
}
@@ -105,7 +105,7 @@ int uncompress_image(char *srcf, char *dstf)
}
}
}
fprintf(stderr, "Output Size: %d\n",dst2-dst);
fprintf(stderr, "Output Size: %lld\n",(long long int)(dst2-dst));
if ((dst2-dst)!=(width*height*2))
fprintf(stderr, "failed?\n");
@@ -119,5 +119,6 @@ int uncompress_image(char *srcf, char *dstf)
//printf("logotool -w %d -h %d -v %s\n", width, height, dstf);
printf("eval PATH=$PWD:$PATH logotool -w %d -h %d -m %s\n", width, height, dstf);
free(dst); free(src);
return 0;
}
+99
View File
@@ -0,0 +1,99 @@
.TH 0xFFFF 1 "November 18, 2010"
.\" Please adjust this date whenever revising the manpage.
.SH NAME
0xFFFF \- Open Free Fiasco Firmware Flasher
.SH SYNOPSIS
.B 0xFFFF
.RB [OPTION]...
.SH DESCRIPTION
The 'Open Free Fiasco Firmware Flasher' aka 0xFFFF utility implements
a free (GPL3) userspace handler for the NOLO bootloader and related
utilities for the Nokia Internet Tablets like flashing, setting device
options, packing/unpacking FIASCO firmware format and more.
.SH OPTIONS
.TP
.BI -b [args]
boots the kernel with arguments
.TP
.BI -c
console prompt mode
.TP
.BI -d [vid:pid]
injects a usb device into the supported list
.TP
.BI -D [0|1|2]
sets the root device to flash (0), mmc (1) or usb (2)
.TP
.BI -f <flags>
set the given RD flags (see '-f help')
.TP
.BI -i
show device information (let standby mode)
.TP
.BI -l
list supported usb device ids
.TP
.BI -p [[p%]file]
piece-of-firmware % file-where-this-piece-is
.TP
.BI -r [0|1]
disable/enable R&D mode
.TP
.BI -R
reboot the omap board
.TP
.BI -U [0|1]
disable/enable the usb host mode
.TP
.BI -Q
enter shared queues server mode (for gui or remote)
.TP
.BI -s [serial]
serial port console (minicom like terminal)
.TP
.BI -h
show help message
.TP
.BI -S [subversion]
unpacks/flash pieces matching this sub-version information
.TP
.BI -n
do not flash or write to disk (simulation)
.TP
.BI -C [/dev/mtd]
check bad blocks on mtd
.TP
.BI -e [path]
dump/extract pieces to path
.TP
.BI -F [fiasco]
flash a fiasco firmware image
.TP
.BI -H [file]
calculate hash for file
.TP
.BI -I [piece]
identify a firmware piece
.TP
.BI -P [new-fiasco]
creates a new fiasco package, pieces as arguments
.TP
.BI -u [fiasco]
unpack target fiasco image
.TP
.BI -v
be verbose and noisy
.TP
.BI -V
show version information and exit.
.TP
.BI -x
extract configuration entries from /dev/mtd1
.SH AUTHOR
0xFFFF was written by pancake.
.PP
This manual page was written by Sebastian Reichel <elektranox@gmail.com>,
for the Debian project (but may be used by others).
+20
View File
@@ -0,0 +1,20 @@
.TH GOXF 1 "November 18, 2010"
.\" Please adjust this date whenever revising the manpage.
.SH NAME
goxf \- 0xFFFF GUI
.SH SYNOPSIS
.B goxf
.RB [FILE]
.SH DESCRIPTION
This utility is a graphical interface to 0xFFFF. It is used to
communicate with the NOLO bootloader of Nokia's internet tablets
(770, N800, N810, N900).
.SH OPTIONS
goxf takes no options.
.SH SEE ALSO
.B 0xFFFF(1)
.SH AUTHOR
goxf was written by pancake.
.PP
This manual page was written by Sebastian Reichel <elektranox@gmail.com>,
for the Debian project (but may be used by others).
+41
View File
@@ -0,0 +1,41 @@
.TH LOGOTOOL 1 "November 18, 2010"
.\" Please adjust this date whenever revising the manpage.
.SH NAME
logotool \- FIASCO logo file tool
.SH SYNOPSIS
.B logotool
.RB [OPTION]...
.SH DESCRIPTION
Tool to compress, uncompress or watch FIASCO logo files.
.SH OPTIONS
.TP
.BI -u img
uncompress image to img.rgb
.TP
.BI -c img
compres a 24 bit rgb raw image to a 16(565) one
.TP
.BI -m img
show image using mplayer (dumps to <img>.yuv)
.TP
.BI -v img
view uncompressed image using the 'display' command from ImageMagick (in monochrome)
.TP
.BI -w
specify width (required for -v and -c)
.TP
.BI -a
force RGBA instead of RGB when compressing (use with -c)
.TP
.BI -h
specify height (required for -v and -c)
.TP
.BI -V
show version information and exit.
.SH SEE ALSO
.B 0xFFFF(1)
.SH AUTHOR
logotool was written by pancake and esteve.
.PP
This manual page was written by Sebastian Reichel <elektranox@gmail.com>,
for the Debian project (but may be used by others).
+4 -1
View File
@@ -6,10 +6,13 @@ BIN=0xFFFF
#LIBS=`${HAVE_USB} && echo -- '-lusb'`
LIBS=`if [ "${HAVE_USB}" = 1 ]; then echo '-lusb'; fi`
CFLAGS+=-DVERSION=\"${VERSION}\" -Wall -I .
CFLAGS+=-pedantic -std=c99 -DHAVE_USB=${HAVE_USB}
CFLAGS+=-pedantic -std=c99 -DHAVE_USB=${HAVE_USB} -Wno-unused-result
USBOBJ=../libusb/error.o ../libusb/usb.o ../libusb/descriptors.o
USBOBJ+=../libusb/linux.o ## XXX not portable
CFLAGS+=-I../libusb
LDFLAGS+=-L../libusb
all: ${BIN}
${BIN}: ${OBJ}
+40 -34
View File
@@ -1,6 +1,7 @@
/*
* 0xFFFF - Open Free Fiasco Firmware Flasher
* Copyright (C) 2007 pancake <pancake@youterm.com>
* Copyright (C) 2007-2009 pancake <pancake@nopcode.org>
* Copyright (C) 2012 Pali Rohár <pali.rohar@gmail.com>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -29,18 +30,31 @@
*
* The following table shows this info:
*
* boot os
* n770 0421:0105 0421:0431
* n800 0421:0431
* omap-rom nolo flash-mode mass-stor pc-suite
* 770 0421:0105 0421:0431
* n800 0421:04c3 0421:0431
* n810 0421:0105
* n900 0421:0106 0421:0105 0421:01c8 0421:01c7 0421:01c8
*
* mode images protocol
* omap-rom 2nd, secondary OMAP messages + Nokia X-Loader protocol
* nolo all except mmc NOLO
* flash-mode mmc MK II
* mass-storage sd, first emmc Standard USB Mass Storage
* pc-suite mmc MK II
*
*/
struct devices supported_devices[SUPPORTED_DEVICES] = {
{ "FFFF", 0x000, 0x0000, 0x0000 }, // dummy
{ "unkn", 0x421, 0x3f00, 0x0000 }, // probably a development board
{ "n770/n810", 0x421, 0x0105, 0x0001 }, // my n770
{ "n800", 0x421, 0x04c3, 0x0001 }, // a n800
{ 0 },
{ 0 }
{ "FFFF", 0x0000, 0x0000, FLASH_NORMAL }, // dummy
{ "unkn", 0x0421, 0x3f00, FLASH_NORMAL }, // probably a development board
{ "n800", 0x0421, 0x04c3, FLASH_NORMAL }, // n800
{ "770/n810/n900", 0x0421, 0x0105, FLASH_NORMAL }, // 770, n810, n900
{ "n900", 0x0421, 0x0106, FLASH_COLD }, // n900 cold flashing
{ "n900", 0x0421, 0x01c8, FLASH_MKII }, // n900 mmc flashing
{ "770/n800", 0x0421, 0x0431, FLASH_DISK }, // 770, n800 usb mass storage
{ "n900", 0x0421, 0x01c7, FLASH_DISK }, // n900 usb mass storage
{ NULL },
{ NULL }
};
/** Returns 0 when no device was found and a positive
@@ -73,7 +87,7 @@ void list_valid_devices()
int i;
struct devices ptr = supported_devices[1];
for(i=1; ptr.vendor_id; ptr = supported_devices[++i])
for(i=1; ptr.name; ptr = supported_devices[++i])
printf("%04x:%04x %s\n", ptr.vendor_id, ptr.product_id, ptr.name);
}
@@ -82,39 +96,31 @@ void list_valid_devices()
* structures for the specified device.
* Otherwise returns false (0)
*/
int usb_device_found(struct usb_device_descriptor *udd, struct devices *it_device)
{
int dev_index = 0;
struct usb_bus *bus;
int dev_index = 0;
if (usb_find_busses() < 0) {
fprintf(stderr, "\nerror: no usb busses found.\n");
if ((usb_find_busses()<0) || (usb_find_devices()==-1)) {
fprintf(stderr, "\nerror: no usb bus or device found.\n");
exit(1);
} else {
switch(usb_find_devices()) {
case -1:
fprintf(stderr, "\nerror: no devices found.\n");
exit(1);
default:
for (bus = usb_busses; bus; bus = bus->next) {
struct usb_device *dev = bus->devices;
D printf("bus: \n");
for (; dev; dev = dev->next) {
*udd = dev->descriptor;
D printf(" dev (%s) - ", dev->filename);
D printf("vendor: %04x product: %04x\n", udd->idVendor, udd->idProduct);
for (bus = usb_busses; bus; bus = bus->next) {
struct usb_device *dev = bus->devices;
D printf("bus: \n");
for (; dev; dev = dev->next) {
*udd = dev->descriptor;
D printf(" dev (%s) - ", dev->filename);
D printf("vendor: %04x product: %04x\n", udd->idVendor, udd->idProduct);
if ((dev_index = is_valid_device(udd))) {
device = dev;
*it_device = supported_devices[dev_index];
return 1;
}
if ((dev_index = is_valid_device(udd))) {
device = dev;
printf("%s found!\n", dev->filename);
*it_device = supported_devices[dev_index];
return 1;
}
}
}
}
return 0;
}
#endif
+72 -16
View File
@@ -1,6 +1,6 @@
/*
* 0xFFFF - Open Free Fiasco Firmware Flasher
* Copyright (C) 2007 pancake <pancake@youterm.com>
* Copyright (C) 2007-2009 pancake <pancake@nopcode.org>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -37,7 +37,7 @@ int rf_extract(char *dev, off_t from, off_t to, char *file)
FILE *fd = fopen(file, "wb+");
if (from>to) {
printf("Bad range %lld - %lld for %s\n", from, to, file);
printf("Bad range %lld - %lld for %s\n", (long long int)from, (long long int)to, file);
goto __rf_extract_exit;
}
if (fs == NULL) { perror(dev); goto __rf_extract_exit; }
@@ -56,7 +56,7 @@ int rf_extract(char *dev, off_t from, off_t to, char *file)
}
printf("\r%s: %lld bytes dumped from %s\n",
file, to-from, dev);
file, (long long int)(to-from), dev);
__rf_extract_exit:
if (fs) fclose(fs);
@@ -69,17 +69,14 @@ __rf_extract_exit:
* This function was covardly copied from nanddump.c @ mtd-utils-20060907
*/
#define _GNU_SOURCE
#include <ctype.h>
#include <errno.h>
#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <getopt.h>
#include <sys/ioctl.h>
#include <sys/types.h>
#include <sys/stat.h>
//#include <asm/types.h>
#include <mtd/mtd-user.h>
#ifndef loff_t
@@ -141,8 +138,8 @@ int mtd_close(int fd, struct nand_oobinfo *old_oobinfo, int oobinfochanged)
// configuration for nanddump //
//int noecc = 0; // don't error correct
int omitoob = 1; // omit oob data
int omitbad = 1;
static int omitoob = 1; // omit oob data
static int omitbad = 1;
// configuration for nanddump //
#define CONFIGURE_FLAGS(x) \
@@ -161,6 +158,7 @@ int check_badblocks(char *mtddev)
unsigned char oobbuf[64];
struct nand_oobinfo old_oobinfo;
struct mtd_oob_buf oob = {0, 16, oobbuf};
/* XXX stat1 is never initialized !!! */
struct mtd_ecc_stats stat1, stat2;
mtd_info_t meminfo;
@@ -171,12 +169,14 @@ int check_badblocks(char *mtddev)
return 1;
}
memset(&stat1, 0, sizeof(stat1));
memset(&stat2, 0, sizeof(stat2));
fprintf(stderr, "Block size %u, page size %u, OOB size %u\n",
meminfo.erasesize, meminfo.writesize, meminfo.oobsize);
fprintf(stderr, "Size %u, flags %u, type 0x%x\n",
meminfo.size, meminfo.flags, (int)meminfo.type);
oob.length = meminfo.oobsize;
for(i = 0; i < meminfo.size; i+= meminfo.writesize) {
@@ -204,8 +204,9 @@ int check_badblocks(char *mtddev)
}
/* ECC stats available ? */
memset (&stat1, 0, sizeof (stat1));
if (eccstats) {
if (ioctl(fd, ECCGETSTATS, &stat2)) {
if (ioctl (fd, ECCGETSTATS, &stat2)) {
perror("ioctl(ECCGETSTATS)");
goto closeall;
}
@@ -245,6 +246,7 @@ closeall:
}
// XXX warning ioob is not used
// isbl is used to skip bad blocks ?
int nanddump(char *mtddev, unsigned long start_addr, unsigned long length, char *dumpfile, int isbl, int ioob)
{
unsigned char readbuf[2048];
@@ -453,22 +455,35 @@ __done:
return 1;
}
int is_n800()
static int is_n900()
{
int n900 = 0;
unsigned char buf[4];
FILE *fd = fopen("/dev/mtd2", "rb");
if (!fd) {
fprintf(stderr, "Cannot open /dev/mtd2.\n");
exit(1);
}
fread(buf, 4, 1, fd);
if (!memcmp("\xff\xff\xff\xff", buf, 4))
n900 = 1;
fclose(fd);
return n900;
}
static int is_n800()
{
int n800 = 0;
unsigned char buf[4];
FILE *fd = fopen("/dev/mtd0", "rb");
if (!fd) {
fprintf(stderr, "Cannot open /dev/mtd0.\n");
exit(1);
}
fread(buf, 4, 1,fd);
fread(buf, 4, 1, fd);
if (!memcmp("\xff\xff\xff\xff", buf, 4))
n800 = 1;
fclose(fd);
return n800;
}
@@ -498,7 +513,7 @@ int dump_config()
break;
if (!memcmp(buf,"ConF", 4)) {
loop:
read(fd, buf, 4);
ret = read(fd, buf, 4);
if (ret == -1) break;
printf("\n0x%08x : ConF %02x %02x %02x %02x : ", i,
buf[0], buf[1], buf[2], buf[3]);
@@ -539,9 +554,50 @@ int dump_config()
return 0;
}
int reverse_extract_pieces_n900(char *dir)
{
char reply;
chdir(dir);
printf("Device detected: n900\n");
// Some of the values here are probably not correct
// I need a firmware to identify if the sizes of the pieces are ok
nanddump("/dev/mtd0", 0, 0, "xloader.bin", 1, 0); // fix size?
nanddump("/dev/mtd1", 0, 0, "config.bin", 1, 0);
nanddump("/dev/mtd3", 0, 0, "nolo.bin", 0, 0);
printf("\n\nExtract rootfs? (y/N): "); fflush(stdout);
read(0, &reply, 1);
if (reply=='y'||reply=='Y') {
//rf_extract("/dev/mtd4", 0x000000, 0x6000000, "rootfs.jffs2");
nanddump("/dev/mtd5", 0x000000, 0, "rootfs.jffs2", 0,0);
} else printf("*** Ignoring rootfs\n");
printf("\n\nStrip dumped files? (y/N): "); fflush(stdout);
read(0, &reply, 1);
if (reply=='y'||reply=='Y') {
rf_strip("xloader.bin");
rf_strip("config.bin");
rf_strip("nolo.bin");
} else printf("*** Ignoring strip\n");
printf("\nIdentifying extracted files...\n");
printf("%s: xloader\n", fpid_file("xloader.bin"));
printf("%s: config.bin\n", fpid_file("config.bin"));
printf("%s: nolo.bin\n", fpid_file("nolo.bin"));
printf("%s: rootfs.jffs2\n", fpid_file("rootfs.jffs2"));
return 1;
}
int reverse_extract_pieces(char *dir)
{
char reply;
if (is_n900())
return reverse_extract_pieces_n900(dir);
printf("Device detected: 770/n800/n900\n");
chdir(dir);
// TODO: get values from /proc/mtd ???
+461 -140
View File
@@ -1,6 +1,7 @@
/*
* 0xFFFF - Open Free Fiasco Firmware Flasher
* Copyright (C) 2007 pancake <pancake@youterm.com>
* Copyright (C) 2007-2011 pancake <pancake@youterm.com>
* Copyright (C) 2011-2012 Pali Rohár <pali.rohar@gmail.com>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -27,18 +28,24 @@
#include "main.h"
#include "hash.h"
char *strdup(const char *s);
int (*fiasco_callback)(struct header_t *header) = NULL;
int openfiasco(char *name, char *piece_grep, int v)
int openfiasco(const char *name, const char *type, const char *device, const char *hwrev, const char *version, int v)
{
struct header_t header;
unsigned char buf[128];
unsigned char data[128];
unsigned char *pdata;
unsigned int namelen;
unsigned char buf[256];
unsigned char data[256];
unsigned char *pdata, *pdataend;
unsigned int headerlen;
unsigned int blockcount;
off_t off, here;
int i,j;
int subsections;
int match;
int i;
memset(&header, 0, sizeof(header));
header.fd = open(name, O_RDONLY);
if (header.fd == -1) {
@@ -47,45 +54,73 @@ int openfiasco(char *name, char *piece_grep, int v)
}
/* read header */
read(header.fd, buf, 5);
if (read(header.fd, buf, 5) != 5) {
printf("Invalid read of 5 bytes\n");
return close(header.fd);
}
if (buf[0] != 0xb4) {
printf("Invalid header\n");
return close(header.fd);
}
memcpy(&namelen,buf+1,4);
namelen = ntohl(namelen);
if (namelen>128) {
memcpy(&headerlen,buf+1,4);
headerlen = ntohl(headerlen);
if (headerlen>128) {
printf("Stupid length at header. Is this a joke?\n");
return close(header.fd);
}
memset(buf,'\0', 128);
read(header.fd, buf, namelen);
if (v) printf("Fiasco version: %2d\n", buf[3]);
strcpy(header.fwname, (char *)buf+6);
if (v)
for(i=6;i<namelen;i+=strlen((char *)(buf+i))+1)
printf("Name: %s\n", buf+i);
memset(buf,'\0', 128);
if (read(header.fd, buf, headerlen) != headerlen) {
printf("Invalid read of %d bytes\n", headerlen);
return close(header.fd);
}
memcpy(&blockcount,buf,4);
blockcount = ntohl(blockcount);
if (blockcount==0) {
printf("Error: No block in header\n");
return close(header.fd);
}
if (v) printf("Number of blocks: %d\n", blockcount);
pdata = buf+4;
while (pdata < buf+headerlen-4) {
if (pdata[0] == 0xe8) {
if (v) printf("Header: %s\n", pdata+2);
} else if (pdata[0] == 0x31) {
i = pdata[1];
if (i >= sizeof(header.swver)) i = sizeof(header.swver)-1;
memset(header.swver, 0, sizeof(header.swver));
strncpy(header.swver, (char *)pdata+2, i);
if (v) printf("SW version: %s\n", header.swver);
} else {
if (v) printf("Unknown header 0x%x, length %d, data %s\n", pdata[0], pdata[1], pdata+2);
}
pdata += (int)pdata[1]+2;
}
/* walk the tree */
while(1) {
here = lseek(header.fd, 0, SEEK_CUR);
if (read(header.fd, buf, 9)<9)
break;
if (buf[0] != 0x54) { // 'T'
/* skipping some bytes */
lseek(header.fd, -9, SEEK_CUR);
for(i=0;buf[0]!=0x54;i++) {
j = read(header.fd, buf, 1);
if (j == -1) {
printf("Cannot find next FIASCO header\n");
return close(header.fd);
}
i = 0;
while(1) {
if (read(header.fd, buf, 7)<7) {
printf("Next valid header not found\n");
return close(header.fd);
}
if (v) printf("Skipping %d padding bytes\n", i);
lseek(header.fd, -1, SEEK_CUR);
continue;
if (buf[0] == 0x54 && buf[2] == 0x2E && buf[3] == 0x19 && buf[4] == 0x01 && buf[5] == 0x01 && buf[6] == 0x00)
break;
lseek(header.fd, -6, SEEK_CUR);
++i;
}
if (i && v) printf("Skipping %d padding bytes\n", i);
subsections = buf[1]-1;
if (read(header.fd, buf+7, 2)<2)
break;
header.hash = buf[7]<<8|buf[8];
/* piece name */
@@ -97,64 +132,192 @@ int openfiasco(char *name, char *piece_grep, int v)
printf(" [eof]\n");
break;
} else if (v) printf(" %s\n", data);
strcpy(header.name, (char *)data);
memset(header.type, 0, sizeof(header.type));
strncpy(header.type, (char *)data, sizeof(header.type)-1);
if (v) {
printf(" header: ");
for (i=0; i<7;++i) printf(" 0x%.2X", (unsigned int)buf[i]);
printf("\n");
}
if (read(header.fd, buf, 9)<9)
break;
return close(header.fd);
memcpy(&header.size, buf,4);
header.size = ntohl(header.size);
if (v) {
printf(" offset: 0x%08x\n", (unsigned int)here);
printf(" size: %d bytes\n", header.size);
printf(" hash: %04x\n", header.hash);
printf(" subsections: %d\n", subsections);
}
//printf("BYTE: %02x %02x %02x %02x %02x\n",
// buf[4], buf[5], buf[6], buf[7], buf[8]);
/* XXX this is not ok */
//printf("BUF8: %02x\n", buf[8]);
while (buf[8] && buf[8]>'0' && buf[8] < '9') {
memset(header.device, 0, sizeof(header.device));
memset(header.hwrevs, 0, sizeof(header.hwrevs));
memset(header.version, 0, sizeof(header.version));
if (header.layout) {
free(header.layout);
header.layout = NULL;
}
while (subsections > 0) {
if (read(header.fd, data, 1)<1)
break;
return close(header.fd);
i = data[0];
if (read(header.fd, data, i)<i)
break;
if (data[0]) {
return close(header.fd);
{
if (v) {
printf(" version-length: %d\n", i);
printf(" version: %s\n", data);
printf(" subinfo\n");
printf(" type: ");
if (buf[8] == '1') printf("version string");
else if (buf[8] == '2') printf("hw revision");
else if (buf[8] == '3') printf("layout");
else printf("unknown (%c:0x%x)", buf[8], buf[8]);
printf("\n");
printf(" length: %d\n", i);
}
pdata = data;
while(pdata<data+i) {
strcat(header.name,pdata==data?"-":",");
strcat(header.name, (char*)pdata);
if (v) printf(" sub-version: %s\n", pdata);
pdata = pdata+strlen((char*)pdata)+1;
for(;*pdata=='\0'&&pdata<data+i;pdata=pdata+1);
pdataend = data+i;
while(pdata<pdataend) {
char buf2[9];
if (buf[8] == '2' && pdata != data) {
memset(buf2, 0, 9);
strncpy(buf2, (char *)pdata, 8);
}
if (v) {
printf(" ");
if (buf[8] == '1') printf("version");
else if (buf[8] == '2' && pdata == data) printf("device");
else if (buf[8] == '2' && pdata != data) printf("hw revision");
else if (buf[8] == '3') printf("layout");
else printf("data");
if (buf[8] == '2' && pdata != data)
printf(": %s\n", buf2);
else if (buf[8] == '3')
printf(": (not printing)\n");
else if (buf[8] == '1' || buf[8] == '2')
printf(": %s\n", pdata);
else {
char *buf3 = malloc(i+1);
memcpy(buf3, pdata, i);
buf3[i] = 0;
printf(": (raw) %s\n", buf3);
free(buf3);
}
}
if (buf[8] == '1') {
strncpy(header.version, (char *)pdata, sizeof(header.version)-1);
} else if (buf[8] == '2' && pdata == data) {
strncpy(header.device, (char *)pdata, sizeof(header.device)-1);
} else if (buf[8] == '2' && pdata != data) {
if (header.hwrevs[0] == 0)
strncpy(header.hwrevs, buf2, sizeof(header.hwrevs)-1);
else {
strcat(header.hwrevs, ",");
strcat(header.hwrevs, buf2);
}
} else if (buf[8] == '3') {
if (header.layout) free(header.layout);
header.layout = malloc(strlen((char*)pdata)+1);
if (header.layout) strcpy(header.layout, (char *)pdata);
}
if (buf[8] == '2' && pdata != data && strlen((char *)pdata) > 8)
pdata += 8;
else
pdata += strlen((char*)pdata)+1;
for(;*pdata=='\0' && pdata<pdataend; pdata++);
}
}
strcpy(header.version, (char *)data);
if (read(header.fd, buf+8, 1)<1)
break;
return close(header.fd);
--subsections;
}
/* callback */
header.name = malloc(strlen(header.type)+strlen(header.device)+strlen(header.hwrevs)+strlen(header.version)+4);
if (!header.name) {
printf("malloc error\n");
exit(1);
}
strcpy(header.name, header.type);
if (header.device[0]) {
strcat(header.name, "-");
strcat(header.name, header.device);
}
if (header.hwrevs[0]) {
strcat(header.name, "-");
strcat(header.name, header.hwrevs);
}
if (header.version[0]) {
strcat(header.name, "-");
strcat(header.name, header.version);
}
off = lseek(header.fd, 0, SEEK_CUR);
if (v) {
printf(" version: %s\n", header.version);
printf(" device: %s\n", header.device);
printf(" hwrevs: %s\n", header.hwrevs);
printf(" name: %s\n", header.name);
printf(" body-at: 0x%08x\n", (unsigned int)off);
}
if (piece_grep==NULL || (strstr(header.name, piece_grep))) {
printf("==> (%s) %s\n", piece_grep, header.name);
match = 1;
if (match && type && strcmp(header.type, type) != 0)
match = 0;
if (match && device && strcmp(header.device, device) != 0)
match = 0;
if (match && version && strcmp(header.version, version) != 0)
match = 0;
if (match && hwrev) {
char *tmp1 = malloc(strlen(header.hwrevs)+3);
char *tmp2 = malloc(strlen(hwrev)+3);
if (!tmp1 || !tmp2) {
printf("malloc error\n");
return close(header.fd);
}
sprintf(tmp1, ",%s,", header.hwrevs);
sprintf(tmp2, ",%s,", hwrev);
if (!strstr(tmp1, tmp2))
match = 0;
free(tmp1);
free(tmp2);
}
/* callback */
if (match) {
printf("==> %s\n", header.name);
if (fiasco_callback != NULL) {
fiasco_callback(&header);
if (header.layout) {
free(header.layout);
header.layout = NULL;
}
free(header.name);
free(header.data);
continue;
} else {
// ??huh
}
} else {
printf("ignored %s\n", header.name);
}
// XXX dup
lseek(header.fd, off, SEEK_SET);
lseek(header.fd, header.size, SEEK_CUR);
if (header.layout) {
free(header.layout);
header.layout = NULL;
}
free(header.name);
}
return close(header.fd);
}
@@ -166,51 +329,72 @@ void fiasco_data_read(struct header_t *header)
printf("Cannot alloc %d bytes\n", header->size);
return;
}
read(header->fd, header->data, header->size);
if (read (header->fd, header->data, header->size) != header->size) {
printf("Cannot read %d bytes\n", header->size);
return;
}
}
/* fiasco writer */
int fiasco_new(const char *filename, const char *name)
int fiasco_new(const char *filename, const char *swver)
{
int fd;
//int len = htonl(strlen(name)+1+6+14);
unsigned int len;
unsigned char len8;
const char *str = "OSSO UART+USB";
fd = open(filename, O_RDWR|O_CREAT, 0644);
if (swver && strlen(swver)+1 > UINT8_MAX) {
printf("SW version is too long\n");
return -1;
}
fd = open(filename, O_RDWR|O_CREAT|O_TRUNC, 0644);
if (fd == -1)
return -1;
#if 1
write(fd, "\xb4\x00\x00\x00\x14\x00\x00\x00\x01\xe8\x0e", 11);
write(fd, "OSSO UART+USB", 14);
#else
/* 2nd format doesnt works. atm stay with old one */
write(fd, "\xb4", 1);
printf("Writing header\n");
write(fd, "\xb4", 1); //signature
len = 4;
len += strlen(str) + 3;
if (swver)
len += strlen(swver) + 3;
len = htonl(len);
write(fd, &len, 4);
/* version header */
write(fd, "\x00\x00\x00\x02\xe8\x0e", 6);
/* firmware type */
write(fd, "OSSO UART+USB", 14);
/* firmware name */
write(fd, name, strlen(name));
write(fd, "", 1);
#endif
if (swver)
len = htonl(2);
else
len = htonl(1);
write(fd, &len, 4);
// header
len = strlen(str)+1;
len8 = len;
write(fd, "\xe8", 1);
write(fd, &len8, 1);
write(fd, str, len);
// sw version
if (swver) {
printf("Writing SW version: %s\n", swver);
len = strlen(swver)+1;
len8 = len;
write(fd, "\x31", 1);
write(fd, &len8, 1);
write(fd, swver, len);
};
return fd;
}
int fiasco_add_eof(int fd)
{
#if 0
unsigned char buf[120];
if (fd == -1)
return -1;
memset(buf,'\xff', 120);
write(fd, buf, 120);
#endif
return 0;
}
int fiasco_add(int fd, const char *name, const char *file, const char *version)
int fiasco_add(int fd, const char *name, const char *file, const char *layout, const char *device, const char *hwrevs, const char *version)
{
int i;
int gd,ret;
int size;
int align;
unsigned int sz;
unsigned char len;
unsigned short hash;
@@ -226,17 +410,40 @@ int fiasco_add(int fd, const char *name, const char *file, const char *version)
if (gd == -1)
return -1;
sz = htonl((unsigned int) lseek(gd, 0, SEEK_END));
sz = lseek(gd, 0, SEEK_END);
if (name) {
if (strcmp(name, "mmc") == 0) // align mmc
sz = ((sz >> 8) + 1) << 8;
else if (strcmp(name, "kernel") == 0) // align kernel
sz = ((sz >> 7) + 1) << 7;
}
printf(" size: %d\n", sz);
sz = htonl((unsigned int) sz);
lseek(gd, 0, SEEK_SET);
// 4 bytes big endian
//write(fd, "T\x02\x2e\x19\x01\x01\x00", 7); // header?
write(fd, "T\x01\x2e\x19\x01\x01\x00", 7); // header (old piece format)
write(fd, "T", 1);
/* number of subsections */
len = 1;
if (version)
++len;
if (device)
++len;
if (layout)
++len;
write(fd, &len, 1);
write(fd, "\x2e\x19\x01\x01\x00", 5);
/* checksum */
hash = do_hash_file(file);
hash = do_hash_file(file, name);
ptr[0]^=ptr[1]; ptr[1]=ptr[0]^ptr[1]; ptr[0]^=ptr[1];
write(fd, &hash, 2);
printf("hash: %04x\n", hash);
printf(" hash: %04x\n", hash);
/* image type name */
memset(bname, '\0', 13);
if (name == NULL)
name = fpid_file(file);
@@ -246,24 +453,104 @@ int fiasco_add(int fd, const char *name, const char *file, const char *version)
strncpy(bname, name, 12);
write(fd, bname, 12);
write(fd, &sz, 4);
write(fd, "\x00\x00\x00\x00", 4);
/* append version subsection */
if (version) {
/* append metadata */
write(fd, "\x00\x00\x00\x00\x31", 5);
len = strlen(version);
write(fd, "1", 1); /* 1 - version */
len = strlen(version)+1;
write(fd, &len, 1);
write(fd, version, len);
write(fd, "\x00\x9b", 2);
} else {
write(fd, "\x00\x00\x00\x00\x9b", 5);
}
/* append device & hwrevs subsection */
if (device) {
const char *ptr = hwrevs;
const char *oldptr = hwrevs;
write(fd, "2", 1); /* 2 - device & hwrevs */
len = 16;
if (hwrevs) {
i = 1;
while ((ptr = strchr(ptr, ','))) { i++; ptr++; }
if ((int)len + i*8 > 255) {
printf("Device string and HW revisions are too long\n");
return -1;
}
len += i*8;
}
write(fd, &len, 1);
len = strlen(device);
if (len > 15) len = 15;
write(fd, device, len);
for (i=0; i<16-len; ++i)
write(fd, "\x00", 1);
if (hwrevs) {
ptr = hwrevs;
oldptr = hwrevs;
while ((ptr = strchr(ptr, ','))) {
len = ptr-oldptr;
if (len > 8) len = 8;
write(fd, oldptr, len);
for (i=0; i<8-len; ++i)
write(fd, "\x00", 1);
++ptr;
oldptr = ptr;
}
len = strlen(oldptr);
if (len > 8) len = 8;
write(fd, oldptr, len);
for (i=0; i<8-len; ++i)
write(fd, "\x00", 1);
}
}
/* append layout subsection */
if (layout) {
int lfd = open(layout, O_RDONLY);
if (lfd >= 0) {
len = read(lfd, buf, sizeof(buf));
if (len > 0) {
write(fd, "3", 1); /* 3 - layout */
write(fd, &len, 1);
write(fd, buf, len);
}
close(lfd);
} else {
printf("Cannot open layout file %s\n", layout);
return -1;
}
}
/* dummy byte - end of all subsections */
write(fd, "\x00", 1);
size = 0;
while(1) {
ret = read(gd, buf, 4096);
size += ret;
if (ret<1)
break;
write(fd, buf, ret);
if (write(fd, buf, ret) != ret) {
fprintf (stderr, "Cannot write %d bytes\n", ret);
return -1;
}
}
/* align mmc and kernel (fill with 0xff) */
align = 0;
if (name) {
if (strcmp(name, "mmc") == 0)
align = ((size >> 8) + 1) << 8;
else if (strcmp(name, "kernel") == 0)
align = ((size >> 7) + 1) << 7;
}
if (align) {
while (size < align) {
write(fd, "\xff", 1);
++size;
}
}
return 0;
@@ -271,57 +558,91 @@ int fiasco_add(int fd, const char *name, const char *file, const char *version)
int fiasco_pack(int optind, char *argv[])
{
const char *file = argv[optind];
char *type;
int fd, ret;
char *file = argv[optind];
int fd, ret, i;
fd = fiasco_new(file, file); // TODO use a format here
char *ptr;
char *arg;
char *type;
char *device;
char *hwrevs;
char *version;
char *layout;
char *swver = NULL;
i = optind;
while((arg=argv[++i])) {
if (strncmp(arg, "version:", strlen("version:"))==0) {
swver = arg+strlen("version:");
break;
}
}
printf("Package: %s\n", file);
fd = fiasco_new(file, swver);
if (fd == -1)
return 1;
printf("Package: %s\n", file);
while((file=argv[++optind])) {
type = (char *)fpid_file(file);
printf("Adding %s: %s..\n", type, file);
ret = fiasco_add(fd, type, file, NULL);
while((arg=argv[++optind])) {
if (strncmp(arg, "version:", strlen("version:"))==0)
continue;
// format: [[[[dev:[hw:]]ver:]type:]file[%layout]
ptr = strdup(arg);
layout = strchr(ptr, '%');
if (layout) {
*(layout++) = 0;
}
type = NULL;
device = NULL;
hwrevs = NULL;
version = NULL;
file = strrchr(ptr, ':');
if (file) {
*(file++) = 0;
type = strrchr(ptr, ':');
if (type) {
*(type++) = 0;
version = strrchr(ptr, ':');
if (version) {
*(version++) = 0;
hwrevs = strchr(ptr, ':');
if (hwrevs)
*(hwrevs++) = 0;
device = ptr;
} else {
version = ptr;
}
} else {
type = ptr;
}
} else {
file = ptr;
}
if (!type)
type = (char *)fpid_file(file);
printf("Adding file: %s\n", file);
printf(" type: %s\n", type);
if (device) printf(" device: %s\n", device);
if (hwrevs) printf(" hw revisions: %s\n", hwrevs);
if (version) printf(" version: %s\n", version);
if (layout) printf(" layout file: %s\n", layout);
ret = fiasco_add(fd, type, file, layout, device, hwrevs, version);
free(ptr);
if (ret<0) {
printf("Error\n");
close(fd);
return 1;
}
}
fiasco_add_eof(fd);
printf("Done!\n");
close(fd);
return 0;
}
/* local code */
#if 0
void my_callback(int fd, struct header_t *header)
{
fiasco_data_read(header);
//read(fd, buf, header->size);
printf("Dumping %s\n", header->name);
printf("DATA: %02x\n", header->data[0]);
fiasco_data_free(header);
}
int main(int argc, char **argv)
{
if (argc!=2) {
printf("Usage: unfiasco [file]\n");
return 1;
}
/*
fd = fiasco_new("myfiasco", "pancake-edition");
fiasco_add(fd, "kernel", "zImage", "2.6.22");
close(fd);
*/
// fiasco_callback = &my_callback;
return openfiasco(argv[1]);
}
#endif
+2 -2
View File
@@ -74,7 +74,7 @@ void check_nolo_order()
check_nolo_order_failed();
}
void flash_image(const char *filename, const char *piece, const char *version)
void flash_image(const char *filename, const char *piece, const char *device, const char *hwrevs, const char *version)
{
FILE *fd;
int vlen = 0;
@@ -84,7 +84,7 @@ void flash_image(const char *filename, const char *piece, const char *version)
unsigned long long size, off;
unsigned char bsize[4], tmp;
unsigned char nolofiller[128];
ushort hash = do_hash_file(filename);
ushort hash = do_hash_file(filename, piece);
if (piece == NULL) {
//exit(1);
+14 -4
View File
@@ -1,6 +1,7 @@
/*
* 0xFFFF - Open Free Fiasco Firmware Flasher
* Copyright (C) 2007 pancake <pancake@youterm.com>
* Copyright (C) 2012 Pali Rohár <pali.rohar@gmail.com>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -23,12 +24,16 @@
/* global structs */
char *pieces[] = {
"xloader", // xloader.bin
"2nd", // 2nd
"2nd", // 2nd.bin
"secondary", // secondary.bin
"kernel", // zImage
"initfs", // jffs'd initfs
"rootfs", // 80mB of blob
"initfs", // initfs
"rootfs", // rootfs
"omap-nand", // 8kB of food for the nand
"mmc", // raw eMMC image
"cmt-2nd", // cmt-2nd
"cmt-algo", // cmt-algo
"cmt-mcusw", // cmt-mcusw
"fiasco", // FIASCO IMAGE
NULL
};
@@ -37,7 +42,12 @@ long fpid_size(const char *filename)
{
long sz;
FILE *fd = fopen(filename, "r");
fseek(fd, 0, SEEK_END);
if (fd == NULL)
return -1;
if (fseek(fd, 0, SEEK_END) != 0) {
fclose(fd);
return -1;
}
sz = ftell(fd);
fclose(fd);
return sz;
+10 -2
View File
@@ -1,8 +1,13 @@
include ../../config.mk
ifeq (${HAVE_GUI},1)
all:
gtkamlc --save-temps --Xcc=-I../squeue ../squeue/squeue.c ../fpid.c ../squeue/squeue.vapi gui.gtkaml extras.vapi --pkg gtk+-2.0 -o goxf
all: goxf
goxf:
${CC} -I../squeue ../squeue/squeue.c ../fpid.c gui.c `pkg-config --cflags --libs gtk+-2.0` -o goxf
c:
gtkamlc --save-temps --Xcc=-I../squeue ../squeue/squeue.c ../fpid.c ../squeue/squeue.vapi gui.gtkon extras.vapi --pkg gtk+-2.0 -o goxf
test:
valac --save-temps --Xcc=-I.. squeue.vapi test.vala ../squeue.c -o v
@@ -11,3 +16,6 @@ else
all:
@true
endif
clean:
rm -f goxf *.o *.c
+1163
View File
File diff suppressed because it is too large. Load diff
@@ -78,7 +78,7 @@
<AboutDialog class:standalone="true" class:private="aboutdialog1" delete-event="{aboutdialog1.hide_on_delete}"
border-width="5" title="About 0xFFFF gui" resizable="false" modal="true"
window-position="{WindowPosition.CENTER_ON_PARENT}" has-separator="false"
program-name="0xFFFF" version="0.3.9" copyright="Copyright (c) 2008 pancake"
program-name="0xFFFF" version="0.5" copyright="Copyright (c) 2007-2009 pancake"
comments="The Free Nokia Internet Tablet flasher"
website="http://www.nopcode.org/0xFFFF/"
authors='{new string[] {"pancake (pancake@youterm.com)", null}}'>
@@ -143,7 +143,7 @@ public bool loadFile( string filename )
{
int err = 0;
try {
string contents; int length;
string contents; size_t length;
FileUtils.get_contents (filename, out contents, out length);
//textview1.buffer.set_text (contents, length);
} catch(Error e) {
+321
View File
@@ -0,0 +1,321 @@
/*
| Frontend for the 0xFFFF flasher in gtkaml
| author: pancake <youterm.com>
*/
Window using="Gtk" gtkon:version=0.4
using:Extras="Extras"
using:SQueues="SQueues"
name="MainWindow"
title="0xFFFF GUI"
{
/* delete-event="{OnWindow1DeleteEvent}" */
VBox {
MenuBar !expand {
MenuItem label="_File" with-mnemonic {
submenu {
Menu {
ImageMenuItem stock-id="gtk-new" activate=OnFileNewEvent;
ImageMenuItem stock-id="gtk-open" activate=OnFileOpenEvent;
SeparatorMenuItem;
ImageMenuItem stock-id="gtk-quit" activate=OnQuitEvent;
}
}
}
MenuItem label="_Target" with-mnemonic {
submenu {
Menu {
ImageMenuItem stock-id="gtk-connect" activate=OnConnect;
ImageMenuItem stock-id="gtk-stop" activate=OnStop;
ImageMenuItem stock-id="gtk-info" activate=OnGetInformation;
ImageMenuItem label="Reset" activate=OnReset;
}
}
}
MenuItem label="_Help" with-mnemonic {
submenu {
Menu {
ImageMenuItem stock-id="gtk-about" activate=OnMenuHelpAboutActivatedEvent;
}
}
}
}
HBox border-width="5" {
VBox border-width="3" spacing="3" {
ScrolledWindow can-focus="true" hscrollbar-policy="{PolicyType.AUTOMATIC}" vscrollbar-policy="{PolicyType.AUTOMATIC}" {
TreeView $.tv;
}
}
VBox !expand border-width="3" spacing="3" {
Button label="gtk-connect" use-stock !expand clicked=OnConnect;
Button label="gtk-stop" use-stock !expand clicked=OnStop;
Button label="gtk-info" use-stock !expand clicked=OnGetInformation;
Label label="";
/*
<!-- <Button label="Options" use-stock="false" expand="false"/>
<Button label="Fiasco!" use-stock="false" expand="false"/>
<Button label="Unpack!" use-stock="false" expand/> -->
*/
Button label="gtk-add" use-stock="true" !expand clicked=OnFileOpenEvent;
Button label="gtk-remove" use-stock="true" expand="false" clicked=list_del;
Label label="";
Button label="gtk-media-record" use-stock="true" expand="false" clicked=OnFileFlashEvent;
}
}
ProgressBar $.pb !expand;
//<!-- <Statusbar expand="false"/> -->
}
AboutDialog gtkaml:standalone $.aboutdialog1 delete-event=aboutdialog1.hide_on_delete
border-width="5" title="About 0xFFFF gui" resizable="false" modal="true"
window-position="{WindowPosition.CENTER_ON_PARENT}" has-separator="false"
program-name="0xFFFF" version="0.5" copyright="Copyright (c) 2007-2009 pancake"
comments="The Free Nokia Internet Tablet flasher"
website="http://www.nopcode.org/0xFFFF/"
authors='{new string[] {"pancake (pancake@youterm.com)", null}}';
-{
private void doCloseApplication () {
Gtk.main_quit ();
}
private void OnReset() {
q->push("reset:device", 1);
}
private void OnFileFlashEvent() {
ListStore ls = (ListStore)tv.get_model();
weak string str;
TreeIter iter;
int n = ls.iter_n_children(null);
if (n >0) {
if (showYesNo("Do you want to flash these files?")) {
ls.get_iter_first(out iter);
do {
ls.get(iter, 2, out str, -1);
//stdout.printf("polla:%s\n", str);
q->push2("flash", str, 1);
} while(ls.iter_next(ref iter));
}
} else showMessage("No files selected", MessageType.ERROR);
}
private void OnFileOpenEvent () {
FileChooserDialog fc = new FileChooserDialog("Select file to open",
this, FileChooserAction.OPEN,
"gtk-cancel", ResponseType.CANCEL,
"gtk-open", ResponseType.ACCEPT);
int resp = fc.run ();
fc.hide ();
if (resp == ResponseType.ACCEPT) {
string file = fc.get_filename();
string *type = External.fpid_file(file);
string size = "%ld".printf(External.fpid_size(file));
if (type == null)
showMessage("Invalid file type", MessageType.ERROR);
else add_file(type, size, file);
}
fc.destroy ();
}
public bool loadFile( string filename ) {
int err = 0;
try {
string contents; size_t length;
FileUtils.get_contents (filename, out contents, out length);
//textview1.buffer.set_text (contents, length);
} catch(Error e) {
showError ("Unexpected error while loading the file, please contact the author with the following information:\n\n" + e.message);
err++;
}
return err == 0;
}
public bool showYesNo(string s) {
MessageDialog md = new MessageDialog (this,
DialogFlags.DESTROY_WITH_PARENT,
MessageType.QUESTION, ButtonsType.YES_NO, s);
int ret = md.run ();
md.destroy ();
return ret==ResponseType.YES;
}
public void showMessage(string s, MessageType mt) {
MessageDialog md = new MessageDialog (this,
DialogFlags.DESTROY_WITH_PARENT,
mt, ButtonsType.CLOSE, s);
md.run ();
md.destroy ();
}
private void OnMenuHelpAboutActivatedEvent () {
aboutdialog1.transient_for = this;
aboutdialog1.response.connect ((x)=> { aboutdialog1.hide (); });
aboutdialog1.run ();
}
public void showError (string s) {
MessageDialog md = new MessageDialog (this,
DialogFlags.DESTROY_WITH_PARENT,
MessageType.ERROR,
ButtonsType.CLOSE,
s);
md.run ();
md.destroy ();
}
private void OnFileNewEvent () {
list_clear();
// TODO: clear file list
}
private void OnQuitEvent () {
doCloseApplication();
// TODO: send message to gracefully kill 0xFFFF
// TODO: handle ^C when flashing
}
public void list_clear() {
((ListStore)tv.model).clear();
}
public void list_del() {
TreeIter iter;
TreeModel model;
TreeSelection sel = tv.get_selection();
if (sel.count_selected_rows() == 1) {
sel.get_selected(out model, out iter);
((ListStore)tv.model).remove(iter);
}
}
public void add_file(string type, string size, string file) {
ListStore listmodel = (ListStore)tv.get_model();
Gtk.TreeIter iter;
listmodel.append (out iter);
listmodel.set (iter, 0, type, 1, size, 2, file, -1);
}
public static void setup_treeview (Gtk.TreeView view) {
/* use liststore to hold accountname, accounttype, balance and color attribute */
/* for more info how gtkTreeview works take a look in the GTK API */
var listmodel = new Gtk.ListStore(4, typeof(string), typeof(string), typeof(string), typeof(string));
view.set_model(listmodel);
view.insert_column_with_attributes (-1, "Type", new Gtk.CellRendererText(), "text", 0, null);
view.insert_column_with_attributes (-1, "Size", new Gtk.CellRendererText(), "text", 1, null);
var cell = new Gtk.CellRendererText ();
cell.set ("foreground_set", true, null);
view.insert_column_with_attributes (-1, "Name", cell, "text", 2, "foreground", 3, null);
// Gtk.TreeIter iter;
// listmodel.append (out iter);
// listmodel.set (iter, 0, "initfs", 1, "3M", 2, "initfs.jffs", -1);
//listmodel.set (iter, 0, "initfs", 1, "3M", 2, "initfs.jffs", 3, "green", -1);
// listmodel.append (out iter);
// listmodel.set (iter, 0, "rootfs", 1, "52M", 2, "rootfs.jffs", -1);
}
public static bool readFunc() {
weak string msg = p->get(0);
if (msg != null && msg[0]!='\0') {
stdout.printf("[<] msg received: %s\n", msg);
string[] foo = msg.split(":",2);
if (foo[1] != null) {
switch(foo[0]) {
case "bar":
viewer.pb.fraction = foo[1].to_int() / 100;
viewer.pb.text = foo[1]+"%";
break;
case "error":
viewer.showMessage(foo[1], MessageType.ERROR);
break;
case "info":
viewer.showMessage(foo[1], MessageType.INFO);
break;
default:
stderr.printf("[E] Unknown message type\n");
break;
}
//viewer.showMessage(msg, MessageType.INFO);
}
p->pop();
}
return true;
}
static SQueue *q = null;
static SQueue *p = null;
private void OnGetInformation() {
msg("info:device");
}
private void OnConnect() {
//msg("connect:device");
OnStop();
External.system("sudo 0xFFFF -Q &");
p->close();
q->close();
p = q = null;
}
private void OnStop() {
External.system("sudo pkill 0xFFFF");
}
private bool chk_queues() {
if (p == null)
p = SQueue.open("/tmp/0xFFFF.1", SQueueMode.OPEN);
if (q == null)
q = SQueue.open("/tmp/0xFFFF.2", SQueueMode.OPEN);
if (p == null || q == null) {
showMessage("Cannot connect to queues", MessageType.ERROR);
return false;
}
return true;
}
public void msg(string str) {
if (!chk_queues())
return;
if (q->push(str, 0)<1) {
stderr.printf("Oops on push\n");
q->free();
q = null;
p->free();
p = null;
}
}
static MainWindow viewer;
static int main (string[] args) {
Gtk.init (ref args);
viewer = new MainWindow();
if (args.length > 1)
viewer.loadFile (args[1]);
viewer.resize(600,400);
viewer.set_position(WindowPosition.CENTER);
viewer.delete_event.connect ((x,y) => { Gtk.main_quit(); return false; });
setup_treeview(viewer.tv);
viewer.show_all ();
// viewer.showMessage("This software is beta and does not guaranties correct functionality", MessageType.WARNING);
Timeout.add(200, (SourceFunc)(readFunc));
Gtk.main ();
return 0;
}
}-
}
+28 -4
View File
@@ -1,6 +1,6 @@
/*
* 0xFFFF - Open Free Fiasco Firmware Flasher
* Copyright (C) 2007 pancake <pancake@youterm.com>
* Copyright (C) 2007-2009 pancake <pancake@youterm.com>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -17,6 +17,7 @@
*/
#include <stdio.h>
#include <string.h>
#include "hash.h"
usho do_hash(usho *b, int len)
@@ -27,11 +28,13 @@ usho do_hash(usho *b, int len)
return result;
}
usho do_hash_file(const char *filename)
usho do_hash_file(const char *filename, const char *type)
{
unsigned char buf[BSIZE];
FILE *fd = fopen(filename, "r");
usho hash = 0;
int align = 0;
int size;
int ret;
if (fd == NULL) {
@@ -39,14 +42,35 @@ usho do_hash_file(const char *filename)
return -1;
}
do { ret = fread(&buf, 1, BSIZE, fd);
if (ret == -1)
do {
ret = fread(&buf, 1, BSIZE, fd);
if (ret == -1) {
fclose(fd);
return 0;
}
hash ^= do_hash((usho *)&buf, ret);
} while(ret);
size = ftell(fd);
fclose(fd);
/* mmc and kernel image must be aligned */
if (type) {
if (strcmp(type, "mmc") == 0)
align = ((size >> 8) + 1) << 8;
else if (strcmp(type, "kernel") == 0)
align = ((size >> 7) + 1) << 7;
}
if (align) {
printf("align from %d to %d\n", size, align);
buf[0] = 0xff;
while (size < align) {
hash ^= do_hash((usho *)&buf, 1);
++size;
}
}
return hash;
}
+1 -1
View File
@@ -5,6 +5,6 @@
#define BSIZE 0x20000
usho do_hash(usho *b, int len);
usho do_hash_file(const char *filename);
usho do_hash_file(const char *filename, const char *type);
#endif
+149 -113
View File
@@ -58,7 +58,6 @@ char *root_devices[] = {
NULL
};
void show_title()
{
printf("0xFFFF v%s // The Free Fiasco Firmware Flasher\n", VERSION);
@@ -68,39 +67,48 @@ void show_usage()
{
int i;
show_title();
#if HAVE_USB
printf("Over USB:\n");
printf(" -b [arg] boots the kernel with arguments\n");
printf(" -c console prompt mode\n");
printf(" -d [vid:pid] injects a usb device into the supported list\n");
printf(" -D [0|1|2] sets the root device to flash (0), mmc (1) or usb (2)\n");
printf(" -f <flags> set the given RD flags (see '-f help')\n");
printf(" -i show device information (let standby mode)\n");
printf(" -l list supported usb device ids\n");
printf(" -p [[p%%]file] piece-of-firmware %% file-where-this-piece-is\n");
printf(" -r [0|1] disable/enable R&D mode\n");
printf(" -R reboot the omap board\n");
printf(" -U [0|1] disable/enable the usb host mode\n");
printf ("Over USB:\n"
" -b [arg] boots the kernel with arguments\n"
" -c console prompt mode\n"
" -d [vid:pid] injects a usb device into the supported list\n"
" -D [0|1|2] sets the root device to flash (0), mmc (1) or usb (2)\n"
" -f <flags> set the given RD flags (see '-f help')\n"
" -i show device information (let standby mode)\n"
" -l list supported usb device ids\n"
" -p format piece-of-firmware\n"
" piece format: [[[[dev:[hw:]]ver:]type:]file[%%layout]\n"
" hw is device HW revision\n"
" dev is device name string\n"
" ver is image version string\n"
" type is image type\n"
" file is image file name\n"
" layout is file name for layout file\n"
" -r [0|1] disable/enable R&D mode\n"
" -R reboot the omap board\n"
" -U [0|1] disable/enable the usb host mode\n");
#endif
#if HAVE_SQUEUE
printf(" -Q enter shared queues server mode (for gui or remote)\n");
#endif
printf("Local stuff:\n");
printf(" -s [serial] serial port console (minicom like terminal)\n");
printf(" -h show this help message\n");
printf(" -S [subversion] unpacks/flash pieces matching this sub-version information\n");
printf(" -n do not flash or write to disk (simulation)\n");
printf(" -C [/dev/mtd] check bad blocks on mtd\n");
printf(" -e [path] dump/extract pieces to path\n");
printf(" -F [fiasco] flash a fiasco firmware image\n");
printf(" -H [file] calculate hash for file\n");
printf(" -I [piece] identify a firmware piece\n");
printf(" -P [new-fiasco] creates a new fiasco package, pieces as arguments\n");
printf(" -u [fiasco] unpack target fiasco image\n");
printf(" -v be verbose and noisy\n");
printf(" -V show 0xFFFF version information\n");
printf(" -x extract configuration entries from /dev/mtd1\n");
printf("Pieces are: ");
printf ("Local stuff:\n"
" -s [serial] serial port console (minicom like terminal)\n"
" -h show this help message\n"
" -S [subversion] unpacks/flash pieces matching this sub-version information\n"
" -n do not flash or write to disk (simulation)\n"
" -C [/dev/mtd] check bad blocks on mtd\n"
" -e [path] dump/extract pieces to path\n"
" -F [fiasco] flash a fiasco firmware image\n"
" -H [file] calculate hash for file\n"
" -I [piece] identify a firmware piece\n"
" -P [new-fiasco] creates a new fiasco package, pieces as arguments\n"
" optional argument 'version:<version>'\n"
" -u [fiasco] unpack target fiasco image\n"
" -v be verbose and noisy\n"
" -V show 0xFFFF version information\n"
" -x extract configuration entries from /dev/mtd1\n"
"Pieces are: ");
for(i=0;pieces[i];i++) printf("%s ", pieces[i]); printf("\n");
// serial port support is not yet done (cold flash is for flashing the 8kB nand)
// TODO: commandline shell prompt for nolo comm
@@ -117,7 +125,7 @@ int unpack_callback(struct header_t *header)
if (strchr(header->name, ',') != NULL) {
if (!strstr(header->name, subverstr)) {
printf("Skipping '%s' does not matches -S subversion\n",
header->name);
header->name);
return 1;
}
}
@@ -125,12 +133,22 @@ int unpack_callback(struct header_t *header)
if (nomode)
return 1;
printf("Unpacking file: %s\n", header->name);
printf(" type: %s\n", header->type);
if (header->device[0]) printf(" device: %s\n", header->device);
if (header->hwrevs[0]) printf(" hw revisions: %s\n", header->hwrevs);
if (header->version[0]) printf(" version: %s\n", header->version);
if (header->layout) printf(" layout file: %s\n", header->layout);
printf(" size: %d\n", header->size);
printf(" hash: %04x\n", header->hash);
fd = fopen(header->name, "wb");
if (fd == NULL) {
printf("Cannot open file.\n");
return 1;
}
fwrite(header->data, header->size, 1, fd);
if (fwrite(header->data, header->size, 1, fd) != 1)
printf("Writing failed\n");
fclose(fd);
return 0;
@@ -147,9 +165,11 @@ int flash_callback(struct header_t *header)
return 1;
}
type = (char *)fpid_file(header->name);
type = header->type;
if (!type[0])
type = (char *)fpid_file(header->name);
printf("\nFlashing %s (%s)\n", header->name, type);
flash_image(header->name, type, NULL);
flash_image(header->name, type, header->device, header->hwrevs, header->version);
return 0;
}
@@ -158,7 +178,7 @@ void unpack_fiasco_image(char *file)
{
printf("Dumping firmware pieces to disk.\n");
fiasco_callback = &unpack_callback;
openfiasco(file, NULL ,1);
openfiasco(file, NULL, NULL, NULL, NULL, 0);
}
int fiasco_flash(const char *file)
@@ -166,10 +186,10 @@ int fiasco_flash(const char *file)
char *p;
char version[64];
if (connect_via_usb()) {
fprintf(stderr, "Cannot connect to device. It is possibly not in boot stage.\n");
return 0;
}
if (connect_via_usb()) {
fprintf(stderr, "Cannot connect to device. It is possibly not in boot stage.\n");
return 0;
}
// if (info)
cmd_info("");
@@ -190,11 +210,11 @@ int fiasco_flash(const char *file)
printf("\n");
fiasco_callback = &flash_callback;
openfiasco(file, "xloader", 0);
openfiasco(file, "secondary", 0);
openfiasco(file, "kernel", 0);
openfiasco(file, "initfs", 0);
openfiasco(file, "rootfs", 0);
openfiasco(file, "xloader", NULL, NULL, NULL, 0);
openfiasco(file, "secondary", NULL, NULL, NULL, 0);
openfiasco(file, "kernel", NULL, NULL, NULL, 0);
openfiasco(file, "initfs", NULL, NULL, NULL, 0);
openfiasco(file, "rootfs", NULL, NULL, NULL, 0);
return 0;
}
@@ -203,67 +223,75 @@ int fiasco_flash(const char *file)
int connect_via_usb()
{
static char pbc[]={'/','-','\\', '|'};
struct usb_device_descriptor udd;
struct devices it_device;
struct usb_device_descriptor udd;
struct devices it_device;
int c = 0;
// usb_set_debug(5);
usb_init();
/* Tries to get access to the Internet Tablet and retries
* if any of the neccessary steps fail.
*
* Note: While a proper device may be found on the bus it may
* not be in the right state to be accessed (e.g. the Nokia is
* not in the boot stage any more).
*/
/* Tries to get access to the Internet Tablet and retries
* if any of the neccessary steps fail.
*
* Note: While a proper device may be found on the bus it may
* not be in the right state to be accessed (e.g. the Nokia is
* not in the boot stage any more).
*/
while(!dev) {
usleep(0xc350); // 0.5s
if(!usb_device_found(&udd, &it_device)) {
if(!usb_device_found(&udd, &it_device)) {
printf("\rWaiting for device... %c", pbc[++c%4]);
fflush(stdout);
continue;
}
/* open device */
if(!(dev = usb_open(device))) {
perror("usb_open");
return 1;
}
/* open device */
if(!(dev = usb_open(device))) {
perror("usb_open");
return 1;
}
if ( usb_claim_interface(dev, 2) < 0) {
//device->config->interface->altsetting->bInterfaceNumber) < 0) { // 2 or 0
D perror("usb_claim_interface");
#if 1
{
char name[32];
name[0] = '\0';
usb_get_driver_np(dev, 2, name, sizeof(name));
printf ("Driver: %s\n", name);
usb_detach_kernel_driver_np(dev, 2);
}
#endif
if (usb_claim_interface(dev, 2) < 0) {
//device->config->interface->altsetting->bInterfaceNumber) < 0) { // 2 or 0
perror("usb_claim_interface");
// Something is broken if closing fails.
if(usb_close(dev)) {
perror("usb_close");
return 1;
}
// Something is broken if closing fails.
if(usb_close(dev)) {
perror("usb_close");
return 1;
}
dev = NULL;
// Try again later.?
exit(1);
}
dev = NULL;
if (usb_set_altinterface(dev, 1) <0) { //device->config->interface->altsetting->bAlternateSetting) < 0) {
perror("usb_set_altinterface");
// Try again later.
continue;
}
// Something is broken if closing fails.
if(usb_close(dev)) {
perror("usb_close");
return 1;
}
if (usb_set_altinterface(dev, 1) <0) { //device->config->interface->altsetting->bAlternateSetting) < 0) {
D perror("usb_set_altinterface");
dev = NULL;
// Try again later.
continue;
}
break;
}
// Something is broken if closing fails.
if(usb_close(dev)) {
perror("usb_close");
return 1;
}
dev = NULL;
// Try again later.
continue;
}
}
printf("found %s (%04x:%04x)\n", it_device.name,
printf("found %s (%04x:%04x)\n", it_device.name,
it_device.vendor_id, it_device.product_id);
/* go go go! */
@@ -278,11 +306,12 @@ int connect_via_usb()
int main(int argc, char **argv)
{
int c;
const char *type;
while((c = getopt(argc, argv, "QC:cp:PvVhRu:ib:U:r:e:ld:I:D:f:F:s:xH:S:n")) != -1) {
switch(c) {
case 'H':
printf("xorpair: %04x\n", do_hash_file(optarg));
printf("xorpair: %04x\n", do_hash_file(optarg, NULL));
return 0;
case 'x':
return dump_config();
@@ -306,8 +335,8 @@ int main(int argc, char **argv)
break;
case 'd':
sscanf(optarg, "%04hx:%04hx",
&supported_devices[SUPPORTED_DEVICES-2].vendor_id,
&supported_devices[SUPPORTED_DEVICES-2].product_id);
&supported_devices[SUPPORTED_DEVICES-2].vendor_id,
&supported_devices[SUPPORTED_DEVICES-2].product_id);
supported_devices[SUPPORTED_DEVICES-2].name = strdup("user");
break;
case 'D':
@@ -315,14 +344,14 @@ int main(int argc, char **argv)
break;
case 'f':
if (!strcmp(optarg,"help")) {
printf("* Flags are composed of:\n");
printf(" 0x02 - disable OMAP watchdog (possibly)\n");
printf(" 0x04 - disable RETU watchdog (possibly)\n");
printf(" 0x08 - disable lifeguard reset\n");
printf(" 0x10 - enable serial console\n");
printf(" 0x20 - disable USB timeout\n");
exit(1);
}
printf("* Flags are composed of:\n");
printf(" 0x02 - disable OMAP watchdog (possibly)\n");
printf(" 0x04 - disable RETU watchdog (possibly)\n");
printf(" 0x08 - disable lifeguard reset\n");
printf(" 0x10 - enable serial console\n");
printf(" 0x20 - disable USB timeout\n");
exit(1);
}
rd_flags = (unsigned short) strtoul(optarg, NULL, 16);
break;
case 'r':
@@ -356,7 +385,10 @@ int main(int argc, char **argv)
case 'P':
return fiasco_pack(optind, argv);
case 'I':
printf("%s: %s\n", fpid_file(optarg), optarg);
type = fpid_file(optarg);
printf("%s: %s\n", type, optarg);
if (type && strcmp(type, "fiasco") == 0)
openfiasco(optarg, NULL, NULL, NULL, NULL, 1);
identify = 1;
break;
case 'C':
@@ -383,7 +415,7 @@ int main(int argc, char **argv)
return 0;
// flags ok?
if ( (fiasco_image == NULL)
if ( (fiasco_image == NULL)
&& (boot_cmdline == NULL)
&& (reverseto == NULL)
&& (pcs_n == 0)
@@ -396,15 +428,19 @@ int main(int argc, char **argv)
{
printf("# The Free Fiasco Firmware Flasher v"VERSION"\n"
"0xFFFF [-chinlQRvVx] [-C mtd-dev] [-d vid:pid] [-D 0|1|2] [-e path] [-f flags]\n"
" [-F fiasco] [-H hash-file] [-I piece] [-p [piece%%]file]] [-r 0|1] [-S subver]\n"
" [-s serial-dev] [-u fiasco-image] [-U 0|1] | [-P new-fiasco] [piece1] [2] ..\n");
"0xFFFF [-chinlQRvVx] [-C mtd-dev] [-d vid:pid] [-D 0|1|2] [-e path] [-f flags]\n"
" [-F fiasco] [-H hash-file] [-I piece] [-p [piece%%]file]] [-r 0|1] [-S subver]\n"
" [-s serial-dev] [-u fiasco-image] [-U 0|1] | [-P new-fiasco] [piece1] [2] ..\n");
return 1;
}
if (unpack) {
if (reverseto)
chdir(reverseto);
if (reverseto) {
if (chdir(reverseto) < 0) {
printf("Error: Cannot change directory to %s\n", reverseto);
return 1;
}
}
unpack_fiasco_image(fiasco_image);
return 0;
}
@@ -415,14 +451,14 @@ int main(int argc, char **argv)
}
#if HAVE_USB
if (connect_via_usb()) {
fprintf(stderr, "Cannot connect to device. It is possibly not in boot stage.\n");
return 0;
}
if (connect_via_usb()) {
fprintf(stderr, "Cannot connect to device. It is possibly not in boot stage.\n");
return 0;
}
// if (info)
cmd_info("");
if (pcs_n) {
char version[64];
check_nolo_order();
@@ -440,15 +476,15 @@ int main(int argc, char **argv)
for(c=0;c<pcs_n;c++) {
printf("Flashing %s (%s)\n", pcs[c].type, pcs[c].name);
flash_image(pcs[c].name, pcs[c].type, pcs[c].vers);
flash_image(pcs[c].name, pcs[c].type, pcs[c].device, pcs[c].hwrevs, pcs[c].version);
}
}
if (rd_mode != -1)
set_rd_mode(rd_mode);
set_rd_mode(rd_mode);
if (rd_flags != -1)
set_rd_flags(rd_flags);
set_rd_flags(rd_flags);
if (root_device != -1)
set_root_device(root_device);
+25 -10
View File
@@ -15,7 +15,7 @@ struct devices;
int queue_mode();
int reverse_extract_pieces(char *dir);
void flash_image(const char *filename, const char *piece, const char *version);
void flash_image(const char *filename, const char *piece, const char *device, const char *hwrevs, const char *version);
int fiasco_read_image(char *file);
void check_nolo_order();
extern struct usb_dev_handle *dev;
@@ -56,21 +56,29 @@ extern int verbose;
#define CMD_WRITE 64
#define CMD_QUERY 192
struct piece_t {
char *name;
char *type;
char *vers;
char *device;
char *hwrevs;
char *version;
};
enum flash_mode {
FLASH_COLD,
FLASH_NORMAL,
FLASH_MKII,
FLASH_DISK,
};
struct devices {
char *name;
unsigned short vendor_id;
unsigned short product_id;
unsigned short flags;
enum flash_mode mode;
};
#define SUPPORTED_DEVICES 6
#define SUPPORTED_DEVICES 10
extern struct devices supported_devices[SUPPORTED_DEVICES];
extern int pcs_n;
@@ -84,18 +92,26 @@ enum {
PIECE_INITFS,
PIECE_ROOTFS,
PIECE_OMAPNAND,
PIECE_MMC,
PIECE_CMT_2ND,
PIECE_CMT_ALGO,
PIECE_CMT_MCUSW,
PIECE_FIASCO,
PIECE_LAST
};
struct header_t {
int fd;
char fwname[128];
char name[128];
char swver[128];
char type[128];
char device[16];
char hwrevs[128];
char version[128];
unsigned short hash;
unsigned int size;
unsigned char *data;
char *name;
char *layout;
};
extern char *pieces[];
@@ -103,12 +119,11 @@ extern char *modes[];
extern char *root_devices[];
// fiasco
int openfiasco(char *name, char *grep, int v);
int openfiasco(const char *name, const char *type, const char *device, const char *hwrev, const char *version, int v);
int fiasco_new(const char *filename, const char *name);
void fiasco_data_read(struct header_t *header);
int fiasco_add_eof(int fd);
extern int (*fiasco_callback)(struct header_t *header);
int fiasco_add(int fd, const char *name, const char *file, const char *version);
int fiasco_add(int fd, const char *name, const char *file, const char *layout, const char *device, const char *hwrevs, const char *version);
int fiasco_pack(int optind, char *argv[]);
int nanddump(char *mtddev, unsigned long start_addr, unsigned long length, char *dumpfile, int isbl, int ioob);
+6 -2
View File
@@ -52,7 +52,9 @@ int add_piece(char *piece)
pcs[pcs_n].name = strdup(file);
pcs[pcs_n].type = strdup(piece);
pcs[pcs_n].vers = NULL; // TODO version string not yet supported
pcs[pcs_n].device = NULL;
pcs[pcs_n].hwrevs = NULL;
pcs[pcs_n].version = NULL; // TODO version string not yet supported
} else {
/*/ autodetect piece type */
pcs[pcs_n].type = (char *)fpid_file(piece);
@@ -66,7 +68,9 @@ int add_piece(char *piece)
} else {
pcs[pcs_n].name = strdup(piece);
pcs[pcs_n].type = strdup(pcs[pcs_n].type);
pcs[pcs_n].vers = NULL;
pcs[pcs_n].device = NULL;
pcs[pcs_n].hwrevs = NULL;
pcs[pcs_n].version = NULL;
}
}
+22 -27
View File
@@ -43,38 +43,33 @@ void process_message(char *msg)
{
char *str;
char *arg;
int c=1;
if (msg == NULL)
return;
printf("[x] (%s)\n", msg);
str = strdup(msg);
arg = strchr(str, ':');
if (c!=0) {
arg[0]='\0';
arg = arg +1;
if (!strcmp(str, "flash")) {
const char *type = fpid_file(arg);
if (type == NULL) {
squeue_push2(p, "error", "Unknown piece format", 1);
} else flash_image(arg, type, NULL);
} else
if (!strcmp(str, "reset")) {
if (reboot_board() == 0) {
squeue_push2(p,"info", "Device reboots", 1);
} else squeue_push2(p,"error", "Cannot reboot device", 1);
} else
if (!strcmp(str, "info")) {
get_rd_flags();
squeue_push2(p, "info", strbuf, 1);
get_nolo_version();
squeue_push2(p, "info", strbuf, 1);
get_usb_mode();
squeue_push2(p, "info", strbuf, 1);
} else
squeue_push2(p, "error", "invalid command", 0);
} else {
squeue_push2(p, "error", "invalid command format", 0);
}
arg[0]='\0';
arg = arg +1;
if (!strcmp(str, "flash")) {
const char *type = fpid_file(arg);
if (type == NULL) {
squeue_push2(p, "error", "Unknown piece format", 1);
} else flash_image(arg, type, NULL, NULL, NULL);
} else
if (!strcmp(str, "reset")) {
if (reboot_board() == 0) {
squeue_push2(p,"info", "Device reboots", 1);
} else squeue_push2(p,"error", "Cannot reboot device", 1);
} else
if (!strcmp(str, "info")) {
get_rd_flags();
squeue_push2(p, "info", strbuf, 1);
get_nolo_version();
squeue_push2(p, "info", strbuf, 1);
get_usb_mode();
squeue_push2(p, "info", strbuf, 1);
} else
squeue_push2(p, "error", "invalid command", 0);
free(str);
}
+9 -13
View File
@@ -1,6 +1,6 @@
/*
* 0xFFFF - Open Free Fiasco Firmware Flasher
* Copyright (C) 2007,2008 pancake <@youterm.com>
* Copyright (C) 2007-2009 pancake <@youterm.com>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -46,8 +46,7 @@ int get_status()
*/
int set_usb_mode(unsigned int mode)
{
if (mode > 1)
{
if (mode > 1) {
printf("Invalid USB mode specified '%d'.\n", mode);
return -1;
}
@@ -79,7 +78,7 @@ int get_usb_mode()
}
sprintf(strbuf, "Device's USB mode is '%s'\n", (mode) ? "host" : "client");
printf(strbuf);
printf("%s", strbuf);
return 0;
}
@@ -178,7 +177,6 @@ int get_root_device()
{
unsigned char opcode;
strbuf[0] = '\0';
if (usb_control_msg(dev, CMD_QUERY, NOLO_GET_RDFLAGS, 0, 1, (char *)&opcode, 1, 2000) < 0) {
fprintf(stderr, "Cannot query root device\n");
return -1;
@@ -189,8 +187,7 @@ int get_root_device()
return -1;
}
sprintf(strbuf, "Root device is: %s\n", root_devices[opcode]);
printf(strbuf);
printf("Root device is: %s\n", root_devices[opcode]);
return 0;
}
@@ -292,13 +289,13 @@ int get_rd_flags()
{
unsigned short flags = 0;
if (usb_control_msg(dev, CMD_QUERY, NOLO_GET_RDFLAGS, 0, 3, (void *) &flags, sizeof(flags), 2000) == -1) {
if (usb_control_msg (dev, CMD_QUERY, NOLO_GET_RDFLAGS, 0, 3, (void *) &flags,sizeof(flags), 2000) == -1) {
fprintf(stderr, "Cannot get rd flags\n");
sprintf(strbuf, "error: Cannot read rd flags\n");
return -1;
}
sprintf(strbuf,
sprintf (strbuf,
"Current rd flag setting:\n"
"disable OMAP watchdog : %s\n"
"disable RETU watchdog : %s\n"
@@ -310,7 +307,7 @@ int get_rd_flags()
, (flags & 0x08) ? "set" : "not set"
, (flags & 0x10) ? "set" : "not set"
, (flags & 0x20) ? "set" : "not set");
printf(strbuf);
puts (strbuf);
return 0;
}
@@ -338,7 +335,6 @@ int get_nolo_version()
return 0;
}
int get_sw_version()
{
int ret;
@@ -359,8 +355,8 @@ int get_sw_version()
if (bytes[0]) {
sprintf(strbuf, "Software Version: %s\n", bytes);
printf("Software Version: %s\n", bytes); //???+strlen(bytes)+1));
} else
printf("No software version detected\n");
} else printf("No software version detected\n");
return 1;
}
+7 -2
View File
@@ -40,13 +40,18 @@ struct squeue_t *squeue_open(const char *file, int mode)
struct squeue_t *q;
char *pool;
int shmid;
int fd;
key_t k;
k = ftok(file, 0x34);
if (k == -1) {
perror("ftok");
squeue_release(file);
close(creat(file, 0666));
if ((fd = creat(file, 0666)) == -1) {
perror("creat");
return NULL;
}
close(fd);
chmod(file, 0666);
k = ftok(file, 0xa3);
if (k == -1) {
@@ -89,7 +94,7 @@ _retry:
}
pool = shmat(shmid, NULL, 0);
if (((int)pool) == -1) {
if (pool == (void *)-1) {
perror("shmat");
return NULL;
}
+1 -1
View File
@@ -22,7 +22,7 @@ namespace SQueues {
[CCode (cname = "squeue_push2")]
public int push2(string cmd, string msg, int l);
[CCode (cname = "squeue_get")]
public weak string get(int l);
public unowned string get(int l);
[CCode (cname = "squeue_pop")]
public int pop();
[CCode (cname = "squeue_stats")]