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