3 * esd gmbh <www.esd-electronics.com>
4 * Reinhard Arlt <reinhard.arlt@esd-electronics.com>
6 * made from cmd_reiserfs by
8 * (C) Copyright 2003 - 2004
9 * Sysgo Real-Time Solutions, AG <www.elinos.com>
10 * Pavel Bartusek <pba@sysgo.com>
12 * See file CREDITS for list of people who contributed to this
15 * This program is free software; you can redistribute it and/or
16 * modify it under the terms of the GNU General Public License as
17 * published by the Free Software Foundation; either version 2 of
18 * the License, or (at your option) any later version.
20 * This program is distributed in the hope that it will be useful,
21 * but WITHOUT ANY WARRANTY; without even the implied warranty of
22 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
23 * GNU General Public License for more details.
25 * You should have received a copy of the GNU General Public License
26 * along with this program; if not, write to the Free Software
27 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
40 #include <linux/ctype.h>
41 #include <asm/byteorder.h>
43 #include <linux/stat.h>
44 #include "../disk/part_dos.h"
47 #if defined(CONFIG_CMD_USB) && defined(CONFIG_USB_STORAGE)
51 #if !defined(CONFIG_DOS_PARTITION) && !defined(CONFIG_EFI_PARTITION)
52 #error DOS or EFI partition support must be selected
55 static int total_sector;
56 static unsigned long part_offset = 0;
57 static unsigned long part_size = 0;
59 static int cur_part = 1;
61 #define DOS_PART_MAGIC_OFFSET 0x1fe
62 #define DOS_FS_TYPE_OFFSET 0x36
63 #define DOS_FS32_TYPE_OFFSET 0x52
66 /*main entrance of mkfs.ext4 or ext4formating..*/
67 extern int mkfs_ext4(block_dev_desc_t *, int);
69 void put_ext4(block_dev_desc_t *dev_desc,uint64_t off, void *buf, uint32_t size)
71 uint64_t startblock,remainder;
72 unsigned int sector_size = 512;
73 unsigned char *temp_ptr=NULL;
74 char sec_buf[SECTOR_SIZE];
75 startblock = off / (uint64_t)sector_size;
76 startblock += part_offset;
77 remainder = off % (uint64_t)sector_size;
78 remainder &= SECTOR_SIZE - 1;
83 if ((startblock + (size/SECTOR_SIZE)) > (part_offset +total_sector))
85 printf("part_offset is %u\n",part_offset);
86 printf("total_sector is %u\n",total_sector);
87 printf("error: overflow occurs\n");
93 if (dev_desc->block_read)
95 dev_desc->block_read(dev_desc->dev, startblock, 1,
96 (unsigned char *) sec_buf);
97 temp_ptr=(unsigned char*)sec_buf;
98 memcpy((temp_ptr + remainder),(unsigned char*)buf,size);
99 dev_desc->block_write(dev_desc->dev, startblock, 1,
100 (unsigned char *)sec_buf);
105 if(size/SECTOR_SIZE!=0)
107 dev_desc->block_write(dev_desc->dev, startblock,
108 size/SECTOR_SIZE,(unsigned long *) buf);
112 dev_desc->block_read(dev_desc->dev, startblock, 1,
113 (unsigned char *) sec_buf);
114 temp_ptr=(unsigned char*)sec_buf;
115 memcpy(temp_ptr,buf,size);
116 dev_desc->block_write(dev_desc->dev, startblock,
117 1,(unsigned long *) sec_buf);
125 int ext4_register_device (block_dev_desc_t * dev_desc, int part_no)
127 unsigned char buffer[SECTOR_SIZE];
129 disk_partition_t info;
131 if (!dev_desc->block_read)
134 /* check if we have a MBR (on floppies we have only a PBR) */
135 if (dev_desc->block_read(dev_desc->dev, 0, 1, (ulong *)buffer) != 1)
137 printf("** Can't read from device %d **\n",
141 if (buffer[DOS_PART_MAGIC_OFFSET] != 0x55 ||
142 buffer[DOS_PART_MAGIC_OFFSET + 1] != 0xaa)
144 /* no signature found */
148 /* First we assume there is a MBR */
149 if (!get_partition_info(dev_desc, part_no, &info))
151 part_offset = info.start;
153 part_size = info.size;
155 else if ((strncmp((char *)&buffer[DOS_FS_TYPE_OFFSET], "FAT", 3) == 0) ||
156 (strncmp((char *)&buffer[DOS_FS32_TYPE_OFFSET], "FAT32", 5) == 0))
158 /* ok, we assume we are on a PBR only */
164 printf("** Partition %d not valid on device %d **\n",
165 part_no, dev_desc->dev);
174 int do_ext4_load (cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
176 char *filename = NULL;
179 ulong addr = 0, part_length;
181 disk_partition_t info;
182 block_dev_desc_t *dev_desc = NULL;
189 addr_str = getenv("loadaddr");
190 if (addr_str != NULL)
191 addr = simple_strtoul (addr_str, NULL, 16);
193 addr = CONFIG_SYS_LOAD_ADDR;
195 filename = getenv ("bootfile");
199 addr = simple_strtoul (argv[3], NULL, 16);
200 filename = getenv ("bootfile");
204 addr = simple_strtoul (argv[3], NULL, 16);
209 addr = simple_strtoul (argv[3], NULL, 16);
211 count = simple_strtoul (argv[5], NULL, 16);
215 return cmd_usage(cmdtp);
219 puts ("** No boot file defined **\n");
223 dev = (int)simple_strtoul (argv[2], &ep, 16);
224 dev_desc = get_dev(argv[1],dev);
225 if (dev_desc==NULL) {
226 printf ("** Block device %s %d not supported\n", argv[1], dev);
231 puts ("** Invalid boot device, use `dev[:part]' **\n");
234 part = (int)simple_strtoul(++ep, NULL, 16);
237 //PRINTF("Using device %s%d, partition %d\n", argv[1], dev, part);
240 if (get_partition_info (dev_desc, part, &info)) {
241 printf ("** Bad partition %d **\n", part);
245 if (strncmp((char *)info.type, BOOT_PART_TYPE, sizeof(info.type)) != 0) {
246 printf ("** Invalid partition type \"%.32s\""
247 " (expect \"" BOOT_PART_TYPE "\")\n",
251 printf ("Loading file \"%s\" "
252 "from %s device %d:%d (%.32s)\n",
254 argv[1], dev, part, info.name);
256 printf ("Loading file \"%s\" from %s device %d\n",
257 filename, argv[1], dev);
261 if ((part_length = ext2fs_set_blk_dev(dev_desc, part)) == 0) {
262 printf ("** Bad partition - %s %d:%d **\n", argv[1], dev, part);
267 if (!ext4fs_mount(part_length)) {
268 printf ("** Bad ext2 partition or disk - %s %d:%d **\n",
274 filelen = ext4fs_open(filename);
276 printf("** File not found %s\n", filename);
280 if ((count < filelen) && (count != 0)) {
284 if (ext4fs_read((char *)addr, filelen) != filelen) {
285 printf("** Unable to read \"%s\" from %s %d:%d **\n",
286 filename, argv[1], dev, part);
293 /* Loading ok, update default load address */
296 printf ("%d bytes read\n", filelen);
297 sprintf(buf, "%X", filelen);
298 setenv("filesize", buf);
306 int do_ext4_ls (cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
308 char *filename = "/";
312 block_dev_desc_t *dev_desc=NULL;
316 return cmd_usage(cmdtp);
318 dev = (int)simple_strtoul (argv[2], &ep, 16);
319 dev_desc = get_dev(argv[1],dev);
321 if (dev_desc == NULL) {
322 printf ("\n** Block device %s %d not supported\n", argv[1], dev);
328 puts ("\n** Invalid boot device, use `dev[:part]' **\n");
331 part = (int)simple_strtoul(++ep, NULL, 16);
337 //PRINTF("Using device %s %d:%d, directory: %s\n", argv[1], dev, part, filename);
339 if ((part_length = ext2fs_set_blk_dev(dev_desc, part)) == 0) {
340 printf ("** Bad partition - %s %d:%d **\n", argv[1], dev, part);
345 if (!ext4fs_mount(part_length)) {
346 printf ("** Bad ext2 partition or disk - %s %d:%d **\n", argv[1], dev, part);
351 if (ext4fs_ls (filename)) {
352 printf ("** Error ext2fs_ls() **\n");
362 int do_ext4_format (cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
364 char *filename = "/";
368 block_dev_desc_t *dev_desc=NULL;
370 disk_partition_t info;
373 return cmd_usage(cmdtp);
375 dev = (int)simple_strtoul (argv[2], &ep, 16);
376 dev_desc = get_dev(argv[1],dev);
378 if (dev_desc == NULL) {
379 printf ("\n** Block device %s %d not supported\n", argv[1], dev);
387 puts ("\n** Invalid boot device, use `dev[:part]' **\n");
390 part = (int)simple_strtoul(++ep, NULL, 16);
396 if ((part_length = ext2fs_set_blk_dev(dev_desc, part)) == 0)
398 printf ("** Bad partition - %s %d:%d **\n", argv[1], dev, part);
403 if (ext4_register_device(dev_desc,part)!=0)
405 printf("\n** Unable to use %s %d:%d for fattable **\n",
410 if (!get_partition_info(dev_desc, part, &info))
412 total_sector = (info.size * info.blksz) / SECTOR_SIZE;
415 printf("error : get partition info\n");
419 printf("formatting...\n\n");
420 if (mkfs_ext4(dev_desc, part))
428 int do_ext4_write(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
430 block_dev_desc_t *dev_desc=NULL;
431 char *filename = "/";
436 unsigned long ram_address;
437 unsigned long file_size;
438 disk_partition_t info;
441 return cmd_usage(cmdtp);
443 dev = (int)simple_strtoul (argv[2], &ep, 16);
444 dev_desc = get_dev(argv[1],dev);
446 if (dev_desc == NULL) {
447 printf ("\n** Block device %s %d not supported\n", argv[1], dev);
453 puts ("\n** Invalid boot device, use `dev[:part]' **\n");
456 part = (int)simple_strtoul(++ep, NULL, 16);
462 /*get the address in hexadecimal format (string to int)*/
463 ram_address = simple_strtoul (argv[4], NULL, 16);
465 /*get the filesize in base 10 format*/
466 file_size=simple_strtoul (argv[5], NULL, 10);
468 /*set the device as block device*/
469 if ((part_length = ext2fs_set_blk_dev(dev_desc, part)) == 0)
471 printf ("** Bad partition - %s %d:%d **\n", argv[1], dev, part);
476 /*register the device and partition*/
477 if (ext4_register_device(dev_desc,part)!=0)
479 printf("\n** Unable to use %s %d:%d for fattable **\n",
485 /*get the partition information*/
486 if (!get_partition_info(dev_desc, part, &info))
488 total_sector = (info.size * info.blksz) / SECTOR_SIZE;
492 printf("error : get partition info\n");
497 /*mount the filesystem*/
498 if (!ext4fs_mount(part_length))
500 printf ("** Bad ext4 partition or disk - %s %d:%d **\n", argv[1], dev, part);
506 if (ext4fs_write(dev_desc,part,filename,(unsigned char*)ram_address,file_size))
508 printf ("** Error ext4fs_write() **\n");
515 int do_ext4_create_dir(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
521 block_dev_desc_t *dev_desc=NULL;
523 disk_partition_t info;
526 return cmd_usage(cmdtp);
528 dev = (int)simple_strtoul (argv[2], &ep, 16);
529 dev_desc = get_dev(argv[1],dev);
531 if (dev_desc == NULL) {
532 printf ("\n** Block device %s %d not supported\n", argv[1], dev);
538 puts ("\n** Invalid boot device, use `dev[:part]' **\n");
541 part = (int)simple_strtoul(++ep, NULL, 16);
547 if ((part_length = ext2fs_set_blk_dev(dev_desc, part)) == 0) {
548 printf ("** Bad partition - %s %d:%d **\n", argv[1], dev, part);
552 /*register the device and partition*/
553 if (ext4_register_device(dev_desc,part)!=0)
555 printf("\n** Unable to use %s %d:%d for fattable **\n",
560 if (!get_partition_info(dev_desc, part, &info))
562 total_sector = (info.size * info.blksz) / SECTOR_SIZE;
565 printf("error : get partition info\n");
569 if (!ext4fs_mount(part_length)) {
570 printf ("** Bad ext4 partition or disk - %s %d:%d **\n", argv[1], dev, part);
575 if (ext4fs_create_dir (dev_desc,dirname)) {
576 printf ("** Error ext4fs_create_dir() **\n");
585 int do_ext4_create_symlink(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
587 char *src_path = "/";
588 char *target_path = "/";
592 block_dev_desc_t *dev_desc=NULL;
595 disk_partition_t info;
598 return cmd_usage(cmdtp);
600 dev = (int)simple_strtoul (argv[2], &ep, 16);
601 dev_desc = get_dev(argv[1],dev);
603 if (dev_desc == NULL) {
604 printf ("\n** Block device %s %d not supported\n", argv[1], dev);
610 puts ("\n** Invalid boot device, use `dev[:part]' **\n");
613 part = (int)simple_strtoul(++ep, NULL, 16);
615 if(!strcmp(argv[3],"H") || !strcmp(argv[3],"h"))
616 link_type = HARD_LINK;
618 if(!strcmp(argv[3],"S") || !strcmp(argv[3],"s"))
619 link_type = SOFT_LINK;
621 return cmd_usage(cmdtp);
624 target_path = argv[5];
626 if ((part_length = ext2fs_set_blk_dev(dev_desc, part)) == 0) {
627 printf ("** Bad partition - %s %d:%d **\n", argv[1], dev, part);
631 /*register the device and partition*/
632 if (ext4_register_device(dev_desc,part)!=0)
634 printf("\n** Unable to use %s %d:%d for fattable **\n",
639 if (!get_partition_info(dev_desc, part, &info))
641 total_sector = (info.size * info.blksz) / SECTOR_SIZE;
644 printf("error : get partition info\n");
648 if (!ext4fs_mount(part_length)) {
649 printf ("** Bad ext4 partition or disk - %s %d:%d **\n", argv[1], dev, part);
654 if (ext4fs_create_symlink (dev_desc,link_type,src_path,target_path)) {
655 printf ("** Error ext4fs_create_dir() **\n");
666 ext4symlink, 6, 1, do_ext4_create_symlink,
667 "create a file in the root directory",
668 "<interface> <dev[:part]> [H:Hardlink/S:Softlink][Absolute Source Path] [Absolute Target Path]\n"
669 " - create a Symbolic Link"
675 ext4mkdir, 4, 1, do_ext4_create_dir,
676 "create a file in the root directory",
677 "<interface> <dev[:part]> [Absolute Directory Path]\n"
678 " - create a directory"
682 ext4write, 6, 1, do_ext4_write,
683 "create a file in the root directory",
684 "<interface> <dev[:part]> [Absolute filename path] [Address] [sizebytes]\n"
685 " - create a file in / directory"
690 ext4format, 3, 1, do_ext4_format,
691 "format device as EXT4 filesystem",
692 "<interface> <dev[:part]>\n"
693 " - format device as EXT4 filesystem on 'dev'"
697 ext4ls, 4, 1, do_ext4_ls,
698 "list files in a directory (default /)",
699 "<interface> <dev[:part]> [directory]\n"
700 " - list files from 'dev' on 'interface' in a 'directory'"
705 ext4load, 6, 0, do_ext4_load,
706 "load binary file from a Ext2 filesystem",
707 "<interface> <dev[:part]> [addr] [filename] [bytes]\n"
708 " - load binary file 'filename' from 'dev' on 'interface'\n"
709 " to address 'addr' from ext2 filesystem"