From 3e2c51d82ce50b0074681c44e81f08de25f34fab Mon Sep 17 00:00:00 2001 From: Nicolas Pennequin Date: Thu, 22 Nov 2007 18:07:40 +0000 Subject: [PATCH] Firmware update utility for the Gigabeat S and probably other MTP devices. Based on libmtp's sendfile.c example, tweaked by Maurus Cuelenaere and me to send firmware files. git-svn-id: svn://svn.rockbox.org/rockbox/trunk@15755 a1c6a512-1295-4272-9138-f99709370657 --- docs/CREDITS | 1 + utils/MTP/Makefile | 11 ++++ utils/MTP/sendfirm.c | 136 +++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 148 insertions(+) create mode 100644 utils/MTP/Makefile create mode 100644 utils/MTP/sendfirm.c diff --git a/docs/CREDITS b/docs/CREDITS index ffff55c90d..dca54732e0 100644 --- a/docs/CREDITS +++ b/docs/CREDITS @@ -347,6 +347,7 @@ Karim Boucher James Espinoza Franz Rühmland Jordan Anderson +Maurus Cuelenaere The libmad team The wavpack team diff --git a/utils/MTP/Makefile b/utils/MTP/Makefile new file mode 100644 index 0000000000..4678546b02 --- /dev/null +++ b/utils/MTP/Makefile @@ -0,0 +1,11 @@ +CFLAGS = -Wall +LIBS = -lmtp +OUTPUT = sendfirm + +all: $(OUTPUT) + +$(OUTPUT): sendfirm.c + gcc $(CFLAGS) $(LIBS) -o $(OUTPUT) sendfirm.c + +clean: + rm -f $(OUTPUT) diff --git a/utils/MTP/sendfirm.c b/utils/MTP/sendfirm.c new file mode 100644 index 0000000000..e216037efc --- /dev/null +++ b/utils/MTP/sendfirm.c @@ -0,0 +1,136 @@ +/*************************************************************************** + * __________ __ ___. + * Open \______ \ ____ ____ | | _\_ |__ _______ ___ + * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / + * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < + * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ + * \/ \/ \/ \/ \/ + * $Id$ + * + * Based on sendfile.c from libmtp: http://libmtp.sourceforge.net + * Modified by Maurus Cuelenaere and Nicolas Pennequin. + * + * Copyright (C) 2005-2007 Linus Walleij + * Copyright (C) 2006 Chris A. Debenham + * + * All files in this archive are subject to the GNU General Public License. + * See the file COPYING in the source tree root for full license agreement. + * + * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY + * KIND, either express or implied. + * + ****************************************************************************/ + +#define _LARGEFILE_SOURCE +#define _LARGEFILE64_SOURCE + +#include +#include +#include +#include +#include +#include "libmtp.h" + +LIBMTP_mtpdevice_t *device; + +static int progress(u_int64_t const sent, u_int64_t const total, + void const *const data) +{ + int percent = (sent * 100) / total; +#ifdef __WIN32__ + printf("Progress: %I64u of %I64u (%d%%)\r", sent, total, percent); +#else + printf("Progress: %llu of %llu (%d%%)\r", sent, total, percent); +#endif + fflush(stdout); + return 0; +} + +void usage(void) +{ + fprintf(stderr, "usage: sendfirm \n"); +} + +int sendfile_function(char *from_path) +{ + printf("Sending %s\n", from_path); + char *filename; + uint64_t filesize; +#ifdef __USE_LARGEFILE64 + struct stat64 sb; +#else + struct stat sb; +#endif + LIBMTP_file_t *genfile; + int ret; + uint32_t parent_id = 0; + +#ifdef __USE_LARGEFILE64 + if (stat64(from_path, &sb) == -1) + { +#else + if (stat(from_path, &sb) == -1) + { +#endif + fprintf(stderr, "%s: ", from_path); + perror("stat"); + exit(1); + } + +#ifdef __USE_LARGEFILE64 + filesize = sb.st_size; +#else + filesize = (uint64_t) sb.st_size; +#endif + filename = basename(from_path); + + genfile = LIBMTP_new_file_t(); + genfile->filesize = filesize; + genfile->filename = strdup("nk.bin"); + genfile->filetype = LIBMTP_FILETYPE_FIRMWARE; + + printf("Sending file...\n"); + ret = LIBMTP_Send_File_From_File(device, from_path, genfile, progress, + NULL, parent_id); + printf("\n"); + if (ret != 0) + { + printf("Error sending file.\n"); + LIBMTP_Dump_Errorstack(device); + LIBMTP_Clear_Errorstack(device); + } + else + { + printf("New file ID: %d\n", genfile->item_id); + } + + LIBMTP_destroy_file_t(genfile); + + return 0; +} + +int main(int argc, char **argv) +{ + if (argc < 2) + { + usage(); + return 1; + } + + LIBMTP_Init(); + + fprintf(stdout, "libmtp version: " LIBMTP_VERSION_STRING "\n\n"); + + device = LIBMTP_Get_First_Device(); + if (device == NULL) + { + printf("No devices.\n"); + return 0; + } + + sendfile_function(argv[1]); + + LIBMTP_Release_Device(device); + + exit(0); +}