Merge branch 'vendor/PAM_PASSWDQC'
[dragonfly.git] / usr.bin / window / parser3.c
1 /*
2  * Copyright (c) 1983, 1993
3  *      The Regents of the University of California.  All rights reserved.
4  *
5  * This code is derived from software contributed to Berkeley by
6  * Edward Wang at The University of California, Berkeley.
7  *
8  * Redistribution and use in source and binary forms, with or without
9  * modification, are permitted provided that the following conditions
10  * are met:
11  * 1. Redistributions of source code must retain the above copyright
12  *    notice, this list of conditions and the following disclaimer.
13  * 2. Redistributions in binary form must reproduce the above copyright
14  *    notice, this list of conditions and the following disclaimer in the
15  *    documentation and/or other materials provided with the distribution.
16  * 3. All advertising materials mentioning features or use of this software
17  *    must display the following acknowledgement:
18  *      This product includes software developed by the University of
19  *      California, Berkeley and its contributors.
20  * 4. Neither the name of the University nor the names of its contributors
21  *    may be used to endorse or promote products derived from this software
22  *    without specific prior written permission.
23  *
24  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
25  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
26  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
27  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
28  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
29  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
30  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
31  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
32  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
33  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
34  * SUCH DAMAGE.
35  *
36  * @(#)parser3.c        8.1 (Berkeley) 6/6/93
37  * $FreeBSD: src/usr.bin/window/parser3.c,v 1.1.1.1.14.1 2001/05/17 09:45:00 obrien Exp $
38  * $DragonFly: src/usr.bin/window/parser3.c,v 1.2 2003/06/17 04:29:34 dillon Exp $
39  */
40
41 #include "parser.h"
42
43 /*
44  * =
45  * ? :
46  * ||
47  * &&
48  * |
49  * ^
50  * &
51  * == !=
52  * <= >=
53  * << >>
54  * + -
55  * * / %
56  * unary - + ~ !
57  */
58 p_expr(v, flag)
59 register struct value *v;
60 char flag;
61 {
62         struct value t;
63         int ret;
64
65         if (p_expr0(&t, flag) < 0)
66                 return -1;
67
68         if (token != T_ASSIGN) {
69                 *v = t;
70                 return 0;
71         }
72         switch (t.v_type) {
73         case V_NUM:
74                 p_error("%d: Not a variable.", t.v_num);
75         case V_ERR:
76                 t.v_str = 0;
77                 break;
78         }
79         ret = p_assign(t.v_str, v, flag);
80         if (t.v_str != 0)
81                 str_free(t.v_str);
82         return ret;
83 }
84
85 /*
86  * ? :
87  */
88 p_expr0(v, flag)
89 register struct value *v;
90 char flag;
91 {
92         struct value t;
93         char true;
94
95         if (p_expr1(v, flag) < 0)
96                 return -1;
97         if (token != T_QUEST)
98                 return 0;
99         switch (v->v_type) {
100         case V_NUM:
101                 true = v->v_num != 0;
102                 break;
103         case V_STR:
104                 p_error("?: Numeric left operand required.");
105                 str_free(v->v_str);
106                 v->v_type = V_ERR;
107         case V_ERR:
108                 flag = 0;
109                 break;
110         }
111         (void) s_gettok();
112         v->v_type = V_ERR;
113         if ((flag && true ? p_expr1(v, 1) : p_expr1(&t, 0)) < 0)
114                 return -1;
115         if (token != T_COLON) {
116                 val_free(*v);
117                 p_synerror();
118                 return -1;
119         }
120         (void) s_gettok();
121         return flag && !true ? p_expr1(v, 1) : p_expr1(&t, 0);
122 }
123
124 /*
125  * ||
126  */
127 p_expr1(v, flag)
128 register struct value *v;
129 char flag;
130 {
131         char true = 0;
132
133         if (p_expr2(v, flag) < 0)
134                 return -1;
135         if (token != T_OROR)
136                 return 0;
137         for (;;) {
138                 switch (v->v_type) {
139                 case V_NUM:
140                         v->v_num = true = true || v->v_num != 0;
141                         break;
142                 case V_STR:
143                         p_error("||: Numeric operands required.");
144                         str_free(v->v_str);
145                         v->v_type = V_ERR;
146                 case V_ERR:
147                         flag = 0;
148                         break;
149                 }
150                 if (token != T_OROR)
151                         return 0;
152                 (void) s_gettok();
153                 if (p_expr2(v, flag && !true) < 0)
154                         return -1;
155         }
156 }
157
158 /*
159  * &&
160  */
161 p_expr2(v, flag)
162 register struct value *v;
163 char flag;
164 {
165         char true = 1;
166
167         if (p_expr3_10(3, v, flag) < 0)
168                 return -1;
169         if (token != T_ANDAND)
170                 return 0;
171         for (;;) {
172                 switch (v->v_type) {
173                 case V_NUM:
174                         v->v_num = true = true && v->v_num != 0;
175                         break;
176                 case V_STR:
177                         p_error("&&: Numeric operands required.");
178                         str_free(v->v_str);
179                         v->v_type = V_ERR;
180                 case V_ERR:
181                         flag = 0;
182                         break;
183                 }
184                 if (token != T_ANDAND)
185                         return 0;
186                 (void) s_gettok();
187                 if (p_expr3_10(3, v, flag && true) < 0)
188                         return -1;
189         }
190         /*NOTREACHED*/
191 }