From 2de059703878fa43decc3a8e61fbbde1ebc12bfd Mon Sep 17 00:00:00 2001 From: steve Date: Fri, 21 Feb 2003 03:40:35 +0000 Subject: [PATCH] Add vpiStop and interactive mode. --- vvp/Makefile.in | 6 +- vvp/configure.in | 2 - vvp/schedule.cc | 94 +++++++++++-------------- vvp/schedule.h | 12 +++- vvp/stop.cc | 179 +++++++++++++++++++++++++++++++++++++++++++++++ vvp/vpi_priv.cc | 9 ++- vvp/vvp.man | 16 ++++- 7 files changed, 256 insertions(+), 62 deletions(-) create mode 100644 vvp/stop.cc diff --git a/vvp/Makefile.in b/vvp/Makefile.in index 3006aeb83..95a3053d8 100644 --- a/vvp/Makefile.in +++ b/vvp/Makefile.in @@ -16,7 +16,7 @@ # 59 Temple Place - Suite 330 # Boston, MA 02111-1307, USA # -#ident "$Id: Makefile.in,v 1.42 2003/01/25 23:48:05 steve Exp $" +#ident "$Id: Makefile.in,v 1.43 2003/02/21 03:40:35 steve Exp $" # # SHELL = /bin/sh @@ -67,8 +67,8 @@ vpi_memory.o vpi_vthr_vector.o vpip_bin.o vpip_hex.o vpip_oct.o \ vpip_to_dec.o vvp_vpi.o O = main.o parse.o parse_misc.o lexor.o arith.o bufif.o compile.o debug.o \ -functor.o fvectors.o npmos.o resolv.o symbols.o ufunc.o codes.o vthread.o \ -schedule.o statistics.o tables.o udp.o memory.o force.o event.o \ +functor.o fvectors.o npmos.o resolv.o stop.o symbols.o ufunc.o codes.o \ +vthread.o schedule.o statistics.o tables.o udp.o memory.o force.o event.o \ logic.o delay.o words.o $V ifeq (@WIN32@,yes) diff --git a/vvp/configure.in b/vvp/configure.in index 7435286d6..c7e28badd 100644 --- a/vvp/configure.in +++ b/vvp/configure.in @@ -40,10 +40,8 @@ AC_CHECK_SIZEOF(unsigned) # For the interactive debugger to work, readline must be installed, # and that in turn requires termcap. check that the libs really do # exist. -if test "${enable_vvp_debug+set}" = set; then AC_CHECK_LIB(termcap, tputs) AC_CHECK_LIB(readline, readline) -fi # -- # Look for a dl library to use. First look for the standard dlopen diff --git a/vvp/schedule.cc b/vvp/schedule.cc index 6bce0df6b..d08ab23b4 100644 --- a/vvp/schedule.cc +++ b/vvp/schedule.cc @@ -17,7 +17,7 @@ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA */ #ifdef HAVE_CVS_IDENT -#ident "$Id: schedule.cc,v 1.22 2003/02/09 23:33:26 steve Exp $" +#ident "$Id: schedule.cc,v 1.23 2003/02/21 03:40:35 steve Exp $" #endif # include "schedule.h" @@ -27,6 +27,7 @@ #ifdef HAVE_MALLOC_H # include #endif +# include # include # include @@ -134,17 +135,43 @@ static struct event_s* synch_list = 0; * simulation. */ static bool schedule_runnable = true; +static bool schedule_stopped = false; void schedule_finish(int) { schedule_runnable = false; } +void schedule_stop(int) +{ + schedule_stopped = true; +} + bool schedule_finished(void) { return !schedule_runnable; } +/* + * These are the signal handling infrastructure. The SIGINT signal + * leads to an implicit $stop. + */ +static void signals_handler(int) +{ + schedule_stopped = true; +} + +static void signals_capture(void) +{ + signal(SIGINT, &signals_handler); +} + +static void signals_revert(void) +{ + signal(SIGINT, SIG_DFL); +} + + /* * This function does all the hard work of putting an event into the * event queue. The event delay is taken from the event structure @@ -334,8 +361,16 @@ void schedule_simulate(void) // Execute pre-simulation callbacks vpiPresim(); + signals_capture(); + while (schedule_runnable && sched_list) { + if (schedule_stopped) { + schedule_stopped = false; + stop_handler(0); + continue; + } + /* Pull the first item off the list. Fixup the last pointer in the next cell, if necessary. */ struct event_s*cur = sched_list; @@ -431,12 +466,17 @@ void schedule_simulate(void) } + signals_revert(); + // Execute post-simulation callbacks vpiPostsim(); } /* * $Log: schedule.cc,v $ + * Revision 1.23 2003/02/21 03:40:35 steve + * Add vpiStop and interactive mode. + * * Revision 1.22 2003/02/09 23:33:26 steve * Spelling fixes. * @@ -462,57 +502,5 @@ void schedule_simulate(void) * Support specified times in cbReadOnlySync, and * add support for cbReadWriteSync. * Keep simulation time in a 64bit number. - * - * Revision 1.15 2002/03/17 03:23:55 steve - * Force the push flags to be explicit. - * - * Revision 1.14 2001/12/06 03:31:25 steve - * Support functor delays for gates and UDP devices. - * (Stephan Boettcher) - * - * Revision 1.13 2001/11/07 03:34:42 steve - * Use functor pointers where vvp_ipoint_t is unneeded. - * - * Revision 1.12 2001/09/15 18:27:05 steve - * Make configure detect malloc.h - * - * Revision 1.11 2001/07/11 02:27:21 steve - * Add support for REadOnlySync and monitors. - * - * Revision 1.10 2001/05/30 03:02:35 steve - * Propagate strength-values instead of drive strengths. - * - * Revision 1.9 2001/05/08 23:32:26 steve - * Add to the debugger the ability to view and - * break on functors. - * - * Add strengths to functors at compile time, - * and Make functors pass their strengths as they - * propagate their output. - * - * Revision 1.8 2001/05/05 23:51:49 steve - * Forward the simulation time for every event. - * - * Revision 1.7 2001/05/01 01:09:39 steve - * Add support for memory objects. (Stephan Boettcher) - * - * Revision 1.6 2001/04/21 00:34:39 steve - * Working %disable and reap handling references from scheduler. - * - * Revision 1.5 2001/04/18 04:21:23 steve - * Put threads into scopes. - * - * Revision 1.4 2001/03/31 19:00:43 steve - * Add VPI support for the simulation time. - * - * Revision 1.3 2001/03/19 01:55:38 steve - * Add support for the vpiReset sim control. - * - * Revision 1.2 2001/03/11 22:42:11 steve - * Functor values and propagation. - * - * Revision 1.1 2001/03/11 00:29:39 steve - * Add the vvp engine to cvs. - * */ diff --git a/vvp/schedule.h b/vvp/schedule.h index 496d82a23..bc20b7275 100644 --- a/vvp/schedule.h +++ b/vvp/schedule.h @@ -19,7 +19,7 @@ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA */ #ifdef HAVE_CVS_IDENT -#ident "$Id: schedule.h,v 1.13 2003/02/09 23:33:26 steve Exp $" +#ident "$Id: schedule.h,v 1.14 2003/02/21 03:40:35 steve Exp $" #endif # include "vthread.h" @@ -88,8 +88,15 @@ extern vvp_time64_t schedule_simtime(void); * schedule_finish() function has been called. */ extern void schedule_finish(int rc); +extern void schedule_stop(int rc); extern bool schedule_finished(void); +/* + * The scheduler calls this function to process stop events. When this + * function returns, the simulation resumes. + */ +extern void stop_handler(int rc); + /* * These are event counters for the sake of performance measurements. */ @@ -101,6 +108,9 @@ extern unsigned long count_event_pool; /* * $Log: schedule.h,v $ + * Revision 1.14 2003/02/21 03:40:35 steve + * Add vpiStop and interactive mode. + * * Revision 1.13 2003/02/09 23:33:26 steve * Spelling fixes. * diff --git a/vvp/stop.cc b/vvp/stop.cc new file mode 100644 index 000000000..5d798546f --- /dev/null +++ b/vvp/stop.cc @@ -0,0 +1,179 @@ +/* + * Copyright (c) 2003 Stephen Williams (steve@icarus.com) + * + * This source code is free software; you can redistribute it + * and/or modify it in source code form under the terms of the GNU + * General Public License as published by the Free Software + * Foundation; either version 2 of the License, or (at your option) + * any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA + */ +#ifdef HAVE_CVS_IDENT +#ident "$Id: stop.cc,v 1.1 2003/02/21 03:40:35 steve Exp $" +#endif + +/* + * This file provides a simple command line debugger for the vvp + * runtime. It is a means to interact with the user running the + * simulation. + */ + +# include "config.h" + + +# include "schedule.h" +# include +#ifdef HAVE_LIBREADLINE +# include +# include +#endif +# include +# include +#ifdef HAVE_MALLOC_H +# include +#endif + +static bool interact_flag = true; + +static void invoke_systf(const char*txt) +{ + printf("**** System invocation not supported yet.\n"); +} + +static void cmd_cont(unsigned, char*[]) +{ + interact_flag = false; +} + +static void cmd_finish(unsigned, char*[]) +{ + interact_flag = false; + schedule_finish(0); +} + +static void cmd_help(unsigned, char*[]); + +static void cmd_time(unsigned, char*[]) +{ + unsigned long ticks = schedule_simtime(); + printf("%lu ticks\n", ticks); +} + +static void cmd_unknown(unsigned, char*argv[]) +{ + printf("Unknown command: %s\n", argv[0]); + printf("Try the help command to get a summary\n" + "of available commands.\n"); +} + +struct { + const char*name; + void (*proc)(unsigned argc, char*argv[]); + const char*summary; +} cmd_table[] = { + { "cont", &cmd_cont, + "Resume (continue) the simulation"}, + { "finish", &cmd_finish, + "Finish the simulation."}, + { "help", &cmd_help, + "Get help."}, + { "time", &cmd_time, + "Print the current simulation time."}, + { 0, &cmd_unknown, 0} +}; + +static void cmd_help(unsigned argc, char*argv[]) +{ + printf("Commands can be from the following table of base commands,\n" + "or can be invocations of system tasks/functions.\n\n"); + for (unsigned idx = 0 ; cmd_table[idx].name != 0 ; idx += 1) { + printf("%-8s - %s\n", cmd_table[idx].name, cmd_table[idx].summary); + } + + printf("\nIf the command starts with a dollar ($) character, it\n" + "is taken instead to be a system task or function call\n" + "and will be parsed and invoked accordingly.\n"); +} + + +static void invoke_command(char*txt) +{ + unsigned argc = 0; + char**argv = new char*[strlen(txt)/2]; + + /* Chop the line into words. */ + for (char*cp = txt+strspn(txt, " ") + ; *cp; cp += strspn(cp, " ")) { + argv[argc] = cp; + + cp += strcspn(cp, " "); + if (*cp) + *cp++ = 0; + + argc += 1; + } + + /* Look up the command, using argv[0] as the key. */ + if (argc > 0) { + unsigned idx; + for (idx = 0 ; cmd_table[idx].name ; idx += 1) + if (strcmp(cmd_table[idx].name, argv[0]) == 0) + break; + + cmd_table[idx].proc (argc, argv); + } + + + delete[]argv; +} + +void stop_handler(int rc) +{ + printf("** VVP Stop(%d) **\n", rc); + printf("** Current simulation time is %lu ticks.\n", schedule_simtime()); + + interact_flag = true; + while (interact_flag) { + char*input = readline("> "); + if (input == 0) + break; + + /* Advance to the first input character. */ + char*first = input; + while (*first && isspace(*first)) + first += 1; + + /* If the line starts with a $, then this is the + invocation of a system task or system function, so + call the invoke_systf function to handle + it. Otherwise, this is a simple command, so invoke + the command processor. */ + + if (*first == '$') { + invoke_systf(first); + + } else { + invoke_command(first); + } + + free(input); + } + + printf("** Continue **\n"); +} + +/* + * $Log: stop.cc,v $ + * Revision 1.1 2003/02/21 03:40:35 steve + * Add vpiStop and interactive mode. + * + */ + diff --git a/vvp/vpi_priv.cc b/vvp/vpi_priv.cc index 5224db20e..165d0e20b 100644 --- a/vvp/vpi_priv.cc +++ b/vvp/vpi_priv.cc @@ -17,7 +17,7 @@ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA */ #ifdef HAVE_CVS_IDENT -#ident "$Id: vpi_priv.cc,v 1.30 2003/02/09 23:33:26 steve Exp $" +#ident "$Id: vpi_priv.cc,v 1.31 2003/02/21 03:40:35 steve Exp $" #endif # include "vpi_priv.h" @@ -372,6 +372,10 @@ extern "C" void vpi_sim_vcontrol(int operation, va_list ap) schedule_finish(0); break; + case vpiStop: + schedule_stop(0); + break; + default: assert(0); } @@ -395,6 +399,9 @@ extern "C" void vpi_control(int operation, ...) /* * $Log: vpi_priv.cc,v $ + * Revision 1.31 2003/02/21 03:40:35 steve + * Add vpiStop and interactive mode. + * * Revision 1.30 2003/02/09 23:33:26 steve * Spelling fixes. * diff --git a/vvp/vvp.man b/vvp/vvp.man index 68e3cb164..56f534f05 100644 --- a/vvp/vvp.man +++ b/vvp/vvp.man @@ -1,4 +1,4 @@ -.TH vvp 1 "$Date: 2003/02/20 00:50:28 $" Version "$Date: 2003/02/20 00:50:28 $" +.TH vvp 1 "$Date: 2003/02/21 03:40:35 $" Version "$Date: 2003/02/21 03:40:35 $" .SH NAME vvp - Icarus Verilog vvp runtime engine @@ -90,6 +90,18 @@ waveforms are dumped in vcd format, but this variable can be used to select lxt format, which is far more compact, though limited to gtkwave or compatible viewers. +.SH INTERACTIVE MODE +.PP +The simulation engine supports an interactive mode. The user may +interrupt the simulation (typically by typing Ctrl-C) to get to the +interactive prompt. From that prompt, the \fIhelp\fP command prints a +brief summary of the available commands. +.PP +The interactive mode may also be entered by a call to the \fI$stop\fP +system task from within the simulation, or by a call to the +\fIvpi_control\fP VPI function with the \fIvpiStop\fP control +argument. These means of entering interactive mode are equivalent. + .SH "AUTHOR" .nf Steve Williams (steve@icarus.com) @@ -101,7 +113,7 @@ iverilog-vpi(1), .SH COPYRIGHT .nf -Copyright \(co 2001 Stephen Williams +Copyright \(co 2001-2003 Stephen Williams This document can be freely redistributed according to the terms of the GNU General Public License version 2.0