From 01d18ac2e6f4fd965b43f2d11425dc33f735e3b4 Mon Sep 17 00:00:00 2001 From: "W. Eric Norum" <wenorum@lbl.gov> Date: Tue, 18 Apr 2000 18:06:18 +0000 Subject: [PATCH] Initial commit of RTEMS sequence commands. --- src/seq/seqCommands.c | 205 ++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 205 insertions(+) create mode 100644 src/seq/seqCommands.c diff --git a/src/seq/seqCommands.c b/src/seq/seqCommands.c new file mode 100644 index 00000000..d94598c3 --- /dev/null +++ b/src/seq/seqCommands.c @@ -0,0 +1,205 @@ +/* + * $ID: $ + * + * DESCRIPTION: EPICS sequencer commands + * + * Author: Eric Norum + * + * Experimental Physics and Industrial Control System (EPICS) + * + * Initial development by: + * Canadian Light Source + * 107 North Road + * University of Saskatchewan + * Saskatoon, Saskatchewan, CANADA + * cls.usask.ca + */ +#include <stdio.h> +#include <stdlib.h> +#include <ctype.h> + +#include <osiThread.h> +#include <cantProceed.h> + +#include <seqCom.h> +#include <CommandInterpreter.h> + +/* + * Until the mechanism for registering sequencer programs and commands + * has been finalized I've got a couple of different methods supported + * in this source. At the moment I'm using C++ constructors to generate + * the calls. + */ +#define SEQ_PROG_REG + +/* + * Prototypes (these probably belong in seqCom.h) + */ +long seqShow (threadId); +long seqChanShow (threadId, char *); +long seqQueueShow (threadId tid); +long seqStop (threadId); + +#ifdef SEQ_PROG_REG +struct sequencerProgram { + struct seqProgram *prog; + struct sequencerProgram *next; + +}; +static struct sequencerProgram *seqHead; + +/* + * This routine is called before multitasking has started, so there's + * no race condition in creating the linked list. + */ +void +seqRegisterSequencerProgram (struct seqProgram *p) +{ + struct sequencerProgram *sp; + + sp = (struct sequencerProgram *)mallocMustSucceed (sizeof *sp, "seqRegisterSequencerProgram"); + sp->prog = p; + sp->next = seqHead; + seqHead = sp; +} +#endif + +static long +seqWrapper (const char *table, char *macroDef, unsigned int stackSize) +{ +#ifdef SEQ_PROG_REG + struct sequencerProgram *sp; +#else + extern struct seqProgram * const seqPrograms[]; + struct seqProgram * const *spp; +#endif + + if (*table == '&') + table++; +#ifdef SEQ_PROG_REG + for (sp = seqHead ; sp != NULL ; sp = sp->next) { + if (!strcmp (table, sp->prog->pProgName)) { + seq (sp->prog, macroDef, stackSize); +#else + for (spp = seqPrograms ; *spp != NULL ; spp++) { + if (!strcmp (table, (*spp)->pProgName)) { + seq (*spp, macroDef, stackSize); +#endif + return 0; + } + } + printf ("Can't find sequencer `%s'.\n", table); + return 1; +} + +static threadId +findThread (const char *name) +{ + threadId id; + char *term; + + id = (threadId)strtoul (name, &term, 16); + if ((term != name) && (*term == '\0')) + return id; + id = threadGetId (name); + if (id) + return id; + printf ("No such thread.\n"); + return NULL; +} + +static long +seqShowWrapper (int argc, char **argv) +{ + threadId id; + + if (argc == 1) + return seqShow (NULL); + if ((id = findThread (argv[1])) != NULL) + return seqShow (id); + return 0; +} + +static long +seqQueueShowWrapper (int argc, char **argv) +{ + threadId id; + + if ((id = findThread (argv[1])) != NULL) + return seqQueueShow (id); + return 0; +} + +static long +seqStopWrapper (int argc, char **argv) +{ + threadId id; + + if ((id = findThread (argv[1])) != NULL) + return seqStop (id); + return 0; +} + +static long +seqChanShowWrapper (int argc, char **argv) +{ + threadId id; + char *chan; + + if (argc <= 2) + chan = NULL; + else + chan = argv[2]; + if (argc == 1) + return seqChanShow (NULL, chan); + if ((id = findThread (argv[1])) != NULL) + return seqChanShow (id, chan); + return 0; +} + +/* + * Command table + */ +typedef long (*cmd)(); +static const struct CommandTableEntry CommandTable[] = { + { "seq", + "Start sequencer", + "**i", (cmd)seqWrapper, 2, 4 + }, + + { "seqShow", + "Show sequencer info", + NULL, (cmd)seqShowWrapper, 1, 2 + }, + + { "seqStop", + "Stop sequencer", + NULL, (cmd)seqStopWrapper, 2, 2 + }, + + { "seqQueueShow", + "Show sequencer queue info", + NULL, (cmd)seqQueueShowWrapper, 2, 2 + }, + + { "seqChanShow", + "Show sequencer channel info", + NULL, (cmd)seqChanShowWrapper, 1, 3 + }, + + { NULL, NULL, NULL, NULL, 0, 0 }, +}; + +/* + * This routine is called before multitasking has started, so there's + * no race condition in the test/set of firsTime. + */ +void +seqRegisterSequencerCommands (void) +{ + static int firstTime = 1; + if (firstTime) { + firstTime = 0; + CommandInterpreterRegisterCommands (CommandTable); + } +}; -- GitLab