Run multiple binaries on your mbed.

Dependencies:   mbed

Files at this revision

API Documentation at this revision

Comitter:
paulg
Date:
Wed May 29 20:06:47 2013 +0000
Child:
1:68f8899ed1ea
Commit message:
Demo of how to run multiple binaries on your mbed.

Changed in this revision

main.cpp Show annotated file Show diff for this revision Revisions of this file
mbed.bld Show annotated file Show diff for this revision Revisions of this file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main.cpp	Wed May 29 20:06:47 2013 +0000
@@ -0,0 +1,372 @@
+/******************************************************************************
+ * File:      main.cpp
+ * Author:    Paul Griffith
+ * Created:   27 May 2013
+ * Last Edit: see below
+ * Version:   see below
+ *
+ * Description:
+ * Test program to demonstrate application switching.
+ 
+ * This program loads and runs one of several different binaries.
+ * The binaries are all present on the local filesystem, but are renamed to
+ * app1.mbd, app2.mbd and so on. The filenames must conform to the local
+ * filesystem's 8+3 filename rule and have an extension other then .bin.
+ * This ensures that the files can be accessed by the local filesystem library
+ * and that the interface chip does not act upon the binaries.
+ * Another requirement is that all other .bin files must be deleted from the
+ * local filesystem. This is necessary because downloaded files will always
+ * have more recent timestamps than ones created by the local filesystem.
+ * To switch applications, the current .bin file is deleted, the chosen app
+ * file is copied to a .bin and the nR pin is driven low. The interface chip
+ * then loads the .bin file into mbed's Flash.
+ *
+ * To use this program:
+ * 1. From the PC, remove all .bin files from the mbed local filesystem,
+ * 2. Compile as is, download to mbed and Flash it into mbed.
+ * 3. From the PC, rename the binary to app1.mbd.
+ * 4. Edit the MYNAME string to app2.bin
+ * 5. Save, recompile and download to mbed. Do NOT Flash into mbed.
+ * 6. From the PC, rename the binary to app2.mbd.
+ * 7. Edit the MYNAME string to app3.bin
+ * 8. Save, recompile and download to mbed. Do NOT Flash into mbed.
+ * 9. From the PC, rename the binary to app3.mbd.
+ * 10 Fit a wire jumper between mbed pin 9 (rstOut) and mbed pin 4 (nR).
+ *    Another mbed I/O pin can be used if you change the RSTPIN definition.
+ *    (If you don't fit a jumper you will have to press the Reset button
+ *    when the Resetting mbed module... prompt appears).
+ *
+ * The program can now be run. It uses the virtual serial port at 9600 baud
+ * and has a simple command interpreter. All commands end with <Enter>.
+ * Use the 1, 2 and 3 commands to switch applications.
+ *
+ * Copyright (c) 2013 Paul Griffith.
+ * Released under the MIT License: http://mbed.org/license/mit
+ *
+ * Modifications:
+ * Ver  Date    By  Details
+ * 0.00 27May13 PG  File created.
+ * 1.00 29May13 PG  Initial release.
+ *
+ ******************************************************************************/
+
+#define VERSION "1.00"
+#define MYNAME "app1.bin"   //edit to desired name before compiling & downloading
+#define RSTPIN p9
+
+#include "mbed.h"
+
+void printHelps(void);
+void badArgs(void);
+void nyi(void);
+void pause(void);
+void usage(void);
+int getVal();
+int exist(char *);
+int copyFile(char*, char*);
+void listDir(char*);
+int renameFile(char*, char*);
+void resetMbed(void);
+
+Serial pc(USBTX, USBRX);
+LocalFileSystem local("local");
+
+int main() {
+    char buf[120], *cp;
+    char arg0[50], arg1[50], arg2[50];
+    int argc, i;
+
+    printf("\nApplication Switcher Demo (Version %s, %s %s)\n",
+        VERSION, __DATE__, __TIME__);
+    printf("I am application %s\n", MYNAME);
+    printf("Type ? for help\n");
+
+    strcpy(arg1, "/local/");    //build file name
+    strcpy(arg2, "/local/");    //build file name            
+
+    while (1) {
+        printf("> ");
+        cp = buf;
+        while ( (*cp++ = putchar(getchar())) != '\r') ;   //get a line of input
+        *cp = '\0';                                       //terminate buffer
+        printf("\n");
+        argc = sscanf(buf, "%s%s%s", arg0, &arg1[7], &arg2[7]);   //extract cmd & args
+        if (argc < 1)
+            continue;
+        switch (arg0[0]) {
+
+            case '1':        //load Application app1.bin
+                if (strcmp(MYNAME, "app1.bin") == 0) {
+                    printf("Application app1.bin is already running!\n");
+                }
+                else {
+                    sprintf(&arg1[7], MYNAME);
+                    remove(arg1);
+                    copyFile("/local/app1.mbd", "/local/app1.bin");
+                    resetMbed();
+                }
+                break; 
+
+            case '2':        //load Application app2.bin
+                if (strcmp(MYNAME, "app2.bin") == 0) {
+                    printf("Application app2.bin is already running!\n");
+                }
+                else {
+                    sprintf(&arg1[7], MYNAME);
+                    remove(arg1);
+                    copyFile("/local/app2.mbd", "/local/app2.bin");
+                    resetMbed();
+                }
+                break; 
+
+            case '3':        //load Application app3.bin
+                if (strcmp(MYNAME, "app3.bin") == 0) {
+                    printf("Application app3.bin is already running!\n");
+                }
+                else {
+                    sprintf(&arg1[7], MYNAME);
+                    remove(arg1);
+                    copyFile("/local/app3.mbd", "/local/app3.bin");
+                    resetMbed();
+                }
+                break; 
+
+            case 'c':        //copy file
+                if (argc != 3) {
+                    usage();
+                    break;
+                }
+                i = copyFile(arg1, arg2);
+                printf("Copy %s to %s returned %d\n", arg1, arg2, i);
+                break;
+
+            case 'd':        //delete file
+                if (argc != 2) {
+                    usage();
+                    break;
+                }
+                if (exist(arg1) == 0)
+                    printf("File does not exist\n");
+                else {
+                    remove(arg1);
+                    printf("File deleted\n");
+                }
+                break;
+
+            case 'e':        //check if file exists
+                if (argc != 2) {
+                    usage();
+                    break;
+                }
+                if (exist(arg1) != 0)
+                    printf("File exists\n");
+                else
+                    printf("File does not exist\n");
+                break;
+
+            case 'i':        //identify self
+                printf("I am application %s\n", MYNAME);
+                break;
+
+            case 'l':        //list files on local filesystem
+                listDir("/local");
+                break;
+
+            case 'r':        //rename file on local filesystem
+                if (argc != 3) {
+                    usage();
+                    break;
+                }
+                i = renameFile(arg1, arg2);
+                printf("Rename %s to %s returned %d\n", arg1, arg2, i);
+                break;
+
+             case 'x':        //reset mbed module
+                resetMbed();
+                break;
+
+            case '?':        //print help
+                printHelps();
+                break;
+                
+            default:
+                printf("?? Unknown command\n");
+                break;
+        }
+    }
+}
+
+//************************
+// Display command summary
+//************************
+
+void printHelps(void) {
+    printf("Command summary:\n");
+    printf("1 - 3      load specified application\n");
+    printf("c old new  copy file on local filesystem\n");
+    printf("d filename delete file on local filesystem\n");
+    printf("e filename check if file exists on local filesystem\n");
+    printf("i          identification\n");
+    printf("l          list files on local filesystem\n");
+    printf("r old new  rename file on local filesystem\n");
+    printf("x          reset mbed module\n");
+}
+
+//************************
+// Miscellaneous functions
+//************************
+
+void badArgs(void) {
+    pc.printf("?? Bad arguments\n");
+}
+
+void nyi(void) {
+    pc.printf("!! Not yet implemented\n");
+}
+
+void pause(void)
+{
+    pc.printf("Press any key to continue . . .\n");
+    pc.getc();
+}
+
+void usage(void) {
+    printf("Invalid command usage\n");
+}
+
+// Get integer value from user. Used in enter functions
+
+int getVal() {
+    char buf[10];
+    char* cp;
+    int v;
+
+    cp = buf;
+    while ( (*cp++ = putchar(getchar())) != '\r') ; 
+    *cp = '\0';
+    printf("\n");
+    v = 0;
+    sscanf(buf, "%d", &v);
+    return v; 
+}
+
+int exist(char *name) {
+    FILE *fp;
+    
+    fp = fopen(name, "r");
+    if (fp != NULL)
+        fclose(fp);
+    return ((fp == NULL) ? 0 : 1);
+}
+
+//*******************
+// Command processing
+//*******************
+
+// Copy file
+
+int copyFile(char *srcfile, char *destfile)
+{
+    char buf[512];
+    int end, r, w;
+    long length, size = 0;
+    FILE *fp, *fp2;
+    Timer timer;
+    
+    fp = fopen(srcfile, "r");
+    if (fp == NULL)
+    {
+        printf("Source file does not exist\n");
+        return(-1);
+    }
+    if (exist(destfile) == 1)
+    {
+        printf("Destination file already exists\n");
+        fclose(fp);
+        return(-2);
+    }
+    fp2 = fopen(destfile, "w");
+    if (fp2 == NULL)
+    {
+        printf("Unable to create file\n");
+        fclose(fp);
+        return(-3);
+    }
+    fseek(fp, 0L, SEEK_END);
+    length = ftell(fp);
+    fseek(fp, 0L, SEEK_SET);
+
+    printf("copy %s to %s\n", srcfile, destfile);
+        
+    printf("file length = %ld\n", length);
+    timer.start();
+    while (size < length)
+    {
+        r = fread(buf, 1, 512, fp);     //read a sector
+        w = fwrite(buf, 1, r, fp2);     //write a sector
+        if (w != r)
+        {
+            printf("file write error\n");
+            fclose(fp);
+            fclose(fp2);
+            return(-4);
+        }
+        if (r < 512)    //reached end
+            break;
+        size += r;
+    }
+    end = timer.read_ms();
+    fclose(fp);
+    fclose(fp2);
+    printf("%ld bytes copied in %d.%03ds\n", size, end/1000, end%1000);
+    return(0);
+}
+
+
+// List directory
+
+void listDir(char *drive) {
+    DIR *d;
+    struct dirent *p;
+
+    d = opendir(drive);
+    if (d != NULL) {
+        while ((p = readdir(d)) != NULL) {
+            printf(" - %s\n", p->d_name);
+        }
+    }
+    else {
+        printf("Could not open directory!\n");
+    }
+    closedir(d);
+}
+
+// Rename file
+// this does not seem to work, perhaps rename() is broken?
+
+int renameFile(char* srcfile, char* destfile) {
+    if (exist(srcfile) == 0)
+    {
+        printf("Source file does not exist\n");
+        return(-2);
+    }
+    if (exist(destfile) == 1)
+    {
+        printf("Destination file already exists\n");
+        return(-3);
+    }
+    return( rename(srcfile, destfile) );
+}
+
+// Reset mbded module
+// Requires a wire jumper between an I/O pin and pin 4
+
+void resetMbed(void) {
+    DigitalOut rst(RSTPIN);
+    
+    printf("Resetting mbed module...\n");
+    rst = 0;
+}
+
+// END of main.cpp
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/mbed.bld	Wed May 29 20:06:47 2013 +0000
@@ -0,0 +1,1 @@
+http://mbed.org/users/mbed_official/code/mbed/builds/b3110cd2dd17
\ No newline at end of file