2 * USB Downloader for SAMSUNG Platform
4 * Copyright (C) 2007-2008 Samsung Electronics
5 * Minkyu Kang <mk7.kang@samsung.com>
11 #include <asm/errno.h>
14 /* version of USB Downloader Application */
15 #define APP_VERSION "1.6.0"
20 #ifdef CONFIG_CMD_MTDPARTS
21 #include <jffs2/load_kernel.h>
22 static struct part_info *parts[16];
25 #ifdef CONFIG_UBIFS_MK
26 #include <mkfs.ubifs.h>
35 static const char pszMe[] = "usbd: ";
37 static struct usbd_ops usbd_ops;
39 static unsigned int part_id;
40 static unsigned int write_part = 0;
41 static unsigned int fs_offset = 0x0;
43 #define NAND_PAGE_SIZE 2048
45 static unsigned long down_ram_addr;
50 extern int do_run(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[]);
53 static int check_ubi_mode(void)
58 env_ubifs = getenv("ubi");
59 ubi_mode = !strcmp(env_ubifs, "enabled");
64 #define check_ubi_mode() 0
67 #ifdef CONFIG_CMD_MTDPARTS
68 int mtdparts_init(void);
69 int find_dev_and_part(const char*, struct mtd_device**, u8*, struct part_info**);
71 /* common/cmd_jffs2.c */
72 extern struct list_head devices;
74 static u8 count_mtdparts(void)
76 struct list_head *dentry, *pentry;
77 struct mtd_device *dev;
80 list_for_each(dentry, &devices) {
81 dev = list_entry(dentry, struct mtd_device, link);
83 /* list partitions for given device */
84 list_for_each(pentry, &dev->parts)
91 static int get_part_info(void)
93 struct mtd_device *dev;
101 #if defined(CONFIG_CMD_NAND)
102 sprintf(nand_name, "nand0");
103 #elif defined(CONFIG_CMD_ONENAND)
104 sprintf(nand_name, "onenand0");
106 printf("Configure your NAND sub-system\n");
113 ubi_mode = check_ubi_mode();
115 part_num = count_mtdparts();
116 for (i = 0; i < part_num; i++) {
117 sprintf(part_name, "%s,%d", nand_name, i);
119 if (find_dev_and_part(part_name, &dev, &out_partnum, &parts[i]))
126 static int get_part_id(char *name)
128 int nparts = count_mtdparts();
131 for (i = 0; i < nparts; i++) {
132 if (strcmp(parts[i]->name, name) == 0)
136 printf("Error: Unknown partition -> %s\n", name);
140 static int get_part_info(void)
142 printf("Error: Can't get patition information\n");
146 static int get_part_id(char *name)
152 static void boot_cmd(char *addr)
154 char *argv[] = { "bootm", addr };
155 do_bootm(NULL, 0, 2, argv);
158 #if defined(CONFIG_CMD_NAND)
159 extern int do_nand(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]);
160 #elif defined(CONFIG_CMD_ONENAND)
161 extern int do_onenand(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]);
164 /* NAND erase and write using nand command */
165 static int nand_cmd(int type, char *p1, char *p2, char *p3)
169 int (*nand_func) (cmd_tbl_t *, int, int, char **);
171 #if defined(CONFIG_CMD_NAND)
172 sprintf(nand_name, "nand");
174 #elif defined(CONFIG_CMD_ONENAND)
175 sprintf(nand_name, "onenand");
176 nand_func = do_onenand;
178 printf("Configure your NAND sub-system\n");
183 char *argv[] = {nand_name, "erase", p1, p2};
184 printf("%s %s %s %s\n", argv[0], argv[1], argv[2], argv[3]);
185 ret = nand_func(NULL, 0, 4, argv);
186 } else if (type == 1) {
187 char *argv[] = {nand_name, "write", p1, p2, p3};
188 printf("%s %s %s %s %s\n", argv[0], argv[1], argv[2],
190 ret = nand_func(NULL, 0, 5, argv);
191 } else if (type == 2) {
192 char *argv[] = {nand_name, "write.yaffs", p1, p2, p3};
193 printf("%s %s %s %s %s\n", argv[0], argv[1], argv[2],
195 ret = nand_func(NULL, 0, 5, argv);
196 } else if (type == 3) {
197 char *argv[] = {nand_name, "lock", p1, p2};
198 printf("%s %s %s %s\n", argv[0], argv[1], argv[2], argv[3]);
199 ret = nand_func(NULL, 0, 4, argv);
203 printf("Error: NAND Command\n");
208 #ifdef CONFIG_CMD_UBI
209 int do_ubi(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]);
211 int ubi_cmd(int part, char *p1, char *p2, char *p3)
215 if (part == RAMDISK_PART_ID) {
216 char *argv[] = {"ubi", "write", p1, "rootfs.cramfs", p2, p3};
217 printf("%s %s %s %s %s %s\n", argv[0], argv[1], argv[2],
218 argv[3], argv[4], argv[5]);
219 ret = do_ubi(NULL, 0, 6, argv);
220 } else if (part == FILESYSTEM_PART_ID) {
221 char *argv[] = {"ubi", "write", p1, "factoryfs.cramfs", p2, p3};
222 printf("%s %s %s %s %s %s\n", argv[0], argv[1], argv[2],
223 argv[3], argv[4], argv[5]);
224 ret = do_ubi(NULL, 0, 6, argv);
225 } else if (part == FILESYSTEM2_PART_ID) {
226 char *argv[] = {"ubi", "write", p1, "datafs.ubifs", p2, p3};
227 printf("%s %s %s %s %s %s\n", argv[0], argv[1], argv[2],
228 argv[3], argv[4], argv[5]);
229 ret = do_ubi(NULL, 0, 6, argv);
236 #ifdef CONFIG_CMD_MMC
240 static struct mmc *mmc;
242 static int mmc_cmd(int ops, int dev_num, ulong start, lbaint_t cnt, void *addr)
247 printf("mmc write 0x%x 0x%x\n", start, cnt);
248 ret = mmc->block_dev.block_write(dev_num, start, cnt, addr);
250 printf("mmc read 0x%x 0x%x\n", start, cnt);
251 ret = mmc->block_dev.block_read(dev_num, start, cnt, addr);
262 #define NORMAL_PARTITION 0
263 #define EXTEND_PARTITION 1
265 #define EXTEND_PART_TYPE 5
267 #define EXTEND_MAX_PART 32
269 static unsigned int cur_blk_offset;
270 static unsigned int cur_part_size;
271 static unsigned int cur_part;
273 static unsigned int mmc_parts;
274 static unsigned int mmc_part_write;
276 static u8 part_mode = 0;
278 struct partition_info {
282 } __attribute__((packed));
284 struct partition_header {
285 u8 fat32head[16]; /* RFSHEAD identifier */
286 struct partition_info partition[EXTEND_MAX_PART];
287 u8 res[112]; /* only data (without MBR) */
288 } __attribute__((packed));
290 struct mul_partition_info {
291 u32 lba_begin; /* absolute address from 0 block */
293 } __attribute__((packed));
295 #define MBR_OFFSET 0x10
297 struct partition_header part_info;
299 struct mul_partition_info mul_info[EXTEND_MAX_PART];
301 static int write_mmc_partition(struct usbd_ops *usbd, u32 *ram_addr, u32 len)
309 if (cur_part_size > len) {
310 blocks = len / usbd->mmc_blk;
313 blocks = cur_part_size / usbd->mmc_blk;
314 ret = len - cur_part_size;
317 if (len % usbd->mmc_blk)
320 loop = blocks / usbd->mmc_max;
321 if (blocks % usbd->mmc_max)
324 for (i = 0; i < loop; i++) {
326 cnt = blocks % usbd->mmc_max;
333 mmc_cmd(OPS_WRITE, usbd->mmc_dev, cur_blk_offset,
334 cnt, (void *)*ram_addr);
336 cur_blk_offset += cnt;
338 *ram_addr += (cnt * usbd->mmc_blk);
344 static int write_file_mmc(struct usbd_ops *usbd, u32 len)
351 if (!usbd->mmc_total) {
352 printf("MMC is not supported!\n");
356 ram_addr = (u32)down_ram_addr;
358 if (cur_blk_offset == 0) {
362 memcpy(&part_info, (void *)ram_addr,
363 sizeof(struct partition_header));
365 ram_addr += sizeof(struct partition_header);
366 len -= sizeof(struct partition_header);
367 mbr = (struct mbr *)ram_addr;
368 mbr_blk_size = mbr->parts[0].lba;
370 if (mbr->parts[0].partition_type != EXTEND_PART_TYPE) {
371 part_mode = NORMAL_PARTITION;
373 /* modify sectors of p1 */
374 mbr->parts[0].nsectors = usbd->mmc_total -
376 mbr->parts[1].nsectors +
377 mbr->parts[2].nsectors +
378 mbr->parts[3].nsectors);
382 /* modify lba_begin of p2 and p3 and p4 */
383 for (i = 1; i < 4; i++) {
384 if (part_info.partition[i].size == 0)
389 mbr->parts[i - 1].lba +
390 mbr->parts[i - 1].nsectors;
394 memcpy(&mbr_info, mbr, sizeof(struct mbr));
396 printf("Total Size: 0x%08x #parts %d\n",
397 (unsigned int)usbd->mmc_total,
399 for (i = 0; i < mmc_parts; i++) {
400 printf("p%d\t0x%08x\t0x%08x\n", i + 1,
401 mbr_info.parts[i].lba,
402 mbr_info.parts[i].nsectors);
406 mmc_cmd(OPS_WRITE, usbd->mmc_dev, 0,
407 mbr_blk_size, (void *)ram_addr);
409 ram_addr += mbr_blk_size * usbd->mmc_blk;
410 len -= mbr_blk_size * usbd->mmc_blk;
412 cur_blk_offset = mbr_blk_size;
414 cur_part_size = part_info.partition[0].size;
416 /* modify p1's total sector */
417 bs = (boot_sector *)ram_addr;
418 bs->total_sect = mbr_info.parts[0].nsectors;
420 printf("\nWrite Partition %d.. %d blocks\n",
422 part_info.partition[cur_part].size /
425 part_mode = EXTEND_PARTITION;
427 for (i = 0; i < EXTEND_MAX_PART; i++) {
428 if (part_info.partition[i].size == 0)
436 printf("found %d partitions\n", mmc_parts);
438 /* build partition table */
440 mul_info[0].num_sectors =
441 usbd->mmc_total - mbr_blk_size;
442 for (i = 1; i < mmc_parts; i++) {
443 mul_info[i].num_sectors =
444 part_info.partition[i].res +
445 mbr_blk_size; /* add MBR */
448 for (i = 1; i < mmc_parts; i++) {
449 mul_info[0].num_sectors -=
450 mul_info[i].num_sectors;
453 mul_info[0].lba_begin = mbr_blk_size;
454 for (i = 1; i < mmc_parts; i++) {
455 mul_info[i].lba_begin =
456 mul_info[i-1].lba_begin +
457 mul_info[i-1].num_sectors;
460 /* modify MBR of extended partition: p1 */
461 mbr->parts[0].nsectors =
462 usbd->mmc_total - mbr_blk_size;
464 /* modify MBR of first logical partition: p5 */
466 (ram_addr + mbr_blk_size * usbd->mmc_blk);
468 mbr->parts[0].nsectors =
469 mul_info[0].num_sectors - mbr_blk_size;
471 mul_info[1].lba_begin - mbr_blk_size;
473 /* modify BPB data of p5 */
475 ((u32)mbr + mbr_blk_size * usbd->mmc_blk);
476 memset(&bs->sectors, 0, 2);
477 bs->total_sect = mbr->parts[0].nsectors;
479 printf("Total Size: 0x%08x #parts %d\n",
480 (unsigned int)usbd->mmc_total,
482 for (i = 0; i < mmc_parts; i++) {
483 printf("p%d\t0x%08x\t0x%08x\n", i + 1,
484 mul_info[i].lba_begin,
485 mul_info[i].num_sectors);
490 cur_part_size = part_info.partition[0].size;
492 printf("\nWrite Partition %d.. %d blocks\n",
494 part_info.partition[cur_part].size /
499 for (i = cur_part; i < mmc_parts; i++) {
500 ret = write_mmc_partition(usbd, &ram_addr, len);
503 cur_part_size -= len;
508 part_info.partition[cur_part].size;
510 if (part_mode == NORMAL_PARTITION) {
512 mbr_info.parts[cur_part].lba;
515 mul_info[cur_part].lba_begin;
517 if (cur_part < mmc_parts) {
518 mbr = (struct mbr *)ram_addr;
520 mul_info[cur_part+1].lba_begin -
530 printf("\nWrite Partition %d.. %d blocks\n",
532 part_info.partition[cur_part].size /
540 static int write_file_mmc_part(struct usbd_ops *usbd, u32 len)
548 ram_addr = (u32)down_ram_addr;
551 if (cur_blk_offset == 0) {
553 mmc_cmd(OPS_READ, usbd->mmc_dev, 0,
554 sizeof(struct mbr)/usbd->mmc_blk, (void *)mbr);
556 mbr_blk_size = mbr->parts[0].lba;
558 if (mbr->parts[0].partition_type != EXTEND_PART_TYPE) {
559 part_mode = NORMAL_PARTITION;
561 for (i = 0; i < 4; i++) {
562 printf("p%d\t0x%08x\t0x%08x\n", i + 1,
563 mbr_info.parts[i].lba,
564 mbr_info.parts[i].nsectors);
568 mbr->parts[mmc_part_write - 1].lba;
569 cur_part = mmc_part_write - 1;
572 mbr->parts[mmc_part_write - 1].nsectors;
574 if (mmc_part_write == 1) {
575 ram_addr += sizeof(struct mbr);
576 cur_blk_offset += sizeof(struct mbr) /
578 len -= sizeof(struct mbr);
581 part_mode = EXTEND_PARTITION;
583 for (i = 1; i < mmc_part_write; i++) {
584 ofs = mbr->parts[0].lba + mbr->parts[1].lba;
585 printf("P%d start blk: 0x%x, size: 0x%x\n", i,
586 ofs, mbr->parts[1].nsectors);
587 mmc_cmd(OPS_READ, usbd->mmc_dev, ofs,
588 (sizeof(struct mbr) / usbd->mmc_blk),
592 ofs = mbr->parts[0].lba + mbr->parts[1].lba;
593 printf("P%d start blk: 0x%x, size: 0x%x\n", i,
594 ofs, mbr->parts[1].nsectors);
596 ofs += mbr_blk_size; /* skip MBR */
597 cur_blk_offset = ofs;
598 cur_part = mmc_part_write - 1;
601 mbr->parts[1].nsectors;
603 if (mmc_part_write == 1) {
606 /* modify BPB data of p1 */
607 mmc_cmd(OPS_READ, usbd->mmc_dev, cur_blk_offset,
608 (sizeof(struct mbr) / usbd->mmc_blk),
611 bs = (boot_sector *)mbr;
612 total_sect = bs->total_sect;
614 bs = (boot_sector *)ram_addr;
615 memset(&bs->sectors, 0, 2);
616 bs->total_sect = total_sect;
621 printf("\nWrite Partition %d.. %d blocks\n",
623 len / (int)usbd->mmc_blk);
625 write_mmc_partition(usbd, &ram_addr, len);
631 static unsigned int mbr_offset[16];
632 static int mbr_parts = 0;
634 static unsigned long memsize_parse (const char *const ptr, const char **retptr)
636 unsigned long ret = simple_strtoul(ptr, (char **)retptr, 0);
656 static void set_mbr_info(struct usbd_ops *usbd, char *ramaddr, u32 len)
662 unsigned int size[16];
665 strncpy(mbr_str, ramaddr, len);
668 for (i = 0; ; i++, p = NULL) {
669 tok = strtok(p, ",");
672 strcpy(save[i], tok);
673 printf("part%d: %s\n", i, save[i]);
677 printf("find %d partitions\n", mbr_parts);
679 for (i = 0; i < mbr_parts; i++) {
681 size[i] = memsize_parse(p, (const char **)&p) / 512;
684 puts("save the MBR Table...\n");
685 set_mbr_table(0x800, mbr_parts, size, mbr_offset);
688 static int write_mmc_image(struct usbd_ops *usbd, unsigned int len, int part_num)
692 if (mbr_parts <= part_num) {
693 printf("Error: MBR table have %d partitions (request %d)\n",
694 mbr_parts, part_num);
699 /* modify size of UMS partition */
700 if (part_num == 4 && fs_offset == 0) {
702 bs = (boot_sector *)down_ram_addr;
703 memset(&bs->sectors, 0, 2);
704 bs->total_sect = usbd->mmc_total - mbr_offset[part_num];
707 ret = mmc_cmd(OPS_WRITE, usbd->mmc_dev,
708 mbr_offset[part_num] + fs_offset,
710 (void *)down_ram_addr);
712 fs_offset += (len / usbd->mmc_blk);
717 static int write_fat_file(struct usbd_ops *usbd, char *file_name,
718 int part_id, int len)
720 #ifdef CONFIG_FAT_WRITE
723 ret = fat_register_device(&mmc->block_dev, part_id);
725 printf("error : fat_register_divce\n");
729 ret = file_fat_write(file_name, (void *)down_ram_addr, len);
731 /* format and write again */
733 printf("formatting\n");
734 if (mkfs_vfat(&mmc->block_dev, part_id)) {
735 printf("error : format device\n");
738 ret = file_fat_write(file_name, (void *)down_ram_addr, len);
742 printf("error : writing uImage\n");
746 printf("error: doesn't support fat_write\n");
752 static int ubi_update = 0;
754 static int write_file_system(char *ramaddr, ulong len, char *offset,
755 char *length, int part_num)
759 #ifdef CONFIG_CMD_MTDPARTS
760 #ifdef CONFIG_CMD_UBI
763 sprintf(length, "0x%x", (uint)len);
764 ret = ubi_cmd(part_id, ramaddr, length, "cont");
769 /* Erase entire partition at the first writing */
770 if (write_part == 0 && ubi_update == 0) {
771 sprintf(offset, "0x%x", (uint)parts[part_num]->offset);
772 sprintf(length, "0x%x", (uint)parts[part_num]->size);
773 nand_cmd(0, offset, length, NULL);
776 sprintf(offset, "0x%x", (uint)(parts[part_num]->offset + fs_offset));
777 sprintf(length, "0x%x", (uint)len);
780 ret = nand_cmd(1, ramaddr, offset, length);
786 static int qboot_erase = 0;
788 /* Erase the qboot */
789 static void erase_qboot_area(void)
791 #ifdef CONFIG_CMD_MTDPARTS
792 char offset[12], length[12];
798 qboot_id = get_part_id("qboot");
800 if (qboot_id != -1) {
801 printf("\nCOMMAND_ERASE_QBOOT\n");
802 sprintf(offset, "%x", parts[qboot_id]->offset);
803 sprintf(length, "%x", parts[qboot_id]->size);
804 nand_cmd(0, offset, length, NULL);
810 /* Erase the environment */
811 static void erase_env_area(struct usbd_ops *usbd)
813 #if defined(CONFIG_ENV_IS_IN_NAND) || defined(CONFIG_ENV_IS_IN_ONENAND)
815 char offset[12], length[12];
817 param_id = get_part_id("params");
819 if (param_id == -1) {
820 sprintf(offset, "%x", CONFIG_ENV_ADDR);
821 sprintf(length, "%x", CONFIG_ENV_SIZE);
823 sprintf(offset, "%x", parts[param_id]->offset);
824 sprintf(length, "%x", parts[param_id]->size);
826 nand_cmd(0, offset, length, NULL);
827 #elif defined(CONFIG_ENV_IS_IN_MMC)
828 char buf[usbd->mmc_blk];
830 memset(buf, 0x0, usbd->mmc_blk);
831 mmc_cmd(OPS_WRITE, CONFIG_SYS_MMC_ENV_DEV,
832 CONFIG_ENV_OFFSET / usbd->mmc_blk,
837 static inline void send_ack(struct usbd_ops *usbd, int data)
839 *((ulong *) usbd->tx_data) = data;
840 usbd->send_data(usbd->tx_data, usbd->tx_len);
843 static inline int check_mmc_device(struct usbd_ops *usbd)
848 printf("\nError: Couldn't find the MMC device\n");
852 static int write_mtd_image(struct usbd_ops *usbd, int img_type,
853 unsigned int len, unsigned int arg)
856 #ifdef CONFIG_CMD_MTDPARTS
857 unsigned int ofs = 0;
858 char offset[12], length[12], ramaddr[12];
860 sprintf(ramaddr, "0x%x", (uint) down_ram_addr);
862 /* Erase and Write to NAND */
865 ofs = parts[part_id]->offset;
866 #ifdef CONFIG_S5PC1XX
867 /* Workaround: for prevent revision mismatch */
868 if (cpu_is_s5pc110() && (down_mode != MODE_FORCE)) {
870 long *img_header = (long *)down_ram_addr;
872 if (*img_header == 0xea000012)
874 else if (*(img_header + 0x400) == 0xea000012)
877 if (img_rev != s5p_get_cpu_rev()) {
878 printf("CPU revision mismatch!\n"
879 "bootloader is %s%s\n"
880 "download image is %s%s\n",
881 s5p_get_cpu_rev() ? "EVT1" : "EVT0",
882 s5p_get_cpu_rev() == 2 ? "-Fused" : "",
883 img_rev ? "EVT1" : "EVT0",
884 img_rev == 2 ? "-Fused" : "");
890 /* Only u-boot.bin is allowed */
892 long *img_header = (long *)down_ram_addr;
894 if (*img_header != 0xea000018) {
895 printf("\n!!! ERROR !!!\n"
896 "Please download the u-boot.bin.\n"
897 "Other images are not allowed.\n\n");
903 erase_env_area(usbd);
905 sprintf(offset, "%x", (uint)ofs);
907 sprintf(length, "%x", parts[part_id]->size - (uint)ofs);
909 sprintf(length, "%x", parts[part_id]->size);
912 nand_cmd(0, offset, length, NULL);
914 sprintf(length, "%x", (unsigned int) len);
915 ret = nand_cmd(1, ramaddr, offset, length);
919 sprintf(offset, "%x", parts[part_id]->offset);
920 sprintf(length, "%x", parts[part_id]->size);
923 nand_cmd(0, offset, length, NULL);
925 sprintf(length, "%x", (unsigned int) len);
926 ret = nand_cmd(1, ramaddr, offset, length);
933 ret = write_file_system(ramaddr, len, offset, length, part_id);
939 sprintf(offset, "%x", parts[part_id]->offset);
940 sprintf(length, "%x", parts[part_id]->size);
944 nand_cmd(0, offset, length, NULL);
946 printf("CSA Clear will be skipped temporary\n");
948 /* Check ubi image, 0x23494255 is UBI# */
950 long *img_header = (long *)down_ram_addr;
952 if (*img_header == 0x23494255)
956 #ifdef CONFIG_UBIFS_MK
957 void *dest_addr = (void *) down_ram_addr + 0xc00000;
958 void *src_addr = (void *) down_ram_addr;
959 int leb_size, max_leb_cnt, mkfs_min_io_size;
960 unsigned long ubifs_dest_size, ubi_dest_size;
961 #ifdef CONFIG_S5PC110
962 mkfs_min_io_size = 4096;
963 leb_size = 248 * 1024;
966 mkfs_min_io_size = 2048;
967 leb_size = 126 * 1024;
970 printf("Start making ubifs\n");
971 ret = mkfs(src_addr, len, dest_addr, &ubifs_dest_size,
972 mkfs_min_io_size, leb_size, max_leb_cnt);
974 printf("Error : making ubifs failed\n");
977 printf("Complete making ubifs\n");
980 #ifdef CONFIG_UBINIZE
981 int peb_size, ubi_min_io_size, subpage_size, vid_hdr_offs;
982 #ifdef CONFIG_S5PC110
983 ubi_min_io_size = 4096;
984 peb_size = 256 * 1024;
988 ubi_min_io_size = 2048;
989 peb_size = 128 * 1024;
993 printf("Start ubinizing\n");
994 ret = ubinize(dest_addr, ubifs_dest_size,
995 src_addr, &ubi_dest_size,
996 peb_size, ubi_min_io_size,
997 subpage_size, vid_hdr_offs);
999 printf("Error : ubinizing failed\n");
1002 printf("Complete ubinizing\n");
1004 len = (unsigned int) ubi_dest_size;
1008 /* Write : arg (0 Modem) / (1 CSA) */
1010 sprintf(length, "%x", (unsigned int) len);
1011 ret = nand_cmd(1, ramaddr, offset, length);
1016 #ifdef CONFIG_CMD_MMC
1018 if (check_mmc_device(usbd))
1022 ret = write_file_mmc_part(usbd, len);
1024 ret = write_file_mmc(usbd, len);
1037 static int write_v2_image(struct usbd_ops *usbd, int img_type,
1038 unsigned int len, unsigned int arg)
1042 if (check_mmc_device(usbd))
1047 ret = write_mmc_image(usbd, len, part_id);
1051 #ifdef CONFIG_CMD_MBR
1052 set_mbr_info(usbd, (char *)down_ram_addr, len);
1056 case IMG_BOOTLOADER:
1057 #ifdef CONFIG_BOOTLOADER_SECTOR
1058 erase_env_area(usbd);
1060 ret = mmc_cmd(OPS_WRITE, usbd->mmc_dev,
1061 CONFIG_BOOTLOADER_SECTOR,
1062 len / usbd->mmc_blk + 1,
1063 (void *)down_ram_addr);
1068 ret = write_fat_file(usbd, "uImage", part_id, len);
1072 ret = write_fat_file(usbd, "modem.bin", part_id, len);
1083 /* Parsing received data packet and Process data */
1084 static int process_data(struct usbd_ops *usbd)
1086 unsigned int cmd = 0, arg = 0, len = 0, flag = 0;
1089 unsigned int blocks = 0;
1094 sprintf(ramaddr, "0x%x", (uint) down_ram_addr);
1097 cmd = *((ulong *) usbd->rx_data + 0);
1098 arg = *((ulong *) usbd->rx_data + 1);
1099 len = *((ulong *) usbd->rx_data + 2);
1100 flag = *((ulong *) usbd->rx_data + 3);
1102 /* Reset tx buffer */
1103 memset(usbd->tx_data, 0, sizeof(usbd->tx_data));
1105 ubi_mode = check_ubi_mode();
1108 case COMMAND_DOWNLOAD_IMAGE:
1109 printf("\nCOMMAND_DOWNLOAD_IMAGE\n");
1112 down_ram_addr = usbd->ram_addr + 0x1000000;
1114 down_ram_addr = usbd->ram_addr;
1116 usbd->recv_setup((char *)down_ram_addr, (int)len);
1117 printf("Download to 0x%08x, %d bytes\n",
1118 (uint)down_ram_addr, (int)len);
1121 send_ack(usbd, STATUS_DONE);
1123 /* Receive image by using dma */
1124 recvlen = usbd->recv_data();
1126 send_ack(usbd, STATUS_ERROR);
1128 } else if (recvlen < len) {
1129 printf("Error: wrong image size -> %d/%d\n",
1130 (int)recvlen, (int)len);
1132 /* Retry this commad */
1133 send_ack(usbd, STATUS_RETRY);
1135 send_ack(usbd, STATUS_DONE);
1139 case COMMAND_DOWNLOAD_SPMODE:
1140 printf("\nCOMMAND_DOWNLOAD_SPMODE\n");
1142 down_ram_addr = usbd->ram_addr + 0x2008000;
1144 usbd->recv_setup((char *)down_ram_addr, (int)len);
1145 printf("Download to 0x%08x, %d bytes\n",
1146 (uint)down_ram_addr, (int)len);
1149 send_ack(usbd, STATUS_DONE);
1151 /* Receive image by using dma */
1152 recvlen = usbd->recv_data();
1153 send_ack(usbd, STATUS_DONE);
1157 /* Report partition info */
1158 case COMMAND_PARTITION_SYNC:
1161 #ifdef CONFIG_CMD_UBI
1163 if (part_id == RAMDISK_PART_ID ||
1164 part_id == FILESYSTEM_PART_ID ||
1165 part_id == FILESYSTEM2_PART_ID) {
1166 /* change to yaffs style */
1170 if (part_id == FILESYSTEM3_PART_ID) {
1171 /* change ubi style */
1177 if (part_id == FILESYSTEM3_PART_ID)
1178 part_id = get_part_id("UBI");
1179 else if (part_id == MODEM_PART_ID)
1180 part_id = get_part_id("modem");
1181 else if (part_id == KERNEL_PART_ID)
1182 part_id = get_part_id("kernel");
1183 else if (part_id == BOOT_PART_ID)
1184 part_id = get_part_id("bootloader");
1185 #ifdef CONFIG_MIRAGE
1189 printf("COMMAND_PARTITION_SYNC - Part%d\n", part_id);
1191 #ifdef CONFIG_CMD_MTDPARTS
1192 blocks = parts[part_id]->size / 1024 / 128;
1194 printf("COMMAND_PARTITION_SYNC - Part%d, %d blocks\n",
1197 send_ack(usbd, blocks);
1200 case COMMAND_WRITE_PART_0:
1202 printf("COMMAND_WRITE_PART_0\n");
1205 case COMMAND_WRITE_PART_1:
1206 printf("COMMAND_WRITE_PART_BOOT\n");
1207 part_id = get_part_id("bootloader");
1208 img_type = IMG_BOOT;
1211 case COMMAND_WRITE_PART_2:
1212 case COMMAND_ERASE_PARAMETER:
1213 printf("COMMAND_PARAMETER - not support!\n");
1216 case COMMAND_WRITE_PART_3:
1217 printf("COMMAND_WRITE_KERNEL\n");
1218 part_id = get_part_id("kernel");
1219 img_type = IMG_KERNEL;
1222 case COMMAND_WRITE_PART_4:
1223 printf("COMMAND_WRITE_ROOTFS\n");
1224 part_id = get_part_id("Root");
1225 img_type = IMG_FILESYSTEM;
1229 case COMMAND_WRITE_PART_5:
1230 printf("COMMAND_WRITE_FACTORYFS\n");
1231 part_id = get_part_id("Fact");
1232 img_type = IMG_FILESYSTEM;
1236 case COMMAND_WRITE_PART_6:
1237 printf("COMMAND_WRITE_DATAFS\n");
1238 part_id = get_part_id("Data");
1239 img_type = IMG_FILESYSTEM;
1243 case COMMAND_WRITE_PART_7:
1244 printf("COMMAND_WRITE_UBI\n");
1245 part_id = get_part_id("UBI");
1246 img_type = IMG_FILESYSTEM;
1248 /* someday, it will be deleted */
1252 case COMMAND_WRITE_PART_8:
1253 printf("COMMAND_WRITE_MODEM\n");
1254 part_id = get_part_id("modem");
1255 img_type = IMG_MODEM;
1258 #ifdef CONFIG_CMD_MMC
1259 case COMMAND_WRITE_PART_9:
1260 printf("COMMAND_WRITE_MMC\n");
1262 mmc_part_write = arg;
1266 case COMMAND_WRITE_IMG_0:
1267 printf("COMMAND_WRITE_MBR\n");
1271 case COMMAND_WRITE_IMG_1:
1272 printf("COMMAND_WRITE_BOOTLOADER\n");
1273 img_type = IMG_BOOTLOADER;
1276 case COMMAND_WRITE_IMG_2:
1277 printf("COMMAND_WRITE_KERNEL\n");
1278 img_type = IMG_KERNEL_V2;
1282 case COMMAND_WRITE_IMG_3:
1283 printf("COMMAND_WRITE_MODEM\n");
1284 img_type = IMG_MODEM_V2;
1288 case COMMAND_WRITE_IMG_4:
1289 printf("COMMAND_WRITE_BOOT_PART\n");
1294 case COMMAND_WRITE_IMG_5:
1295 printf("COMMAND_WRITE_SYSTEM_PART\n");
1300 case COMMAND_WRITE_IMG_6:
1301 printf("COMMAND_WRITE_UMS_PART\n");
1306 case COMMAND_WRITE_UBI_INFO:
1307 printf("COMMAND_WRITE_UBI_INFO\n");
1310 #ifdef CONFIG_CMD_UBI
1312 sprintf(length, "0x%x", (uint)len);
1313 ret = ubi_cmd(part_id, ramaddr, length, "begin");
1316 printf("Error: Not UBI mode\n");
1320 /* Write image success -> Report status */
1321 send_ack(usbd, ret);
1324 /* Download complete -> reset */
1325 case COMMAND_RESET_PDA:
1326 printf("\nDownload finished and Auto reset!\nWait........\n");
1331 if (usbd->cpu_reset)
1334 run_command("reset", 0);
1339 case COMMAND_RESET_USB:
1340 printf("\nError is occured!(maybe previous step)->\
1341 Turn off and restart!\n");
1347 case COMMAND_RAM_BOOT:
1352 case COMMAND_RAMDISK_MODE:
1353 printf("COMMAND_RAMDISK_MODE\n");
1354 #ifdef CONFIG_RAMDISK_ADDR
1356 down_ram_addr = usbd->ram_addr;
1358 down_ram_addr = CONFIG_RAMDISK_ADDR;
1359 run_command("run ramboot", 0);
1364 #ifdef CONFIG_DOWN_PHONE
1365 case COMMAND_DOWN_PHONE:
1366 printf("COMMAND_RESET_PHONE\n");
1370 send_ack(usbd, STATUS_DONE);
1373 case COMMAND_CHANGE_USB:
1374 printf("COMMAND_CHANGE_USB\n");
1381 run_command("reset", 0);
1384 case COMMAND_CSA_CLEAR:
1385 printf("COMMAND_CSA_CLEAR\n");
1386 part_id = get_part_id("csa");
1387 img_type = IMG_MODEM;
1390 case COMMAND_PROGRESS:
1391 if (usbd->set_progress)
1392 usbd->set_progress(arg);
1396 printf("Error: Unknown command -> (%d)\n", (int)cmd);
1400 if (img_type < IMG_V2)
1401 ret = write_mtd_image(usbd, img_type, len, arg);
1403 ret = write_v2_image(usbd, img_type, len, arg);
1406 send_ack(usbd, STATUS_ERROR);
1409 /* Retry this commad */
1410 send_ack(usbd, STATUS_RETRY);
1413 send_ack(usbd, STATUS_DONE);
1417 /* Reset write count for another image */
1426 static const char *recv_key = "SAMSUNG";
1427 static const char *tx_key = "MPL";
1429 int do_usbd_down(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
1431 struct usbd_ops *usbd;
1436 down_mode = simple_strtoul(argv[1], NULL, 10);
1438 down_mode = MODE_NORMAL;
1440 printf("USB Downloader v%s\n", APP_VERSION);
1442 /* get partition info */
1443 err = get_part_info();
1447 /* interface setting */
1448 usbd = usbd_set_interface(&usbd_ops);
1449 down_ram_addr = usbd->ram_addr;
1451 #ifdef CONFIG_CMD_MBR
1453 mbr_parts = get_mbr_table(mbr_offset);
1457 puts("using default MBR\n");
1459 mbrparts = getenv("mbrparts");
1460 set_mbr_info(usbd, mbrparts, strlen(mbrparts));
1464 /* init the usb controller */
1465 if (!usbd->usb_init()) {
1466 usbd->down_cancel(END_BOOT);
1469 mmc = find_mmc_device(usbd->mmc_dev);
1472 /* receive setting */
1473 usbd->recv_setup(usbd->rx_data, usbd->rx_len);
1475 /* detect the download request from Host PC */
1476 ret = usbd->recv_data();
1478 if (strncmp(usbd->rx_data, recv_key, strlen(recv_key)) == 0) {
1479 printf("Download request from the Host PC\n");
1482 strcpy(usbd->tx_data, tx_key);
1483 usbd->send_data(usbd->tx_data, usbd->tx_len);
1485 printf("No download request from the Host PC!! 1\n");
1488 } else if (ret < 0) {
1489 usbd->down_cancel(END_RETRY);
1492 usbd->down_cancel(END_BOOT);
1497 printf("Receive the packet\n");
1499 /* receive the data from Host PC */
1501 usbd->recv_setup(usbd->rx_data, usbd->rx_len);
1503 ret = usbd->recv_data();
1505 ret = process_data(usbd);
1507 usbd->down_cancel(END_RETRY);
1509 } else if (ret == 0) {
1510 usbd->down_cancel(END_NORMAL);
1513 } else if (ret < 0) {
1514 usbd->down_cancel(END_RETRY);
1517 usbd->down_cancel(END_BOOT);
1525 U_BOOT_CMD(usbdown, CONFIG_SYS_MAXARGS, 1, do_usbd_down,
1526 "Initialize USB device and Run USB Downloader (specific)",
1528 "usbdown mode - specific mode (0: NORAML, 1: FORCE)"