1f8dd34f6Sespie /* Plural expression evaluation.
2*a1acfa9bSespie Copyright (C) 2000-2003 Free Software Foundation, Inc.
3f8dd34f6Sespie
4f8dd34f6Sespie This program is free software; you can redistribute it and/or modify it
5f8dd34f6Sespie under the terms of the GNU Library General Public License as published
6f8dd34f6Sespie by the Free Software Foundation; either version 2, or (at your option)
7f8dd34f6Sespie any later version.
8f8dd34f6Sespie
9f8dd34f6Sespie This program is distributed in the hope that it will be useful,
10f8dd34f6Sespie but WITHOUT ANY WARRANTY; without even the implied warranty of
11f8dd34f6Sespie MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12f8dd34f6Sespie Library General Public License for more details.
13f8dd34f6Sespie
14f8dd34f6Sespie You should have received a copy of the GNU Library General Public
15f8dd34f6Sespie License along with this program; if not, write to the Free Software
16f8dd34f6Sespie Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
17f8dd34f6Sespie USA. */
18f8dd34f6Sespie
19f8dd34f6Sespie #ifndef STATIC
20f8dd34f6Sespie #define STATIC static
21f8dd34f6Sespie #endif
22f8dd34f6Sespie
23f8dd34f6Sespie /* Evaluate the plural expression and return an index value. */
24f8dd34f6Sespie STATIC
25f8dd34f6Sespie unsigned long int
26f8dd34f6Sespie internal_function
plural_eval(struct expression * pexp,unsigned long int n)27*a1acfa9bSespie plural_eval (struct expression *pexp, unsigned long int n)
28f8dd34f6Sespie {
29f8dd34f6Sespie switch (pexp->nargs)
30f8dd34f6Sespie {
31f8dd34f6Sespie case 0:
32f8dd34f6Sespie switch (pexp->operation)
33f8dd34f6Sespie {
34f8dd34f6Sespie case var:
35f8dd34f6Sespie return n;
36f8dd34f6Sespie case num:
37f8dd34f6Sespie return pexp->val.num;
38f8dd34f6Sespie default:
39f8dd34f6Sespie break;
40f8dd34f6Sespie }
41f8dd34f6Sespie /* NOTREACHED */
42f8dd34f6Sespie break;
43f8dd34f6Sespie case 1:
44f8dd34f6Sespie {
45f8dd34f6Sespie /* pexp->operation must be lnot. */
46f8dd34f6Sespie unsigned long int arg = plural_eval (pexp->val.args[0], n);
47f8dd34f6Sespie return ! arg;
48f8dd34f6Sespie }
49f8dd34f6Sespie case 2:
50f8dd34f6Sespie {
51f8dd34f6Sespie unsigned long int leftarg = plural_eval (pexp->val.args[0], n);
52f8dd34f6Sespie if (pexp->operation == lor)
53f8dd34f6Sespie return leftarg || plural_eval (pexp->val.args[1], n);
54f8dd34f6Sespie else if (pexp->operation == land)
55f8dd34f6Sespie return leftarg && plural_eval (pexp->val.args[1], n);
56f8dd34f6Sespie else
57f8dd34f6Sespie {
58f8dd34f6Sespie unsigned long int rightarg = plural_eval (pexp->val.args[1], n);
59f8dd34f6Sespie
60f8dd34f6Sespie switch (pexp->operation)
61f8dd34f6Sespie {
62f8dd34f6Sespie case mult:
63f8dd34f6Sespie return leftarg * rightarg;
64f8dd34f6Sespie case divide:
65*a1acfa9bSespie #if !INTDIV0_RAISES_SIGFPE
66*a1acfa9bSespie if (rightarg == 0)
67*a1acfa9bSespie raise (SIGFPE);
68*a1acfa9bSespie #endif
69f8dd34f6Sespie return leftarg / rightarg;
70f8dd34f6Sespie case module:
71*a1acfa9bSespie #if !INTDIV0_RAISES_SIGFPE
72*a1acfa9bSespie if (rightarg == 0)
73*a1acfa9bSespie raise (SIGFPE);
74*a1acfa9bSespie #endif
75f8dd34f6Sespie return leftarg % rightarg;
76f8dd34f6Sespie case plus:
77f8dd34f6Sespie return leftarg + rightarg;
78f8dd34f6Sespie case minus:
79f8dd34f6Sespie return leftarg - rightarg;
80f8dd34f6Sespie case less_than:
81f8dd34f6Sespie return leftarg < rightarg;
82f8dd34f6Sespie case greater_than:
83f8dd34f6Sespie return leftarg > rightarg;
84f8dd34f6Sespie case less_or_equal:
85f8dd34f6Sespie return leftarg <= rightarg;
86f8dd34f6Sespie case greater_or_equal:
87f8dd34f6Sespie return leftarg >= rightarg;
88f8dd34f6Sespie case equal:
89f8dd34f6Sespie return leftarg == rightarg;
90f8dd34f6Sespie case not_equal:
91f8dd34f6Sespie return leftarg != rightarg;
92f8dd34f6Sespie default:
93f8dd34f6Sespie break;
94f8dd34f6Sespie }
95f8dd34f6Sespie }
96f8dd34f6Sespie /* NOTREACHED */
97f8dd34f6Sespie break;
98f8dd34f6Sespie }
99f8dd34f6Sespie case 3:
100f8dd34f6Sespie {
101f8dd34f6Sespie /* pexp->operation must be qmop. */
102f8dd34f6Sespie unsigned long int boolarg = plural_eval (pexp->val.args[0], n);
103f8dd34f6Sespie return plural_eval (pexp->val.args[boolarg ? 1 : 2], n);
104f8dd34f6Sespie }
105f8dd34f6Sespie }
106f8dd34f6Sespie /* NOTREACHED */
107f8dd34f6Sespie return 0;
108f8dd34f6Sespie }
109