$$ = $1 / $3;
}
| expr '^' expr { $$ = Pow($1, $3); }
| '(' expr ')' { $$ = $2; }
| '-' expr %prec UNARYMINUS { $$ = -$2; }
;
%%
/* end of grammar */
#include stdio.h
#include ctype.h
char *progname;
int lineno = 1;
#include setjmp.h
jmp_buf begin;
main(argc, argv) /* hoc3 */
char *argv[];
{
progname = argv[0];
init;
setjmp(begin);
yyparse;
}
yyerror(s)
char *s;
{
warning(s, (char *)0);
}
execerror(s, t)
char *s, *t;
{
warning(s, t);
longjmp(begin, 0);
}
warning(s, t)
char *s, *t;
{
fprintf (stderr, "%s: %s", progname, s);
if (t *t)
fprintf(stderr, " %s", t);
fprintf(stderr, " near line %d\n", lineno);
}
3.4.3 init.c
#include "hoc.h"
#include "y.tab.h"
#include math.h
extern double Log, Log10, Exp, Sqrt, integer;
static struct { /* Constants */
char *name;
double eval;
} consts [] = {
"PI", 3.14159265358979323846,
"E", 2.71828182845904523536,
"GAMMA", 0.57721566490153286060, /* Euler */
"DEG", 57.29577951308232087680, /* deg/radian */
"PHI", 1.61803398874989484820, /* golden ratio */
0, 0
};
static struct { /* Built-ins */
char *name;
double (*func);
} builtins[] = {
"sin", sin,
"cos", cos,
"atan", atan,
"log", Log, /* checks argument */
"log10", Log10, /* checks argument */
"exp", Exp, /* checks argument */
"sqrt", Sqrt, /* checks argument */
"int", integer,
"abs", fabs,
0, 0
};
init /* install constants and built-ins in table */
{
int i;
Symbol *s;
for (i = 0; consts[i].name; i++)
install(consts[i].name, VAR, consts[i].eval);
for (i = 0; builtins[i].name; i++) {
s = install(builtins[i].name, BLTIN, 0.0);
s-u.ptr = builtins[i].func;
}
}
3.4.4. lex.l
%{
#include "hoc.h"
#include "y.tab.h"
extern int lineno;
%}
%%
[ \t] { ; } /* skip blanks and tabs */
[0-9]+\.?|[0-9][0-9]+ {
sscanf(yytext, "%lf", yylval.val);
return NUMBER;
}
[a-zA-Z][a-zA-Z0-9]* {
Symbol *s;
if ((s=lookup(yytext)) == 0)
s = install(yytext, UNDEF, 0.0);
yylval.sym = s;
return s-type == UNDEF ? VAR : s-type;
}
\n {
lineno++;
return '\n';
} /* everything else */
. { return yytext[0]; }
3.4.5 makefile
YFLAGS = -d
OBJS = hoc.o lex.o init.o math.o symbol.o
hoc3: $(OBJS)
cc $(OBJS) -lm -ll -o hoc3
hoc.o: hoc.h
lex.o init.o symbol.o: hoc.h y.tab.h
3.4.6 math.c
#include math.h
#include errno.h
extern int errno;
double errcheck;
double Log(x)
double x;
{
return errcheck(log(x), "log");
}
double Log10(x)
double x;
{
return errcheck(log10(x), "log10");
}
double Sqrt(x)
double x;
{
return errcheck(sqrt(x), "sqrt");
}
double Exp(x)
double x;
{
return errcheck(exp(x), "exp");
}
double Pow(x, y)
double x, y;
{
return errcheck(pow(x,y), "exponentiation");
}
double integer(x)
double x;
{
return (double)(long)x;
}