#include <stdarg.h>
#include <stdlib.h>
#include <sys/types.h>
-#ifdef HAVE_SYS_SOCKET_H
-# include <sys/socket.h>
-# include <netinet/in.h>
-# include <arpa/inet.h>
-# include <netdb.h>
-#endif
#include <sys/time.h>
+#ifdef SOCKET_AVAIL
+# include HEADER_SOCKET
+# if defined HAVE_SYS_SOCKET_H
+# include <netinet/in.h>
+# include <arpa/inet.h>
+# include <netdb.h>
+# endif
+#endif
#if FD_HEADER_OK
# include HEADER_FD
#endif
-#include <unistd.h>
+#ifdef HAVE_UNISTD_H
+# include <unistd.h>
+#endif
#include "i_string.h"
+#include "cmdlexcl.h"
+#include "cmdpars.h"
+
// prj
#include "globals.h"
#include "utils.h"
extern "C" int vasprintf(char **strp, const char *format, va_list ap);
extern "C" int vsnprintf(char *str, size_t size,const char *format,va_list ap);
-static int
-cmd_do_print(FILE *f, char *format, va_list ap)
-{
- int ret;
-#ifdef HAVE_VASPRINTF
- char *msg= NULL;
- vasprintf(&msg, format, ap);
- ret= fprintf(f, "%s", msg);
- free(msg);
-#else
-# ifdef HAVE_VSNPRINTF
- char msg[80*25];
- vsnprintf(msg, 80*25, format, ap);
- ret= fprintf(f, "%s", msg);
-# else
-# ifdef HAVE_VPRINTF
- char msg[80*25];
- vsprintf(msg, format, ap); /* Dangerous */
- ret= fprintf(f, "%s", msg);
-# else
-# ifdef HAVE_DOPRNT
- /* ??? */
- /*strcpy(msg, "Unimplemented printf has called.\n");*/
-# else
- /*strcpy(msg, "printf can not be implemented, upgrade your libc.\n");*/
-# endif
-# endif
-# endif
-#endif
- fflush(f);
- return(ret);
-}
-
/*
* Options of console
{
FILE *f;
- last_command= NULL;
app= the_app;
in= 0;
if (fin)
flags|= CONS_INTERACTIVE;
else
;//fprintf(stderr, "Warning: non-interactive console\n");
+ rout= 0;
id= 0;
+ lines_printed= new cl_ustrings(100, 100, "console_cache");
}
cl_console::cl_console(FILE *fin, FILE *fout, class cl_app *the_app):
cl_base()
{
- last_command= NULL;
app= the_app;
in = fin;
out= fout;
- rout=(FILE *)0;
prompt= 0;
flags= CONS_NONE;
if (in &&
flags|= CONS_INTERACTIVE;
else
;//fprintf(stderr, "Warning: non-interactive console\n");
+ rout= 0;
id= 0;
+ lines_printed= new cl_ustrings(100, 100, "console_cache");
}
/*
{
int sock= connect_to_port(portnumber);
- last_command= NULL;
app= the_app;
if (!(in= fdopen(sock, "r")))
fprintf(stderr, "cannot open port for input\n");
fprintf(stderr, "cannot open port for output\n");
//fprintf(stderr, "init socket done\n");
id= 0;
+ lines_printed= new cl_ustrings(1, 1, "console_cache");
}
#endif
{
FILE *fi= 0, *fo= 0;
- if (fin)
- if (fi= fopen(fin, "r"), !fi)
- {
- fprintf(stderr, "Can't open `%s': %s\n", fin, strerror(errno));
- return(0);
- }
+ if (!fin)
+ return(0);
+ if (fi= fopen(fin, "r"), !fi)
+ {
+ fprintf(stderr, "Can't open `%s': %s\n", fin, strerror(errno));
+ return(0);
+ }
if ((fo= fdopen(dup(fileno(out)), "a")) == 0)
{
fclose(fi);
welcome();
flags&= ~CONS_PROMPT;
//print_prompt();
+ last_command= 0;
+ last_cmdline= 0;
return(0);
}
if (out)
{
if (flags & CONS_PROMPT)
- fprintf(out, "\n");
+ fprintf(out, "\n");
fflush(out);
fclose(out);
}
}
+bool
+cl_console::accept_last(void)
+{
+ if (!in)
+ return(DD_FALSE);
+ if (isatty(fileno(in)))
+ return(DD_TRUE);
+ return(DD_FALSE);
+}
+
+
/*
* Output functions
*/
void
cl_console::welcome(void)
{
- FILE *Out= rout?rout:out;
-
- if (!Out ||
- (flags & CONS_NOWELCOME))
- return;
- fprintf(Out, "uCsim %s, Copyright (C) 1997 Daniel Drotos, Talker Bt.\n"
- "uCsim comes with ABSOLUTELY NO WARRANTY; for details type "
- "`show w'.\n"
- "This is free software, and you are welcome to redistribute it\n"
- "under certain conditions; type `show c' for details.\n",
- VERSIONSTR);
- fflush(Out);
+ if (!(flags & CONS_NOWELCOME))
+ {
+ dd_printf("uCsim %s, Copyright (C) 1997 Daniel Drotos, Talker Bt.\n"
+ "uCsim comes with ABSOLUTELY NO WARRANTY; for details type "
+ "`show w'.\n"
+ "This is free software, and you are welcome to redistribute it\n"
+ "under certain conditions; type `show c' for details.\n",
+ VERSIONSTR);
+ }
}
void
{
if ((rout= fopen(fname, mode)) == NULL)
dd_printf("Unable to open file '%s' for %s: %s\n",
- fname, (mode[0]=='w')?"write":"append", strerror(errno));
+ fname, (mode[0]=='w')?"write":"append", strerror(errno));
}
void
fclose(rout);
rout= NULL;
}
-
+
+
+int
+cl_console::cmd_do_print(char *format, va_list ap)
+{
+ FILE *f = get_out();
+ int ret = 0;
+
+ if (f)
+ {
+ vfprintf(f, format, ap);
+ fflush(f);
+ }
+
+ return(ret);
+}
+
void
cl_console::print_prompt(void)
{
- //char *p;
- FILE *Out= rout?rout:out;
-
if (flags & (CONS_PROMPT|CONS_FROZEN|CONS_INACTIVE))
return;
flags|= CONS_PROMPT;
- if (!Out)
- return;
if (/*app->args->arg_avail('P')*/null_prompt_option->get_value(bool(0)))
- putc('\0', Out);
+ {
+ FILE *Out = get_out();
+ if (Out)
+ {
+ putc('\0', Out);
+ fflush(Out);
+ }
+ }
else
{
- fprintf(Out, "%d", id);
- fprintf(Out, "%s", (prompt && prompt[0])?prompt:"> ");
- // ((p= app->args->get_sarg(0, "prompt"))?p:"> "));
+ dd_printf("%d%s", id, (prompt && prompt[0])?prompt:"> ");
+ // ((p= app->args->get_sarg(0, "prompt"))?p:"> "));
}
- fflush(Out);
}
int
{
va_list ap;
int ret= 0;
- FILE *Out= rout?rout:out;
- if (Out)
- {
- va_start(ap, format);
- ret= cmd_do_print(Out, format, ap);
- va_end(ap);
- }
+ va_start(ap, format);
+ ret= cmd_do_print(format, ap);
+ va_end(ap);
+
+ return(ret);
+}
+
+int
+cl_console::debug(char *format, ...)
+{
+ if ((flags & CONS_DEBUG) == 0)
+ return(0);
+
+ va_list ap;
+ int ret= 0;
+
+ va_start(ap, format);
+ ret= cmd_do_print(format, ap);
+ va_end(ap);
+
return(ret);
}
cl_console::print_bin(long data, int bits)
{
long mask= 1;
- FILE *Out= rout?rout:out;
- if (!Out)
- return;
mask= mask << ((bits >= 1)?(bits-1):0);
while (bits--)
{
- fprintf(Out, "%c", (data&mask)?'1':'0');
+ dd_printf("%c", (data&mask)?'1':'0');
mask>>= 1;
}
}
void
cl_console::print_char_octal(char c)
{
- FILE *Out= rout?rout:out;
+ FILE *Out= get_out();
if (Out)
::print_char_octal(c, Out);
cl_console::input_avail(void)
{
struct timeval tv;
- int i;
+ UCSOCKET_T i;
if ((i= get_in_fd()) < 0)
return(0);
else
{
if (cmdstr &&
- *cmdstr == '\004')
- retval= 1;
+ *cmdstr == '\004')
+ retval= 1;
else
- {
- class cl_cmdline *cmdline;
- class cl_cmd *cm;
- if (flags & CONS_ECHO)
- dd_printf("%s\n", cmdstr);
- cmdline= new cl_cmdline(app, cmdstr, this);
- cmdline->init();
- cm= cmdset->get_cmd(cmdline);
- if (cm)
- retval= cm->work(app, cmdline, this);
- delete cmdline;
- if (!cm)
- retval= interpret(cmdstr);
- }
+ {
+ class cl_cmdline *cmdline= 0;
+ class cl_cmd *cm= 0;
+ if (flags & CONS_ECHO)
+ dd_printf("%s\n", cmdstr);
+ cmdline= new cl_cmdline(app, cmdstr, this);
+ cmdline->init();
+ if (cmdline->repeat() &&
+ accept_last() &&
+ last_command)
+ {
+ cm= last_command;
+ delete cmdline;
+ cmdline= last_cmdline;
+ }
+ else
+ {
+ cm= cmdset->get_cmd(cmdline, accept_last());
+ if (last_cmdline)
+ {
+ delete last_cmdline;
+ last_cmdline= 0;
+ }
+ last_command= 0;
+ }
+ if (cm)
+ {
+ retval= cm->work(app, cmdline, this);
+ if (cm->can_repeat)
+ {
+ last_command= cm;
+ last_cmdline= cmdline;
+ }
+ else
+ delete cmdline;
+ }
+ else
+ {
+ class YY_cl_ucsim_parser_CLASS *pars;
+ class cl_ucsim_lexer *lexer;
+ lexer= new cl_ucsim_lexer(cmdstr);
+ pars= new YY_cl_ucsim_parser_CLASS(lexer);
+ pars->yyparse();
+ delete cmdline;
+ delete pars;
+ }
+ /*if (!cm)
+ retval= interpret(cmdstr);*/
+ }
}
//retval= sim->do_cmd(cmd, this);
un_redirect();
int
cl_console::interpret(char *cmd)
{
- FILE *Out= rout?rout:out;
-
- fprintf(Out, "Unknown command\n");
+ dd_printf("Unknown command\n");
return(0);
}
cl_listen_console::cl_listen_console(int serverport, class cl_app *the_app)
{
- last_command= NULL;
app= the_app;
if ((sock= make_server_socket(serverport)) >= 0)
{
if (listen(sock, 10) < 0)
- fprintf(stderr, "Listen on port %d: %s\n",
- serverport, strerror(errno));
+ fprintf(stderr, "Listen on port %d: %s\n",
+ serverport, strerror(errno));
}
in= out= 0;
}
*/
cl_sub_console::cl_sub_console(class cl_console *the_parent,
- FILE *fin, FILE *fout, class cl_app *the_app):
+ FILE *fin, FILE *fout, class cl_app *the_app):
cl_console(fin, fout, the_app)
{
parent= the_parent;
*/
cl_commander::cl_commander(class cl_app *the_app, class cl_cmdset *acmdset
- /*, class cl_sim *asim*/):
+ /*, class cl_sim *asim*/):
cl_base()
{
app= the_app;
- cons= new cl_list(1, 1);
+ cons= new cl_list(1, 1, "consoles");
actual_console= frozen_console= 0;
cmdset= acmdset;
}
cl_commander::init(void)
{
class cl_optref console_on_option(this);
+ class cl_optref config_file_option(this);
+ class cl_optref port_number_option(this);
+ class cl_console *con;
console_on_option.init();
console_on_option.use("console_on");
+ config_file_option.init();
+ config_file_option.use("config_file");
+ port_number_option.init();
cl_base::init();
set_name("Commander");
- char *Config= app->args->get_sarg(0, "Config");
- if (Config)
- {
- class cl_console *con= mk_console(0/*"/dev/tty"*/);
- add_console(con);
- }
+ bool need_config= DD_TRUE;
- //if (app->args->arg_avail('c'))
- {
- char *cn= console_on_option.get_value(cn);
- if (cn)
- add_console(mk_console(cn, cn));
- }
#ifdef SOCKET_AVAIL
- if (app->args->arg_avail('Z'))
- add_console(mk_console(app->args->get_iarg(0, "Zport")));
- if (app->args->arg_avail('r'))
- add_console(mk_console(app->args->get_iarg('r', 0)));
+ if (port_number_option.use("port_number"))
+ add_console(mk_console(port_number_option.get_value((long)0)));
#endif
+
+ /* The following code is commented out because it produces gcc warnings
+ * newcmd.cc: In member function `virtual int cl_commander::init()':
+ * newcmd.cc:785: warning: 'Config' might be used uninitialized in this function
+ * newcmd.cc:786: warning: 'cn' might be used uninitialized in this function
+ */
+ /*
+ char *Config= config_file_option.get_value(Config);
+ char *cn= console_on_option.get_value(cn);
+ */
+ /* Here shoud probably be something else, but is still better then the former code... */
+ char *Config= config_file_option.get_value("");
+ char *cn= console_on_option.get_value("");
+
+ if (cn)
+ {
+ add_console(con= mk_console(cn, cn));
+ exec_on(con, Config);
+ need_config= DD_FALSE;
+ }
if (cons->get_count() == 0)
- add_console(mk_console(stdin, stdout));
+ {
+ add_console(con= mk_console(stdin, stdout));
+ exec_on(con, Config);
+ need_config= DD_FALSE;
+ }
+ if (need_config &&
+ Config &&
+ *Config)
+ {
+ FILE *fc= fopen(Config, "r");
+ if (!fc)
+ fprintf(stderr, "Can't open `%s': %s\n", Config, strerror(errno));
+ else
+ {
+ con= mk_console(fc, stderr);
+ con->flags|= CONS_NOWELCOME|CONS_ECHO;
+ add_console(con);
+ }
+ }
return(0);
}
fd_num= 0;
for (i= 0; i < cons->count; i++)
{
- int fd;
+ UCSOCKET_T fd;
class cl_console *c= (class cl_console*)(cons->at(i));
if ((fd= c->get_in_fd()) >= 0)
- {
- if ((c->flags & CONS_FROZEN) == 0 ||
- (c->flags & CONS_INTERACTIVE) != 0)
- {
- FD_SET(fd, &read_set);
- if (fd > fd_num)
- fd_num= fd;
- }
- }
+ {
+ if ((c->flags & CONS_FROZEN) == 0 ||
+ (c->flags & CONS_INTERACTIVE) != 0)
+ {
+ FD_SET(fd, &read_set);
+ if (fd > fd_num)
+ fd_num= fd;
+ }
+ }
else
- ;//fprintf(stderr, "** Skipping console %p\n",c);
+ ;//fprintf(stderr, "** Skipping console %p\n",c);
}
fd_num++;
}
for (i= 0; i < cons->count; i++)
{
class cl_console *c= (class cl_console*)(cons->at(i));
- FILE *Out= c->get_out();
- if (Out)
- {
- va_start(ap, format);
- ret= cmd_do_print(Out, format, ap);
- va_end(ap);
- }
+
+ va_start(ap, format);
+ ret= c->cmd_do_print(format, ap);
+ va_end(ap);
}
return(ret);
}
}
}
-int
-cl_commander::all_print(char *string, int length)
-{
- int i;
-
- for (i= 0; i < cons->count; i++)
- {
- class cl_console *c= (class cl_console*)(cons->at(i));
- FILE *Out= c->get_out();
- if (Out)
- {
- for (int j= 0; j < length; j++)
- putc(string[j], Out);
- }
- }
- return(0);
-}
-
/*
* Printing to actual_console
*/
{
va_list ap;
int ret= 0;
- FILE *f;
+ class cl_console *con;
if (actual_console)
- f= actual_console->get_out();
+ {
+ con= actual_console;
+ }
else if (frozen_console)
- f= frozen_console->get_out();
+ {
+ con= frozen_console;
+ }
else
- f= 0;
- if (/*actual_console &&
- actual_console->out*/f)
+ {
+ con= 0;
+ }
+ if (con)
{
va_start(ap, format);
- ret= cmd_do_print(f/*actual_console->out*/, format, ap);
+ ret= con->cmd_do_print(format, ap);
va_end(ap);
}
return(ret);
for (i= 0; i < cons->count; i++)
{
class cl_console *c= (class cl_console*)(cons->at(i));
- FILE *Out= c->get_out();
- if (Out &&
- c->flags & CONS_DEBUG)
- {
- va_start(ap, format);
- ret= cmd_do_print(Out, format, ap);
- va_end(ap);
- }
+ if (c->flags & CONS_DEBUG)
+ {
+ va_start(ap, format);
+ ret= c->cmd_do_print(format, ap);
+ va_end(ap);
+ }
+ }
+ return(ret);
+}
+
+int
+cl_commander::debug(char *format, va_list ap)
+{
+ int i, ret= 0;
+
+ for (i= 0; i < cons->count; i++)
+ {
+ class cl_console *c= (class cl_console*)(cons->at(i));
+ if (c->flags & CONS_DEBUG)
+ {
+ ret= c->cmd_do_print(format, ap);
+ }
}
return(ret);
}
for (i= 0; i < cons->count; i++)
{
class cl_console *c= (class cl_console*)(cons->at(i));
- FILE *Out= c->get_out();
- if (Out &&
- (c->flags & iflags) == iflags)
- {
- va_start(ap, format);
- ret= cmd_do_print(Out, format, ap);
- va_end(ap);
- }
+ if ((c->flags & iflags) == iflags)
+ {
+ va_start(ap, format);
+ ret= c->cmd_do_print(format, ap);
+ va_end(ap);
+ }
}
return(ret);
}
int
cl_commander::proc_input(void)
{
- int i;
+ UCSOCKET_T i;
for (i= 0; i < fd_num; i++)
if (FD_ISSET(i, &active_set))
{
- class cl_console *c;
- int j;
- for (j= 0; j < cons->count; j++)
- {
- c= (class cl_console*)(cons->at(j));
- if (c->match(i))
- {
- actual_console= c;
- int retval= c->proc_input(cmdset);
- if (retval)
- {
- del_console(c);
- delete c;
- }
- actual_console= 0;
- return(cons->count == 0);
- }
- }
+ class cl_console *c;
+ int j;
+ for (j= 0; j < cons->count; j++)
+ {
+ c= (class cl_console*)(cons->at(j));
+ if (c->match(i))
+ {
+ actual_console= c;
+ int retval= c->proc_input(cmdset);
+ if (retval)
+ {
+ del_console(c);
+ delete c;
+ }
+ actual_console= 0;
+ return(cons->count == 0);
+ }
+ }
}
return(0);
}
+void
+cl_commander::exec_on(class cl_console *cons, char *file_name)
+{
+ FILE *fi= fopen(file_name, "r");
+
+ if (!cons ||
+ !fi)
+ return;
+ class cl_console *subcon= cons->clone_for_exec(file_name);
+ subcon->flags|= CONS_NOWELCOME;
+ add_console(subcon);
+}
+
/* End of cmd.src/newcmd.cc */