/************************************************************************** * * commands.c -- mgquery command processing functions * Copyright (C) 1994 Neil Sharman * * 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 * (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., 675 Mass Ave, Cambridge, MA 02139, USA. * * $Id: commands.c 3745 2003-02-20 21:20:24Z mdewsnip $ * **************************************************************************/ /* $Log$ Revision 1.1 2003/02/20 21:18:23 mdewsnip Addition of MG package for search and retrieval Revision 1.1 1999/08/10 21:17:47 sjboddie renamed mg-1.3d directory mg Revision 1.1 1998/11/17 09:34:32 rjmcnab *** empty log message *** * Revision 1.2 1994/09/20 04:41:22 tes * For version 1.1 * */ static char *RCSID = "$Id: commands.c 3745 2003-02-20 21:20:24Z mdewsnip $"; #include "sysfuncs.h" #include "memlib.h" #include "messages.h" #include "environment.h" #include "mg.h" #include "locallib.h" #include "backend.h" /* for qd */ #include "term_lists.h" /* for MAXTERMSTRLEN */ /* [RPAP - Feb 97: WIN32 Port] */ #ifdef __WIN32__ # define OPENPIPE _popen # define CLOSEPIPE _pclose #else # define OPENPIPE popen # define CLOSEPIPE pclose #endif extern char *PathName; extern FILE *OutFile, *InFile; extern int OutPipe, InPipe; extern int Quitting; char *CommandsErrorStr = NULL; /* [TS: June/95] */ /* current qd for use by any commands */ static query_data *the_qd = NULL; #include "help.mg.h" #include "warranty.h" #include "conditions.h" static void CmdQuit (void) { Quitting = 1; } static void CmdPush (void) { PushEnv (); } static void CmdPop (void) { PopEnv (); if (EnvStackHeight () == 1) PushEnv (); } static void CmdHelp (void) { FILE *more; int i; if (!(more = OPENPIPE (GetDefEnv ("pager", "more"), "w"))) /* [RPAP - Feb 97: WIN32 Port] */ { fprintf (stderr, "ERROR : Unable to run more\n"); return; } for (i = 0; i < sizeof (help_str) / sizeof (help_str[0]); i++) fputs (help_str[i], more); CLOSEPIPE (more); /* [RPAP - Feb 97: WIN32 Port] */ } static void CmdWarranty (void) { FILE *more; int i; if (!(more = OPENPIPE (GetDefEnv ("pager", "more"), "w"))) /* [RPAP - Feb 97: WIN32 Port] */ { fprintf (stderr, "ERROR : Unable to run more\n"); return; } for (i = 0; i < sizeof (warranty_str) / sizeof (warranty_str[0]); i++) fputs (warranty_str[i], more); CLOSEPIPE (more); /* [RPAP - Feb 97: WIN32 Port] */ } static void CmdConditions (void) { FILE *more; int i; if (!(more = OPENPIPE (GetDefEnv ("pager", "more"), "w"))) /* [RPAP - Feb 97: WIN32 Port] */ { fprintf (stderr, "ERROR : Unable to run more\n"); return; } for (i = 0; i < sizeof (cond_str) / sizeof (cond_str[0]); i++) fputs (cond_str[i], more); CLOSEPIPE (more); } static void CmdReset (void) { while (EnvStackHeight () > 1) PopEnv (); PushEnv (); } static void CmdDisplay (void) { int i; size_t l = 0; char *name; for (i = 0; (name = GetEnvName (i)) != NULL; i++) if (strlen (name) > l) l = strlen (name); for (i = 0; (name = GetEnvName (i)) != NULL; i++) printf ("%-*s = \"%s\"\n", (int) l, name, GetEnv (name)); } static void CmdQueryTerms (void) { static char terms_str[MAXTERMSTRLEN + 1]; if (the_qd && the_qd->TL) { ConvertTermsToString (the_qd->TL, terms_str); printf ("%s\n", terms_str); fflush (stdout); } } static void CmdSet (char *name, char *value) { if (!*name) { CommandsErrorStr = "Blank names are not permitted"; return; } switch (SetEnv (name, value, NULL)) { case -1: CommandsErrorStr = "Out of memory\n"; break; case -2: CommandsErrorStr = ConstraintErrorStr; break; } } static void CmdUnset (char *name) { if (!*name) { CommandsErrorStr = "Blank names are not permitted"; return; } if (UnsetEnv (name, 0) == -1) CommandsErrorStr = "Specified name does not exist"; } /* * Do the .input command */ static void CmdInput (char *param1, char *param2) { enum { READ, APPEND, PIPEFROM } mode; FILE *NewInput; char *buf, *s; /* join the two parameters together */ buf = Xmalloc (strlen (param1) + strlen (param2) + 1); strcpy (buf, param1); strcat (buf, param2); s = buf; while (*s == ' ' || *s == '\t') s++; if (*s == '<') { s++; mode = READ; } else if (*s == '|') { mode = PIPEFROM; s++; } else { if (InPipe) CLOSEPIPE (InFile); /* [RPAP - Feb 97: WIN32 Port] */ else if (InFile != stdin) fclose (InFile); InPipe = 0; InFile = stdin; Xfree (buf); return; } while (*s == ' ' || *s == '\t') s++; if (*s) { if (mode == READ) NewInput = fopen (s, "r"); else NewInput = OPENPIPE (s, "r"); /* [RPAP - Feb 97: WIN32 Port] */ if (NewInput) { if (InPipe) CLOSEPIPE (InFile); /* [RPAP - Feb 97: WIN32 Port] */ else if (InFile != stdin) fclose (InFile); InPipe = (mode == PIPEFROM); InFile = NewInput; } else CommandsErrorStr = "Bad input file/pipe"; } else { if (InPipe) CLOSEPIPE (InFile); /* [RPAP - Feb 97: WIN32 Port] */ else if (InFile != stdin) fclose (InFile); InPipe = 0; InFile = stdin; } Xfree (buf); } static void CmdOutput (char *param1, char *param2) { enum { WRITE, APPEND, PIPETO } mode; char *buf, *s; FILE *NewOutput; /* join the two parameters together */ buf = Xmalloc (strlen (param1) + strlen (param2) + 1); strcpy (buf, param1); strcat (buf, param2); s = buf; while (*s == ' ' || *s == '\t') s++; if (*s == '>') { s++; mode = APPEND; if (*s == '>') s++; else mode = WRITE; } else if (*s == '|') { mode = PIPETO; s++; } else { if (OutPipe) CLOSEPIPE (OutFile); /* [RPAP - Feb 97: WIN32 Port] */ else if (OutFile != stdout) fclose (OutFile); OutPipe = 0; OutFile = stdout; Xfree (buf); return; } while (*s == ' ' || *s == '\t') s++; if (*s) { if (mode == PIPETO) NewOutput = OPENPIPE (s, "w"); /* [RPAP - Feb 97: WIN32 Port] */ else NewOutput = fopen (s, mode == WRITE ? "w" : "a"); if (NewOutput) { if (OutPipe) CLOSEPIPE (OutFile); /* [RPAP - Feb 97: WIN32 Port] */ else if (OutFile != stdout) fclose (OutFile); OutPipe = (mode == PIPETO); OutFile = NewOutput; } else CommandsErrorStr = "Bad output file/pipe"; } else { if (OutPipe) CLOSEPIPE (OutFile); /* [RPAP - Feb 97: WIN32 Port] */ else if (OutFile != stdout) fclose (OutFile); OutPipe = 0; OutFile = stdout; } Xfree (buf); } static char * ParseArg (char *line, char *buffer) { if (*line == '\"') { line++; while (*line != '\"' && *line != '\0') { if (*line == '\\') *buffer++ = *line++; if (*line != '\0') *buffer++ = *line++; } if (*line == '\"') line++; } else while (*line != ' ' && *line != '\t' && *line != '\0') { if (*line == '\\') line++; if (*line != '\0') *buffer++ = *line++; } *buffer = '\0'; while (*line == ' ' || *line == '\t') line++; return (line); } char * ProcessCommands (char *line, query_data * qd) { struct { char *Command; void (*action) (void); void (*action1) (char *); void (*action2) (char *, char *); } *dc, dot_command[] = { { "set", NULL, NULL, CmdSet } , { "input", NULL, NULL, CmdInput } , { "output", NULL, NULL, CmdOutput } , { "unset", NULL, CmdUnset, NULL } , { "help", CmdHelp, NULL, NULL } , { "reset", CmdReset, NULL, NULL } , { "display", CmdDisplay, NULL, NULL } , { "push", CmdPush, NULL, NULL } , { "quit", CmdQuit, NULL, NULL } , { "pop", CmdPop, NULL, NULL } , { "warranty", CmdWarranty, NULL, NULL } , { "conditions", CmdConditions, NULL, NULL } , { "queryterms", CmdQueryTerms, NULL, NULL } }; char command[512]; char param1[512], param2[512]; CommandsErrorStr = NULL; the_qd = qd; /* set globally to be accessed by command functions if needed */ while (*line == ' ' || *line == '\t') line++; while (*line == '.') { int i; line++; for (i = 0; isalpha (*line) && i < 512; i++, line++) command[i] = tolower (*line); while (*line == ' ' || *line == '\t') line++; if (i != 512) { command[i] = '\0'; for (i = 0, dc = dot_command; i < NUMOF (dot_command); i++, dc++) if (!strcmp (dc->Command, command)) { if (dc->action) dc->action (); else if (dc->action1) { line = ParseArg (line, param1); dc->action1 (param1); break; } else if (dc->action2) { line = ParseArg (line, param1); line = ParseArg (line, param2); dc->action2 (param1, param2); break; } if (CommandsErrorStr) *line = '\0'; break; } if (i == NUMOF (dot_command)) i = 100; } if (i == 100) { CommandsErrorStr = "Illegal command"; *line = '\0'; } while (*line == ' ' || *line == '\t') line++; } return (line); } void read_mgrc_file (void) { char line[1000]; char FileName[256]; int LineNum = 0; FILE *mgrc; strcpy (FileName, ".mgrc"); mgrc = fopen (FileName, "r"); if (!mgrc) { char *home_path = getenv ("HOME"); if (home_path) { sprintf (FileName, "%s/.mgrc", home_path); mgrc = fopen (FileName, "r"); } } if (!mgrc) return; while (fgets (line, sizeof (line), mgrc)) { char *s, linebuf[1000]; LineNum++; if ((s = strchr (line, '\n')) != NULL) *s = '\0'; strcpy (linebuf, line); if ((s = strchr (line, '#')) != NULL) *s = '\0'; if (!*line) continue; ProcessCommands (line, NULL); if (CommandsErrorStr) Message ("%s\n%s : ERROR in line %d of %s\n%s : %s\n", linebuf, msg_prefix, LineNum, FileName, msg_prefix, CommandsErrorStr); } fclose (mgrc); }