fix telnet async messages. retired telnet_async command - no user serviceable parts...
[fw/openocd] / src / target / target.c
index d0936d996585040898fd9a8dab87d8e94dd96273..66c80f4e7d96b6f603ae114f47a3b5afd09983e0 100644 (file)
@@ -11,6 +11,9 @@
  *   Copyright (C) 2008 by Spencer Oliver                                  *
  *   spen@spen-soft.co.uk                                                  *
  *                                                                         *
+ *   Copyright (C) 2008 by Rick Altherr                                    *
+ *   kc8apf@kc8apf.net>                                                    *
+ *                                                                         *
  *   This program is free software; you can redistribute it and/or modify  *
  *   it under the terms of the GNU General Public License as published by  *
  *   the Free Software Foundation; either version 2 of the License, or     *
@@ -172,6 +175,11 @@ const Jim_Nvp nvp_target_event[] = {
        { .value = TARGET_EVENT_RESUME_START, .name = "resume-start" },
        { .value = TARGET_EVENT_RESUME_END, .name = "resume-end" },
 
+
+       { .name = "gdb-start", .value = TARGET_EVENT_GDB_START },
+       { .name = "gdb-end", .value = TARGET_EVENT_GDB_END },
+
+
        /* historical name */
 
        { .value = TARGET_EVENT_RESET_START, .name = "reset-start" },
@@ -1444,6 +1452,71 @@ int handle_working_area_command(struct command_context_s *cmd_ctx, char *cmd, ch
 }
 
 
+// every 300ms we check for reset & powerdropout and issue a "reset halt" if
+// so.
+
+static int powerDropout;
+static int srstAsserted;
+
+static int sense_handler()
+{
+       static int prevSrstAsserted = 0;
+       static int prevPowerdropout = 0;
+
+       int retval;
+       if ((retval=jtag_power_dropout(&powerDropout))!=ERROR_OK)
+               return retval;
+
+       int powerRestored;
+       powerRestored = prevPowerdropout && !powerDropout;
+       if (powerRestored)
+       {
+               LOG_USER("Sensed power restore.");
+       }
+
+       long long current = timeval_ms();
+       static long long lastPower = 0;
+       int waitMore = lastPower + 2000 > current;
+       if (powerDropout && !waitMore)
+       {
+               LOG_USER("Sensed power dropout.");
+               lastPower = current;
+       }
+
+       if ((retval=jtag_srst_asserted(&srstAsserted))!=ERROR_OK)
+               return retval;
+
+       int srstDeasserted;
+       srstDeasserted = prevSrstAsserted && !srstAsserted;
+
+       static long long lastSrst = 0;
+       waitMore = lastSrst + 2000 > current;
+       if (srstDeasserted && !waitMore)
+       {
+               LOG_USER("Sensed nSRST deasserted");
+               lastSrst = current;
+       }
+
+       if (!prevSrstAsserted && srstAsserted)
+       {
+               LOG_USER("Sensed nSRST asserted");
+       }
+
+       prevSrstAsserted = srstAsserted;
+       prevPowerdropout = powerDropout;
+
+       if (srstDeasserted || powerRestored)
+       {
+               /* Other than logging the event we can't do anything here.
+                * Issuing a reset is a particularly bad idea as we might
+                * be inside a reset already.
+                */
+       }
+
+       return ERROR_OK;
+}
+
+
 /* process target state changes */
 int handle_target(void *priv)
 {
@@ -1452,7 +1525,10 @@ int handle_target(void *priv)
 
        while (target)
        {
-               if (target_continous_poll)
+               sense_handler();
+
+               /* only poll target if we've got power and srst isn't asserted */
+               if (target_continous_poll&&!powerDropout&&!srstAsserted)
                {
                        /* polling may fail silently until the target has been examined */
                        if((retval = target_poll(target)) != ERROR_OK)
@@ -3770,6 +3846,8 @@ target_create( Jim_GetOptInfo *goi )
        target->next                = NULL;
        target->arch_info           = NULL;
 
+       target->display             = 1;
+
        /* initialize trace information */
        target->trace_info = malloc(sizeof(trace_t));
        target->trace_info->num_trace_points         = 0;
@@ -3877,7 +3955,6 @@ jim_target( Jim_Interp *interp, int argc, Jim_Obj *const *argv )
        }
        if( target_types[x] ){
                /* YES IT IS OLD SYNTAX */
-               int      chain_position_offset;
                Jim_Obj *new_argv[10];
                int      new_argc;
 
@@ -3891,22 +3968,14 @@ jim_target( Jim_Interp *interp, int argc, Jim_Obj *const *argv )
                 *
                 * target <typename> <endian> <reset mode> <chain position> <variant>
                 *
-                * The following uses the number of arguments to switch between them.
                 */
-               if( argc < 5 ){
+
+               /* The minimum number of arguments is 4 */
+               if( argc < 4 ){
                        Jim_WrongNumArgs( interp, 1, argv, "[OLDSYNTAX] ?TYPE? ?ENDIAN? ?CHAIN-POSITION? ?VARIANT?");
                        return JIM_ERR;
                }
 
-               /* Use the correct argument offset for the chain position */
-               if (argc < 6) {
-                       /* target <type> <endian> <chain position> <variant> */
-                       chain_position_offset = 2;
-               } else {
-                       chain_position_offset = 3;
-                       /* target <type> <endian> <reset mode> <chain position> <variant> */
-               }
-
                /* the command */
                new_argv[0] = argv[0];
                new_argv[1] = Jim_NewStringObj( interp, "create", -1 );
@@ -3919,10 +3988,29 @@ jim_target( Jim_Interp *interp, int argc, Jim_Obj *const *argv )
                new_argv[4] = Jim_NewStringObj( interp, "-endian", -1 );
                new_argv[5] = goi.argv[1];
                new_argv[6] = Jim_NewStringObj( interp, "-chain-position", -1 );
-               new_argv[7] = goi.argv[chain_position_offset];
-               new_argv[8] = Jim_NewStringObj( interp, "-variant", -1 );
-               new_argv[9] = goi.argv[chain_position_offset + 1];
-               new_argc = 10;
+
+               /* If goi.argv[2] is not a number, we need to skip it since it is the reset mode. */
+               jim_wide w;
+               int chain_position_argv = 2;
+               if (JIM_ERR == Jim_GetWide(interp, goi.argv[chain_position_argv], &w)) {
+                       if (chain_position_argv + 1 < goi.argc) {
+                               chain_position_argv += 1;
+                       } else {
+                               Jim_WrongNumArgs( interp, 1, argv, "[OLDSYNTAX] ?TYPE? ?ENDIAN? ?RESET? ?CHAIN-POSITION? ?VARIANT?");
+                               return JIM_ERR;
+                       }
+               }
+
+               new_argv[7] = goi.argv[chain_position_argv];
+
+               /* Only provide a variant configure option if there was a variant specified */
+               if (chain_position_argv + 1 < goi.argc) {
+                       new_argv[8] = Jim_NewStringObj( interp, "-variant", -1 );
+                       new_argv[9] = goi.argv[chain_position_argv + 1];
+                       new_argc = 10;
+               } else {
+                       new_argc = 8;
+               }
 
                /*
                 * new arg syntax:
@@ -3930,10 +4018,6 @@ jim_target( Jim_Interp *interp, int argc, Jim_Obj *const *argv )
                 *   argv[1] = create
                 *   argv[2] = cmdname
                 *   argv[3] = typename
-                *   argv[4] = **FIRST** "configure" option.
-                *
-                * Here, we make them:
-                *
                 *   argv[4] = -endian
                 *   argv[5] = little
                 *   argv[6] = -position