int.c revision 1.8 1 1.8 sekiya /* $NetBSD: int.c,v 1.8 2004/07/06 23:56:13 sekiya Exp $ */
2 1.1 sekiya
3 1.1 sekiya /*
4 1.1 sekiya * Copyright (c) 2004 Christopher SEKIYA
5 1.1 sekiya * All rights reserved.
6 1.1 sekiya *
7 1.1 sekiya * Redistribution and use in source and binary forms, with or without
8 1.1 sekiya * modification, are permitted provided that the following conditions
9 1.1 sekiya * are met:
10 1.1 sekiya * 1. Redistributions of source code must retain the above copyright
11 1.1 sekiya * notice, this list of conditions and the following disclaimer.
12 1.1 sekiya * 2. Redistributions in binary form must reproduce the above copyright
13 1.1 sekiya * notice, this list of conditions and the following disclaimer in the
14 1.1 sekiya * documentation and/or other materials provided with the distribution.
15 1.1 sekiya * 3. The name of the author may not be used to endorse or promote products
16 1.1 sekiya * derived from this software without specific prior written permission.
17 1.1 sekiya *
18 1.1 sekiya * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
19 1.1 sekiya * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
20 1.1 sekiya * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
21 1.1 sekiya * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
22 1.1 sekiya * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
23 1.1 sekiya * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24 1.1 sekiya * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25 1.1 sekiya * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 1.1 sekiya * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
27 1.1 sekiya * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 1.1 sekiya */
29 1.1 sekiya
30 1.1 sekiya /*
31 1.5 pooka * INT/INT2/INT3 interrupt controller (used in Indy's, Indigo's, etc..)
32 1.1 sekiya */
33 1.1 sekiya
34 1.1 sekiya #include <sys/cdefs.h>
35 1.8 sekiya __KERNEL_RCSID(0, "$NetBSD: int.c,v 1.8 2004/07/06 23:56:13 sekiya Exp $");
36 1.1 sekiya
37 1.1 sekiya #include "opt_cputype.h"
38 1.1 sekiya
39 1.1 sekiya #include <sys/param.h>
40 1.1 sekiya #include <sys/proc.h>
41 1.1 sekiya #include <sys/systm.h>
42 1.1 sekiya #include <sys/kernel.h>
43 1.1 sekiya #include <sys/device.h>
44 1.8 sekiya #include <sys/malloc.h>
45 1.1 sekiya
46 1.1 sekiya #include <dev/ic/i8253reg.h>
47 1.1 sekiya #include <machine/sysconf.h>
48 1.1 sekiya #include <machine/machtype.h>
49 1.1 sekiya #include <machine/bus.h>
50 1.1 sekiya #include <mips/locore.h>
51 1.1 sekiya
52 1.1 sekiya #include <mips/cache.h>
53 1.1 sekiya
54 1.1 sekiya #include <sgimips/dev/int2reg.h>
55 1.3 sekiya #include <sgimips/dev/int2var.h>
56 1.1 sekiya
57 1.1 sekiya static bus_space_handle_t ioh;
58 1.1 sekiya static bus_space_tag_t iot;
59 1.1 sekiya
60 1.1 sekiya struct int_softc {
61 1.1 sekiya struct device sc_dev;
62 1.1 sekiya };
63 1.1 sekiya
64 1.1 sekiya
65 1.1 sekiya static int int_match(struct device *, struct cfdata *, void *);
66 1.1 sekiya static void int_attach(struct device *, struct device *, void *);
67 1.1 sekiya void int_local0_intr(u_int32_t, u_int32_t, u_int32_t, u_int32_t);
68 1.1 sekiya void int_local1_intr(u_int32_t, u_int32_t, u_int32_t, u_int32_t);
69 1.1 sekiya int int_mappable_intr(void *);
70 1.1 sekiya void *int_intr_establish(int, int, int (*)(void *), void *);
71 1.1 sekiya unsigned long int_cal_timer(void);
72 1.1 sekiya void int_8254_cal(void);
73 1.1 sekiya
74 1.1 sekiya CFATTACH_DECL(int, sizeof(struct int_softc),
75 1.1 sekiya int_match, int_attach, NULL, NULL);
76 1.1 sekiya
77 1.1 sekiya static int
78 1.1 sekiya int_match(struct device *parent, struct cfdata *match, void *aux)
79 1.1 sekiya {
80 1.6 pooka
81 1.6 pooka if ((mach_type == MACH_SGI_IP12) || (mach_type == MACH_SGI_IP20) ||
82 1.6 pooka (mach_type == MACH_SGI_IP22) )
83 1.1 sekiya return 1;
84 1.1 sekiya
85 1.1 sekiya return 0;
86 1.1 sekiya }
87 1.1 sekiya
88 1.1 sekiya static void
89 1.1 sekiya int_attach(struct device *parent, struct device *self, void *aux)
90 1.1 sekiya {
91 1.1 sekiya u_int32_t address;
92 1.1 sekiya
93 1.1 sekiya if (mach_type == MACH_SGI_IP12)
94 1.1 sekiya address = INT_IP12;
95 1.1 sekiya else if (mach_type == MACH_SGI_IP20)
96 1.1 sekiya address = INT_IP20;
97 1.1 sekiya else if (mach_type == MACH_SGI_IP22) {
98 1.1 sekiya if (mach_subtype == MACH_SGI_IP22_FULLHOUSE)
99 1.1 sekiya address = INT_IP22;
100 1.1 sekiya else
101 1.1 sekiya address = INT_IP24;
102 1.7 pooka } else
103 1.1 sekiya panic("\nint0: passed match, but failed attach?");
104 1.1 sekiya
105 1.1 sekiya printf(" addr 0x%x", address);
106 1.1 sekiya
107 1.1 sekiya bus_space_map(iot, address, 0, 0, &ioh);
108 1.1 sekiya iot = SGIMIPS_BUS_SPACE_NORMAL;
109 1.1 sekiya
110 1.1 sekiya /* Clean out interrupt masks */
111 1.1 sekiya bus_space_write_4(iot, ioh, INT2_LOCAL0_MASK, 0);
112 1.1 sekiya bus_space_write_4(iot, ioh, INT2_LOCAL1_MASK, 0);
113 1.1 sekiya bus_space_write_4(iot, ioh, INT2_MAP_MASK0, 0);
114 1.1 sekiya bus_space_write_4(iot, ioh, INT2_MAP_MASK1, 0);
115 1.1 sekiya
116 1.1 sekiya /* Reset timer interrupts */
117 1.1 sekiya bus_space_write_4(iot, ioh, INT2_TIMER_CLEAR, 0x03);
118 1.1 sekiya
119 1.1 sekiya switch (mach_type) {
120 1.1 sekiya case MACH_SGI_IP12:
121 1.1 sekiya platform.intr1 = int_local0_intr;
122 1.1 sekiya platform.intr2 = int_local1_intr;
123 1.1 sekiya int_8254_cal();
124 1.1 sekiya break;
125 1.4 pooka #ifdef MIPS3
126 1.1 sekiya case MACH_SGI_IP20:
127 1.1 sekiya case MACH_SGI_IP22:
128 1.4 pooka {
129 1.4 pooka int i;
130 1.4 pooka unsigned long cps;
131 1.4 pooka unsigned long ctrdiff[3];
132 1.4 pooka
133 1.1 sekiya platform.intr0 = int_local0_intr;
134 1.1 sekiya platform.intr1 = int_local1_intr;
135 1.1 sekiya
136 1.1 sekiya /* calibrate timer */
137 1.1 sekiya int_cal_timer();
138 1.1 sekiya
139 1.1 sekiya cps = 0;
140 1.6 pooka for (i = 0;
141 1.6 pooka i < sizeof(ctrdiff) / sizeof(ctrdiff[0]); i++) {
142 1.1 sekiya do {
143 1.1 sekiya ctrdiff[i] = int_cal_timer();
144 1.1 sekiya } while (ctrdiff[i] == 0);
145 1.1 sekiya
146 1.1 sekiya cps += ctrdiff[i];
147 1.1 sekiya }
148 1.1 sekiya
149 1.1 sekiya cps = cps / (sizeof(ctrdiff) / sizeof(ctrdiff[0]));
150 1.1 sekiya
151 1.6 pooka printf(": bus %luMHz, CPU %luMHz",
152 1.6 pooka cps / 10000, cps / 5000);
153 1.1 sekiya
154 1.1 sekiya /* R4k/R4400/R4600/R5k count at half CPU frequency */
155 1.1 sekiya curcpu()->ci_cpu_freq = 2 * cps * hz;
156 1.4 pooka }
157 1.4 pooka #endif /* MIPS3 */
158 1.1 sekiya
159 1.1 sekiya break;
160 1.1 sekiya default:
161 1.1 sekiya panic("int0: unsupported machine type %i\n", mach_type);
162 1.1 sekiya break;
163 1.1 sekiya }
164 1.1 sekiya
165 1.1 sekiya printf("\n");
166 1.1 sekiya
167 1.1 sekiya curcpu()->ci_cycles_per_hz = curcpu()->ci_cpu_freq / (2 * hz);
168 1.1 sekiya curcpu()->ci_divisor_delay = curcpu()->ci_cpu_freq / (2 * 1000000);
169 1.1 sekiya MIPS_SET_CI_RECIPRICAL(curcpu());
170 1.1 sekiya
171 1.1 sekiya if (mach_type == MACH_SGI_IP22) {
172 1.1 sekiya /* Wire interrupts 7, 11 to mappable interrupt 0,1 handlers */
173 1.1 sekiya intrtab[7].ih_fun = int_mappable_intr;
174 1.1 sekiya intrtab[7].ih_arg = (void*) 0;
175 1.1 sekiya
176 1.1 sekiya intrtab[11].ih_fun = int_mappable_intr;
177 1.1 sekiya intrtab[11].ih_arg = (void*) 1;
178 1.1 sekiya }
179 1.1 sekiya
180 1.1 sekiya platform.intr_establish = int_intr_establish;
181 1.1 sekiya }
182 1.1 sekiya
183 1.1 sekiya int
184 1.1 sekiya int_mappable_intr(void *arg)
185 1.1 sekiya {
186 1.1 sekiya int i;
187 1.1 sekiya int ret;
188 1.1 sekiya int intnum;
189 1.1 sekiya u_int32_t mstat;
190 1.1 sekiya u_int32_t mmask;
191 1.1 sekiya int which = (int)arg;
192 1.8 sekiya struct sgimips_intrhand *ih;
193 1.1 sekiya
194 1.1 sekiya ret = 0;
195 1.1 sekiya mstat = bus_space_read_4(iot, ioh, INT2_MAP_STATUS);
196 1.1 sekiya mmask = bus_space_read_4(iot, ioh, INT2_MAP_MASK0 + (which << 2));
197 1.1 sekiya
198 1.1 sekiya mstat &= mmask;
199 1.1 sekiya
200 1.1 sekiya for (i = 0; i < 8; i++) {
201 1.1 sekiya intnum = i + 16 + (which << 3);
202 1.1 sekiya if (mstat & (1 << i)) {
203 1.8 sekiya for (ih = &intrtab[intnum]; ih != NULL;
204 1.8 sekiya ih = ih->ih_next) {
205 1.8 sekiya if (ih->ih_fun != NULL)
206 1.8 sekiya ret |= (ih->ih_fun)(ih->ih_arg);
207 1.8 sekiya else
208 1.8 sekiya printf("int0: unexpected mapped "
209 1.8 sekiya "interrupt %d\n", intnum);
210 1.8 sekiya }
211 1.1 sekiya }
212 1.1 sekiya }
213 1.1 sekiya
214 1.1 sekiya return ret;
215 1.1 sekiya }
216 1.1 sekiya
217 1.1 sekiya void
218 1.6 pooka int_local0_intr(u_int32_t status, u_int32_t cause, u_int32_t pc,
219 1.6 pooka u_int32_t ipending)
220 1.1 sekiya {
221 1.1 sekiya int i;
222 1.1 sekiya u_int32_t l0stat;
223 1.1 sekiya u_int32_t l0mask;
224 1.8 sekiya struct sgimips_intrhand *ih;
225 1.1 sekiya
226 1.1 sekiya l0stat = bus_space_read_4(iot, ioh, INT2_LOCAL0_STATUS);
227 1.1 sekiya l0mask = bus_space_read_4(iot, ioh, INT2_LOCAL0_MASK);
228 1.1 sekiya
229 1.8 sekiya /* The "FIFO full" bit is apparently not latched in the ISR, which
230 1.8 sekiya means that it won't be present in l0stat unless we're very lucky.
231 1.8 sekiya If no interrupts are pending, assume that it was caused by a full
232 1.8 sekiya FIFO and dispatch.
233 1.8 sekiya */
234 1.8 sekiya bus_space_write_4(iot, ioh, INT2_LOCAL0_MASK, l0mask & (0xfe));
235 1.8 sekiya if ( (l0stat & l0mask) == 0)
236 1.8 sekiya l0stat = 0x01;
237 1.1 sekiya
238 1.1 sekiya for (i = 0; i < 8; i++) {
239 1.8 sekiya if ( (l0stat & l0mask) & (1 << i)) {
240 1.8 sekiya for (ih = &intrtab[i]; ih != NULL; ih = ih->ih_next) {
241 1.8 sekiya if (ih->ih_fun != NULL)
242 1.8 sekiya (ih->ih_fun)(ih->ih_arg);
243 1.8 sekiya else
244 1.8 sekiya printf("int0: unexpected local0 "
245 1.8 sekiya "interrupt %d\n", i);
246 1.8 sekiya }
247 1.1 sekiya }
248 1.1 sekiya }
249 1.8 sekiya
250 1.8 sekiya /* Unmask FIFO */
251 1.8 sekiya bus_space_write_4(iot, ioh, INT2_LOCAL0_MASK, l0mask | 0x01);
252 1.1 sekiya }
253 1.1 sekiya
254 1.1 sekiya void
255 1.6 pooka int_local1_intr(u_int32_t status, u_int32_t cause, u_int32_t pc,
256 1.6 pooka u_int32_t ipending)
257 1.1 sekiya {
258 1.1 sekiya int i;
259 1.1 sekiya u_int32_t l1stat;
260 1.1 sekiya u_int32_t l1mask;
261 1.8 sekiya struct sgimips_intrhand *ih;
262 1.1 sekiya
263 1.1 sekiya l1stat = bus_space_read_4(iot, ioh, INT2_LOCAL1_STATUS);
264 1.1 sekiya l1mask = bus_space_read_4(iot, ioh, INT2_LOCAL1_MASK);
265 1.1 sekiya
266 1.1 sekiya l1stat &= l1mask;
267 1.1 sekiya
268 1.1 sekiya for (i = 0; i < 8; i++) {
269 1.1 sekiya if (l1stat & (1 << i)) {
270 1.8 sekiya for (ih = &intrtab[8+i]; ih != NULL; ih = ih->ih_next) {
271 1.8 sekiya if (ih->ih_fun != NULL)
272 1.8 sekiya (ih->ih_fun)(ih->ih_arg);
273 1.8 sekiya else
274 1.8 sekiya printf("int0: unexpected local1 "
275 1.8 sekiya " interrupt %x\n", 8 + i);
276 1.8 sekiya }
277 1.1 sekiya }
278 1.1 sekiya }
279 1.1 sekiya }
280 1.1 sekiya
281 1.1 sekiya void *
282 1.1 sekiya int_intr_establish(int level, int ipl, int (*handler) (void *), void *arg)
283 1.1 sekiya {
284 1.1 sekiya u_int32_t mask;
285 1.1 sekiya
286 1.1 sekiya if (level < 0 || level >= NINTR)
287 1.1 sekiya panic("invalid interrupt level");
288 1.1 sekiya
289 1.8 sekiya if (intrtab[level].ih_fun == NULL) {
290 1.8 sekiya intrtab[level].ih_fun = handler;
291 1.8 sekiya intrtab[level].ih_arg = arg;
292 1.8 sekiya intrtab[level].ih_next = NULL;
293 1.8 sekiya } else {
294 1.8 sekiya struct sgimips_intrhand *n, *ih = malloc(sizeof *ih,
295 1.8 sekiya M_DEVBUF, M_NOWAIT);
296 1.8 sekiya
297 1.8 sekiya if (ih == NULL) {
298 1.8 sekiya printf("int_intr_establish: can't allocate handler\n");
299 1.8 sekiya return (void *)NULL;
300 1.8 sekiya }
301 1.8 sekiya
302 1.8 sekiya ih->ih_fun = handler;
303 1.8 sekiya ih->ih_arg = arg;
304 1.8 sekiya ih->ih_next = NULL;
305 1.8 sekiya
306 1.8 sekiya for (n = &intrtab[level]; n->ih_next != NULL; n = n->ih_next)
307 1.8 sekiya ;
308 1.8 sekiya
309 1.8 sekiya n->ih_next = ih;
310 1.8 sekiya
311 1.8 sekiya return (void *)NULL; /* vector already set */
312 1.1 sekiya }
313 1.1 sekiya
314 1.1 sekiya
315 1.1 sekiya if (level < 8) {
316 1.1 sekiya mask = bus_space_read_4(iot, ioh, INT2_LOCAL0_MASK);
317 1.1 sekiya mask |= (1 << level);
318 1.1 sekiya bus_space_write_4(iot, ioh, INT2_LOCAL0_MASK, mask);
319 1.1 sekiya } else if (level < 16) {
320 1.1 sekiya mask = bus_space_read_4(iot, ioh, INT2_LOCAL1_MASK);
321 1.1 sekiya mask |= (1 << (level - 8));
322 1.1 sekiya bus_space_write_4(iot, ioh, INT2_LOCAL1_MASK, mask);
323 1.1 sekiya } else if (level < 24) {
324 1.1 sekiya /* Map0 interrupt maps to l0 bit 7, so turn that on too */
325 1.1 sekiya mask = bus_space_read_4(iot, ioh, INT2_LOCAL0_MASK);
326 1.1 sekiya mask |= (1 << 7);
327 1.1 sekiya bus_space_write_4(iot, ioh, INT2_LOCAL0_MASK, mask);
328 1.1 sekiya
329 1.1 sekiya mask = bus_space_read_4(iot, ioh, INT2_MAP_MASK0);
330 1.1 sekiya mask |= (1 << (level - 16));
331 1.1 sekiya bus_space_write_4(iot, ioh, INT2_MAP_MASK0, mask);
332 1.1 sekiya } else {
333 1.1 sekiya /* Map1 interrupt maps to l1 bit 3, so turn that on too */
334 1.1 sekiya mask = bus_space_read_4(iot, ioh, INT2_LOCAL1_MASK);
335 1.1 sekiya mask |= (1 << 3);
336 1.1 sekiya bus_space_write_4(iot, ioh, INT2_LOCAL1_MASK, mask);
337 1.1 sekiya
338 1.1 sekiya mask = bus_space_read_4(iot, ioh, INT2_MAP_MASK1);
339 1.1 sekiya mask |= (1 << (level - 24));
340 1.1 sekiya bus_space_write_4(iot, ioh, INT2_MAP_MASK1, mask);
341 1.1 sekiya }
342 1.1 sekiya
343 1.1 sekiya return (void *)NULL;
344 1.1 sekiya }
345 1.1 sekiya
346 1.4 pooka #ifdef MIPS3
347 1.1 sekiya unsigned long
348 1.1 sekiya int_cal_timer(void)
349 1.1 sekiya {
350 1.1 sekiya int s;
351 1.1 sekiya int roundtime;
352 1.1 sekiya int sampletime;
353 1.1 sekiya int startmsb, lsb, msb;
354 1.1 sekiya unsigned long startctr, endctr;
355 1.1 sekiya
356 1.1 sekiya /*
357 1.1 sekiya * NOTE: HZ must be greater than 15 for this to work, as otherwise
358 1.1 sekiya * we'll overflow the counter. We round the answer to hearest 1
359 1.1 sekiya * MHz of the master (2x) clock.
360 1.1 sekiya */
361 1.1 sekiya roundtime = (1000000 / hz) / 2;
362 1.1 sekiya sampletime = (1000000 / hz) + 0xff;
363 1.1 sekiya startmsb = (sampletime >> 8);
364 1.1 sekiya
365 1.1 sekiya s = splhigh();
366 1.1 sekiya
367 1.1 sekiya bus_space_write_4(iot, ioh, INT2_TIMER_CONTROL,
368 1.1 sekiya ( TIMER_SEL2 | TIMER_16BIT | TIMER_RATEGEN) );
369 1.1 sekiya bus_space_write_4(iot, ioh, INT2_TIMER_2, (sampletime & 0xff));
370 1.1 sekiya bus_space_write_4(iot, ioh, INT2_TIMER_2, (sampletime >> 8));
371 1.1 sekiya
372 1.1 sekiya startctr = mips3_cp0_count_read();
373 1.1 sekiya
374 1.1 sekiya /* Wait for the MSB to count down to zero */
375 1.1 sekiya do {
376 1.1 sekiya bus_space_write_4(iot, ioh, INT2_TIMER_CONTROL, TIMER_SEL2 );
377 1.1 sekiya lsb = bus_space_read_4(iot, ioh, INT2_TIMER_2) & 0xff;
378 1.1 sekiya msb = bus_space_read_4(iot, ioh, INT2_TIMER_2) & 0xff;
379 1.1 sekiya
380 1.1 sekiya endctr = mips3_cp0_count_read();
381 1.1 sekiya } while (msb);
382 1.1 sekiya
383 1.1 sekiya /* Turn off timer */
384 1.1 sekiya bus_space_write_4(iot, ioh, INT2_TIMER_CONTROL,
385 1.1 sekiya ( TIMER_SEL2 | TIMER_16BIT | TIMER_SWSTROBE) );
386 1.1 sekiya
387 1.1 sekiya splx(s);
388 1.1 sekiya
389 1.1 sekiya return (endctr - startctr) / roundtime * roundtime;
390 1.1 sekiya }
391 1.4 pooka #endif /* MIPS3 */
392 1.1 sekiya
393 1.1 sekiya void
394 1.1 sekiya int_8254_cal(void)
395 1.1 sekiya {
396 1.1 sekiya int s;
397 1.1 sekiya
398 1.1 sekiya s = splhigh();
399 1.1 sekiya
400 1.7 pooka bus_space_write_1(iot, ioh, INT2_TIMER_0 + 15,
401 1.1 sekiya TIMER_SEL0|TIMER_RATEGEN|TIMER_16BIT);
402 1.7 pooka bus_space_write_1(iot, ioh, INT2_TIMER_0 + 3, (20000 / hz) % 256);
403 1.1 sekiya wbflush();
404 1.1 sekiya delay(4);
405 1.7 pooka bus_space_write_1(iot, ioh, INT2_TIMER_0 + 3, (20000 / hz) / 256);
406 1.1 sekiya
407 1.7 pooka bus_space_write_1(iot, ioh, INT2_TIMER_0 + 15,
408 1.1 sekiya TIMER_SEL2|TIMER_RATEGEN|TIMER_16BIT);
409 1.7 pooka bus_space_write_1(iot, ioh, INT2_TIMER_0 + 11, 50);
410 1.1 sekiya wbflush();
411 1.1 sekiya delay(4);
412 1.7 pooka bus_space_write_1(iot, ioh, INT2_TIMER_0 + 11, 0);
413 1.1 sekiya splx(s);
414 1.1 sekiya }
415 1.3 sekiya
416 1.3 sekiya void
417 1.3 sekiya int2_wait_fifo(u_int32_t flag)
418 1.3 sekiya {
419 1.8 sekiya if (ioh == 0)
420 1.8 sekiya delay(5000);
421 1.8 sekiya else
422 1.8 sekiya while (bus_space_read_4(iot, ioh, INT2_LOCAL0_STATUS) & flag)
423 1.8 sekiya ;
424 1.3 sekiya }
425