summaryrefslogtreecommitdiff
path: root/common/cmd_load.c
diff options
context:
space:
mode:
authorMarkus Klotzbuecher <mk@denx.de>2006-03-30 13:40:55 +0200
committerMarkus Klotzbücher <mk@pollux.denx.de>2006-03-30 13:40:55 +0200
commitf2841d377060cb2c3bedfcdfda6aab3066d6c4f1 (patch)
tree6cfc398bad35e22130a63f005b7b3e580191bf29 /common/cmd_load.c
parenteeaab720f66f0281b9a1ea3c1f8765bf34e4411e (diff)
downloadu-boot-imx-f2841d377060cb2c3bedfcdfda6aab3066d6c4f1.zip
u-boot-imx-f2841d377060cb2c3bedfcdfda6aab3066d6c4f1.tar.gz
u-boot-imx-f2841d377060cb2c3bedfcdfda6aab3066d6c4f1.tar.bz2
Add support for ymodem protocol (loady command).
Patch by Stefano Babic, 29 Mar 2006
Diffstat (limited to 'common/cmd_load.c')
-rw-r--r--common/cmd_load.c105
1 files changed, 92 insertions, 13 deletions
diff --git a/common/cmd_load.c b/common/cmd_load.c
index 7498497..54460cd 100644
--- a/common/cmd_load.c
+++ b/common/cmd_load.c
@@ -29,10 +29,11 @@
#include <s_record.h>
#include <net.h>
#include <exports.h>
-
+#include <xyzModem.h>
#if (CONFIG_COMMANDS & CFG_CMD_LOADS)
static ulong load_serial (ulong offset);
+static ulong load_serial_ymodem (ulong offset);
static int read_record (char *buf, ulong len);
# if (CONFIG_COMMANDS & CFG_CMD_SAVES)
static int save_serial (ulong offset, ulong size);
@@ -475,21 +476,31 @@ int do_load_serial_bin (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
}
}
- printf ("## Ready for binary (kermit) download "
- "to 0x%08lX at %d bps...\n",
- offset,
- load_baudrate);
- addr = load_serial_bin (offset);
+ if (strcmp(argv[0],"loady")==0) {
+ printf ("## Ready for binary (ymodem) download "
+ "to 0x%08lX at %d bps...\n",
+ offset,
+ load_baudrate);
+
+ addr = load_serial_ymodem (offset);
- if (addr == ~0) {
- load_addr = 0;
- printf ("## Binary (kermit) download aborted\n");
- rcode = 1;
} else {
- printf ("## Start Addr = 0x%08lX\n", addr);
- load_addr = addr;
- }
+ printf ("## Ready for binary (kermit) download "
+ "to 0x%08lX at %d bps...\n",
+ offset,
+ load_baudrate);
+ addr = load_serial_bin (offset);
+
+ if (addr == ~0) {
+ load_addr = 0;
+ printf ("## Binary (kermit) download aborted\n");
+ rcode = 1;
+ } else {
+ printf ("## Start Addr = 0x%08lX\n", addr);
+ load_addr = addr;
+ }
+ }
if (load_baudrate != current_baudrate) {
printf ("## Switch baudrate to %d bps and press ESC ...\n",
current_baudrate);
@@ -963,6 +974,66 @@ START:
}
return ((ulong) os_data_addr - (ulong) bin_start_address);
}
+
+static int getcxmodem(void) {
+ if (tstc())
+ return (getc());
+ return -1;
+}
+static ulong load_serial_ymodem (ulong offset)
+{
+ int size;
+ char buf[32];
+ int err;
+ int res;
+ connection_info_t info;
+ char ymodemBuf[1024];
+ ulong store_addr = ~0;
+ ulong addr = 0;
+
+ size=0;
+ info.mode=xyzModem_ymodem;
+ res=xyzModem_stream_open(&info, &err);
+ if (!res) {
+
+ while ((res=xyzModem_stream_read(ymodemBuf, 1024, &err)) > 0 ){
+ store_addr = addr + offset;
+ size+=res;
+ addr+=res;
+#ifndef CFG_NO_FLASH
+ if (addr2info(store_addr)) {
+ int rc;
+
+ rc = flash_write((char *)ymodemBuf,store_addr,res);
+ if (rc != 0) {
+ flash_perror (rc);
+ return (~0);
+ }
+ } else
+#endif
+ {
+ memcpy ((char *)(store_addr), ymodemBuf, res);
+ }
+
+ }
+ }
+ else {
+ printf ("%s\n",xyzModem_error(err));
+ }
+
+ xyzModem_stream_close(&err);
+ xyzModem_stream_terminate(false,&getcxmodem);
+
+
+ flush_cache (offset, size);
+
+ printf("## Total Size = 0x%08x = %d Bytes\n", size, size);
+ sprintf(buf, "%X", size);
+ setenv("filesize", buf);
+
+ return offset;
+}
+
#endif /* CFG_CMD_LOADB */
/* -------------------------------------------------------------------- */
@@ -1022,6 +1093,14 @@ U_BOOT_CMD(
" with offset 'off' and baudrate 'baud'\n"
);
+U_BOOT_CMD(
+ loady, 3, 0, do_load_serial_bin,
+ "loady - load binary file over serial line (ymodem mode)\n",
+ "[ off ] [ baud ]\n"
+ " - load binary file over serial line"
+ " with offset 'off' and baudrate 'baud'\n"
+);
+
#endif /* CFG_CMD_LOADB */
/* -------------------------------------------------------------------- */