annotate eval.c @ 1516:0f0e9dfa6723 libavcodec

theora decoding support (only keyframes for now, because by theora the frame isn't flipped so the motion vectors are getting screwed up)
author alex
date Sat, 11 Oct 2003 17:44:21 +0000
parents 1e39f273ecd6
children 932d306bf1dc
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
612
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
1 /*
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
2 * simple arithmetic expression evaluator
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
3 *
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
4 * Copyright (c) 2002 Michael Niedermayer <michaelni@gmx.at>
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
5 *
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
6 * This library is free software; you can redistribute it and/or
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
7 * modify it under the terms of the GNU Lesser General Public
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
8 * License as published by the Free Software Foundation; either
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
9 * version 2 of the License, or (at your option) any later version.
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
10 *
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
11 * This library is distributed in the hope that it will be useful,
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
14 * Lesser General Public License for more details.
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
15 *
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
16 * You should have received a copy of the GNU Lesser General Public
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
17 * License along with this library; if not, write to the Free Software
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
19 *
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
20 */
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
21
1106
1e39f273ecd6 per file doxy
michaelni
parents: 1057
diff changeset
22 /**
1e39f273ecd6 per file doxy
michaelni
parents: 1057
diff changeset
23 * @file eval.c
1e39f273ecd6 per file doxy
michaelni
parents: 1057
diff changeset
24 * simple arithmetic expression evaluator.
1e39f273ecd6 per file doxy
michaelni
parents: 1057
diff changeset
25 *
612
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
26 * see http://joe.hotchkiss.com/programming/eval/eval.html
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
27 */
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
28
1057
bb5de8a59da8 * static,const,compiler warning cleanup
kabi
parents: 627
diff changeset
29 #include "avcodec.h"
bb5de8a59da8 * static,const,compiler warning cleanup
kabi
parents: 627
diff changeset
30 #include "mpegvideo.h"
bb5de8a59da8 * static,const,compiler warning cleanup
kabi
parents: 627
diff changeset
31
612
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
32 #include <stdio.h>
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
33 #include <stdlib.h>
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
34 #include <string.h>
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
35 #include <math.h>
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
36
614
b786f15df503 NAN doesnt exist on FreeBSD patch by (R?mi Guyomarch <rguyom at pobox dot com>)
michaelni
parents: 612
diff changeset
37 #ifndef NAN
b786f15df503 NAN doesnt exist on FreeBSD patch by (R?mi Guyomarch <rguyom at pobox dot com>)
michaelni
parents: 612
diff changeset
38 #define NAN 0
b786f15df503 NAN doesnt exist on FreeBSD patch by (R?mi Guyomarch <rguyom at pobox dot com>)
michaelni
parents: 612
diff changeset
39 #endif
b786f15df503 NAN doesnt exist on FreeBSD patch by (R?mi Guyomarch <rguyom at pobox dot com>)
michaelni
parents: 612
diff changeset
40
627
79c43f519d02 undefined M_PI / M_E fix
michaelni
parents: 614
diff changeset
41 #ifndef M_PI
79c43f519d02 undefined M_PI / M_E fix
michaelni
parents: 614
diff changeset
42 #define M_PI 3.14159265358979323846
79c43f519d02 undefined M_PI / M_E fix
michaelni
parents: 614
diff changeset
43 #endif
79c43f519d02 undefined M_PI / M_E fix
michaelni
parents: 614
diff changeset
44
612
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
45 #define STACK_SIZE 100
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
46
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
47 typedef struct Parser{
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
48 double stack[STACK_SIZE];
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
49 int stack_index;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
50 char *s;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
51 double *const_value;
1057
bb5de8a59da8 * static,const,compiler warning cleanup
kabi
parents: 627
diff changeset
52 const char **const_name; // NULL terminated
612
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
53 double (**func1)(void *, double a); // NULL terminated
1057
bb5de8a59da8 * static,const,compiler warning cleanup
kabi
parents: 627
diff changeset
54 const char **func1_name; // NULL terminated
612
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
55 double (**func2)(void *, double a, double b); // NULL terminated
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
56 char **func2_name; // NULL terminated
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
57 void *opaque;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
58 } Parser;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
59
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
60 static void evalExpression(Parser *p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
61
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
62 static void push(Parser *p, double d){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
63 if(p->stack_index+1>= STACK_SIZE){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
64 fprintf(stderr, "stack overflow in the parser\n");
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
65 return;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
66 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
67 p->stack[ p->stack_index++ ]= d;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
68 //printf("push %f\n", d); fflush(stdout);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
69 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
70
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
71 static double pop(Parser *p){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
72 if(p->stack_index<=0){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
73 fprintf(stderr, "stack underflow in the parser\n");
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
74 return NAN;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
75 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
76 //printf("pop\n"); fflush(stdout);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
77 return p->stack[ --p->stack_index ];
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
78 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
79
1057
bb5de8a59da8 * static,const,compiler warning cleanup
kabi
parents: 627
diff changeset
80 static int strmatch(const char *s, const char *prefix){
612
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
81 int i;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
82 for(i=0; prefix[i]; i++){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
83 if(prefix[i] != s[i]) return 0;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
84 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
85 return 1;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
86 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
87
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
88 static void evalPrimary(Parser *p){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
89 double d, d2=NAN;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
90 char *next= p->s;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
91 int i;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
92
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
93 /* number */
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
94 d= strtod(p->s, &next);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
95 if(next != p->s){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
96 push(p, d);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
97 p->s= next;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
98 return;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
99 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
100
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
101 /* named constants */
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
102 for(i=0; p->const_name[i]; i++){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
103 if(strmatch(p->s, p->const_name[i])){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
104 push(p, p->const_value[i]);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
105 p->s+= strlen(p->const_name[i]);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
106 return;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
107 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
108 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
109
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
110 p->s= strchr(p->s, '(');
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
111 if(p->s==NULL){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
112 fprintf(stderr, "Parser: missing ( in \"%s\"\n", next);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
113 return;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
114 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
115 p->s++; // "("
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
116 evalExpression(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
117 d= pop(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
118 p->s++; // ")" or ","
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
119 if(p->s[-1]== ','){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
120 evalExpression(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
121 d2= pop(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
122 p->s++; // ")"
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
123 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
124
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
125 if( strmatch(next, "sinh" ) ) d= sinh(d);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
126 else if( strmatch(next, "cosh" ) ) d= cosh(d);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
127 else if( strmatch(next, "tanh" ) ) d= tanh(d);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
128 else if( strmatch(next, "sin" ) ) d= sin(d);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
129 else if( strmatch(next, "cos" ) ) d= cos(d);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
130 else if( strmatch(next, "tan" ) ) d= tan(d);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
131 else if( strmatch(next, "exp" ) ) d= exp(d);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
132 else if( strmatch(next, "log" ) ) d= log(d);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
133 else if( strmatch(next, "squish") ) d= 1/(1+exp(4*d));
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
134 else if( strmatch(next, "gauss" ) ) d= exp(-d*d/2)/sqrt(2*M_PI);
1057
bb5de8a59da8 * static,const,compiler warning cleanup
kabi
parents: 627
diff changeset
135 else if( strmatch(next, "abs" ) ) d= fabs(d);
612
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
136 else if( strmatch(next, "max" ) ) d= d > d2 ? d : d2;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
137 else if( strmatch(next, "min" ) ) d= d < d2 ? d : d2;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
138 else if( strmatch(next, "gt" ) ) d= d > d2 ? 1.0 : 0.0;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
139 else if( strmatch(next, "lt" ) ) d= d > d2 ? 0.0 : 1.0;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
140 else if( strmatch(next, "eq" ) ) d= d == d2 ? 1.0 : 0.0;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
141 // else if( strmatch(next, "l1" ) ) d= 1 + d2*(d - 1);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
142 // else if( strmatch(next, "sq01" ) ) d= (d >= 0.0 && d <=1.0) ? 1.0 : 0.0;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
143 else{
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
144 int error=1;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
145 for(i=0; p->func1_name && p->func1_name[i]; i++){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
146 if(strmatch(next, p->func1_name[i])){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
147 d= p->func1[i](p->opaque, d);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
148 error=0;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
149 break;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
150 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
151 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
152
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
153 for(i=0; p->func2_name && p->func2_name[i]; i++){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
154 if(strmatch(next, p->func2_name[i])){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
155 d= p->func2[i](p->opaque, d, d2);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
156 error=0;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
157 break;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
158 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
159 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
160
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
161 if(error){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
162 fprintf(stderr, "Parser: unknown function in \"%s\"\n", next);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
163 return;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
164 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
165 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
166
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
167 if(p->s[-1]!= ')'){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
168 fprintf(stderr, "Parser: missing ) in \"%s\"\n", next);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
169 return;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
170 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
171 push(p, d);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
172 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
173
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
174 static void evalPow(Parser *p){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
175 int neg= 0;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
176 if(p->s[0]=='+') p->s++;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
177
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
178 if(p->s[0]=='-'){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
179 neg= 1;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
180 p->s++;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
181 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
182
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
183 if(p->s[0]=='('){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
184 p->s++;;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
185 evalExpression(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
186
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
187 if(p->s[0]!=')')
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
188 fprintf(stderr, "Parser: missing )\n");
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
189 p->s++;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
190 }else{
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
191 evalPrimary(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
192 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
193
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
194 if(neg) push(p, -pop(p));
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
195 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
196
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
197 static void evalFactor(Parser *p){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
198 evalPow(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
199 while(p->s[0]=='^'){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
200 double d;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
201
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
202 p->s++;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
203 evalPow(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
204 d= pop(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
205 push(p, pow(pop(p), d));
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
206 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
207 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
208
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
209 static void evalTerm(Parser *p){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
210 evalFactor(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
211 while(p->s[0]=='*' || p->s[0]=='/'){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
212 int inv= p->s[0]=='/';
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
213 double d;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
214
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
215 p->s++;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
216 evalFactor(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
217 d= pop(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
218 if(inv) d= 1.0/d;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
219 push(p, d * pop(p));
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
220 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
221 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
222
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
223 static void evalExpression(Parser *p){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
224 evalTerm(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
225 while(p->s[0]=='+' || p->s[0]=='-'){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
226 int sign= p->s[0]=='-';
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
227 double d;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
228
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
229 p->s++;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
230 evalTerm(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
231 d= pop(p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
232 if(sign) d= -d;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
233 push(p, d + pop(p));
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
234 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
235 }
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
236
1057
bb5de8a59da8 * static,const,compiler warning cleanup
kabi
parents: 627
diff changeset
237 double ff_eval(char *s, double *const_value, const char **const_name,
bb5de8a59da8 * static,const,compiler warning cleanup
kabi
parents: 627
diff changeset
238 double (**func1)(void *, double), const char **func1_name,
612
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
239 double (**func2)(void *, double, double), char **func2_name,
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
240 void *opaque){
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
241 Parser p;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
242
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
243 p.stack_index=0;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
244 p.s= s;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
245 p.const_value= const_value;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
246 p.const_name = const_name;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
247 p.func1 = func1;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
248 p.func1_name = func1_name;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
249 p.func2 = func2;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
250 p.func2_name = func2_name;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
251 p.opaque = opaque;
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
252
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
253 evalExpression(&p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
254 return pop(&p);
c0005de2be59 new ratecontrol code
michaelni
parents:
diff changeset
255 }