Commit 592b5315219881c6c0af4785f96456ad2043193a
Committed by
Bartlomiej Zolnierkiewicz
1 parent
3f023b0138
Exists in
master
and in
39 other branches
ide: move read_sff_dma_status() method to 'struct ide_dma_ops'
Move apparently misplaced read_sff_dma_status() method from 'struct ide_tp_ops' to 'struct ide_dma_ops', renaming it to dma_sff_read_status() and making only required for SFF-8038i compatible IDE controller drivers (greatly cutting down the number of initializers) as its only user (outside ide-dma-sff.c and such drivers) appears to be ide_pci_check_simplex() which is only called for such controllers... Signed-off-by: Sergei Shtylyov <sshtylyov@ru.mvista.com> Signed-off-by: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com>
Showing 23 changed files with 65 additions and 42 deletions Side-by-side Diff
- drivers/ide/alim15x3.c
- drivers/ide/au1xxx-ide.c
- drivers/ide/cmd64x.c
- drivers/ide/falconide.c
- drivers/ide/hpt366.c
- drivers/ide/ide-dma-sff.c
- drivers/ide/ide-h8300.c
- drivers/ide/ide-iops.c
- drivers/ide/ide-probe.c
- drivers/ide/it821x.c
- drivers/ide/ns87415.c
- drivers/ide/pdc202xx_old.c
- drivers/ide/pmac.c
- drivers/ide/q40ide.c
- drivers/ide/sc1200.c
- drivers/ide/scc_pata.c
- drivers/ide/setup-pci.c
- drivers/ide/sgiioc4.c
- drivers/ide/siimage.c
- drivers/ide/sl82c105.c
- drivers/ide/tc86c001.c
- drivers/ide/tx4939ide.c
- include/linux/ide.h
drivers/ide/alim15x3.c
... | ... | @@ -509,6 +509,7 @@ |
509 | 509 | .dma_test_irq = ide_dma_test_irq, |
510 | 510 | .dma_lost_irq = ide_dma_lost_irq, |
511 | 511 | .dma_timeout = ide_dma_timeout, |
512 | + .dma_sff_read_status = ide_dma_sff_read_status, | |
512 | 513 | }; |
513 | 514 | |
514 | 515 | static const struct ide_port_info ali15x3_chipset __devinitdata = { |
drivers/ide/au1xxx-ide.c
drivers/ide/cmd64x.c
... | ... | @@ -385,6 +385,7 @@ |
385 | 385 | .dma_test_irq = cmd64x_dma_test_irq, |
386 | 386 | .dma_lost_irq = ide_dma_lost_irq, |
387 | 387 | .dma_timeout = ide_dma_timeout, |
388 | + .dma_sff_read_status = ide_dma_sff_read_status, | |
388 | 389 | }; |
389 | 390 | |
390 | 391 | static const struct ide_dma_ops cmd646_rev1_dma_ops = { |
... | ... | @@ -396,6 +397,7 @@ |
396 | 397 | .dma_test_irq = ide_dma_test_irq, |
397 | 398 | .dma_lost_irq = ide_dma_lost_irq, |
398 | 399 | .dma_timeout = ide_dma_timeout, |
400 | + .dma_sff_read_status = ide_dma_sff_read_status, | |
399 | 401 | }; |
400 | 402 | |
401 | 403 | static const struct ide_dma_ops cmd648_dma_ops = { |
... | ... | @@ -407,6 +409,7 @@ |
407 | 409 | .dma_test_irq = cmd648_dma_test_irq, |
408 | 410 | .dma_lost_irq = ide_dma_lost_irq, |
409 | 411 | .dma_timeout = ide_dma_timeout, |
412 | + .dma_sff_read_status = ide_dma_sff_read_status, | |
410 | 413 | }; |
411 | 414 | |
412 | 415 | static const struct ide_port_info cmd64x_chipsets[] __devinitdata = { |
drivers/ide/falconide.c
drivers/ide/hpt366.c
... | ... | @@ -1424,6 +1424,7 @@ |
1424 | 1424 | .dma_test_irq = hpt374_dma_test_irq, |
1425 | 1425 | .dma_lost_irq = ide_dma_lost_irq, |
1426 | 1426 | .dma_timeout = ide_dma_timeout, |
1427 | + .dma_sff_read_status = ide_dma_sff_read_status, | |
1427 | 1428 | }; |
1428 | 1429 | |
1429 | 1430 | static const struct ide_dma_ops hpt370_dma_ops = { |
... | ... | @@ -1435,6 +1436,7 @@ |
1435 | 1436 | .dma_test_irq = ide_dma_test_irq, |
1436 | 1437 | .dma_lost_irq = ide_dma_lost_irq, |
1437 | 1438 | .dma_timeout = hpt370_dma_timeout, |
1439 | + .dma_sff_read_status = ide_dma_sff_read_status, | |
1438 | 1440 | }; |
1439 | 1441 | |
1440 | 1442 | static const struct ide_dma_ops hpt36x_dma_ops = { |
... | ... | @@ -1446,6 +1448,7 @@ |
1446 | 1448 | .dma_test_irq = ide_dma_test_irq, |
1447 | 1449 | .dma_lost_irq = hpt366_dma_lost_irq, |
1448 | 1450 | .dma_timeout = ide_dma_timeout, |
1451 | + .dma_sff_read_status = ide_dma_sff_read_status, | |
1449 | 1452 | }; |
1450 | 1453 | |
1451 | 1454 | static const struct ide_port_info hpt366_chipsets[] __devinitdata = { |
drivers/ide/ide-dma-sff.c
... | ... | @@ -50,6 +50,17 @@ |
50 | 50 | return 0; |
51 | 51 | } |
52 | 52 | |
53 | +u8 ide_dma_sff_read_status(ide_hwif_t *hwif) | |
54 | +{ | |
55 | + unsigned long addr = hwif->dma_base + ATA_DMA_STATUS; | |
56 | + | |
57 | + if (hwif->host_flags & IDE_HFLAG_MMIO) | |
58 | + return readb((void __iomem *)addr); | |
59 | + else | |
60 | + return inb(addr); | |
61 | +} | |
62 | +EXPORT_SYMBOL_GPL(ide_dma_sff_read_status); | |
63 | + | |
53 | 64 | /** |
54 | 65 | * ide_dma_host_set - Enable/disable DMA on a host |
55 | 66 | * @drive: drive to control |
... | ... | @@ -62,7 +73,7 @@ |
62 | 73 | { |
63 | 74 | ide_hwif_t *hwif = drive->hwif; |
64 | 75 | u8 unit = drive->dn & 1; |
65 | - u8 dma_stat = hwif->tp_ops->read_sff_dma_status(hwif); | |
76 | + u8 dma_stat = hwif->dma_ops->dma_sff_read_status(hwif); | |
66 | 77 | |
67 | 78 | if (on) |
68 | 79 | dma_stat |= (1 << (5 + unit)); |
... | ... | @@ -200,7 +211,7 @@ |
200 | 211 | outb(reading, hwif->dma_base + ATA_DMA_CMD); |
201 | 212 | |
202 | 213 | /* read DMA status for INTR & ERROR flags */ |
203 | - dma_stat = hwif->tp_ops->read_sff_dma_status(hwif); | |
214 | + dma_stat = hwif->dma_ops->dma_sff_read_status(hwif); | |
204 | 215 | |
205 | 216 | /* clear INTR & ERROR flags */ |
206 | 217 | if (mmio) |
... | ... | @@ -232,7 +243,7 @@ |
232 | 243 | static int dma_timer_expiry(ide_drive_t *drive) |
233 | 244 | { |
234 | 245 | ide_hwif_t *hwif = drive->hwif; |
235 | - u8 dma_stat = hwif->tp_ops->read_sff_dma_status(hwif); | |
246 | + u8 dma_stat = hwif->dma_ops->dma_sff_read_status(hwif); | |
236 | 247 | |
237 | 248 | printk(KERN_WARNING "%s: %s: DMA status (0x%02x)\n", |
238 | 249 | drive->name, __func__, dma_stat); |
... | ... | @@ -305,7 +316,7 @@ |
305 | 316 | } |
306 | 317 | |
307 | 318 | /* get DMA status */ |
308 | - dma_stat = hwif->tp_ops->read_sff_dma_status(hwif); | |
319 | + dma_stat = hwif->dma_ops->dma_sff_read_status(hwif); | |
309 | 320 | |
310 | 321 | if (mmio) |
311 | 322 | /* clear the INTR & ERROR bits */ |
... | ... | @@ -331,7 +342,7 @@ |
331 | 342 | int ide_dma_test_irq(ide_drive_t *drive) |
332 | 343 | { |
333 | 344 | ide_hwif_t *hwif = drive->hwif; |
334 | - u8 dma_stat = hwif->tp_ops->read_sff_dma_status(hwif); | |
345 | + u8 dma_stat = hwif->dma_ops->dma_sff_read_status(hwif); | |
335 | 346 | |
336 | 347 | return (dma_stat & ATA_DMA_INTR) ? 1 : 0; |
337 | 348 | } |
... | ... | @@ -346,6 +357,7 @@ |
346 | 357 | .dma_test_irq = ide_dma_test_irq, |
347 | 358 | .dma_timeout = ide_dma_timeout, |
348 | 359 | .dma_lost_irq = ide_dma_lost_irq, |
360 | + .dma_sff_read_status = ide_dma_sff_read_status, | |
349 | 361 | }; |
350 | 362 | EXPORT_SYMBOL_GPL(sff_dma_ops); |
drivers/ide/ide-h8300.c
drivers/ide/ide-iops.c
... | ... | @@ -105,15 +105,6 @@ |
105 | 105 | } |
106 | 106 | EXPORT_SYMBOL_GPL(ide_read_altstatus); |
107 | 107 | |
108 | -u8 ide_read_sff_dma_status(ide_hwif_t *hwif) | |
109 | -{ | |
110 | - if (hwif->host_flags & IDE_HFLAG_MMIO) | |
111 | - return readb((void __iomem *)(hwif->dma_base + ATA_DMA_STATUS)); | |
112 | - else | |
113 | - return inb(hwif->dma_base + ATA_DMA_STATUS); | |
114 | -} | |
115 | -EXPORT_SYMBOL_GPL(ide_read_sff_dma_status); | |
116 | - | |
117 | 108 | void ide_set_irq(ide_hwif_t *hwif, int on) |
118 | 109 | { |
119 | 110 | u8 ctl = ATA_DEVCTL_OBS; |
... | ... | @@ -388,7 +379,6 @@ |
388 | 379 | .exec_command = ide_exec_command, |
389 | 380 | .read_status = ide_read_status, |
390 | 381 | .read_altstatus = ide_read_altstatus, |
391 | - .read_sff_dma_status = ide_read_sff_dma_status, | |
392 | 382 | |
393 | 383 | .set_irq = ide_set_irq, |
394 | 384 |
drivers/ide/ide-probe.c
... | ... | @@ -1229,6 +1229,8 @@ |
1229 | 1229 | if ((d->host_flags & IDE_HFLAG_NO_DMA) == 0) { |
1230 | 1230 | int rc; |
1231 | 1231 | |
1232 | + hwif->dma_ops = d->dma_ops; | |
1233 | + | |
1232 | 1234 | if (d->init_dma) |
1233 | 1235 | rc = d->init_dma(hwif, d); |
1234 | 1236 | else |
1235 | 1237 | |
... | ... | @@ -1236,12 +1238,13 @@ |
1236 | 1238 | |
1237 | 1239 | if (rc < 0) { |
1238 | 1240 | printk(KERN_INFO "%s: DMA disabled\n", hwif->name); |
1241 | + | |
1242 | + hwif->dma_ops = NULL; | |
1239 | 1243 | hwif->dma_base = 0; |
1240 | 1244 | hwif->swdma_mask = 0; |
1241 | 1245 | hwif->mwdma_mask = 0; |
1242 | 1246 | hwif->ultra_mask = 0; |
1243 | - } else if (d->dma_ops) | |
1244 | - hwif->dma_ops = d->dma_ops; | |
1247 | + } | |
1245 | 1248 | } |
1246 | 1249 | |
1247 | 1250 | if ((d->host_flags & IDE_HFLAG_SERIALIZE) || |
drivers/ide/it821x.c
drivers/ide/ns87415.c
... | ... | @@ -56,7 +56,7 @@ |
56 | 56 | return superio_ide_inb(hwif->io_ports.status_addr); |
57 | 57 | } |
58 | 58 | |
59 | -static u8 superio_read_sff_dma_status(ide_hwif_t *hwif) | |
59 | +static u8 superio_dma_sff_read_status(ide_hwif_t *hwif) | |
60 | 60 | { |
61 | 61 | return superio_ide_inb(hwif->dma_base + ATA_DMA_STATUS); |
62 | 62 | } |
... | ... | @@ -109,7 +109,6 @@ |
109 | 109 | .exec_command = ide_exec_command, |
110 | 110 | .read_status = superio_read_status, |
111 | 111 | .read_altstatus = ide_read_altstatus, |
112 | - .read_sff_dma_status = superio_read_sff_dma_status, | |
113 | 112 | |
114 | 113 | .set_irq = ide_set_irq, |
115 | 114 | |
... | ... | @@ -132,6 +131,8 @@ |
132 | 131 | tmp = superio_ide_inb(dma_stat); |
133 | 132 | outb(tmp | 0x66, dma_stat); |
134 | 133 | } |
134 | +#else | |
135 | +#define superio_dma_sff_read_status ide_dma_sff_read_status | |
135 | 136 | #endif |
136 | 137 | |
137 | 138 | static unsigned int ns87415_count = 0, ns87415_control[MAX_HWIFS] = { 0 }; |
... | ... | @@ -201,7 +202,7 @@ |
201 | 202 | u8 dma_stat = 0, dma_cmd = 0; |
202 | 203 | |
203 | 204 | drive->waiting_for_dma = 0; |
204 | - dma_stat = hwif->tp_ops->read_sff_dma_status(hwif); | |
205 | + dma_stat = hwif->dma_ops->dma_sff_read_status(hwif); | |
205 | 206 | /* get DMA command mode */ |
206 | 207 | dma_cmd = inb(hwif->dma_base + ATA_DMA_CMD); |
207 | 208 | /* stop DMA */ |
... | ... | @@ -308,6 +309,7 @@ |
308 | 309 | .dma_test_irq = ide_dma_test_irq, |
309 | 310 | .dma_lost_irq = ide_dma_lost_irq, |
310 | 311 | .dma_timeout = ide_dma_timeout, |
312 | + .dma_sff_read_status = superio_dma_sff_read_status, | |
311 | 313 | }; |
312 | 314 | |
313 | 315 | static const struct ide_port_info ns87415_chipset __devinitdata = { |
drivers/ide/pdc202xx_old.c
... | ... | @@ -337,6 +337,7 @@ |
337 | 337 | .dma_test_irq = pdc202xx_dma_test_irq, |
338 | 338 | .dma_lost_irq = pdc202xx_dma_lost_irq, |
339 | 339 | .dma_timeout = pdc202xx_dma_timeout, |
340 | + .dma_sff_read_status = ide_dma_sff_read_status, | |
340 | 341 | }; |
341 | 342 | |
342 | 343 | static const struct ide_dma_ops pdc2026x_dma_ops = { |
... | ... | @@ -348,6 +349,7 @@ |
348 | 349 | .dma_test_irq = pdc202xx_dma_test_irq, |
349 | 350 | .dma_lost_irq = pdc202xx_dma_lost_irq, |
350 | 351 | .dma_timeout = pdc202xx_dma_timeout, |
352 | + .dma_sff_read_status = ide_dma_sff_read_status, | |
351 | 353 | }; |
352 | 354 | |
353 | 355 | #define DECLARE_PDC2026X_DEV(udma, sectors) \ |
drivers/ide/pmac.c
drivers/ide/q40ide.c
drivers/ide/sc1200.c
drivers/ide/scc_pata.c
... | ... | @@ -143,7 +143,7 @@ |
143 | 143 | return (u8)in_be32((void *)hwif->io_ports.ctl_addr); |
144 | 144 | } |
145 | 145 | |
146 | -static u8 scc_read_sff_dma_status(ide_hwif_t *hwif) | |
146 | +static u8 scc_dma_sff_read_status(ide_hwif_t *hwif) | |
147 | 147 | { |
148 | 148 | return (u8)in_be32((void *)(hwif->dma_base + 4)); |
149 | 149 | } |
... | ... | @@ -853,7 +853,6 @@ |
853 | 853 | .exec_command = scc_exec_command, |
854 | 854 | .read_status = scc_read_status, |
855 | 855 | .read_altstatus = scc_read_altstatus, |
856 | - .read_sff_dma_status = scc_read_sff_dma_status, | |
857 | 856 | |
858 | 857 | .set_irq = scc_set_irq, |
859 | 858 | |
... | ... | @@ -880,6 +879,7 @@ |
880 | 879 | .dma_test_irq = scc_dma_test_irq, |
881 | 880 | .dma_lost_irq = ide_dma_lost_irq, |
882 | 881 | .dma_timeout = ide_dma_timeout, |
882 | + .dma_sff_read_status = scc_dma_sff_read_status, | |
883 | 883 | }; |
884 | 884 | |
885 | 885 | #define DECLARE_SCC_DEV(name_str) \ |
drivers/ide/setup-pci.c
... | ... | @@ -130,7 +130,7 @@ |
130 | 130 | * we tune the drive then try to grab DMA ownership if we want to be |
131 | 131 | * the DMA end. This has to be become dynamic to handle hot-plug. |
132 | 132 | */ |
133 | - dma_stat = hwif->tp_ops->read_sff_dma_status(hwif); | |
133 | + dma_stat = hwif->dma_ops->dma_sff_read_status(hwif); | |
134 | 134 | if ((dma_stat & 0x80) && hwif->mate && hwif->mate->dma_base) { |
135 | 135 | printk(KERN_INFO "%s %s: simplex device: DMA disabled\n", |
136 | 136 | d->name, pci_name(dev)); |
... | ... | @@ -377,6 +377,9 @@ |
377 | 377 | |
378 | 378 | hwif->dma_base = base; |
379 | 379 | |
380 | + if (hwif->dma_ops == NULL) | |
381 | + hwif->dma_ops = &sff_dma_ops; | |
382 | + | |
380 | 383 | if (ide_pci_check_simplex(hwif, d) < 0) |
381 | 384 | return -1; |
382 | 385 | |
... | ... | @@ -393,8 +396,6 @@ |
393 | 396 | |
394 | 397 | if (ide_allocate_dma_engine(hwif)) |
395 | 398 | return -1; |
396 | - | |
397 | - hwif->dma_ops = &sff_dma_ops; | |
398 | 399 | } |
399 | 400 | |
400 | 401 | return 0; |
drivers/ide/sgiioc4.c
drivers/ide/siimage.c
drivers/ide/sl82c105.c
... | ... | @@ -299,6 +299,7 @@ |
299 | 299 | .dma_test_irq = ide_dma_test_irq, |
300 | 300 | .dma_lost_irq = sl82c105_dma_lost_irq, |
301 | 301 | .dma_timeout = sl82c105_dma_timeout, |
302 | + .dma_sff_read_status = ide_dma_sff_read_status, | |
302 | 303 | }; |
303 | 304 | |
304 | 305 | static const struct ide_port_info sl82c105_chipset __devinitdata = { |
drivers/ide/tc86c001.c
... | ... | @@ -188,6 +188,7 @@ |
188 | 188 | .dma_test_irq = ide_dma_test_irq, |
189 | 189 | .dma_lost_irq = ide_dma_lost_irq, |
190 | 190 | .dma_timeout = ide_dma_timeout, |
191 | + .dma_sff_read_status = ide_dma_sff_read_status, | |
191 | 192 | }; |
192 | 193 | |
193 | 194 | static const struct ide_port_info tc86c001_chipset __devinitdata = { |
drivers/ide/tx4939ide.c
... | ... | @@ -397,6 +397,17 @@ |
397 | 397 | return found; |
398 | 398 | } |
399 | 399 | |
400 | +#ifdef __BIG_ENDIAN | |
401 | +static u8 tx4939ide_dma_sff_read_status(ide_hwif_t *hwif) | |
402 | +{ | |
403 | + void __iomem *base = TX4939IDE_BASE(hwif); | |
404 | + | |
405 | + return tx4939ide_readb(base, TX4939IDE_DMA_Stat); | |
406 | +} | |
407 | +#else | |
408 | +#define tx4939ide_dma_sff_read_status ide_dma_sff_read_status | |
409 | +#endif | |
410 | + | |
400 | 411 | static void tx4939ide_init_hwif(ide_hwif_t *hwif) |
401 | 412 | { |
402 | 413 | void __iomem *base = TX4939IDE_BASE(hwif); |
... | ... | @@ -443,13 +454,6 @@ |
443 | 454 | |
444 | 455 | #ifdef __BIG_ENDIAN |
445 | 456 | |
446 | -static u8 tx4939ide_read_sff_dma_status(ide_hwif_t *hwif) | |
447 | -{ | |
448 | - void __iomem *base = TX4939IDE_BASE(hwif); | |
449 | - | |
450 | - return tx4939ide_readb(base, TX4939IDE_DMA_Stat); | |
451 | -} | |
452 | - | |
453 | 457 | /* custom iops (independent from SWAP_IO_SPACE) */ |
454 | 458 | static u8 tx4939ide_inb(unsigned long port) |
455 | 459 | { |
... | ... | @@ -585,7 +589,6 @@ |
585 | 589 | .exec_command = ide_exec_command, |
586 | 590 | .read_status = ide_read_status, |
587 | 591 | .read_altstatus = ide_read_altstatus, |
588 | - .read_sff_dma_status = tx4939ide_read_sff_dma_status, | |
589 | 592 | |
590 | 593 | .set_irq = ide_set_irq, |
591 | 594 | |
... | ... | @@ -609,7 +612,6 @@ |
609 | 612 | .exec_command = ide_exec_command, |
610 | 613 | .read_status = ide_read_status, |
611 | 614 | .read_altstatus = ide_read_altstatus, |
612 | - .read_sff_dma_status = ide_read_sff_dma_status, | |
613 | 615 | |
614 | 616 | .set_irq = ide_set_irq, |
615 | 617 | |
... | ... | @@ -638,6 +640,7 @@ |
638 | 640 | .dma_test_irq = tx4939ide_dma_test_irq, |
639 | 641 | .dma_lost_irq = ide_dma_lost_irq, |
640 | 642 | .dma_timeout = ide_dma_timeout, |
643 | + .dma_sff_read_status = tx4939ide_dma_sff_read_status, | |
641 | 644 | }; |
642 | 645 | |
643 | 646 | static const struct ide_port_info tx4939ide_port_info __initdata = { |
include/linux/ide.h
... | ... | @@ -674,7 +674,6 @@ |
674 | 674 | void (*exec_command)(struct hwif_s *, u8); |
675 | 675 | u8 (*read_status)(struct hwif_s *); |
676 | 676 | u8 (*read_altstatus)(struct hwif_s *); |
677 | - u8 (*read_sff_dma_status)(struct hwif_s *); | |
678 | 677 | |
679 | 678 | void (*set_irq)(struct hwif_s *, int); |
680 | 679 | |
... | ... | @@ -735,6 +734,11 @@ |
735 | 734 | int (*dma_test_irq)(struct ide_drive_s *); |
736 | 735 | void (*dma_lost_irq)(struct ide_drive_s *); |
737 | 736 | void (*dma_timeout)(struct ide_drive_s *); |
737 | + /* | |
738 | + * The following method is optional and only required to be | |
739 | + * implemented for the SFF-8038i compatible controllers. | |
740 | + */ | |
741 | + u8 (*dma_sff_read_status)(struct hwif_s *); | |
738 | 742 | }; |
739 | 743 | |
740 | 744 | struct ide_host; |
... | ... | @@ -1177,7 +1181,6 @@ |
1177 | 1181 | void ide_exec_command(ide_hwif_t *, u8); |
1178 | 1182 | u8 ide_read_status(ide_hwif_t *); |
1179 | 1183 | u8 ide_read_altstatus(ide_hwif_t *); |
1180 | -u8 ide_read_sff_dma_status(ide_hwif_t *); | |
1181 | 1184 | |
1182 | 1185 | void ide_set_irq(ide_hwif_t *, int); |
1183 | 1186 | |
... | ... | @@ -1458,6 +1461,7 @@ |
1458 | 1461 | extern void ide_dma_start(ide_drive_t *); |
1459 | 1462 | int ide_dma_end(ide_drive_t *); |
1460 | 1463 | int ide_dma_test_irq(ide_drive_t *); |
1464 | +u8 ide_dma_sff_read_status(ide_hwif_t *); | |
1461 | 1465 | extern const struct ide_dma_ops sff_dma_ops; |
1462 | 1466 | #else |
1463 | 1467 | static inline int config_drive_for_dma(ide_drive_t *drive) { return 0; } |