From f77d4ff8506ca4f608052486d87f8a3ed03d5202 Mon Sep 17 00:00:00 2001 From: Alexey Kardashevskiy Date: Wed, 19 Oct 2016 10:05:26 +1100 Subject: [PATCH 01/73] pseries: Update SLOF firmware image to 20161019 The main changes are: * virtio-serial * booting speed imrovement * better PCI bridge support The complete changelog is: > virtio-serial: Fix compile error > scsi: Remove debug functions from scsi-loader.fs > scsi: Remove unused read-6 command > obp-tftp: Remove the ciregs-buffer > libnet: Simplify the net-load arguments passing > libnet: Simplify the Forth-to-C wrapper of ping() > Do not link libnet to net-snk anymore, and remove net-snk from board-qemu > Add a Forth-to-C wrapper for the ping command, too > Link libnet code to Paflof and add a wrapper for netboot() > Remember execution tokens of "write" and "read" for socket operations > Add virtio-serial device support > Generalize output banner write routine > Improve indentation in OF.fs > scsi: implement READ (16) command > rtas: Improve rtas-do-config-@ and rtas-do-config-! a little bit > libnet: Make netapps.h includable from .code files > libnet: Remove unused prototypes from netapps.h > libnet: Fix the printout of the ping command > libnet: Make sure to close sockets when we're done > scsi: implement read-capacity-16 > pci: Fix secondary and subordinate PCI bus enumeration with board-qemu > pci-phb: Fix stack underflow in phb-pci-walk-bridge > paflof: Add a read() function to read keyboard input > paflof: Add socket(), send() and recv() functions to paflof > paflof: Provide get_timer() and set_timer() helper functions > paflof: Add a write_mm_log helper function > paflof: Copy sbrk code from net-snk > paflof: Use CFLAGS from make.rules instead of completely redefining them > Do not include the FCode evaluator by default anymore > Source code beautification of board-qemu/slof/pci-interrupts.fs > Allow PCI devices in PCI bridge slots greater than 4 > Fix bad interrupt pin numbering in interrupt-map property of PCI bridges > Improve SLOF_alloc_mem_aligned() > instance: Fix set-my-args for empty arguments > Fix remaining compiler warnings in sloffs.c > Remove misleading padding fields from ROM header definition > Improve indentation in calculatecrc.h > Do not include calculatecrc.h from assembler files > Remove unused defines in calculatecrc.h > libnet: Re-initialize global variables at the beginning of tftp() > Remove dependency on cpu/@0 for booting > usb: Set XHCI slot speed according to port status > usb: Build correct route string for USB3 devices behind a hub > usb: Initialize USB3 devices on a hub and keep track of hub topology > usb: Increase amount of maximum slot IDs and add a sanity check > usb: Move XHCI port state arrays from header to .c file > tools: add copy functionality > tools: added support to sloffs to read from /dev/slof_flash > tools: added file append functionality > tools: use crc checking code from romfs/tools > tools: added initial version of sloffs > romfs: factored out crc code, to make it usable from other locations > tools: remove unused parts from the Makefile > usb-hid: Fix non-working comma key > fat-files: Fix access to FAT32 dir/files when cluster > 16-bits > virtio-net: fix ring handling in receive > net: Remove remainders of the MTFTP code > net: Move also files from clients/net-snk/app/netapps/ to lib/libnet/ > net: Move files from clients/net-snk/app/netlib/ to lib/libnet/ > net-snk: Get rid of netlib and netapps prefixes in include statements > usb-xhci: assign field4 before conditional > Improve F12 key handling in boot menu > Fix stack underflow that occurs with duplicated ESC in input > rtas-nvram: optimize erase > ipv6: Replace magic number 1500 with ETH_MTU_SIZE (i.e. 1518) > ipv6: Fix NULL pointer dereference in ip6addr_add() > ipv6: Fix memory leak in set_ipv6_address() / ip6_create_ll_address() > ipv6: Clear memory after malloc if necessary > ipv6: Fix possible NULL-pointer dereference in send_ipv6() > ping: use gateway address for routing > ping: add netmask in the ping argument > xhci: fix missing keys from keyboard > xhci: add memory barrier after filling the trb > loaders: Remove netflash command > boot: Remove legacy Forth words for network loading > base: Move cnt-bits and bcd-to-bin to board-js2x folder > base: Move huge-tftp-load variable to obp-tftp package > base: Remove unused IP address conversion functions > virtio: White space cleanup in virtio-9p.c > virtio: Add modern version 1.0 support to 9p driver > virtio: Set a proper name for virtio-9p device tree nodes > pci: Fix mistype in "unkown-bridge" > ipv6: Indent code with tabs, not with spaces > ipv6: send_ipv6() has to return after doing NDP > ipv6: Do not use unitialized MAC address array > ipv6: Add support for sending packets through a router > Remove unused sms code. > virtio-net: initialize to populate mac address > libbootmsg: Do not use '\b' characters when printing checkpoints > dev-null: The "read" function has to return 0 if nothing has been read Signed-off-by: Alexey Kardashevskiy Signed-off-by: David Gibson --- pc-bios/README | 2 +- pc-bios/slof.bin | Bin 923832 -> 898232 bytes roms/SLOF | 2 +- 3 files changed, 2 insertions(+), 2 deletions(-) diff --git a/pc-bios/README b/pc-bios/README index 5a8a93193e..779192eb7c 100644 --- a/pc-bios/README +++ b/pc-bios/README @@ -17,7 +17,7 @@ - SLOF (Slimline Open Firmware) is a free IEEE 1275 Open Firmware implementation for certain IBM POWER hardware. The sources are at https://github.com/aik/SLOF, and the image currently in qemu is - built from git tag qemu-slof-20160223. + built from git tag qemu-slof-20161019. - sgabios (the Serial Graphics Adapter option ROM) provides a means for legacy x86 software to communicate with an attached serial console as diff --git a/pc-bios/slof.bin b/pc-bios/slof.bin index f2384939efd167dad1153ac744d0624ad8591cfa..30ce7ac384146c1a30c2b3067ccd532efe78f189 100644 GIT binary patch delta 305765 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 diff --git a/roms/SLOF b/roms/SLOF index e3d05727a0..efd65f4992 160000 --- a/roms/SLOF +++ b/roms/SLOF @@ -1 +1 @@ -Subproject commit e3d05727a074619fc12d0a67f05cf2c42c875cce +Subproject commit efd65f49929d7db775b26066d538c8120ae3db94 From b1fc72f0fb0aeae4194ff89c454aabe019983d0d Mon Sep 17 00:00:00 2001 From: Benjamin Herrenschmidt Date: Mon, 17 Oct 2016 22:33:14 +0200 Subject: [PATCH 02/73] ppc/xics: Add xics to the monitor "info pic" command MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Useful to debug interrupt problems. Signed-off-by: Benjamin Herrenschmidt [clg: - updated for qemu-2.7 - added a test on ->irqs as it is not necessarily allocated (PHB3_MSI) - removed static variable g_xics and replace with a loop on all children to find the xics objects. - rebased on InterruptStatsProvider interface ] Signed-off-by: Cédric Le Goater Signed-off-by: David Gibson --- hw/intc/xics.c | 49 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 49 insertions(+) diff --git a/hw/intc/xics.c b/hw/intc/xics.c index f40b00003a..7fac964fbd 100644 --- a/hw/intc/xics.c +++ b/hw/intc/xics.c @@ -35,6 +35,8 @@ #include "hw/ppc/xics.h" #include "qemu/error-report.h" #include "qapi/visitor.h" +#include "monitor/monitor.h" +#include "hw/intc/intc.h" int xics_get_cpu_index_by_dt_id(int cpu_dt_id) { @@ -90,6 +92,47 @@ void xics_cpu_setup(XICSState *xics, PowerPCCPU *cpu) } } +static void xics_common_pic_print_info(InterruptStatsProvider *obj, + Monitor *mon) +{ + XICSState *xics = XICS_COMMON(obj); + ICSState *ics; + uint32_t i; + + for (i = 0; i < xics->nr_servers; i++) { + ICPState *icp = &xics->ss[i]; + + if (!icp->output) { + continue; + } + monitor_printf(mon, "CPU %d XIRR=%08x (%p) PP=%02x MFRR=%02x\n", + i, icp->xirr, icp->xirr_owner, + icp->pending_priority, icp->mfrr); + } + + QLIST_FOREACH(ics, &xics->ics, list) { + monitor_printf(mon, "ICS %4x..%4x %p\n", + ics->offset, ics->offset + ics->nr_irqs - 1, ics); + + if (!ics->irqs) { + continue; + } + + for (i = 0; i < ics->nr_irqs; i++) { + ICSIRQState *irq = ics->irqs + i; + + if (!(irq->flags & XICS_FLAGS_IRQ_MASK)) { + continue; + } + monitor_printf(mon, " %4x %s %02x %02x\n", + ics->offset + i, + (irq->flags & XICS_FLAGS_IRQ_LSI) ? + "LSI" : "MSI", + irq->priority, irq->status); + } + } +} + /* * XICS Common class - parent for emulated XICS and KVM-XICS */ @@ -190,8 +233,10 @@ static void xics_common_initfn(Object *obj) static void xics_common_class_init(ObjectClass *oc, void *data) { DeviceClass *dc = DEVICE_CLASS(oc); + InterruptStatsProviderClass *ic = INTERRUPT_STATS_PROVIDER_CLASS(oc); dc->reset = xics_common_reset; + ic->print_info = xics_common_pic_print_info; } static const TypeInfo xics_common_info = { @@ -201,6 +246,10 @@ static const TypeInfo xics_common_info = { .class_size = sizeof(XICSStateClass), .instance_init = xics_common_initfn, .class_init = xics_common_class_init, + .interfaces = (InterfaceInfo[]) { + { TYPE_INTERRUPT_STATS_PROVIDER }, + { } + }, }; /* From f62e0bbb39eec088ff4fbe6a7ec38af51fac5e94 Mon Sep 17 00:00:00 2001 From: Laurent Vivier Date: Mon, 17 Oct 2016 12:30:19 +0200 Subject: [PATCH 03/73] tests: fix memory leak in virtio-scsi-test vs is allocated in qvirtio_scsi_pci_init() and never freed. Signed-off-by: Laurent Vivier Reviewed-by: Greg Kurz Reviewed-by: Thomas Huth Signed-off-by: David Gibson --- tests/virtio-scsi-test.c | 1 + 1 file changed, 1 insertion(+) diff --git a/tests/virtio-scsi-test.c b/tests/virtio-scsi-test.c index 79088bb249..94d75b1493 100644 --- a/tests/virtio-scsi-test.c +++ b/tests/virtio-scsi-test.c @@ -64,6 +64,7 @@ static void qvirtio_scsi_pci_free(QVirtIOSCSI *vs) qvirtio_pci_device_disable(container_of(vs->dev, QVirtioPCIDevice, vdev)); g_free(vs->dev); qpci_free_pc(vs->bus); + g_free(vs); } static uint64_t qvirtio_scsi_alloc(QVirtIOSCSI *vs, size_t alloc_size, From 458f3b2c953bdc7110896cb3691251023652523f Mon Sep 17 00:00:00 2001 From: Laurent Vivier Date: Mon, 17 Oct 2016 12:30:20 +0200 Subject: [PATCH 04/73] tests: don't check if qtest_spapr_boot() returns NULL qtest_spapr_boot()/qtest_pc_boot()/qtest_boot() call qtest_vboot() and qtest_vboot() calls g_malloc(), and g_malloc() never fails: if memory allocation fails, the application is terminated. Signed-off-by: Laurent Vivier Reviewed-by: Thomas Huth Reviewed-by: Greg Kurz Signed-off-by: David Gibson --- tests/libqos/libqos.c | 2 ++ tests/rtas-test.c | 1 - 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/tests/libqos/libqos.c b/tests/libqos/libqos.c index 7abb48254e..6226546c28 100644 --- a/tests/libqos/libqos.c +++ b/tests/libqos/libqos.c @@ -10,6 +10,8 @@ /** * Launch QEMU with the given command line, * and then set up interrupts and our guest malloc interface. + * Never returns NULL: + * Terminates the application in case an error is encountered. */ QOSState *qtest_vboot(QOSOps *ops, const char *cmdline_fmt, va_list ap) { diff --git a/tests/rtas-test.c b/tests/rtas-test.c index ba0867afbd..276c87ef84 100644 --- a/tests/rtas-test.c +++ b/tests/rtas-test.c @@ -14,7 +14,6 @@ static void test_rtas_get_time_of_day(void) time_t t1, t2; qs = qtest_spapr_boot("-machine pseries"); - g_assert(qs != NULL); t1 = time(NULL); ret = qrtas_get_time_of_day(qs->alloc, &tm, &ns); From 6b9cdf4cf1fd52c1a59a7640a02a718176bfd217 Mon Sep 17 00:00:00 2001 From: Laurent Vivier Date: Mon, 17 Oct 2016 12:30:21 +0200 Subject: [PATCH 05/73] tests: move QVirtioBus pointer into QVirtioDevice This allows to not have to pass bus and device for every virtio functions. Signed-off-by: Laurent Vivier Reviewed-by: Greg Kurz Reviewed-by: Thomas Huth [dwg: Fix style nit] Signed-off-by: David Gibson --- tests/libqos/virtio-mmio.c | 1 + tests/libqos/virtio-pci.c | 2 + tests/libqos/virtio.c | 78 +++++++++----------- tests/libqos/virtio.h | 47 ++++++------ tests/vhost-user-test.c | 33 ++++----- tests/virtio-9p-test.c | 15 ++-- tests/virtio-blk-test.c | 147 +++++++++++++++++-------------------- tests/virtio-net-test.c | 59 +++++++-------- tests/virtio-scsi-test.c | 17 ++--- 9 files changed, 184 insertions(+), 215 deletions(-) diff --git a/tests/libqos/virtio-mmio.c b/tests/libqos/virtio-mmio.c index 0cab38f296..bced6803e6 100644 --- a/tests/libqos/virtio-mmio.c +++ b/tests/libqos/virtio-mmio.c @@ -199,6 +199,7 @@ QVirtioMMIODevice *qvirtio_mmio_init_device(uint64_t addr, uint32_t page_size) dev->addr = addr; dev->page_size = page_size; dev->vdev.device_type = readl(addr + QVIRTIO_MMIO_DEVICE_ID); + dev->vdev.bus = &qvirtio_mmio; writel(addr + QVIRTIO_MMIO_GUEST_PAGE_SIZE, page_size); diff --git a/tests/libqos/virtio-pci.c b/tests/libqos/virtio-pci.c index 6e005c1835..bbfed58dcf 100644 --- a/tests/libqos/virtio-pci.c +++ b/tests/libqos/virtio-pci.c @@ -286,6 +286,8 @@ QVirtioPCIDevice *qvirtio_pci_device_find(QPCIBus *bus, uint16_t device_type) QVirtioPCIDevice *dev = NULL; qvirtio_pci_foreach(bus, device_type, qvirtio_pci_assign_device, &dev); + dev->vdev.bus = &qvirtio_pci; + return dev; } diff --git a/tests/libqos/virtio.c b/tests/libqos/virtio.c index 105bccecaa..ec30cb99b2 100644 --- a/tests/libqos/virtio.c +++ b/tests/libqos/virtio.c @@ -13,45 +13,40 @@ #include "standard-headers/linux/virtio_config.h" #include "standard-headers/linux/virtio_ring.h" -uint8_t qvirtio_config_readb(const QVirtioBus *bus, QVirtioDevice *d, - uint64_t addr) +uint8_t qvirtio_config_readb(QVirtioDevice *d, uint64_t addr) { - return bus->config_readb(d, addr); + return d->bus->config_readb(d, addr); } -uint16_t qvirtio_config_readw(const QVirtioBus *bus, QVirtioDevice *d, - uint64_t addr) +uint16_t qvirtio_config_readw(QVirtioDevice *d, uint64_t addr) { - return bus->config_readw(d, addr); + return d->bus->config_readw(d, addr); } -uint32_t qvirtio_config_readl(const QVirtioBus *bus, QVirtioDevice *d, - uint64_t addr) +uint32_t qvirtio_config_readl(QVirtioDevice *d, uint64_t addr) { - return bus->config_readl(d, addr); + return d->bus->config_readl(d, addr); } -uint64_t qvirtio_config_readq(const QVirtioBus *bus, QVirtioDevice *d, - uint64_t addr) +uint64_t qvirtio_config_readq(QVirtioDevice *d, uint64_t addr) { - return bus->config_readq(d, addr); + return d->bus->config_readq(d, addr); } -uint32_t qvirtio_get_features(const QVirtioBus *bus, QVirtioDevice *d) +uint32_t qvirtio_get_features(QVirtioDevice *d) { - return bus->get_features(d); + return d->bus->get_features(d); } -void qvirtio_set_features(const QVirtioBus *bus, QVirtioDevice *d, - uint32_t features) +void qvirtio_set_features(QVirtioDevice *d, uint32_t features) { - bus->set_features(d, features); + d->bus->set_features(d, features); } -QVirtQueue *qvirtqueue_setup(const QVirtioBus *bus, QVirtioDevice *d, - QGuestAllocator *alloc, uint16_t index) +QVirtQueue *qvirtqueue_setup(QVirtioDevice *d, + QGuestAllocator *alloc, uint16_t index) { - return bus->virtqueue_setup(d, alloc, index); + return d->bus->virtqueue_setup(d, alloc, index); } void qvirtqueue_cleanup(const QVirtioBus *bus, QVirtQueue *vq, @@ -60,40 +55,40 @@ void qvirtqueue_cleanup(const QVirtioBus *bus, QVirtQueue *vq, return bus->virtqueue_cleanup(vq, alloc); } -void qvirtio_reset(const QVirtioBus *bus, QVirtioDevice *d) +void qvirtio_reset(QVirtioDevice *d) { - bus->set_status(d, 0); - g_assert_cmphex(bus->get_status(d), ==, 0); + d->bus->set_status(d, 0); + g_assert_cmphex(d->bus->get_status(d), ==, 0); } -void qvirtio_set_acknowledge(const QVirtioBus *bus, QVirtioDevice *d) +void qvirtio_set_acknowledge(QVirtioDevice *d) { - bus->set_status(d, bus->get_status(d) | VIRTIO_CONFIG_S_ACKNOWLEDGE); - g_assert_cmphex(bus->get_status(d), ==, VIRTIO_CONFIG_S_ACKNOWLEDGE); + d->bus->set_status(d, d->bus->get_status(d) | VIRTIO_CONFIG_S_ACKNOWLEDGE); + g_assert_cmphex(d->bus->get_status(d), ==, VIRTIO_CONFIG_S_ACKNOWLEDGE); } -void qvirtio_set_driver(const QVirtioBus *bus, QVirtioDevice *d) +void qvirtio_set_driver(QVirtioDevice *d) { - bus->set_status(d, bus->get_status(d) | VIRTIO_CONFIG_S_DRIVER); - g_assert_cmphex(bus->get_status(d), ==, + d->bus->set_status(d, d->bus->get_status(d) | VIRTIO_CONFIG_S_DRIVER); + g_assert_cmphex(d->bus->get_status(d), ==, VIRTIO_CONFIG_S_DRIVER | VIRTIO_CONFIG_S_ACKNOWLEDGE); } -void qvirtio_set_driver_ok(const QVirtioBus *bus, QVirtioDevice *d) +void qvirtio_set_driver_ok(QVirtioDevice *d) { - bus->set_status(d, bus->get_status(d) | VIRTIO_CONFIG_S_DRIVER_OK); - g_assert_cmphex(bus->get_status(d), ==, VIRTIO_CONFIG_S_DRIVER_OK | + d->bus->set_status(d, d->bus->get_status(d) | VIRTIO_CONFIG_S_DRIVER_OK); + g_assert_cmphex(d->bus->get_status(d), ==, VIRTIO_CONFIG_S_DRIVER_OK | VIRTIO_CONFIG_S_DRIVER | VIRTIO_CONFIG_S_ACKNOWLEDGE); } -void qvirtio_wait_queue_isr(const QVirtioBus *bus, QVirtioDevice *d, +void qvirtio_wait_queue_isr(QVirtioDevice *d, QVirtQueue *vq, gint64 timeout_us) { gint64 start_time = g_get_monotonic_time(); for (;;) { clock_step(100); - if (bus->get_queue_isr_status(d, vq)) { + if (d->bus->get_queue_isr_status(d, vq)) { return; } g_assert(g_get_monotonic_time() - start_time <= timeout_us); @@ -105,8 +100,7 @@ void qvirtio_wait_queue_isr(const QVirtioBus *bus, QVirtioDevice *d, * The virtqueue interrupt must not be raised, making this useful for testing * event_index functionality. */ -uint8_t qvirtio_wait_status_byte_no_isr(const QVirtioBus *bus, - QVirtioDevice *d, +uint8_t qvirtio_wait_status_byte_no_isr(QVirtioDevice *d, QVirtQueue *vq, uint64_t addr, gint64 timeout_us) @@ -116,20 +110,19 @@ uint8_t qvirtio_wait_status_byte_no_isr(const QVirtioBus *bus, while ((val = readb(addr)) == 0xff) { clock_step(100); - g_assert(!bus->get_queue_isr_status(d, vq)); + g_assert(!d->bus->get_queue_isr_status(d, vq)); g_assert(g_get_monotonic_time() - start_time <= timeout_us); } return val; } -void qvirtio_wait_config_isr(const QVirtioBus *bus, QVirtioDevice *d, - gint64 timeout_us) +void qvirtio_wait_config_isr(QVirtioDevice *d, gint64 timeout_us) { gint64 start_time = g_get_monotonic_time(); for (;;) { clock_step(100); - if (bus->get_config_isr_status(d)) { + if (d->bus->get_config_isr_status(d)) { return; } g_assert(g_get_monotonic_time() - start_time <= timeout_us); @@ -253,8 +246,7 @@ uint32_t qvirtqueue_add_indirect(QVirtQueue *vq, QVRingIndirectDesc *indirect) return vq->free_head++; /* Return and increase, in this order */ } -void qvirtqueue_kick(const QVirtioBus *bus, QVirtioDevice *d, QVirtQueue *vq, - uint32_t free_head) +void qvirtqueue_kick(QVirtioDevice *d, QVirtQueue *vq, uint32_t free_head) { /* vq->avail->idx */ uint16_t idx = readw(vq->avail + 2); @@ -276,7 +268,7 @@ void qvirtqueue_kick(const QVirtioBus *bus, QVirtioDevice *d, QVirtQueue *vq, /* < 1 because we add elements to avail queue one by one */ if ((flags & VRING_USED_F_NO_NOTIFY) == 0 && (!vq->event || (uint16_t)(idx-avail_event) < 1)) { - bus->virtqueue_kick(d, vq); + d->bus->virtqueue_kick(d, vq); } } diff --git a/tests/libqos/virtio.h b/tests/libqos/virtio.h index 0250842bf2..ac4669a11b 100644 --- a/tests/libqos/virtio.h +++ b/tests/libqos/virtio.h @@ -15,7 +15,10 @@ #define QVIRTIO_F_BAD_FEATURE 0x40000000 +typedef struct QVirtioBus QVirtioBus; + typedef struct QVirtioDevice { + const QVirtioBus *bus; /* Device type */ uint16_t device_type; } QVirtioDevice; @@ -39,7 +42,7 @@ typedef struct QVRingIndirectDesc { uint16_t elem; } QVRingIndirectDesc; -typedef struct QVirtioBus { +struct QVirtioBus { uint8_t (*config_readb)(QVirtioDevice *d, uint64_t addr); uint16_t (*config_readw)(QVirtioDevice *d, uint64_t addr); uint32_t (*config_readl)(QVirtioDevice *d, uint64_t addr); @@ -84,7 +87,7 @@ typedef struct QVirtioBus { /* Notify changes in virtqueue */ void (*virtqueue_kick)(QVirtioDevice *d, QVirtQueue *vq); -} QVirtioBus; +}; static inline uint32_t qvring_size(uint32_t num, uint32_t align) { @@ -93,34 +96,27 @@ static inline uint32_t qvring_size(uint32_t num, uint32_t align) + sizeof(uint16_t) * 3 + sizeof(struct vring_used_elem) * num; } -uint8_t qvirtio_config_readb(const QVirtioBus *bus, QVirtioDevice *d, - uint64_t addr); -uint16_t qvirtio_config_readw(const QVirtioBus *bus, QVirtioDevice *d, - uint64_t addr); -uint32_t qvirtio_config_readl(const QVirtioBus *bus, QVirtioDevice *d, - uint64_t addr); -uint64_t qvirtio_config_readq(const QVirtioBus *bus, QVirtioDevice *d, - uint64_t addr); -uint32_t qvirtio_get_features(const QVirtioBus *bus, QVirtioDevice *d); -void qvirtio_set_features(const QVirtioBus *bus, QVirtioDevice *d, - uint32_t features); +uint8_t qvirtio_config_readb(QVirtioDevice *d, uint64_t addr); +uint16_t qvirtio_config_readw(QVirtioDevice *d, uint64_t addr); +uint32_t qvirtio_config_readl(QVirtioDevice *d, uint64_t addr); +uint64_t qvirtio_config_readq(QVirtioDevice *d, uint64_t addr); +uint32_t qvirtio_get_features(QVirtioDevice *d); +void qvirtio_set_features(QVirtioDevice *d, uint32_t features); -void qvirtio_reset(const QVirtioBus *bus, QVirtioDevice *d); -void qvirtio_set_acknowledge(const QVirtioBus *bus, QVirtioDevice *d); -void qvirtio_set_driver(const QVirtioBus *bus, QVirtioDevice *d); -void qvirtio_set_driver_ok(const QVirtioBus *bus, QVirtioDevice *d); +void qvirtio_reset(QVirtioDevice *d); +void qvirtio_set_acknowledge(QVirtioDevice *d); +void qvirtio_set_driver(QVirtioDevice *d); +void qvirtio_set_driver_ok(QVirtioDevice *d); -void qvirtio_wait_queue_isr(const QVirtioBus *bus, QVirtioDevice *d, +void qvirtio_wait_queue_isr(QVirtioDevice *d, QVirtQueue *vq, gint64 timeout_us); -uint8_t qvirtio_wait_status_byte_no_isr(const QVirtioBus *bus, - QVirtioDevice *d, +uint8_t qvirtio_wait_status_byte_no_isr(QVirtioDevice *d, QVirtQueue *vq, uint64_t addr, gint64 timeout_us); -void qvirtio_wait_config_isr(const QVirtioBus *bus, QVirtioDevice *d, - gint64 timeout_us); -QVirtQueue *qvirtqueue_setup(const QVirtioBus *bus, QVirtioDevice *d, - QGuestAllocator *alloc, uint16_t index); +void qvirtio_wait_config_isr(QVirtioDevice *d, gint64 timeout_us); +QVirtQueue *qvirtqueue_setup(QVirtioDevice *d, + QGuestAllocator *alloc, uint16_t index); void qvirtqueue_cleanup(const QVirtioBus *bus, QVirtQueue *vq, QGuestAllocator *alloc); @@ -132,8 +128,7 @@ void qvring_indirect_desc_add(QVRingIndirectDesc *indirect, uint64_t data, uint32_t qvirtqueue_add(QVirtQueue *vq, uint64_t data, uint32_t len, bool write, bool next); uint32_t qvirtqueue_add_indirect(QVirtQueue *vq, QVRingIndirectDesc *indirect); -void qvirtqueue_kick(const QVirtioBus *bus, QVirtioDevice *d, QVirtQueue *vq, - uint32_t free_head); +void qvirtqueue_kick(QVirtioDevice *d, QVirtQueue *vq, uint32_t free_head); void qvirtqueue_set_used_event(QVirtQueue *vq, uint16_t idx); #endif diff --git a/tests/vhost-user-test.c b/tests/vhost-user-test.c index a7f06291cb..e4b2900898 100644 --- a/tests/vhost-user-test.c +++ b/tests/vhost-user-test.c @@ -172,15 +172,15 @@ static void init_virtio_dev(TestServer *s) g_assert_nonnull(dev); qvirtio_pci_device_enable(dev); - qvirtio_reset(&qvirtio_pci, &dev->vdev); - qvirtio_set_acknowledge(&qvirtio_pci, &dev->vdev); - qvirtio_set_driver(&qvirtio_pci, &dev->vdev); + qvirtio_reset(&dev->vdev); + qvirtio_set_acknowledge(&dev->vdev); + qvirtio_set_driver(&dev->vdev); - features = qvirtio_get_features(&qvirtio_pci, &dev->vdev); + features = qvirtio_get_features(&dev->vdev); features = features & VIRTIO_NET_F_MAC; - qvirtio_set_features(&qvirtio_pci, &dev->vdev, features); + qvirtio_set_features(&dev->vdev, features); - qvirtio_set_driver_ok(&qvirtio_pci, &dev->vdev); + qvirtio_set_driver_ok(&dev->vdev); } static void wait_for_fds(TestServer *s) @@ -847,24 +847,24 @@ static QVirtioPCIDevice *virtio_net_pci_init(QPCIBus *bus, int slot) g_assert_cmphex(dev->vdev.device_type, ==, VIRTIO_ID_NET); qvirtio_pci_device_enable(dev); - qvirtio_reset(&qvirtio_pci, &dev->vdev); - qvirtio_set_acknowledge(&qvirtio_pci, &dev->vdev); - qvirtio_set_driver(&qvirtio_pci, &dev->vdev); + qvirtio_reset(&dev->vdev); + qvirtio_set_acknowledge(&dev->vdev); + qvirtio_set_driver(&dev->vdev); return dev; } -static void driver_init(const QVirtioBus *bus, QVirtioDevice *dev) +static void driver_init(QVirtioDevice *dev) { uint32_t features; - features = qvirtio_get_features(bus, dev); + features = qvirtio_get_features(dev); features = features & ~(QVIRTIO_F_BAD_FEATURE | (1u << VIRTIO_RING_F_INDIRECT_DESC) | (1u << VIRTIO_RING_F_EVENT_IDX)); - qvirtio_set_features(bus, dev, features); + qvirtio_set_features(dev, features); - qvirtio_set_driver_ok(bus, dev); + qvirtio_set_driver_ok(dev); } #define PCI_SLOT 0x04 @@ -896,16 +896,15 @@ static void test_multiqueue(void) alloc = pc_alloc_init(); for (i = 0; i < queues * 2; i++) { - vq[i] = (QVirtQueuePCI *)qvirtqueue_setup(&qvirtio_pci, &dev->vdev, - alloc, i); + vq[i] = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, i); } - driver_init(&qvirtio_pci, &dev->vdev); + driver_init(&dev->vdev); wait_for_rings_started(s, queues * 2); /* End test */ for (i = 0; i < queues * 2; i++) { - qvirtqueue_cleanup(&qvirtio_pci, &vq[i]->vq, alloc); + qvirtqueue_cleanup(dev->vdev.bus, &vq[i]->vq, alloc); } pc_alloc_uninit(alloc); qvirtio_pci_device_disable(dev); diff --git a/tests/virtio-9p-test.c b/tests/virtio-9p-test.c index e8b21967d8..2341622a3b 100644 --- a/tests/virtio-9p-test.c +++ b/tests/virtio-9p-test.c @@ -71,17 +71,17 @@ static QVirtIO9P *qvirtio_9p_pci_init(void) v9p->dev = (QVirtioDevice *) dev; qvirtio_pci_device_enable(dev); - qvirtio_reset(&qvirtio_pci, v9p->dev); - qvirtio_set_acknowledge(&qvirtio_pci, v9p->dev); - qvirtio_set_driver(&qvirtio_pci, v9p->dev); + qvirtio_reset(v9p->dev); + qvirtio_set_acknowledge(v9p->dev); + qvirtio_set_driver(v9p->dev); - v9p->vq = qvirtqueue_setup(&qvirtio_pci, v9p->dev, v9p->alloc, 0); + v9p->vq = qvirtqueue_setup(v9p->dev, v9p->alloc, 0); return v9p; } static void qvirtio_9p_pci_free(QVirtIO9P *v9p) { - qvirtqueue_cleanup(&qvirtio_pci, v9p->vq, v9p->alloc); + qvirtqueue_cleanup(v9p->dev->bus, v9p->vq, v9p->alloc); pc_alloc_uninit(v9p->alloc); qvirtio_pci_device_disable(container_of(v9p->dev, QVirtioPCIDevice, vdev)); g_free(v9p->dev); @@ -101,15 +101,14 @@ static void pci_basic_config(void) v9p = qvirtio_9p_pci_init(); addr = ((QVirtioPCIDevice *) v9p->dev)->addr + VIRTIO_PCI_CONFIG_OFF(false); - tag_len = qvirtio_config_readw(&qvirtio_pci, v9p->dev, + tag_len = qvirtio_config_readw(v9p->dev, (uint64_t)(uintptr_t)addr); g_assert_cmpint(tag_len, ==, strlen(mount_tag)); addr += sizeof(uint16_t); tag = g_malloc(tag_len); for (i = 0; i < tag_len; i++) { - tag[i] = qvirtio_config_readb(&qvirtio_pci, v9p->dev, - (uint64_t)(uintptr_t)addr + i); + tag[i] = qvirtio_config_readb(v9p->dev, (uint64_t)(uintptr_t)addr + i); } g_assert_cmpmem(tag, tag_len, mount_tag, tag_len); g_free(tag); diff --git a/tests/virtio-blk-test.c b/tests/virtio-blk-test.c index 0506917341..9a6f2cff97 100644 --- a/tests/virtio-blk-test.c +++ b/tests/virtio-blk-test.c @@ -110,9 +110,9 @@ static QVirtioPCIDevice *virtio_blk_pci_init(QPCIBus *bus, int slot) g_assert_cmphex(dev->pdev->devfn, ==, ((slot << 3) | PCI_FN)); qvirtio_pci_device_enable(dev); - qvirtio_reset(&qvirtio_pci, &dev->vdev); - qvirtio_set_acknowledge(&qvirtio_pci, &dev->vdev); - qvirtio_set_driver(&qvirtio_pci, &dev->vdev); + qvirtio_reset(&dev->vdev); + qvirtio_set_acknowledge(&dev->vdev); + qvirtio_set_driver(&dev->vdev); return dev; } @@ -150,8 +150,8 @@ static uint64_t virtio_blk_request(QGuestAllocator *alloc, QVirtioBlkReq *req, return addr; } -static void test_basic(const QVirtioBus *bus, QVirtioDevice *dev, - QGuestAllocator *alloc, QVirtQueue *vq, uint64_t device_specific) +static void test_basic(QVirtioDevice *dev, QGuestAllocator *alloc, + QVirtQueue *vq, uint64_t device_specific) { QVirtioBlkReq req; uint64_t req_addr; @@ -161,18 +161,18 @@ static void test_basic(const QVirtioBus *bus, QVirtioDevice *dev, uint8_t status; char *data; - capacity = qvirtio_config_readq(bus, dev, device_specific); + capacity = qvirtio_config_readq(dev, device_specific); g_assert_cmpint(capacity, ==, TEST_IMAGE_SIZE / 512); - features = qvirtio_get_features(bus, dev); + features = qvirtio_get_features(dev); features = features & ~(QVIRTIO_F_BAD_FEATURE | (1u << VIRTIO_RING_F_INDIRECT_DESC) | (1u << VIRTIO_RING_F_EVENT_IDX) | (1u << VIRTIO_BLK_F_SCSI)); - qvirtio_set_features(bus, dev, features); + qvirtio_set_features(dev, features); - qvirtio_set_driver_ok(bus, dev); + qvirtio_set_driver_ok(dev); /* Write and read with 3 descriptor layout */ /* Write request */ @@ -190,9 +190,9 @@ static void test_basic(const QVirtioBus *bus, QVirtioDevice *dev, qvirtqueue_add(vq, req_addr + 16, 512, false, true); qvirtqueue_add(vq, req_addr + 528, 1, true, false); - qvirtqueue_kick(bus, dev, vq, free_head); + qvirtqueue_kick(dev, vq, free_head); - qvirtio_wait_queue_isr(bus, dev, vq, QVIRTIO_BLK_TIMEOUT_US); + qvirtio_wait_queue_isr(dev, vq, QVIRTIO_BLK_TIMEOUT_US); status = readb(req_addr + 528); g_assert_cmpint(status, ==, 0); @@ -212,9 +212,9 @@ static void test_basic(const QVirtioBus *bus, QVirtioDevice *dev, qvirtqueue_add(vq, req_addr + 16, 512, true, true); qvirtqueue_add(vq, req_addr + 528, 1, true, false); - qvirtqueue_kick(bus, dev, vq, free_head); + qvirtqueue_kick(dev, vq, free_head); - qvirtio_wait_queue_isr(bus, dev, vq, QVIRTIO_BLK_TIMEOUT_US); + qvirtio_wait_queue_isr(dev, vq, QVIRTIO_BLK_TIMEOUT_US); status = readb(req_addr + 528); g_assert_cmpint(status, ==, 0); @@ -240,9 +240,9 @@ static void test_basic(const QVirtioBus *bus, QVirtioDevice *dev, free_head = qvirtqueue_add(vq, req_addr, 528, false, true); qvirtqueue_add(vq, req_addr + 528, 1, true, false); - qvirtqueue_kick(bus, dev, vq, free_head); + qvirtqueue_kick(dev, vq, free_head); - qvirtio_wait_queue_isr(bus, dev, vq, QVIRTIO_BLK_TIMEOUT_US); + qvirtio_wait_queue_isr(dev, vq, QVIRTIO_BLK_TIMEOUT_US); status = readb(req_addr + 528); g_assert_cmpint(status, ==, 0); @@ -261,9 +261,9 @@ static void test_basic(const QVirtioBus *bus, QVirtioDevice *dev, free_head = qvirtqueue_add(vq, req_addr, 16, false, true); qvirtqueue_add(vq, req_addr + 16, 513, true, false); - qvirtqueue_kick(bus, dev, vq, free_head); + qvirtqueue_kick(dev, vq, free_head); - qvirtio_wait_queue_isr(bus, dev, vq, QVIRTIO_BLK_TIMEOUT_US); + qvirtio_wait_queue_isr(dev, vq, QVIRTIO_BLK_TIMEOUT_US); status = readb(req_addr + 528); g_assert_cmpint(status, ==, 0); @@ -288,17 +288,15 @@ static void pci_basic(void) dev = virtio_blk_pci_init(bus, PCI_SLOT); alloc = pc_alloc_init(); - vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&qvirtio_pci, &dev->vdev, - alloc, 0); + vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, 0); /* MSI-X is not enabled */ addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(false); - test_basic(&qvirtio_pci, &dev->vdev, alloc, &vqpci->vq, - (uint64_t)(uintptr_t)addr); + test_basic(&dev->vdev, alloc, &vqpci->vq, (uint64_t)(uintptr_t)addr); /* End test */ - qvirtqueue_cleanup(&qvirtio_pci, &vqpci->vq, alloc); + qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, alloc); pc_alloc_uninit(alloc); qvirtio_pci_device_disable(dev); g_free(dev); @@ -329,21 +327,19 @@ static void pci_indirect(void) /* MSI-X is not enabled */ addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(false); - capacity = qvirtio_config_readq(&qvirtio_pci, &dev->vdev, - (uint64_t)(uintptr_t)addr); + capacity = qvirtio_config_readq(&dev->vdev, (uint64_t)(uintptr_t)addr); g_assert_cmpint(capacity, ==, TEST_IMAGE_SIZE / 512); - features = qvirtio_get_features(&qvirtio_pci, &dev->vdev); + features = qvirtio_get_features(&dev->vdev); g_assert_cmphex(features & (1u << VIRTIO_RING_F_INDIRECT_DESC), !=, 0); features = features & ~(QVIRTIO_F_BAD_FEATURE | (1u << VIRTIO_RING_F_EVENT_IDX) | (1u << VIRTIO_BLK_F_SCSI)); - qvirtio_set_features(&qvirtio_pci, &dev->vdev, features); + qvirtio_set_features(&dev->vdev, features); alloc = pc_alloc_init(); - vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&qvirtio_pci, &dev->vdev, - alloc, 0); - qvirtio_set_driver_ok(&qvirtio_pci, &dev->vdev); + vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, 0); + qvirtio_set_driver_ok(&dev->vdev); /* Write request */ req.type = VIRTIO_BLK_T_OUT; @@ -360,9 +356,9 @@ static void pci_indirect(void) qvring_indirect_desc_add(indirect, req_addr, 528, false); qvring_indirect_desc_add(indirect, req_addr + 528, 1, true); free_head = qvirtqueue_add_indirect(&vqpci->vq, indirect); - qvirtqueue_kick(&qvirtio_pci, &dev->vdev, &vqpci->vq, free_head); + qvirtqueue_kick(&dev->vdev, &vqpci->vq, free_head); - qvirtio_wait_queue_isr(&qvirtio_pci, &dev->vdev, &vqpci->vq, + qvirtio_wait_queue_isr(&dev->vdev, &vqpci->vq, QVIRTIO_BLK_TIMEOUT_US); status = readb(req_addr + 528); g_assert_cmpint(status, ==, 0); @@ -385,9 +381,9 @@ static void pci_indirect(void) qvring_indirect_desc_add(indirect, req_addr, 16, false); qvring_indirect_desc_add(indirect, req_addr + 16, 513, true); free_head = qvirtqueue_add_indirect(&vqpci->vq, indirect); - qvirtqueue_kick(&qvirtio_pci, &dev->vdev, &vqpci->vq, free_head); + qvirtqueue_kick(&dev->vdev, &vqpci->vq, free_head); - qvirtio_wait_queue_isr(&qvirtio_pci, &dev->vdev, &vqpci->vq, + qvirtio_wait_queue_isr(&dev->vdev, &vqpci->vq, QVIRTIO_BLK_TIMEOUT_US); status = readb(req_addr + 528); g_assert_cmpint(status, ==, 0); @@ -401,7 +397,7 @@ static void pci_indirect(void) guest_free(alloc, req_addr); /* End test */ - qvirtqueue_cleanup(&qvirtio_pci, &vqpci->vq, alloc); + qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, alloc); pc_alloc_uninit(alloc); qvirtio_pci_device_disable(dev); g_free(dev); @@ -424,18 +420,16 @@ static void pci_config(void) /* MSI-X is not enabled */ addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(false); - capacity = qvirtio_config_readq(&qvirtio_pci, &dev->vdev, - (uint64_t)(uintptr_t)addr); + capacity = qvirtio_config_readq(&dev->vdev, (uint64_t)(uintptr_t)addr); g_assert_cmpint(capacity, ==, TEST_IMAGE_SIZE / 512); - qvirtio_set_driver_ok(&qvirtio_pci, &dev->vdev); + qvirtio_set_driver_ok(&dev->vdev); qmp("{ 'execute': 'block_resize', 'arguments': { 'device': 'drive0', " " 'size': %d } }", n_size); - qvirtio_wait_config_isr(&qvirtio_pci, &dev->vdev, QVIRTIO_BLK_TIMEOUT_US); + qvirtio_wait_config_isr(&dev->vdev, QVIRTIO_BLK_TIMEOUT_US); - capacity = qvirtio_config_readq(&qvirtio_pci, &dev->vdev, - (uint64_t)(uintptr_t)addr); + capacity = qvirtio_config_readq(&dev->vdev, (uint64_t)(uintptr_t)addr); g_assert_cmpint(capacity, ==, n_size / 512); qvirtio_pci_device_disable(dev); @@ -471,30 +465,27 @@ static void pci_msix(void) /* MSI-X is enabled */ addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(true); - capacity = qvirtio_config_readq(&qvirtio_pci, &dev->vdev, - (uint64_t)(uintptr_t)addr); + capacity = qvirtio_config_readq(&dev->vdev, (uint64_t)(uintptr_t)addr); g_assert_cmpint(capacity, ==, TEST_IMAGE_SIZE / 512); - features = qvirtio_get_features(&qvirtio_pci, &dev->vdev); + features = qvirtio_get_features(&dev->vdev); features = features & ~(QVIRTIO_F_BAD_FEATURE | (1u << VIRTIO_RING_F_INDIRECT_DESC) | (1u << VIRTIO_RING_F_EVENT_IDX) | (1u << VIRTIO_BLK_F_SCSI)); - qvirtio_set_features(&qvirtio_pci, &dev->vdev, features); + qvirtio_set_features(&dev->vdev, features); - vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&qvirtio_pci, &dev->vdev, - alloc, 0); + vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, 0); qvirtqueue_pci_msix_setup(dev, vqpci, alloc, 1); - qvirtio_set_driver_ok(&qvirtio_pci, &dev->vdev); + qvirtio_set_driver_ok(&dev->vdev); qmp("{ 'execute': 'block_resize', 'arguments': { 'device': 'drive0', " " 'size': %d } }", n_size); - qvirtio_wait_config_isr(&qvirtio_pci, &dev->vdev, QVIRTIO_BLK_TIMEOUT_US); + qvirtio_wait_config_isr(&dev->vdev, QVIRTIO_BLK_TIMEOUT_US); - capacity = qvirtio_config_readq(&qvirtio_pci, &dev->vdev, - (uint64_t)(uintptr_t)addr); + capacity = qvirtio_config_readq(&dev->vdev, (uintptr_t)addr); g_assert_cmpint(capacity, ==, n_size / 512); /* Write request */ @@ -511,9 +502,9 @@ static void pci_msix(void) free_head = qvirtqueue_add(&vqpci->vq, req_addr, 16, false, true); qvirtqueue_add(&vqpci->vq, req_addr + 16, 512, false, true); qvirtqueue_add(&vqpci->vq, req_addr + 528, 1, true, false); - qvirtqueue_kick(&qvirtio_pci, &dev->vdev, &vqpci->vq, free_head); + qvirtqueue_kick(&dev->vdev, &vqpci->vq, free_head); - qvirtio_wait_queue_isr(&qvirtio_pci, &dev->vdev, &vqpci->vq, + qvirtio_wait_queue_isr(&dev->vdev, &vqpci->vq, QVIRTIO_BLK_TIMEOUT_US); status = readb(req_addr + 528); @@ -535,10 +526,10 @@ static void pci_msix(void) qvirtqueue_add(&vqpci->vq, req_addr + 16, 512, true, true); qvirtqueue_add(&vqpci->vq, req_addr + 528, 1, true, false); - qvirtqueue_kick(&qvirtio_pci, &dev->vdev, &vqpci->vq, free_head); + qvirtqueue_kick(&dev->vdev, &vqpci->vq, free_head); - qvirtio_wait_queue_isr(&qvirtio_pci, &dev->vdev, &vqpci->vq, + qvirtio_wait_queue_isr(&dev->vdev, &vqpci->vq, QVIRTIO_BLK_TIMEOUT_US); status = readb(req_addr + 528); @@ -552,7 +543,7 @@ static void pci_msix(void) guest_free(alloc, req_addr); /* End test */ - qvirtqueue_cleanup(&qvirtio_pci, &vqpci->vq, alloc); + qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, alloc); pc_alloc_uninit(alloc); qpci_msix_disable(dev->pdev); qvirtio_pci_device_disable(dev); @@ -587,22 +578,20 @@ static void pci_idx(void) /* MSI-X is enabled */ addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(true); - capacity = qvirtio_config_readq(&qvirtio_pci, &dev->vdev, - (uint64_t)(uintptr_t)addr); + capacity = qvirtio_config_readq(&dev->vdev, (uint64_t)(uintptr_t)addr); g_assert_cmpint(capacity, ==, TEST_IMAGE_SIZE / 512); - features = qvirtio_get_features(&qvirtio_pci, &dev->vdev); + features = qvirtio_get_features(&dev->vdev); features = features & ~(QVIRTIO_F_BAD_FEATURE | (1u << VIRTIO_RING_F_INDIRECT_DESC) | (1u << VIRTIO_F_NOTIFY_ON_EMPTY) | (1u << VIRTIO_BLK_F_SCSI)); - qvirtio_set_features(&qvirtio_pci, &dev->vdev, features); + qvirtio_set_features(&dev->vdev, features); - vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&qvirtio_pci, &dev->vdev, - alloc, 0); + vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, 0); qvirtqueue_pci_msix_setup(dev, vqpci, alloc, 1); - qvirtio_set_driver_ok(&qvirtio_pci, &dev->vdev); + qvirtio_set_driver_ok(&dev->vdev); /* Write request */ req.type = VIRTIO_BLK_T_OUT; @@ -618,10 +607,9 @@ static void pci_idx(void) free_head = qvirtqueue_add(&vqpci->vq, req_addr, 16, false, true); qvirtqueue_add(&vqpci->vq, req_addr + 16, 512, false, true); qvirtqueue_add(&vqpci->vq, req_addr + 528, 1, true, false); - qvirtqueue_kick(&qvirtio_pci, &dev->vdev, &vqpci->vq, free_head); + qvirtqueue_kick(&dev->vdev, &vqpci->vq, free_head); - qvirtio_wait_queue_isr(&qvirtio_pci, &dev->vdev, &vqpci->vq, - QVIRTIO_BLK_TIMEOUT_US); + qvirtio_wait_queue_isr(&dev->vdev, &vqpci->vq, QVIRTIO_BLK_TIMEOUT_US); /* Write request */ req.type = VIRTIO_BLK_T_OUT; @@ -639,10 +627,10 @@ static void pci_idx(void) free_head = qvirtqueue_add(&vqpci->vq, req_addr, 16, false, true); qvirtqueue_add(&vqpci->vq, req_addr + 16, 512, false, true); qvirtqueue_add(&vqpci->vq, req_addr + 528, 1, true, false); - qvirtqueue_kick(&qvirtio_pci, &dev->vdev, &vqpci->vq, free_head); + qvirtqueue_kick(&dev->vdev, &vqpci->vq, free_head); /* No notification expected */ - status = qvirtio_wait_status_byte_no_isr(&qvirtio_pci, &dev->vdev, + status = qvirtio_wait_status_byte_no_isr(&dev->vdev, &vqpci->vq, req_addr + 528, QVIRTIO_BLK_TIMEOUT_US); g_assert_cmpint(status, ==, 0); @@ -663,9 +651,9 @@ static void pci_idx(void) qvirtqueue_add(&vqpci->vq, req_addr + 16, 512, true, true); qvirtqueue_add(&vqpci->vq, req_addr + 528, 1, true, false); - qvirtqueue_kick(&qvirtio_pci, &dev->vdev, &vqpci->vq, free_head); + qvirtqueue_kick(&dev->vdev, &vqpci->vq, free_head); - qvirtio_wait_queue_isr(&qvirtio_pci, &dev->vdev, &vqpci->vq, + qvirtio_wait_queue_isr(&dev->vdev, &vqpci->vq, QVIRTIO_BLK_TIMEOUT_US); status = readb(req_addr + 528); @@ -679,7 +667,7 @@ static void pci_idx(void) guest_free(alloc, req_addr); /* End test */ - qvirtqueue_cleanup(&qvirtio_pci, &vqpci->vq, alloc); + qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, alloc); pc_alloc_uninit(alloc); qpci_msix_disable(dev->pdev); qvirtio_pci_device_disable(dev); @@ -724,28 +712,25 @@ static void mmio_basic(void) g_assert(dev != NULL); g_assert_cmphex(dev->vdev.device_type, ==, VIRTIO_ID_BLOCK); - qvirtio_reset(&qvirtio_mmio, &dev->vdev); - qvirtio_set_acknowledge(&qvirtio_mmio, &dev->vdev); - qvirtio_set_driver(&qvirtio_mmio, &dev->vdev); + qvirtio_reset(&dev->vdev); + qvirtio_set_acknowledge(&dev->vdev); + qvirtio_set_driver(&dev->vdev); alloc = generic_alloc_init(MMIO_RAM_ADDR, MMIO_RAM_SIZE, MMIO_PAGE_SIZE); - vq = qvirtqueue_setup(&qvirtio_mmio, &dev->vdev, alloc, 0); + vq = qvirtqueue_setup(&dev->vdev, alloc, 0); - test_basic(&qvirtio_mmio, &dev->vdev, alloc, vq, - QVIRTIO_MMIO_DEVICE_SPECIFIC); + test_basic(&dev->vdev, alloc, vq, QVIRTIO_MMIO_DEVICE_SPECIFIC); qmp("{ 'execute': 'block_resize', 'arguments': { 'device': 'drive0', " " 'size': %d } }", n_size); - qvirtio_wait_queue_isr(&qvirtio_mmio, &dev->vdev, vq, - QVIRTIO_BLK_TIMEOUT_US); + qvirtio_wait_queue_isr(&dev->vdev, vq, QVIRTIO_BLK_TIMEOUT_US); - capacity = qvirtio_config_readq(&qvirtio_mmio, &dev->vdev, - QVIRTIO_MMIO_DEVICE_SPECIFIC); + capacity = qvirtio_config_readq(&dev->vdev, QVIRTIO_MMIO_DEVICE_SPECIFIC); g_assert_cmpint(capacity, ==, n_size / 512); /* End test */ - qvirtqueue_cleanup(&qvirtio_mmio, vq, alloc); + qvirtqueue_cleanup(dev->vdev.bus, vq, alloc); generic_alloc_uninit(alloc); g_free(dev); test_end(); diff --git a/tests/virtio-net-test.c b/tests/virtio-net-test.c index a343a6b048..6fa385e90e 100644 --- a/tests/virtio-net-test.c +++ b/tests/virtio-net-test.c @@ -46,9 +46,9 @@ static QVirtioPCIDevice *virtio_net_pci_init(QPCIBus *bus, int slot) g_assert_cmphex(dev->vdev.device_type, ==, VIRTIO_ID_NET); qvirtio_pci_device_enable(dev); - qvirtio_reset(&qvirtio_pci, &dev->vdev); - qvirtio_set_acknowledge(&qvirtio_pci, &dev->vdev); - qvirtio_set_driver(&qvirtio_pci, &dev->vdev); + qvirtio_reset(&dev->vdev); + qvirtio_set_acknowledge(&dev->vdev); + qvirtio_set_driver(&dev->vdev); return dev; } @@ -65,20 +65,20 @@ static QPCIBus *pci_test_start(int socket) return qpci_init_pc(NULL); } -static void driver_init(const QVirtioBus *bus, QVirtioDevice *dev) +static void driver_init(QVirtioDevice *dev) { uint32_t features; - features = qvirtio_get_features(bus, dev); + features = qvirtio_get_features(dev); features = features & ~(QVIRTIO_F_BAD_FEATURE | (1u << VIRTIO_RING_F_INDIRECT_DESC) | (1u << VIRTIO_RING_F_EVENT_IDX)); - qvirtio_set_features(bus, dev, features); + qvirtio_set_features(dev, features); - qvirtio_set_driver_ok(bus, dev); + qvirtio_set_driver_ok(dev); } -static void rx_test(const QVirtioBus *bus, QVirtioDevice *dev, +static void rx_test(QVirtioDevice *dev, QGuestAllocator *alloc, QVirtQueue *vq, int socket) { @@ -101,19 +101,19 @@ static void rx_test(const QVirtioBus *bus, QVirtioDevice *dev, req_addr = guest_alloc(alloc, 64); free_head = qvirtqueue_add(vq, req_addr, 64, true, false); - qvirtqueue_kick(bus, dev, vq, free_head); + qvirtqueue_kick(dev, vq, free_head); ret = iov_send(socket, iov, 2, 0, sizeof(len) + sizeof(test)); g_assert_cmpint(ret, ==, sizeof(test) + sizeof(len)); - qvirtio_wait_queue_isr(bus, dev, vq, QVIRTIO_NET_TIMEOUT_US); + qvirtio_wait_queue_isr(dev, vq, QVIRTIO_NET_TIMEOUT_US); memread(req_addr + VNET_HDR_SIZE, buffer, sizeof(test)); g_assert_cmpstr(buffer, ==, "TEST"); guest_free(alloc, req_addr); } -static void tx_test(const QVirtioBus *bus, QVirtioDevice *dev, +static void tx_test(QVirtioDevice *dev, QGuestAllocator *alloc, QVirtQueue *vq, int socket) { @@ -127,9 +127,9 @@ static void tx_test(const QVirtioBus *bus, QVirtioDevice *dev, memwrite(req_addr + VNET_HDR_SIZE, "TEST", 4); free_head = qvirtqueue_add(vq, req_addr, 64, false, false); - qvirtqueue_kick(bus, dev, vq, free_head); + qvirtqueue_kick(dev, vq, free_head); - qvirtio_wait_queue_isr(bus, dev, vq, QVIRTIO_NET_TIMEOUT_US); + qvirtio_wait_queue_isr(dev, vq, QVIRTIO_NET_TIMEOUT_US); guest_free(alloc, req_addr); ret = qemu_recv(socket, &len, sizeof(len), 0); @@ -140,7 +140,7 @@ static void tx_test(const QVirtioBus *bus, QVirtioDevice *dev, g_assert_cmpstr(buffer, ==, "TEST"); } -static void rx_stop_cont_test(const QVirtioBus *bus, QVirtioDevice *dev, +static void rx_stop_cont_test(QVirtioDevice *dev, QGuestAllocator *alloc, QVirtQueue *vq, int socket) { @@ -164,7 +164,7 @@ static void rx_stop_cont_test(const QVirtioBus *bus, QVirtioDevice *dev, req_addr = guest_alloc(alloc, 64); free_head = qvirtqueue_add(vq, req_addr, 64, true, false); - qvirtqueue_kick(bus, dev, vq, free_head); + qvirtqueue_kick(dev, vq, free_head); rsp = qmp("{ 'execute' : 'stop'}"); QDECREF(rsp); @@ -180,26 +180,26 @@ static void rx_stop_cont_test(const QVirtioBus *bus, QVirtioDevice *dev, rsp = qmp("{ 'execute' : 'cont'}"); QDECREF(rsp); - qvirtio_wait_queue_isr(bus, dev, vq, QVIRTIO_NET_TIMEOUT_US); + qvirtio_wait_queue_isr(dev, vq, QVIRTIO_NET_TIMEOUT_US); memread(req_addr + VNET_HDR_SIZE, buffer, sizeof(test)); g_assert_cmpstr(buffer, ==, "TEST"); guest_free(alloc, req_addr); } -static void send_recv_test(const QVirtioBus *bus, QVirtioDevice *dev, +static void send_recv_test(QVirtioDevice *dev, QGuestAllocator *alloc, QVirtQueue *rvq, QVirtQueue *tvq, int socket) { - rx_test(bus, dev, alloc, rvq, socket); - tx_test(bus, dev, alloc, tvq, socket); + rx_test(dev, alloc, rvq, socket); + tx_test(dev, alloc, tvq, socket); } -static void stop_cont_test(const QVirtioBus *bus, QVirtioDevice *dev, +static void stop_cont_test(QVirtioDevice *dev, QGuestAllocator *alloc, QVirtQueue *rvq, QVirtQueue *tvq, int socket) { - rx_stop_cont_test(bus, dev, alloc, rvq, socket); + rx_stop_cont_test(dev, alloc, rvq, socket); } static void pci_basic(gconstpointer data) @@ -208,8 +208,7 @@ static void pci_basic(gconstpointer data) QPCIBus *bus; QVirtQueuePCI *tx, *rx; QGuestAllocator *alloc; - void (*func) (const QVirtioBus *bus, - QVirtioDevice *dev, + void (*func) (QVirtioDevice *dev, QGuestAllocator *alloc, QVirtQueue *rvq, QVirtQueue *tvq, @@ -223,18 +222,16 @@ static void pci_basic(gconstpointer data) dev = virtio_net_pci_init(bus, PCI_SLOT); alloc = pc_alloc_init(); - rx = (QVirtQueuePCI *)qvirtqueue_setup(&qvirtio_pci, &dev->vdev, - alloc, 0); - tx = (QVirtQueuePCI *)qvirtqueue_setup(&qvirtio_pci, &dev->vdev, - alloc, 1); + rx = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, 0); + tx = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, 1); - driver_init(&qvirtio_pci, &dev->vdev); - func(&qvirtio_pci, &dev->vdev, alloc, &rx->vq, &tx->vq, sv[0]); + driver_init(&dev->vdev); + func(&dev->vdev, alloc, &rx->vq, &tx->vq, sv[0]); /* End test */ close(sv[0]); - qvirtqueue_cleanup(&qvirtio_pci, &tx->vq, alloc); - qvirtqueue_cleanup(&qvirtio_pci, &rx->vq, alloc); + qvirtqueue_cleanup(dev->vdev.bus, &tx->vq, alloc); + qvirtqueue_cleanup(dev->vdev.bus, &rx->vq, alloc); pc_alloc_uninit(alloc); qvirtio_pci_device_disable(dev); g_free(dev->pdev); diff --git a/tests/virtio-scsi-test.c b/tests/virtio-scsi-test.c index 94d75b1493..3dbec2f5f0 100644 --- a/tests/virtio-scsi-test.c +++ b/tests/virtio-scsi-test.c @@ -58,7 +58,7 @@ static void qvirtio_scsi_pci_free(QVirtIOSCSI *vs) int i; for (i = 0; i < vs->num_queues + 2; i++) { - qvirtqueue_cleanup(&qvirtio_pci, vs->vq[i], vs->alloc); + qvirtqueue_cleanup(vs->dev->bus, vs->vq[i], vs->alloc); } pc_alloc_uninit(vs->alloc); qvirtio_pci_device_disable(container_of(vs->dev, QVirtioPCIDevice, vdev)); @@ -119,8 +119,8 @@ static uint8_t virtio_scsi_do_command(QVirtIOSCSI *vs, const uint8_t *cdb, qvirtqueue_add(vq, data_in_addr, data_in_len, true, false); } - qvirtqueue_kick(&qvirtio_pci, vs->dev, vq, free_head); - qvirtio_wait_queue_isr(&qvirtio_pci, vs->dev, vq, QVIRTIO_SCSI_TIMEOUT_US); + qvirtqueue_kick(vs->dev, vq, free_head); + qvirtio_wait_queue_isr(vs->dev, vq, QVIRTIO_SCSI_TIMEOUT_US); response = readb(resp_addr + offsetof(struct virtio_scsi_cmd_resp, response)); @@ -155,18 +155,17 @@ static QVirtIOSCSI *qvirtio_scsi_pci_init(int slot) g_assert_cmphex(vs->dev->device_type, ==, VIRTIO_ID_SCSI); qvirtio_pci_device_enable(dev); - qvirtio_reset(&qvirtio_pci, vs->dev); - qvirtio_set_acknowledge(&qvirtio_pci, vs->dev); - qvirtio_set_driver(&qvirtio_pci, vs->dev); + qvirtio_reset(vs->dev); + qvirtio_set_acknowledge(vs->dev); + qvirtio_set_driver(vs->dev); addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(false); - vs->num_queues = qvirtio_config_readl(&qvirtio_pci, vs->dev, - (uint64_t)(uintptr_t)addr); + vs->num_queues = qvirtio_config_readl(vs->dev, (uint64_t)(uintptr_t)addr); g_assert_cmpint(vs->num_queues, <, MAX_NUM_QUEUES); for (i = 0; i < vs->num_queues + 2; i++) { - vs->vq[i] = qvirtqueue_setup(&qvirtio_pci, vs->dev, vs->alloc, i); + vs->vq[i] = qvirtqueue_setup(vs->dev, vs->alloc, i); } /* Clear the POWER ON OCCURRED unit attention */ From 8b4b80c37630e976f2dd02a7d42bd9bea1ce676e Mon Sep 17 00:00:00 2001 From: Laurent Vivier Date: Mon, 17 Oct 2016 12:30:22 +0200 Subject: [PATCH 06/73] tests: rename target_big_endian() as qvirtio_is_big_endian() Move the definition to libqos/virtio.h as it must be used only with virtio functions. Add a QVirtioDevice parameter as it will be needed to know if the virtio device is using virtio 1.0 specification and thus is always little-endian (to do) Signed-off-by: Laurent Vivier Reviewed-by: Greg Kurz Reviewed-by: Thomas Huth Signed-off-by: David Gibson --- tests/libqos/virtio-pci.c | 2 +- tests/libqos/virtio.h | 6 ++++++ tests/libqtest.h | 10 ---------- tests/virtio-blk-test.c | 36 ++++++++++++++++++------------------ 4 files changed, 25 insertions(+), 29 deletions(-) diff --git a/tests/libqos/virtio-pci.c b/tests/libqos/virtio-pci.c index bbfed58dcf..7aa29b1a9c 100644 --- a/tests/libqos/virtio-pci.c +++ b/tests/libqos/virtio-pci.c @@ -86,7 +86,7 @@ static uint64_t qvirtio_pci_config_readq(QVirtioDevice *d, uint64_t addr) int i; uint64_t u64 = 0; - if (target_big_endian()) { + if (qvirtio_is_big_endian(d)) { for (i = 0; i < 8; ++i) { u64 |= (uint64_t)qpci_io_readb(dev->pdev, (void *)(uintptr_t)addr + i) << (7 - i) * 8; diff --git a/tests/libqos/virtio.h b/tests/libqos/virtio.h index ac4669a11b..3397a080e9 100644 --- a/tests/libqos/virtio.h +++ b/tests/libqos/virtio.h @@ -89,6 +89,12 @@ struct QVirtioBus { void (*virtqueue_kick)(QVirtioDevice *d, QVirtQueue *vq); }; +static inline bool qvirtio_is_big_endian(QVirtioDevice *d) +{ + /* FIXME: virtio 1.0 is always little-endian */ + return qtest_big_endian(global_qtest); +} + static inline uint32_t qvring_size(uint32_t num, uint32_t align) { return ((sizeof(struct vring_desc) * num + sizeof(uint16_t) * (3 + num) diff --git a/tests/libqtest.h b/tests/libqtest.h index 4be1f77877..0224f06d65 100644 --- a/tests/libqtest.h +++ b/tests/libqtest.h @@ -881,16 +881,6 @@ static inline int64_t clock_set(int64_t val) return qtest_clock_set(global_qtest, val); } -/** - * target_big_endian: - * - * Returns: True if the architecture under test has a big endian configuration. - */ -static inline bool target_big_endian(void) -{ - return qtest_big_endian(global_qtest); -} - QDict *qmp_fd_receive(int fd); void qmp_fd_sendv(int fd, const char *fmt, va_list ap); void qmp_fd_send(int fd, const char *fmt, ...); diff --git a/tests/virtio-blk-test.c b/tests/virtio-blk-test.c index 9a6f2cff97..79e21c5daa 100644 --- a/tests/virtio-blk-test.c +++ b/tests/virtio-blk-test.c @@ -117,23 +117,23 @@ static QVirtioPCIDevice *virtio_blk_pci_init(QPCIBus *bus, int slot) return dev; } -static inline void virtio_blk_fix_request(QVirtioBlkReq *req) +static inline void virtio_blk_fix_request(QVirtioDevice *d, QVirtioBlkReq *req) { #ifdef HOST_WORDS_BIGENDIAN - bool host_endian = true; + const bool host_is_big_endian = true; #else - bool host_endian = false; + const bool host_is_big_endian = false; #endif - if (target_big_endian() != host_endian) { + if (qvirtio_is_big_endian(d) != host_is_big_endian) { req->type = bswap32(req->type); req->ioprio = bswap32(req->ioprio); req->sector = bswap64(req->sector); } } -static uint64_t virtio_blk_request(QGuestAllocator *alloc, QVirtioBlkReq *req, - uint64_t data_size) +static uint64_t virtio_blk_request(QGuestAllocator *alloc, QVirtioDevice *d, + QVirtioBlkReq *req, uint64_t data_size) { uint64_t addr; uint8_t status = 0xFF; @@ -141,7 +141,7 @@ static uint64_t virtio_blk_request(QGuestAllocator *alloc, QVirtioBlkReq *req, g_assert_cmpuint(data_size % 512, ==, 0); addr = guest_alloc(alloc, sizeof(*req) + data_size); - virtio_blk_fix_request(req); + virtio_blk_fix_request(d, req); memwrite(addr, req, 16); memwrite(addr + 16, req->data, data_size); @@ -182,7 +182,7 @@ static void test_basic(QVirtioDevice *dev, QGuestAllocator *alloc, req.data = g_malloc0(512); strcpy(req.data, "TEST"); - req_addr = virtio_blk_request(alloc, &req, 512); + req_addr = virtio_blk_request(alloc, dev, &req, 512); g_free(req.data); @@ -204,7 +204,7 @@ static void test_basic(QVirtioDevice *dev, QGuestAllocator *alloc, req.sector = 0; req.data = g_malloc0(512); - req_addr = virtio_blk_request(alloc, &req, 512); + req_addr = virtio_blk_request(alloc, dev, &req, 512); g_free(req.data); @@ -234,7 +234,7 @@ static void test_basic(QVirtioDevice *dev, QGuestAllocator *alloc, req.data = g_malloc0(512); strcpy(req.data, "TEST"); - req_addr = virtio_blk_request(alloc, &req, 512); + req_addr = virtio_blk_request(alloc, dev, &req, 512); g_free(req.data); @@ -254,7 +254,7 @@ static void test_basic(QVirtioDevice *dev, QGuestAllocator *alloc, req.sector = 1; req.data = g_malloc0(512); - req_addr = virtio_blk_request(alloc, &req, 512); + req_addr = virtio_blk_request(alloc, dev, &req, 512); g_free(req.data); @@ -348,7 +348,7 @@ static void pci_indirect(void) req.data = g_malloc0(512); strcpy(req.data, "TEST"); - req_addr = virtio_blk_request(alloc, &req, 512); + req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); g_free(req.data); @@ -373,7 +373,7 @@ static void pci_indirect(void) req.data = g_malloc0(512); strcpy(req.data, "TEST"); - req_addr = virtio_blk_request(alloc, &req, 512); + req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); g_free(req.data); @@ -495,7 +495,7 @@ static void pci_msix(void) req.data = g_malloc0(512); strcpy(req.data, "TEST"); - req_addr = virtio_blk_request(alloc, &req, 512); + req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); g_free(req.data); @@ -518,7 +518,7 @@ static void pci_msix(void) req.sector = 0; req.data = g_malloc0(512); - req_addr = virtio_blk_request(alloc, &req, 512); + req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); g_free(req.data); @@ -600,7 +600,7 @@ static void pci_idx(void) req.data = g_malloc0(512); strcpy(req.data, "TEST"); - req_addr = virtio_blk_request(alloc, &req, 512); + req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); g_free(req.data); @@ -618,7 +618,7 @@ static void pci_idx(void) req.data = g_malloc0(512); strcpy(req.data, "TEST"); - req_addr = virtio_blk_request(alloc, &req, 512); + req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); g_free(req.data); @@ -643,7 +643,7 @@ static void pci_idx(void) req.sector = 1; req.data = g_malloc0(512); - req_addr = virtio_blk_request(alloc, &req, 512); + req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); g_free(req.data); From a980f7f2c2f4d7e9a1eba4f804cd66dbd458b6d4 Mon Sep 17 00:00:00 2001 From: Laurent Vivier Date: Mon, 17 Oct 2016 12:30:23 +0200 Subject: [PATCH 07/73] tests: use qtest_pc_boot()/qtest_shutdown() in virtio tests This patch replaces calls to qtest_start() and qtest_end() by calls to qtest_pc_boot() and qtest_shutdown(). This allows to initialize memory allocator and PCI interface functions. This will ease to enable virtio tests on other architectures by only adding a specific qtest_XXX_boot() (like qtest_spapr_boot()). Signed-off-by: Laurent Vivier Reviewed-by: Greg Kurz Signed-off-by: David Gibson --- tests/virtio-9p-test.c | 50 ++++++------- tests/virtio-blk-test.c | 148 +++++++++++++++++---------------------- tests/virtio-net-test.c | 39 ++++------- tests/virtio-scsi-test.c | 65 ++++++++--------- 4 files changed, 127 insertions(+), 175 deletions(-) diff --git a/tests/virtio-9p-test.c b/tests/virtio-9p-test.c index 2341622a3b..851ec99404 100644 --- a/tests/virtio-9p-test.c +++ b/tests/virtio-9p-test.c @@ -10,62 +10,57 @@ #include "qemu/osdep.h" #include "libqtest.h" #include "qemu-common.h" -#include "libqos/pci-pc.h" +#include "libqos/libqos-pc.h" #include "libqos/virtio.h" #include "libqos/virtio-pci.h" -#include "libqos/malloc.h" -#include "libqos/malloc-pc.h" #include "standard-headers/linux/virtio_ids.h" #include "standard-headers/linux/virtio_pci.h" static const char mount_tag[] = "qtest"; static char *test_share; -static void qvirtio_9p_start(void) + +static QOSState *qvirtio_9p_start(void) { - char *args; + const char *cmd = "-fsdev local,id=fsdev0,security_model=none,path=%s " + "-device virtio-9p-pci,fsdev=fsdev0,mount_tag=%s"; test_share = g_strdup("/tmp/qtest.XXXXXX"); g_assert_nonnull(mkdtemp(test_share)); - args = g_strdup_printf("-fsdev local,id=fsdev0,security_model=none,path=%s " - "-device virtio-9p-pci,fsdev=fsdev0,mount_tag=%s", - test_share, mount_tag); - - qtest_start(args); - g_free(args); + return qtest_pc_boot(cmd, test_share, mount_tag); } -static void qvirtio_9p_stop(void) +static void qvirtio_9p_stop(QOSState *qs) { - qtest_end(); + qtest_shutdown(qs); rmdir(test_share); g_free(test_share); } static void pci_nop(void) { - qvirtio_9p_start(); - qvirtio_9p_stop(); + QOSState *qs; + + qs = qvirtio_9p_start(); + qvirtio_9p_stop(qs); } typedef struct { QVirtioDevice *dev; - QGuestAllocator *alloc; - QPCIBus *bus; + QOSState *qs; QVirtQueue *vq; } QVirtIO9P; -static QVirtIO9P *qvirtio_9p_pci_init(void) +static QVirtIO9P *qvirtio_9p_pci_init(QOSState *qs) { QVirtIO9P *v9p; QVirtioPCIDevice *dev; v9p = g_new0(QVirtIO9P, 1); - v9p->alloc = pc_alloc_init(); - v9p->bus = qpci_init_pc(NULL); - dev = qvirtio_pci_device_find(v9p->bus, VIRTIO_ID_9P); + v9p->qs = qs; + dev = qvirtio_pci_device_find(v9p->qs->pcibus, VIRTIO_ID_9P); g_assert_nonnull(dev); g_assert_cmphex(dev->vdev.device_type, ==, VIRTIO_ID_9P); v9p->dev = (QVirtioDevice *) dev; @@ -75,17 +70,15 @@ static QVirtIO9P *qvirtio_9p_pci_init(void) qvirtio_set_acknowledge(v9p->dev); qvirtio_set_driver(v9p->dev); - v9p->vq = qvirtqueue_setup(v9p->dev, v9p->alloc, 0); + v9p->vq = qvirtqueue_setup(v9p->dev, v9p->qs->alloc, 0); return v9p; } static void qvirtio_9p_pci_free(QVirtIO9P *v9p) { - qvirtqueue_cleanup(v9p->dev->bus, v9p->vq, v9p->alloc); - pc_alloc_uninit(v9p->alloc); + qvirtqueue_cleanup(v9p->dev->bus, v9p->vq, v9p->qs->alloc); qvirtio_pci_device_disable(container_of(v9p->dev, QVirtioPCIDevice, vdev)); g_free(v9p->dev); - qpci_free_pc(v9p->bus); g_free(v9p); } @@ -96,9 +89,10 @@ static void pci_basic_config(void) size_t tag_len; char *tag; int i; + QOSState *qs; - qvirtio_9p_start(); - v9p = qvirtio_9p_pci_init(); + qs = qvirtio_9p_start(); + v9p = qvirtio_9p_pci_init(qs); addr = ((QVirtioPCIDevice *) v9p->dev)->addr + VIRTIO_PCI_CONFIG_OFF(false); tag_len = qvirtio_config_readw(v9p->dev, @@ -114,7 +108,7 @@ static void pci_basic_config(void) g_free(tag); qvirtio_9p_pci_free(v9p); - qvirtio_9p_stop(); + qvirtio_9p_stop(qs); } int main(int argc, char **argv) diff --git a/tests/virtio-blk-test.c b/tests/virtio-blk-test.c index 79e21c5daa..2382eb5cc1 100644 --- a/tests/virtio-blk-test.c +++ b/tests/virtio-blk-test.c @@ -10,12 +10,10 @@ #include "qemu/osdep.h" #include "libqtest.h" +#include "libqos/libqos-pc.h" #include "libqos/virtio.h" #include "libqos/virtio-pci.h" #include "libqos/virtio-mmio.h" -#include "libqos/pci-pc.h" -#include "libqos/malloc.h" -#include "libqos/malloc-pc.h" #include "libqos/malloc-generic.h" #include "qemu/bswap.h" #include "standard-headers/linux/virtio_ids.h" @@ -58,24 +56,21 @@ static char *drive_create(void) return tmp_path; } -static QPCIBus *pci_test_start(void) +static QOSState *pci_test_start(void) { - char *cmdline; + QOSState *qs; char *tmp_path; + const char *cmd = "-drive if=none,id=drive0,file=%s,format=raw " + "-drive if=none,id=drive1,file=/dev/null,format=raw " + "-device virtio-blk-pci,id=drv0,drive=drive0," + "addr=%x.%x"; tmp_path = drive_create(); - cmdline = g_strdup_printf("-drive if=none,id=drive0,file=%s,format=raw " - "-drive if=none,id=drive1,file=/dev/null,format=raw " - "-device virtio-blk-pci,id=drv0,drive=drive0," - "addr=%x.%x", - tmp_path, PCI_SLOT, PCI_FN); - qtest_start(cmdline); + qs = qtest_pc_boot(cmd, tmp_path, PCI_SLOT, PCI_FN); unlink(tmp_path); g_free(tmp_path); - g_free(cmdline); - - return qpci_init_pc(NULL); + return qs; } static void arm_test_start(void) @@ -279,37 +274,32 @@ static void test_basic(QVirtioDevice *dev, QGuestAllocator *alloc, static void pci_basic(void) { QVirtioPCIDevice *dev; - QPCIBus *bus; + QOSState *qs; QVirtQueuePCI *vqpci; - QGuestAllocator *alloc; void *addr; - bus = pci_test_start(); - dev = virtio_blk_pci_init(bus, PCI_SLOT); + qs = pci_test_start(); + dev = virtio_blk_pci_init(qs->pcibus, PCI_SLOT); - alloc = pc_alloc_init(); - vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, 0); + vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, qs->alloc, 0); /* MSI-X is not enabled */ addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(false); - test_basic(&dev->vdev, alloc, &vqpci->vq, (uint64_t)(uintptr_t)addr); + test_basic(&dev->vdev, qs->alloc, &vqpci->vq, (uint64_t)(uintptr_t)addr); /* End test */ - qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, alloc); - pc_alloc_uninit(alloc); + qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, qs->alloc); qvirtio_pci_device_disable(dev); g_free(dev); - qpci_free_pc(bus); - test_end(); + qtest_shutdown(qs); } static void pci_indirect(void) { QVirtioPCIDevice *dev; - QPCIBus *bus; QVirtQueuePCI *vqpci; - QGuestAllocator *alloc; + QOSState *qs; QVirtioBlkReq req; QVRingIndirectDesc *indirect; void *addr; @@ -320,9 +310,9 @@ static void pci_indirect(void) uint8_t status; char *data; - bus = pci_test_start(); + qs = pci_test_start(); - dev = virtio_blk_pci_init(bus, PCI_SLOT); + dev = virtio_blk_pci_init(qs->pcibus, PCI_SLOT); /* MSI-X is not enabled */ addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(false); @@ -337,8 +327,7 @@ static void pci_indirect(void) (1u << VIRTIO_BLK_F_SCSI)); qvirtio_set_features(&dev->vdev, features); - alloc = pc_alloc_init(); - vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, 0); + vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, qs->alloc, 0); qvirtio_set_driver_ok(&dev->vdev); /* Write request */ @@ -348,11 +337,11 @@ static void pci_indirect(void) req.data = g_malloc0(512); strcpy(req.data, "TEST"); - req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); + req_addr = virtio_blk_request(qs->alloc, &dev->vdev, &req, 512); g_free(req.data); - indirect = qvring_indirect_desc_setup(&dev->vdev, alloc, 2); + indirect = qvring_indirect_desc_setup(&dev->vdev, qs->alloc, 2); qvring_indirect_desc_add(indirect, req_addr, 528, false); qvring_indirect_desc_add(indirect, req_addr + 528, 1, true); free_head = qvirtqueue_add_indirect(&vqpci->vq, indirect); @@ -364,7 +353,7 @@ static void pci_indirect(void) g_assert_cmpint(status, ==, 0); g_free(indirect); - guest_free(alloc, req_addr); + guest_free(qs->alloc, req_addr); /* Read request */ req.type = VIRTIO_BLK_T_IN; @@ -373,11 +362,11 @@ static void pci_indirect(void) req.data = g_malloc0(512); strcpy(req.data, "TEST"); - req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); + req_addr = virtio_blk_request(qs->alloc, &dev->vdev, &req, 512); g_free(req.data); - indirect = qvring_indirect_desc_setup(&dev->vdev, alloc, 2); + indirect = qvring_indirect_desc_setup(&dev->vdev, qs->alloc, 2); qvring_indirect_desc_add(indirect, req_addr, 16, false); qvring_indirect_desc_add(indirect, req_addr + 16, 513, true); free_head = qvirtqueue_add_indirect(&vqpci->vq, indirect); @@ -394,28 +383,26 @@ static void pci_indirect(void) g_free(data); g_free(indirect); - guest_free(alloc, req_addr); + guest_free(qs->alloc, req_addr); /* End test */ - qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, alloc); - pc_alloc_uninit(alloc); + qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, qs->alloc); qvirtio_pci_device_disable(dev); g_free(dev); - qpci_free_pc(bus); - test_end(); + qtest_shutdown(qs); } static void pci_config(void) { QVirtioPCIDevice *dev; - QPCIBus *bus; + QOSState *qs; int n_size = TEST_IMAGE_SIZE / 2; void *addr; uint64_t capacity; - bus = pci_test_start(); + qs = pci_test_start(); - dev = virtio_blk_pci_init(bus, PCI_SLOT); + dev = virtio_blk_pci_init(qs->pcibus, PCI_SLOT); /* MSI-X is not enabled */ addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(false); @@ -434,16 +421,15 @@ static void pci_config(void) qvirtio_pci_device_disable(dev); g_free(dev); - qpci_free_pc(bus); - test_end(); + + qtest_shutdown(qs); } static void pci_msix(void) { QVirtioPCIDevice *dev; - QPCIBus *bus; + QOSState *qs; QVirtQueuePCI *vqpci; - QGuestAllocator *alloc; QVirtioBlkReq req; int n_size = TEST_IMAGE_SIZE / 2; void *addr; @@ -454,13 +440,12 @@ static void pci_msix(void) uint8_t status; char *data; - bus = pci_test_start(); - alloc = pc_alloc_init(); + qs = pci_test_start(); - dev = virtio_blk_pci_init(bus, PCI_SLOT); + dev = virtio_blk_pci_init(qs->pcibus, PCI_SLOT); qpci_msix_enable(dev->pdev); - qvirtio_pci_set_msix_configuration_vector(dev, alloc, 0); + qvirtio_pci_set_msix_configuration_vector(dev, qs->alloc, 0); /* MSI-X is enabled */ addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(true); @@ -475,8 +460,8 @@ static void pci_msix(void) (1u << VIRTIO_BLK_F_SCSI)); qvirtio_set_features(&dev->vdev, features); - vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, 0); - qvirtqueue_pci_msix_setup(dev, vqpci, alloc, 1); + vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, qs->alloc, 0); + qvirtqueue_pci_msix_setup(dev, vqpci, qs->alloc, 1); qvirtio_set_driver_ok(&dev->vdev); @@ -495,7 +480,7 @@ static void pci_msix(void) req.data = g_malloc0(512); strcpy(req.data, "TEST"); - req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); + req_addr = virtio_blk_request(qs->alloc, &dev->vdev, &req, 512); g_free(req.data); @@ -510,7 +495,7 @@ static void pci_msix(void) status = readb(req_addr + 528); g_assert_cmpint(status, ==, 0); - guest_free(alloc, req_addr); + guest_free(qs->alloc, req_addr); /* Read request */ req.type = VIRTIO_BLK_T_IN; @@ -518,7 +503,7 @@ static void pci_msix(void) req.sector = 0; req.data = g_malloc0(512); - req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); + req_addr = virtio_blk_request(qs->alloc, &dev->vdev, &req, 512); g_free(req.data); @@ -540,24 +525,21 @@ static void pci_msix(void) g_assert_cmpstr(data, ==, "TEST"); g_free(data); - guest_free(alloc, req_addr); + guest_free(qs->alloc, req_addr); /* End test */ - qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, alloc); - pc_alloc_uninit(alloc); + qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, qs->alloc); qpci_msix_disable(dev->pdev); qvirtio_pci_device_disable(dev); g_free(dev); - qpci_free_pc(bus); - test_end(); + qtest_shutdown(qs); } static void pci_idx(void) { QVirtioPCIDevice *dev; - QPCIBus *bus; + QOSState *qs; QVirtQueuePCI *vqpci; - QGuestAllocator *alloc; QVirtioBlkReq req; void *addr; uint64_t req_addr; @@ -567,13 +549,12 @@ static void pci_idx(void) uint8_t status; char *data; - bus = pci_test_start(); - alloc = pc_alloc_init(); + qs = pci_test_start(); - dev = virtio_blk_pci_init(bus, PCI_SLOT); + dev = virtio_blk_pci_init(qs->pcibus, PCI_SLOT); qpci_msix_enable(dev->pdev); - qvirtio_pci_set_msix_configuration_vector(dev, alloc, 0); + qvirtio_pci_set_msix_configuration_vector(dev, qs->alloc, 0); /* MSI-X is enabled */ addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(true); @@ -588,8 +569,8 @@ static void pci_idx(void) (1u << VIRTIO_BLK_F_SCSI)); qvirtio_set_features(&dev->vdev, features); - vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, 0); - qvirtqueue_pci_msix_setup(dev, vqpci, alloc, 1); + vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, qs->alloc, 0); + qvirtqueue_pci_msix_setup(dev, vqpci, qs->alloc, 1); qvirtio_set_driver_ok(&dev->vdev); @@ -600,7 +581,7 @@ static void pci_idx(void) req.data = g_malloc0(512); strcpy(req.data, "TEST"); - req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); + req_addr = virtio_blk_request(qs->alloc, &dev->vdev, &req, 512); g_free(req.data); @@ -618,7 +599,7 @@ static void pci_idx(void) req.data = g_malloc0(512); strcpy(req.data, "TEST"); - req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); + req_addr = virtio_blk_request(qs->alloc, &dev->vdev, &req, 512); g_free(req.data); @@ -635,7 +616,7 @@ static void pci_idx(void) QVIRTIO_BLK_TIMEOUT_US); g_assert_cmpint(status, ==, 0); - guest_free(alloc, req_addr); + guest_free(qs->alloc, req_addr); /* Read request */ req.type = VIRTIO_BLK_T_IN; @@ -643,7 +624,7 @@ static void pci_idx(void) req.sector = 1; req.data = g_malloc0(512); - req_addr = virtio_blk_request(alloc, &dev->vdev, &req, 512); + req_addr = virtio_blk_request(qs->alloc, &dev->vdev, &req, 512); g_free(req.data); @@ -664,38 +645,35 @@ static void pci_idx(void) g_assert_cmpstr(data, ==, "TEST"); g_free(data); - guest_free(alloc, req_addr); + guest_free(qs->alloc, req_addr); /* End test */ - qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, alloc); - pc_alloc_uninit(alloc); + qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, qs->alloc); qpci_msix_disable(dev->pdev); qvirtio_pci_device_disable(dev); g_free(dev); - qpci_free_pc(bus); - test_end(); + qtest_shutdown(qs); } static void pci_hotplug(void) { - QPCIBus *bus; QVirtioPCIDevice *dev; + QOSState *qs; - bus = pci_test_start(); + qs = pci_test_start(); /* plug secondary disk */ qpci_plug_device_test("virtio-blk-pci", "drv1", PCI_SLOT_HP, "'drive': 'drive1'"); - dev = virtio_blk_pci_init(bus, PCI_SLOT_HP); + dev = virtio_blk_pci_init(qs->pcibus, PCI_SLOT_HP); g_assert(dev); qvirtio_pci_device_disable(dev); g_free(dev); /* unplug secondary disk */ qpci_unplug_acpi_device_test("drv1", PCI_SLOT_HP); - qpci_free_pc(bus); - test_end(); + qtest_shutdown(qs); } static void mmio_basic(void) @@ -731,8 +709,8 @@ static void mmio_basic(void) /* End test */ qvirtqueue_cleanup(dev->vdev.bus, vq, alloc); - generic_alloc_uninit(alloc); g_free(dev); + generic_alloc_uninit(alloc); test_end(); } diff --git a/tests/virtio-net-test.c b/tests/virtio-net-test.c index 6fa385e90e..6bec784f81 100644 --- a/tests/virtio-net-test.c +++ b/tests/virtio-net-test.c @@ -12,12 +12,9 @@ #include "qemu-common.h" #include "qemu/sockets.h" #include "qemu/iov.h" -#include "libqos/pci-pc.h" +#include "libqos/libqos-pc.h" #include "libqos/virtio.h" #include "libqos/virtio-pci.h" -#include "libqos/malloc.h" -#include "libqos/malloc-pc.h" -#include "libqos/malloc-generic.h" #include "qemu/bswap.h" #include "hw/virtio/virtio-net.h" #include "standard-headers/linux/virtio_ids.h" @@ -53,16 +50,12 @@ static QVirtioPCIDevice *virtio_net_pci_init(QPCIBus *bus, int slot) return dev; } -static QPCIBus *pci_test_start(int socket) +static QOSState *pci_test_start(int socket) { - char *cmdline; + const char *cmd = "-netdev socket,fd=%d,id=hs0 -device " + "virtio-net-pci,netdev=hs0"; - cmdline = g_strdup_printf("-netdev socket,fd=%d,id=hs0 -device " - "virtio-net-pci,netdev=hs0", socket); - qtest_start(cmdline); - g_free(cmdline); - - return qpci_init_pc(NULL); + return qtest_pc_boot(cmd, socket); } static void driver_init(QVirtioDevice *dev) @@ -205,9 +198,8 @@ static void stop_cont_test(QVirtioDevice *dev, static void pci_basic(gconstpointer data) { QVirtioPCIDevice *dev; - QPCIBus *bus; + QOSState *qs; QVirtQueuePCI *tx, *rx; - QGuestAllocator *alloc; void (*func) (QVirtioDevice *dev, QGuestAllocator *alloc, QVirtQueue *rvq, @@ -218,26 +210,23 @@ static void pci_basic(gconstpointer data) ret = socketpair(PF_UNIX, SOCK_STREAM, 0, sv); g_assert_cmpint(ret, !=, -1); - bus = pci_test_start(sv[1]); - dev = virtio_net_pci_init(bus, PCI_SLOT); + qs = pci_test_start(sv[1]); + dev = virtio_net_pci_init(qs->pcibus, PCI_SLOT); - alloc = pc_alloc_init(); - rx = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, 0); - tx = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, alloc, 1); + rx = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, qs->alloc, 0); + tx = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, qs->alloc, 1); driver_init(&dev->vdev); - func(&dev->vdev, alloc, &rx->vq, &tx->vq, sv[0]); + func(&dev->vdev, qs->alloc, &rx->vq, &tx->vq, sv[0]); /* End test */ close(sv[0]); - qvirtqueue_cleanup(dev->vdev.bus, &tx->vq, alloc); - qvirtqueue_cleanup(dev->vdev.bus, &rx->vq, alloc); - pc_alloc_uninit(alloc); + qvirtqueue_cleanup(dev->vdev.bus, &tx->vq, qs->alloc); + qvirtqueue_cleanup(dev->vdev.bus, &rx->vq, qs->alloc); qvirtio_pci_device_disable(dev); g_free(dev->pdev); g_free(dev); - qpci_free_pc(bus); - test_end(); + qtest_shutdown(qs); } #endif diff --git a/tests/virtio-scsi-test.c b/tests/virtio-scsi-test.c index 3dbec2f5f0..7d697abac0 100644 --- a/tests/virtio-scsi-test.c +++ b/tests/virtio-scsi-test.c @@ -11,12 +11,9 @@ #include "qemu/osdep.h" #include "libqtest.h" #include "block/scsi.h" +#include "libqos/libqos-pc.h" #include "libqos/virtio.h" #include "libqos/virtio-pci.h" -#include "libqos/pci-pc.h" -#include "libqos/malloc.h" -#include "libqos/malloc-pc.h" -#include "libqos/malloc-generic.h" #include "standard-headers/linux/virtio_ids.h" #include "standard-headers/linux/virtio_pci.h" #include "standard-headers/linux/virtio_scsi.h" @@ -29,28 +26,23 @@ typedef struct { QVirtioDevice *dev; - QGuestAllocator *alloc; - QPCIBus *bus; + QOSState *qs; int num_queues; QVirtQueue *vq[MAX_NUM_QUEUES + 2]; } QVirtIOSCSI; -static void qvirtio_scsi_start(const char *extra_opts) +static QOSState *qvirtio_scsi_start(const char *extra_opts) { - char *cmdline; + const char *cmd = "-drive id=drv0,if=none,file=/dev/null,format=raw " + "-device virtio-scsi-pci,id=vs0 " + "-device scsi-hd,bus=vs0.0,drive=drv0 %s"; - cmdline = g_strdup_printf( - "-drive id=drv0,if=none,file=/dev/null,format=raw " - "-device virtio-scsi-pci,id=vs0 " - "-device scsi-hd,bus=vs0.0,drive=drv0 %s", - extra_opts ? : ""); - qtest_start(cmdline); - g_free(cmdline); + return qtest_pc_boot(cmd, extra_opts ? : ""); } -static void qvirtio_scsi_stop(void) +static void qvirtio_scsi_stop(QOSState *qs) { - qtest_end(); + qtest_shutdown(qs); } static void qvirtio_scsi_pci_free(QVirtIOSCSI *vs) @@ -58,12 +50,11 @@ static void qvirtio_scsi_pci_free(QVirtIOSCSI *vs) int i; for (i = 0; i < vs->num_queues + 2; i++) { - qvirtqueue_cleanup(vs->dev->bus, vs->vq[i], vs->alloc); + qvirtqueue_cleanup(vs->dev->bus, vs->vq[i], vs->qs->alloc); } - pc_alloc_uninit(vs->alloc); qvirtio_pci_device_disable(container_of(vs->dev, QVirtioPCIDevice, vdev)); g_free(vs->dev); - qpci_free_pc(vs->bus); + qvirtio_scsi_stop(vs->qs); g_free(vs); } @@ -72,7 +63,7 @@ static uint64_t qvirtio_scsi_alloc(QVirtIOSCSI *vs, size_t alloc_size, { uint64_t addr; - addr = guest_alloc(vs->alloc, alloc_size); + addr = guest_alloc(vs->qs->alloc, alloc_size); if (data) { memwrite(addr, data, alloc_size); } @@ -129,10 +120,10 @@ static uint8_t virtio_scsi_do_command(QVirtIOSCSI *vs, const uint8_t *cdb, memread(resp_addr, resp_out, sizeof(*resp_out)); } - guest_free(vs->alloc, req_addr); - guest_free(vs->alloc, resp_addr); - guest_free(vs->alloc, data_in_addr); - guest_free(vs->alloc, data_out_addr); + guest_free(vs->qs->alloc, req_addr); + guest_free(vs->qs->alloc, resp_addr); + guest_free(vs->qs->alloc, data_in_addr); + guest_free(vs->qs->alloc, data_out_addr); return response; } @@ -146,10 +137,11 @@ static QVirtIOSCSI *qvirtio_scsi_pci_init(int slot) int i; vs = g_new0(QVirtIOSCSI, 1); - vs->alloc = pc_alloc_init(); - vs->bus = qpci_init_pc(NULL); - dev = qvirtio_pci_device_find(vs->bus, VIRTIO_ID_SCSI); + vs->qs = qvirtio_scsi_start("-drive file=blkdebug::null-co://," + "if=none,id=dr1,format=raw,file.align=4k " + "-device scsi-disk,drive=dr1,lun=0,scsi-id=1"); + dev = qvirtio_pci_device_find(vs->qs->pcibus, VIRTIO_ID_SCSI); vs->dev = (QVirtioDevice *)dev; g_assert(dev != NULL); g_assert_cmphex(vs->dev->device_type, ==, VIRTIO_ID_SCSI); @@ -165,7 +157,7 @@ static QVirtIOSCSI *qvirtio_scsi_pci_init(int slot) g_assert_cmpint(vs->num_queues, <, MAX_NUM_QUEUES); for (i = 0; i < vs->num_queues + 2; i++) { - vs->vq[i] = qvirtqueue_setup(vs->dev, vs->alloc, i); + vs->vq[i] = qvirtqueue_setup(vs->dev, vs->qs->alloc, i); } /* Clear the POWER ON OCCURRED unit attention */ @@ -184,15 +176,18 @@ static QVirtIOSCSI *qvirtio_scsi_pci_init(int slot) /* Tests only initialization so far. TODO: Replace with functional tests */ static void pci_nop(void) { - qvirtio_scsi_start(NULL); - qvirtio_scsi_stop(); + QOSState *qs; + + qs = qvirtio_scsi_start(NULL); + qvirtio_scsi_stop(qs); } static void hotplug(void) { QDict *response; + QOSState *qs; - qvirtio_scsi_start("-drive id=drv1,if=none,file=/dev/null,format=raw"); + qs = qvirtio_scsi_start("-drive id=drv1,if=none,file=/dev/null,format=raw"); response = qmp("{\"execute\": \"device_add\"," " \"arguments\": {" " \"driver\": \"scsi-hd\"," @@ -214,7 +209,7 @@ static void hotplug(void) g_assert(qdict_haskey(response, "event")); g_assert(!strcmp(qdict_get_str(response, "event"), "DEVICE_DELETED")); QDECREF(response); - qvirtio_scsi_stop(); + qvirtio_scsi_stop(qs); } /* Test WRITE SAME with the lba not aligned */ @@ -230,9 +225,6 @@ static void test_unaligned_write_same(void) 0x41, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x33, 0x00, 0x00 }; - qvirtio_scsi_start("-drive file=blkdebug::null-co://,if=none,id=dr1" - ",format=raw,file.align=4k " - "-device scsi-disk,drive=dr1,lun=0,scsi-id=1"); vs = qvirtio_scsi_pci_init(PCI_SLOT); g_assert_cmphex(0, ==, @@ -242,7 +234,6 @@ static void test_unaligned_write_same(void) virtio_scsi_do_command(vs, write_same_cdb_2, NULL, 0, buf2, 512, NULL)); qvirtio_scsi_pci_free(vs); - qvirtio_scsi_stop(); } int main(int argc, char **argv) From 30ca440eec9fe1d7eec5a48addac656438778278 Mon Sep 17 00:00:00 2001 From: Laurent Vivier Date: Mon, 17 Oct 2016 12:30:24 +0200 Subject: [PATCH 08/73] tests: enable virtio tests on SPAPR but disable MSI-X tests on SPAPR as we can't check the result (the memory region used on PC is not readable on SPAPR). Signed-off-by: Laurent Vivier Signed-off-by: David Gibson --- tests/Makefile.include | 3 ++- tests/libqos/virtio-pci.c | 24 ++++++++++++++++++++++-- tests/virtio-9p-test.c | 12 +++++++++++- tests/virtio-blk-test.c | 25 ++++++++++++++++++++----- tests/virtio-net-test.c | 18 ++++++++++++++++-- tests/virtio-rng-test.c | 7 ++++++- tests/virtio-scsi-test.c | 12 +++++++++++- 7 files changed, 88 insertions(+), 13 deletions(-) diff --git a/tests/Makefile.include b/tests/Makefile.include index 22656eaf26..1a135d2340 100644 --- a/tests/Makefile.include +++ b/tests/Makefile.include @@ -282,6 +282,7 @@ check-qtest-ppc64-y += tests/usb-hcd-uhci-test$(EXESUF) gcov-files-ppc64-y += hw/usb/hcd-uhci.c check-qtest-ppc64-y += tests/usb-hcd-xhci-test$(EXESUF) gcov-files-ppc64-y += hw/usb/hcd-xhci.c +check-qtest-ppc64-y += $(check-qtest-virtio-y) check-qtest-sh4-y = tests/endianness-test$(EXESUF) @@ -615,7 +616,7 @@ libqos-pc-obj-y += tests/libqos/ahci.o libqos-omap-obj-y = $(libqos-obj-y) tests/libqos/i2c-omap.o libqos-imx-obj-y = $(libqos-obj-y) tests/libqos/i2c-imx.o libqos-usb-obj-y = $(libqos-spapr-obj-y) $(libqos-pc-obj-y) tests/libqos/usb.o -libqos-virtio-obj-y = $(libqos-pc-obj-y) tests/libqos/virtio.o tests/libqos/virtio-pci.o tests/libqos/virtio-mmio.o tests/libqos/malloc-generic.o +libqos-virtio-obj-y = $(libqos-spapr-obj-y) $(libqos-pc-obj-y) tests/libqos/virtio.o tests/libqos/virtio-pci.o tests/libqos/virtio-mmio.o tests/libqos/malloc-generic.o tests/device-introspect-test$(EXESUF): tests/device-introspect-test.o tests/rtc-test$(EXESUF): tests/rtc-test.o diff --git a/tests/libqos/virtio-pci.c b/tests/libqos/virtio-pci.c index 7aa29b1a9c..7e60b3a427 100644 --- a/tests/libqos/virtio-pci.c +++ b/tests/libqos/virtio-pci.c @@ -68,16 +68,36 @@ static uint8_t qvirtio_pci_config_readb(QVirtioDevice *d, uint64_t addr) return qpci_io_readb(dev->pdev, (void *)(uintptr_t)addr); } +/* PCI is always read in little-endian order + * but virtio ( < 1.0) is in guest order + * so with a big-endian guest the order has been reversed, + * reverse it again + * virtio-1.0 is always little-endian, like PCI, but this + * case will be managed inside qvirtio_is_big_endian() + */ + static uint16_t qvirtio_pci_config_readw(QVirtioDevice *d, uint64_t addr) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - return qpci_io_readw(dev->pdev, (void *)(uintptr_t)addr); + uint16_t value; + + value = qpci_io_readw(dev->pdev, (void *)(uintptr_t)addr); + if (qvirtio_is_big_endian(d)) { + value = bswap16(value); + } + return value; } static uint32_t qvirtio_pci_config_readl(QVirtioDevice *d, uint64_t addr) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - return qpci_io_readl(dev->pdev, (void *)(uintptr_t)addr); + uint32_t value; + + value = qpci_io_readl(dev->pdev, (void *)(uintptr_t)addr); + if (qvirtio_is_big_endian(d)) { + value = bswap32(value); + } + return value; } static uint64_t qvirtio_pci_config_readq(QVirtioDevice *d, uint64_t addr) diff --git a/tests/virtio-9p-test.c b/tests/virtio-9p-test.c index 851ec99404..693920af5f 100644 --- a/tests/virtio-9p-test.c +++ b/tests/virtio-9p-test.c @@ -11,6 +11,7 @@ #include "libqtest.h" #include "qemu-common.h" #include "libqos/libqos-pc.h" +#include "libqos/libqos-spapr.h" #include "libqos/virtio.h" #include "libqos/virtio-pci.h" #include "standard-headers/linux/virtio_ids.h" @@ -22,13 +23,22 @@ static char *test_share; static QOSState *qvirtio_9p_start(void) { + const char *arch = qtest_get_arch(); const char *cmd = "-fsdev local,id=fsdev0,security_model=none,path=%s " "-device virtio-9p-pci,fsdev=fsdev0,mount_tag=%s"; test_share = g_strdup("/tmp/qtest.XXXXXX"); g_assert_nonnull(mkdtemp(test_share)); - return qtest_pc_boot(cmd, test_share, mount_tag); + if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { + return qtest_pc_boot(cmd, test_share, mount_tag); + } + if (strcmp(arch, "ppc64") == 0) { + return qtest_spapr_boot(cmd, test_share, mount_tag); + } + + g_printerr("virtio-9p tests are only available on x86 or ppc64\n"); + exit(EXIT_FAILURE); } static void qvirtio_9p_stop(QOSState *qs) diff --git a/tests/virtio-blk-test.c b/tests/virtio-blk-test.c index 2382eb5cc1..f737c406e3 100644 --- a/tests/virtio-blk-test.c +++ b/tests/virtio-blk-test.c @@ -11,6 +11,7 @@ #include "qemu/osdep.h" #include "libqtest.h" #include "libqos/libqos-pc.h" +#include "libqos/libqos-spapr.h" #include "libqos/virtio.h" #include "libqos/virtio-pci.h" #include "libqos/virtio-mmio.h" @@ -59,6 +60,7 @@ static char *drive_create(void) static QOSState *pci_test_start(void) { QOSState *qs; + const char *arch = qtest_get_arch(); char *tmp_path; const char *cmd = "-drive if=none,id=drive0,file=%s,format=raw " "-drive if=none,id=drive1,file=/dev/null,format=raw " @@ -67,7 +69,14 @@ static QOSState *pci_test_start(void) tmp_path = drive_create(); - qs = qtest_pc_boot(cmd, tmp_path, PCI_SLOT, PCI_FN); + if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { + qs = qtest_pc_boot(cmd, tmp_path, PCI_SLOT, PCI_FN); + } else if (strcmp(arch, "ppc64") == 0) { + qs = qtest_spapr_boot(cmd, tmp_path, PCI_SLOT, PCI_FN); + } else { + g_printerr("virtio-blk tests are only available on x86 or ppc64\n"); + exit(EXIT_FAILURE); + } unlink(tmp_path); g_free(tmp_path); return qs; @@ -659,6 +668,7 @@ static void pci_hotplug(void) { QVirtioPCIDevice *dev; QOSState *qs; + const char *arch = qtest_get_arch(); qs = pci_test_start(); @@ -672,7 +682,9 @@ static void pci_hotplug(void) g_free(dev); /* unplug secondary disk */ - qpci_unplug_acpi_device_test("drv1", PCI_SLOT_HP); + if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { + qpci_unplug_acpi_device_test("drv1", PCI_SLOT_HP); + } qtest_shutdown(qs); } @@ -720,12 +732,15 @@ int main(int argc, char **argv) g_test_init(&argc, &argv, NULL); - if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { + if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0 || + strcmp(arch, "ppc64") == 0) { qtest_add_func("/virtio/blk/pci/basic", pci_basic); qtest_add_func("/virtio/blk/pci/indirect", pci_indirect); qtest_add_func("/virtio/blk/pci/config", pci_config); - qtest_add_func("/virtio/blk/pci/msix", pci_msix); - qtest_add_func("/virtio/blk/pci/idx", pci_idx); + if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { + qtest_add_func("/virtio/blk/pci/msix", pci_msix); + qtest_add_func("/virtio/blk/pci/idx", pci_idx); + } qtest_add_func("/virtio/blk/pci/hotplug", pci_hotplug); } else if (strcmp(arch, "arm") == 0) { qtest_add_func("/virtio/blk/mmio/basic", mmio_basic); diff --git a/tests/virtio-net-test.c b/tests/virtio-net-test.c index 6bec784f81..8f94360480 100644 --- a/tests/virtio-net-test.c +++ b/tests/virtio-net-test.c @@ -13,6 +13,7 @@ #include "qemu/sockets.h" #include "qemu/iov.h" #include "libqos/libqos-pc.h" +#include "libqos/libqos-spapr.h" #include "libqos/virtio.h" #include "libqos/virtio-pci.h" #include "qemu/bswap.h" @@ -52,10 +53,18 @@ static QVirtioPCIDevice *virtio_net_pci_init(QPCIBus *bus, int slot) static QOSState *pci_test_start(int socket) { + const char *arch = qtest_get_arch(); const char *cmd = "-netdev socket,fd=%d,id=hs0 -device " "virtio-net-pci,netdev=hs0"; - return qtest_pc_boot(cmd, socket); + if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { + return qtest_pc_boot(cmd, socket); + } + if (strcmp(arch, "ppc64") == 0) { + return qtest_spapr_boot(cmd, socket); + } + g_printerr("virtio-net tests are only available on x86 or ppc64\n"); + exit(EXIT_FAILURE); } static void driver_init(QVirtioDevice *dev) @@ -232,10 +241,15 @@ static void pci_basic(gconstpointer data) static void hotplug(void) { + const char *arch = qtest_get_arch(); + qtest_start("-device virtio-net-pci"); qpci_plug_device_test("virtio-net-pci", "net1", PCI_SLOT_HP, NULL); - qpci_unplug_acpi_device_test("net1", PCI_SLOT_HP); + + if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { + qpci_unplug_acpi_device_test("net1", PCI_SLOT_HP); + } test_end(); } diff --git a/tests/virtio-rng-test.c b/tests/virtio-rng-test.c index e1b26401f9..dcecf77463 100644 --- a/tests/virtio-rng-test.c +++ b/tests/virtio-rng-test.c @@ -20,8 +20,13 @@ static void pci_nop(void) static void hotplug(void) { + const char *arch = qtest_get_arch(); + qpci_plug_device_test("virtio-rng-pci", "rng1", PCI_SLOT_HP, NULL); - qpci_unplug_acpi_device_test("rng1", PCI_SLOT_HP); + + if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { + qpci_unplug_acpi_device_test("rng1", PCI_SLOT_HP); + } } int main(int argc, char **argv) diff --git a/tests/virtio-scsi-test.c b/tests/virtio-scsi-test.c index 7d697abac0..60dc9abd60 100644 --- a/tests/virtio-scsi-test.c +++ b/tests/virtio-scsi-test.c @@ -12,6 +12,7 @@ #include "libqtest.h" #include "block/scsi.h" #include "libqos/libqos-pc.h" +#include "libqos/libqos-spapr.h" #include "libqos/virtio.h" #include "libqos/virtio-pci.h" #include "standard-headers/linux/virtio_ids.h" @@ -33,11 +34,20 @@ typedef struct { static QOSState *qvirtio_scsi_start(const char *extra_opts) { + const char *arch = qtest_get_arch(); const char *cmd = "-drive id=drv0,if=none,file=/dev/null,format=raw " "-device virtio-scsi-pci,id=vs0 " "-device scsi-hd,bus=vs0.0,drive=drv0 %s"; - return qtest_pc_boot(cmd, extra_opts ? : ""); + if (strcmp(arch, "i386") == 0 || strcmp(arch, "x86_64") == 0) { + return qtest_pc_boot(cmd, extra_opts ? : ""); + } + if (strcmp(arch, "ppc64") == 0) { + return qtest_spapr_boot(cmd, extra_opts ? : ""); + } + + g_printerr("virtio-scsi tests are only available on x86 or ppc64\n"); + exit(EXIT_FAILURE); } static void qvirtio_scsi_stop(QOSState *qs) From 4bcfa56ca9f6970974255dd5621b08e5aa9e5af5 Mon Sep 17 00:00:00 2001 From: Michael Roth Date: Tue, 18 Oct 2016 15:50:23 -0500 Subject: [PATCH 09/73] spapr_pci: advertise explicit numa IDs even when there's 1 node With the addition of "numa_node" properties for PHBs we began advertising NUMA affinity in cases where nb_numa_nodes > 1. Since the default on the guest side is to make no assumptions about PHB NUMA affinity (defaulting to -1), there is still a valid use-case for explicitly defining a PHB's NUMA affinity even when there's just one node. In particular, some workloads make faulty assumptions about /sys/bus/pci//numa_node being >= 0, warranting the use of this property as a workaround even if there's just 1 PHB or NUMA node. Enable this use-case by always advertising the PHB's NUMA affinity if "numa_node" has been explicitly set. We could achieve this by relaxing the check to simply be nb_numa_nodes > 0, but even safer would be to check numa_info[nodeid].present explicitly, and to fail at start time for cases where it does not exist. This has an additional affect of no longer advertising PHB NUMA affinity unconditionally if nb_numa_nodes > 1 and "numa_node" property is unset/-1, but since the default value on the guest side for each PHB is also -1, the behavior should be the same for that situation. We could still retain the old behavior if desired, but the decision seems arbitrary, so we take the simpler route. Cc: Alexey Kardashevskiy Cc: Shivaprasad G. Bhat Signed-off-by: Michael Roth Signed-off-by: David Gibson --- hw/ppc/spapr_pci.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/hw/ppc/spapr_pci.c b/hw/ppc/spapr_pci.c index 2a1ccf59ea..7cde30ee09 100644 --- a/hw/ppc/spapr_pci.c +++ b/hw/ppc/spapr_pci.c @@ -1392,6 +1392,12 @@ static void spapr_phb_realize(DeviceState *dev, Error **errp) return; } + if (sphb->numa_node != -1 && + (sphb->numa_node >= MAX_NODES || !numa_info[sphb->numa_node].present)) { + error_setg(errp, "Invalid NUMA node ID for PCI host bridge"); + return; + } + sphb->dtbusname = g_strdup_printf("pci@%" PRIx64, sphb->buid); namebuf = alloca(strlen(sphb->dtbusname) + 32); @@ -1880,7 +1886,7 @@ int spapr_populate_pci_dt(sPAPRPHBState *phb, } /* Advertise NUMA via ibm,associativity */ - if (nb_numa_nodes > 1) { + if (phb->numa_node != -1) { _FDT(fdt_setprop(fdt, bus_off, "ibm,associativity", associativity, sizeof(associativity))); } From 55d9950aaa8e87372cfae2a7efc810f078f36818 Mon Sep 17 00:00:00 2001 From: Thomas Huth Date: Tue, 18 Oct 2016 22:46:40 +0200 Subject: [PATCH 10/73] nvram: Introduce helper functions for CHRP "system" and "free space" partitions The "system partition" and "free space" partition layouts are defined by the CHRP and LoPAPR specification, and used by OpenBIOS and SLOF. We can re-use this code for other machines that use OpenBIOS and SLOF, too. So let's make this code independent from the MAC NVRAM environment and put it into two proper helper functions. Signed-off-by: Thomas Huth Tested-by: Mark Cave-Ayland Signed-off-by: David Gibson --- hw/nvram/Makefile.objs | 1 + hw/nvram/chrp_nvram.c | 76 +++++++++++++++++++++++++++++++++++ hw/nvram/mac_nvram.c | 38 ++++-------------- include/hw/nvram/chrp_nvram.h | 24 +++++++++++ 4 files changed, 108 insertions(+), 31 deletions(-) create mode 100644 hw/nvram/chrp_nvram.c create mode 100644 include/hw/nvram/chrp_nvram.h diff --git a/hw/nvram/Makefile.objs b/hw/nvram/Makefile.objs index e9a66940e0..c018f6b2ff 100644 --- a/hw/nvram/Makefile.objs +++ b/hw/nvram/Makefile.objs @@ -1,5 +1,6 @@ common-obj-$(CONFIG_DS1225Y) += ds1225y.o common-obj-y += eeprom93xx.o common-obj-y += fw_cfg.o +common-obj-y += chrp_nvram.o common-obj-$(CONFIG_MAC_NVRAM) += mac_nvram.o obj-$(CONFIG_PSERIES) += spapr_nvram.o diff --git a/hw/nvram/chrp_nvram.c b/hw/nvram/chrp_nvram.c new file mode 100644 index 0000000000..f6183ed044 --- /dev/null +++ b/hw/nvram/chrp_nvram.c @@ -0,0 +1,76 @@ +/* + * Common Hardware Reference Platform NVRAM helper functions. + * + * The CHRP NVRAM layout is used by OpenBIOS and SLOF. See CHRP + * specification, chapter 8, or the LoPAPR specification for details + * about the NVRAM layout. + * + * This code is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published + * by the Free Software Foundation; either version 2 of the License, + * or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, see . + */ + +#include "qemu/osdep.h" +#include "qemu/cutils.h" +#include "hw/hw.h" +#include "hw/nvram/chrp_nvram.h" +#include "hw/nvram/openbios_firmware_abi.h" +#include "sysemu/sysemu.h" + +/** + * Create a "system partition", used for the Open Firmware + * environment variables. + */ +int chrp_nvram_create_system_partition(uint8_t *data, int min_len) +{ + struct OpenBIOS_nvpart_v1 *part_header; + unsigned int i; + int end; + + part_header = (struct OpenBIOS_nvpart_v1 *)data; + part_header->signature = OPENBIOS_PART_SYSTEM; + pstrcpy(part_header->name, sizeof(part_header->name), "system"); + + end = sizeof(struct OpenBIOS_nvpart_v1); + for (i = 0; i < nb_prom_envs; i++) { + end = OpenBIOS_set_var(data, end, prom_envs[i]); + } + + /* End marker */ + data[end++] = '\0'; + + end = (end + 15) & ~15; + /* XXX: OpenBIOS is not able to grow up a partition. Leave some space for + new variables. */ + if (end < min_len) { + end = min_len; + } + OpenBIOS_finish_partition(part_header, end); + + return end; +} + +/** + * Create a "free space" partition + */ +int chrp_nvram_create_free_partition(uint8_t *data, int len) +{ + struct OpenBIOS_nvpart_v1 *part_header; + + part_header = (struct OpenBIOS_nvpart_v1 *)data; + part_header->signature = OPENBIOS_PART_FREE; + pstrcpy(part_header->name, sizeof(part_header->name), "free"); + + OpenBIOS_finish_partition(part_header, len); + + return len; +} diff --git a/hw/nvram/mac_nvram.c b/hw/nvram/mac_nvram.c index 24f61212ba..c0e62a52b3 100644 --- a/hw/nvram/mac_nvram.c +++ b/hw/nvram/mac_nvram.c @@ -25,7 +25,7 @@ #include "qemu/osdep.h" #include "hw/hw.h" #include "hw/nvram/openbios_firmware_abi.h" -#include "sysemu/sysemu.h" +#include "hw/nvram/chrp_nvram.h" #include "hw/ppc/mac.h" #include "qemu/cutils.h" #include @@ -146,38 +146,14 @@ static void macio_nvram_register_types(void) static void pmac_format_nvram_partition_of(MacIONVRAMState *nvr, int off, int len) { - unsigned int i; - uint32_t start = off, end; - struct OpenBIOS_nvpart_v1 *part_header; + int sysp_end; - // OpenBIOS nvram variables - // Variable partition - part_header = (struct OpenBIOS_nvpart_v1 *)&nvr->data[start]; - part_header->signature = OPENBIOS_PART_SYSTEM; - pstrcpy(part_header->name, sizeof(part_header->name), "system"); + /* OpenBIOS nvram variables partition */ + sysp_end = chrp_nvram_create_system_partition(&nvr->data[off], + DEF_SYSTEM_SIZE) + off; - end = start + sizeof(struct OpenBIOS_nvpart_v1); - for (i = 0; i < nb_prom_envs; i++) - end = OpenBIOS_set_var(nvr->data, end, prom_envs[i]); - - // End marker - nvr->data[end++] = '\0'; - - end = start + ((end - start + 15) & ~15); - /* XXX: OpenBIOS is not able to grow up a partition. Leave some space for - new variables. */ - if (end < DEF_SYSTEM_SIZE) - end = DEF_SYSTEM_SIZE; - OpenBIOS_finish_partition(part_header, end - start); - - // free partition - start = end; - part_header = (struct OpenBIOS_nvpart_v1 *)&nvr->data[start]; - part_header->signature = OPENBIOS_PART_FREE; - pstrcpy(part_header->name, sizeof(part_header->name), "free"); - - end = len; - OpenBIOS_finish_partition(part_header, end - start); + /* Free space partition */ + chrp_nvram_create_free_partition(&nvr->data[sysp_end], len - sysp_end); } #define OSX_NVRAM_SIGNATURE (0x5A) diff --git a/include/hw/nvram/chrp_nvram.h b/include/hw/nvram/chrp_nvram.h new file mode 100644 index 0000000000..18d19765d0 --- /dev/null +++ b/include/hw/nvram/chrp_nvram.h @@ -0,0 +1,24 @@ +/* + * Common Hardware Reference Platform NVRAM functions. + * + * This code is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published + * by the Free Software Foundation; either version 2 of the License, + * or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, see . + */ + +#ifndef CHRP_NVRAM_H +#define CHRP_NVRAM_H + +int chrp_nvram_create_system_partition(uint8_t *data, int min_len); +int chrp_nvram_create_free_partition(uint8_t *data, int len); + +#endif From 2024c01421eb990e7043afa0e0e4d67f4477596f Mon Sep 17 00:00:00 2001 From: Thomas Huth Date: Tue, 18 Oct 2016 22:46:41 +0200 Subject: [PATCH 11/73] sparc: Use the new common NVRAM functions for system and free space partition The system and free space NVRAM partitions (for OpenBIOS) are created in exactly the same way as the Mac-style CHRP NVRAM partitions, so we can use the new common helper functions to do this job here, too. Signed-off-by: Thomas Huth Tested-by: Mark Cave-Ayland Signed-off-by: David Gibson --- hw/sparc/sun4m.c | 33 ++++++--------------------------- hw/sparc64/sun4u.c | 33 ++++++--------------------------- 2 files changed, 12 insertions(+), 54 deletions(-) diff --git a/hw/sparc/sun4m.c b/hw/sparc/sun4m.c index b3915e4fd6..1b8d172c4e 100644 --- a/hw/sparc/sun4m.c +++ b/hw/sparc/sun4m.c @@ -39,6 +39,7 @@ #include "hw/scsi/esp.h" #include "hw/i386/pc.h" #include "hw/isa/isa.h" +#include "hw/nvram/chrp_nvram.h" #include "hw/nvram/fw_cfg.h" #include "hw/char/escc.h" #include "hw/empty_slot.h" @@ -117,39 +118,17 @@ static void nvram_init(Nvram *nvram, uint8_t *macaddr, int nvram_machine_id, const char *arch) { unsigned int i; - uint32_t start, end; + int sysp_end; uint8_t image[0x1ff0]; - struct OpenBIOS_nvpart_v1 *part_header; NvramClass *k = NVRAM_GET_CLASS(nvram); memset(image, '\0', sizeof(image)); - start = 0; + /* OpenBIOS nvram variables partition */ + sysp_end = chrp_nvram_create_system_partition(image, 0); - // OpenBIOS nvram variables - // Variable partition - part_header = (struct OpenBIOS_nvpart_v1 *)&image[start]; - part_header->signature = OPENBIOS_PART_SYSTEM; - pstrcpy(part_header->name, sizeof(part_header->name), "system"); - - end = start + sizeof(struct OpenBIOS_nvpart_v1); - for (i = 0; i < nb_prom_envs; i++) - end = OpenBIOS_set_var(image, end, prom_envs[i]); - - // End marker - image[end++] = '\0'; - - end = start + ((end - start + 15) & ~15); - OpenBIOS_finish_partition(part_header, end - start); - - // free partition - start = end; - part_header = (struct OpenBIOS_nvpart_v1 *)&image[start]; - part_header->signature = OPENBIOS_PART_FREE; - pstrcpy(part_header->name, sizeof(part_header->name), "free"); - - end = 0x1fd0; - OpenBIOS_finish_partition(part_header, end - start); + /* Free space partition */ + chrp_nvram_create_free_partition(&image[sysp_end], 0x1fd0 - sysp_end); Sun_init_header((struct Sun_nvram *)&image[0x1fd8], macaddr, nvram_machine_id); diff --git a/hw/sparc64/sun4u.c b/hw/sparc64/sun4u.c index 7b8134ef51..83708abbf4 100644 --- a/hw/sparc64/sun4u.c +++ b/hw/sparc64/sun4u.c @@ -37,6 +37,7 @@ #include "sysemu/sysemu.h" #include "hw/boards.h" #include "hw/nvram/openbios_firmware_abi.h" +#include "hw/nvram/chrp_nvram.h" #include "hw/nvram/fw_cfg.h" #include "hw/sysbus.h" #include "hw/ide.h" @@ -124,39 +125,17 @@ static int sun4u_NVRAM_set_params(Nvram *nvram, uint16_t NVRAM_size, const uint8_t *macaddr) { unsigned int i; - uint32_t start, end; + int sysp_end; uint8_t image[0x1ff0]; - struct OpenBIOS_nvpart_v1 *part_header; NvramClass *k = NVRAM_GET_CLASS(nvram); memset(image, '\0', sizeof(image)); - start = 0; + /* OpenBIOS nvram variables partition */ + sysp_end = chrp_nvram_create_system_partition(image, 0); - // OpenBIOS nvram variables - // Variable partition - part_header = (struct OpenBIOS_nvpart_v1 *)&image[start]; - part_header->signature = OPENBIOS_PART_SYSTEM; - pstrcpy(part_header->name, sizeof(part_header->name), "system"); - - end = start + sizeof(struct OpenBIOS_nvpart_v1); - for (i = 0; i < nb_prom_envs; i++) - end = OpenBIOS_set_var(image, end, prom_envs[i]); - - // End marker - image[end++] = '\0'; - - end = start + ((end - start + 15) & ~15); - OpenBIOS_finish_partition(part_header, end - start); - - // free partition - start = end; - part_header = (struct OpenBIOS_nvpart_v1 *)&image[start]; - part_header->signature = OPENBIOS_PART_FREE; - pstrcpy(part_header->name, sizeof(part_header->name), "free"); - - end = 0x1fd0; - OpenBIOS_finish_partition(part_header, end - start); + /* Free space partition */ + chrp_nvram_create_free_partition(&image[sysp_end], 0x1fd0 - sysp_end); Sun_init_header((struct Sun_nvram *)&image[0x1fd8], macaddr, 0x80); From ad723fe5a050b685e496f2202a919f9e32c45c43 Mon Sep 17 00:00:00 2001 From: Thomas Huth Date: Tue, 18 Oct 2016 22:46:43 +0200 Subject: [PATCH 12/73] nvram: Move the remaining CHRP NVRAM related code to chrp_nvram.[ch] Everything that is related to CHRP NVRAM should rather reside in chrp_nvram.c / chrp_nvram.h instead of openbios_firmware_abi.h. Signed-off-by: Thomas Huth Tested-by: Mark Cave-Ayland Signed-off-by: David Gibson --- hw/nvram/chrp_nvram.c | 31 +++++++++++------- hw/nvram/mac_nvram.c | 7 ++-- include/hw/nvram/chrp_nvram.h | 30 +++++++++++++++++ include/hw/nvram/openbios_firmware_abi.h | 41 ------------------------ tests/postcopy-test.c | 8 ++--- 5 files changed, 57 insertions(+), 60 deletions(-) diff --git a/hw/nvram/chrp_nvram.c b/hw/nvram/chrp_nvram.c index f6183ed044..3837510dd2 100644 --- a/hw/nvram/chrp_nvram.c +++ b/hw/nvram/chrp_nvram.c @@ -23,26 +23,35 @@ #include "qemu/cutils.h" #include "hw/hw.h" #include "hw/nvram/chrp_nvram.h" -#include "hw/nvram/openbios_firmware_abi.h" #include "sysemu/sysemu.h" +static int chrp_nvram_set_var(uint8_t *nvram, int addr, const char *str) +{ + int len; + + len = strlen(str) + 1; + memcpy(&nvram[addr], str, len); + + return addr + len; +} + /** * Create a "system partition", used for the Open Firmware * environment variables. */ int chrp_nvram_create_system_partition(uint8_t *data, int min_len) { - struct OpenBIOS_nvpart_v1 *part_header; + ChrpNvramPartHdr *part_header; unsigned int i; int end; - part_header = (struct OpenBIOS_nvpart_v1 *)data; - part_header->signature = OPENBIOS_PART_SYSTEM; + part_header = (ChrpNvramPartHdr *)data; + part_header->signature = CHRP_NVPART_SYSTEM; pstrcpy(part_header->name, sizeof(part_header->name), "system"); - end = sizeof(struct OpenBIOS_nvpart_v1); + end = sizeof(ChrpNvramPartHdr); for (i = 0; i < nb_prom_envs; i++) { - end = OpenBIOS_set_var(data, end, prom_envs[i]); + end = chrp_nvram_set_var(data, end, prom_envs[i]); } /* End marker */ @@ -54,7 +63,7 @@ int chrp_nvram_create_system_partition(uint8_t *data, int min_len) if (end < min_len) { end = min_len; } - OpenBIOS_finish_partition(part_header, end); + chrp_nvram_finish_partition(part_header, end); return end; } @@ -64,13 +73,13 @@ int chrp_nvram_create_system_partition(uint8_t *data, int min_len) */ int chrp_nvram_create_free_partition(uint8_t *data, int len) { - struct OpenBIOS_nvpart_v1 *part_header; + ChrpNvramPartHdr *part_header; - part_header = (struct OpenBIOS_nvpart_v1 *)data; - part_header->signature = OPENBIOS_PART_FREE; + part_header = (ChrpNvramPartHdr *)data; + part_header->signature = CHRP_NVPART_FREE; pstrcpy(part_header->name, sizeof(part_header->name), "free"); - OpenBIOS_finish_partition(part_header, len); + chrp_nvram_finish_partition(part_header, len); return len; } diff --git a/hw/nvram/mac_nvram.c b/hw/nvram/mac_nvram.c index c0e62a52b3..63f9ed1d82 100644 --- a/hw/nvram/mac_nvram.c +++ b/hw/nvram/mac_nvram.c @@ -24,7 +24,6 @@ */ #include "qemu/osdep.h" #include "hw/hw.h" -#include "hw/nvram/openbios_firmware_abi.h" #include "hw/nvram/chrp_nvram.h" #include "hw/ppc/mac.h" #include "qemu/cutils.h" @@ -163,15 +162,15 @@ static void pmac_format_nvram_partition_osx(MacIONVRAMState *nvr, int off, int len) { uint32_t start = off; - struct OpenBIOS_nvpart_v1 *part_header; + ChrpNvramPartHdr *part_header; unsigned char *data = &nvr->data[start]; /* empty partition */ - part_header = (struct OpenBIOS_nvpart_v1 *)data; + part_header = (ChrpNvramPartHdr *)data; part_header->signature = OSX_NVRAM_SIGNATURE; pstrcpy(part_header->name, sizeof(part_header->name), "wwwwwwwwwwww"); - OpenBIOS_finish_partition(part_header, len); + chrp_nvram_finish_partition(part_header, len); /* Generation */ stl_be_p(&data[20], 2); diff --git a/include/hw/nvram/chrp_nvram.h b/include/hw/nvram/chrp_nvram.h index 18d19765d0..b4f5b2b104 100644 --- a/include/hw/nvram/chrp_nvram.h +++ b/include/hw/nvram/chrp_nvram.h @@ -18,6 +18,36 @@ #ifndef CHRP_NVRAM_H #define CHRP_NVRAM_H +/* OpenBIOS NVRAM partition */ +typedef struct { + uint8_t signature; + uint8_t checksum; + uint16_t len; /* Big endian, length divided by 16 */ + char name[12]; +} ChrpNvramPartHdr; + +#define CHRP_NVPART_SYSTEM 0x70 +#define CHRP_NVPART_FREE 0x7f + +static inline void +chrp_nvram_finish_partition(ChrpNvramPartHdr *header, uint32_t size) +{ + unsigned int i, sum; + uint8_t *tmpptr; + + /* Length divided by 16 */ + header->len = cpu_to_be16(size >> 4); + + /* Checksum */ + tmpptr = (uint8_t *)header; + sum = *tmpptr; + for (i = 0; i < 14; i++) { + sum += tmpptr[2 + i]; + sum = (sum + ((sum & 0xff00) >> 8)) & 0xff; + } + header->checksum = sum & 0xff; +} + int chrp_nvram_create_system_partition(uint8_t *data, int min_len); int chrp_nvram_create_free_partition(uint8_t *data, int len); diff --git a/include/hw/nvram/openbios_firmware_abi.h b/include/hw/nvram/openbios_firmware_abi.h index 74cfd56180..27ce9f4a53 100644 --- a/include/hw/nvram/openbios_firmware_abi.h +++ b/include/hw/nvram/openbios_firmware_abi.h @@ -1,47 +1,6 @@ #ifndef OPENBIOS_FIRMWARE_ABI_H #define OPENBIOS_FIRMWARE_ABI_H -/* OpenBIOS NVRAM partition */ -struct OpenBIOS_nvpart_v1 { - uint8_t signature; - uint8_t checksum; - uint16_t len; // BE, length divided by 16 - char name[12]; -}; - -#define OPENBIOS_PART_SYSTEM 0x70 -#define OPENBIOS_PART_FREE 0x7f - -static inline void -OpenBIOS_finish_partition(struct OpenBIOS_nvpart_v1 *header, uint32_t size) -{ - unsigned int i, sum; - uint8_t *tmpptr; - - // Length divided by 16 - header->len = cpu_to_be16(size >> 4); - - // Checksum - tmpptr = (uint8_t *)header; - sum = *tmpptr; - for (i = 0; i < 14; i++) { - sum += tmpptr[2 + i]; - sum = (sum + ((sum & 0xff00) >> 8)) & 0xff; - } - header->checksum = sum & 0xff; -} - -static inline uint32_t -OpenBIOS_set_var(uint8_t *nvram, uint32_t addr, const char *str) -{ - uint32_t len; - - len = strlen(str) + 1; - memcpy(&nvram[addr], str, len); - - return addr + len; -} - /* Sun IDPROM structure at the end of NVRAM */ /* from http://www.squirrel.com/squirrel/sun-nvram-hostid.faq.html */ struct Sun_nvram { diff --git a/tests/postcopy-test.c b/tests/postcopy-test.c index 41ed1a976f..d6613c5fa4 100644 --- a/tests/postcopy-test.c +++ b/tests/postcopy-test.c @@ -18,7 +18,7 @@ #include "qemu/sockets.h" #include "sysemu/char.h" #include "sysemu/sysemu.h" -#include "hw/nvram/openbios_firmware_abi.h" +#include "hw/nvram/chrp_nvram.h" #define MIN_NVRAM_SIZE 8192 /* from spapr_nvram.c */ @@ -137,15 +137,15 @@ static void init_bootfile_ppc(const char *bootpath) { FILE *bootfile; char buf[MIN_NVRAM_SIZE]; - struct OpenBIOS_nvpart_v1 *header = (struct OpenBIOS_nvpart_v1 *)buf; + ChrpNvramPartHdr *header = (ChrpNvramPartHdr *)buf; memset(buf, 0, MIN_NVRAM_SIZE); /* Create a "common" partition in nvram to store boot-command property */ - header->signature = OPENBIOS_PART_SYSTEM; + header->signature = CHRP_NVPART_SYSTEM; memcpy(header->name, "common", 6); - OpenBIOS_finish_partition(header, MIN_NVRAM_SIZE); + chrp_nvram_finish_partition(header, MIN_NVRAM_SIZE); /* FW_MAX_SIZE is 4MB, but slof.bin is only 900KB, * so let's modify memory between 1MB and 100MB From c6363bae1731754a7153bf8b08c616f52c635304 Mon Sep 17 00:00:00 2001 From: Thomas Huth Date: Tue, 18 Oct 2016 22:46:44 +0200 Subject: [PATCH 13/73] nvram: Rename openbios_firmware_abi.h into sun_nvram.h The header now only contains inline functions related to the Sun NVRAM, so the a name like sun_nvram.h seems to be more appropriate now. Signed-off-by: Thomas Huth Tested-by: Mark Cave-Ayland Signed-off-by: David Gibson --- hw/sparc/sun4m.c | 2 +- hw/sparc64/sun4u.c | 2 +- include/hw/nvram/{openbios_firmware_abi.h => sun_nvram.h} | 6 +++--- 3 files changed, 5 insertions(+), 5 deletions(-) rename include/hw/nvram/{openbios_firmware_abi.h => sun_nvram.h} (90%) diff --git a/hw/sparc/sun4m.c b/hw/sparc/sun4m.c index 1b8d172c4e..6224288ac3 100644 --- a/hw/sparc/sun4m.c +++ b/hw/sparc/sun4m.c @@ -35,10 +35,10 @@ #include "sysemu/sysemu.h" #include "net/net.h" #include "hw/boards.h" -#include "hw/nvram/openbios_firmware_abi.h" #include "hw/scsi/esp.h" #include "hw/i386/pc.h" #include "hw/isa/isa.h" +#include "hw/nvram/sun_nvram.h" #include "hw/nvram/chrp_nvram.h" #include "hw/nvram/fw_cfg.h" #include "hw/char/escc.h" diff --git a/hw/sparc64/sun4u.c b/hw/sparc64/sun4u.c index 83708abbf4..271d8bc592 100644 --- a/hw/sparc64/sun4u.c +++ b/hw/sparc64/sun4u.c @@ -36,7 +36,7 @@ #include "qemu/timer.h" #include "sysemu/sysemu.h" #include "hw/boards.h" -#include "hw/nvram/openbios_firmware_abi.h" +#include "hw/nvram/sun_nvram.h" #include "hw/nvram/chrp_nvram.h" #include "hw/nvram/fw_cfg.h" #include "hw/sysbus.h" diff --git a/include/hw/nvram/openbios_firmware_abi.h b/include/hw/nvram/sun_nvram.h similarity index 90% rename from include/hw/nvram/openbios_firmware_abi.h rename to include/hw/nvram/sun_nvram.h index 27ce9f4a53..68eaa60308 100644 --- a/include/hw/nvram/openbios_firmware_abi.h +++ b/include/hw/nvram/sun_nvram.h @@ -1,5 +1,5 @@ -#ifndef OPENBIOS_FIRMWARE_ABI_H -#define OPENBIOS_FIRMWARE_ABI_H +#ifndef SUN_NVRAM_H +#define SUN_NVRAM_H /* Sun IDPROM structure at the end of NVRAM */ /* from http://www.squirrel.com/squirrel/sun-nvram-hostid.faq.html */ @@ -31,4 +31,4 @@ Sun_init_header(struct Sun_nvram *header, const uint8_t *macaddr, int machine_id header->checksum = tmp; } -#endif /* OPENBIOS_FIRMWARE_ABI_H */ +#endif /* SUN_NVRAM_H */ From cc8b6e76e3d924de7a4413706a3749e413ccf6fb Mon Sep 17 00:00:00 2001 From: Nikunj A Dadhania Date: Wed, 19 Oct 2016 11:36:46 +0530 Subject: [PATCH 14/73] target-ppc: implement vnegw/d instructions Vector Integer Negate Instructions: vnegw: Vector Negate Word vnegd: Vector Negate Doubleword Signed-off-by: Nikunj A Dadhania Reviewed-by: Thomas Huth Reviewed-by: Richard Henderson Signed-off-by: David Gibson --- target-ppc/helper.h | 2 ++ target-ppc/int_helper.c | 12 ++++++++++++ target-ppc/translate/vmx-impl.inc.c | 2 ++ target-ppc/translate/vmx-ops.inc.c | 2 ++ 4 files changed, 18 insertions(+) diff --git a/target-ppc/helper.h b/target-ppc/helper.h index 04c64217b7..5fcc546078 100644 --- a/target-ppc/helper.h +++ b/target-ppc/helper.h @@ -272,6 +272,8 @@ DEF_HELPER_2(vextsh2w, void, avr, avr) DEF_HELPER_2(vextsb2d, void, avr, avr) DEF_HELPER_2(vextsh2d, void, avr, avr) DEF_HELPER_2(vextsw2d, void, avr, avr) +DEF_HELPER_2(vnegw, void, avr, avr) +DEF_HELPER_2(vnegd, void, avr, avr) DEF_HELPER_2(vupkhpx, void, avr, avr) DEF_HELPER_2(vupklpx, void, avr, avr) DEF_HELPER_2(vupkhsb, void, avr, avr) diff --git a/target-ppc/int_helper.c b/target-ppc/int_helper.c index 5aee0a81c7..dca479838d 100644 --- a/target-ppc/int_helper.c +++ b/target-ppc/int_helper.c @@ -1949,6 +1949,18 @@ VEXT_SIGNED(vextsh2d, s64, UINT16_MAX, int16_t, int64_t) VEXT_SIGNED(vextsw2d, s64, UINT32_MAX, int32_t, int64_t) #undef VEXT_SIGNED +#define VNEG(name, element) \ +void helper_##name(ppc_avr_t *r, ppc_avr_t *b) \ +{ \ + int i; \ + VECTOR_FOR_INORDER_I(i, element) { \ + r->element[i] = -b->element[i]; \ + } \ +} +VNEG(vnegw, s32) +VNEG(vnegd, s64) +#undef VNEG + #define VSPLTI(suffix, element, splat_type) \ void helper_vspltis##suffix(ppc_avr_t *r, uint32_t splat) \ { \ diff --git a/target-ppc/translate/vmx-impl.inc.c b/target-ppc/translate/vmx-impl.inc.c index c8998f3eab..563f101642 100644 --- a/target-ppc/translate/vmx-impl.inc.c +++ b/target-ppc/translate/vmx-impl.inc.c @@ -815,6 +815,8 @@ GEN_VXFORM_NOA(vclzb, 1, 28) GEN_VXFORM_NOA(vclzh, 1, 29) GEN_VXFORM_NOA(vclzw, 1, 30) GEN_VXFORM_NOA(vclzd, 1, 31) +GEN_VXFORM_NOA_2(vnegw, 1, 24, 6) +GEN_VXFORM_NOA_2(vnegd, 1, 24, 7) GEN_VXFORM_NOA_2(vextsb2w, 1, 24, 16) GEN_VXFORM_NOA_2(vextsh2w, 1, 24, 17) GEN_VXFORM_NOA_2(vextsb2d, 1, 24, 24) diff --git a/target-ppc/translate/vmx-ops.inc.c b/target-ppc/translate/vmx-ops.inc.c index 68cba3e474..ab64ab2e01 100644 --- a/target-ppc/translate/vmx-ops.inc.c +++ b/target-ppc/translate/vmx-ops.inc.c @@ -215,6 +215,8 @@ GEN_VXFORM_DUAL_INV(vspltish, vinserth, 6, 13, 0x00000000, 0x100000, GEN_VXFORM_DUAL_INV(vspltisw, vinsertw, 6, 14, 0x00000000, 0x100000, PPC_ALTIVEC), GEN_VXFORM_300_EXT(vinsertd, 6, 15, 0x100000), +GEN_VXFORM_300_EO(vnegw, 0x01, 0x18, 0x06), +GEN_VXFORM_300_EO(vnegd, 0x01, 0x18, 0x07), GEN_VXFORM_300_EO(vextsb2w, 0x01, 0x18, 0x10), GEN_VXFORM_300_EO(vextsh2w, 0x01, 0x18, 0x11), GEN_VXFORM_300_EO(vextsb2d, 0x01, 0x18, 0x18), From 14fd8ab26752c725b16766c823952e3138924293 Mon Sep 17 00:00:00 2001 From: Nikunj A Dadhania Date: Wed, 19 Oct 2016 11:36:47 +0530 Subject: [PATCH 15/73] target-ppc: implement xxbr[qdwh] instruction Add required helpers (GEN_XX2FORM_EO) for supporting this instruction. xxbrh: VSX Vector Byte-Reverse Halfword xxbrw: VSX Vector Byte-Reverse Word xxbrd: VSX Vector Byte-Reverse Doubleword xxbrq: VSX Vector Byte-Reverse Quadword Signed-off-by: Nikunj A Dadhania Reviewed-by: Richard Henderson Signed-off-by: David Gibson --- target-ppc/translate.c | 32 ++++++++++++ target-ppc/translate/vsx-impl.inc.c | 77 +++++++++++++++++++++++++++++ target-ppc/translate/vsx-ops.inc.c | 8 +++ 3 files changed, 117 insertions(+) diff --git a/target-ppc/translate.c b/target-ppc/translate.c index dab8f19a91..94989b2abd 100644 --- a/target-ppc/translate.c +++ b/target-ppc/translate.c @@ -376,6 +376,9 @@ GEN_OPCODE2(name, onam, opc1, opc2, opc3, inval, type, type2) #define GEN_HANDLER_E_2(name, opc1, opc2, opc3, opc4, inval, type, type2) \ GEN_OPCODE3(name, opc1, opc2, opc3, opc4, inval, type, type2) +#define GEN_HANDLER2_E_2(name, onam, opc1, opc2, opc3, opc4, inval, typ, typ2) \ +GEN_OPCODE4(name, onam, opc1, opc2, opc3, opc4, inval, typ, typ2) + typedef struct opcode_t { unsigned char opc1, opc2, opc3, opc4; #if HOST_LONG_BITS == 64 /* Explicitly align to 64 bits */ @@ -662,6 +665,21 @@ EXTRACT_HELPER(IMM8, 11, 8); }, \ .oname = stringify(name), \ } +#define GEN_OPCODE4(name, onam, op1, op2, op3, op4, invl, _typ, _typ2) \ +{ \ + .opc1 = op1, \ + .opc2 = op2, \ + .opc3 = op3, \ + .opc4 = op4, \ + .handler = { \ + .inval1 = invl, \ + .type = _typ, \ + .type2 = _typ2, \ + .handler = &gen_##name, \ + .oname = onam, \ + }, \ + .oname = onam, \ +} #else #define GEN_OPCODE(name, op1, op2, op3, invl, _typ, _typ2) \ { \ @@ -720,6 +738,20 @@ EXTRACT_HELPER(IMM8, 11, 8); }, \ .oname = stringify(name), \ } +#define GEN_OPCODE4(name, onam, op1, op2, op3, op4, invl, _typ, _typ2) \ +{ \ + .opc1 = op1, \ + .opc2 = op2, \ + .opc3 = op3, \ + .opc4 = op4, \ + .handler = { \ + .inval1 = invl, \ + .type = _typ, \ + .type2 = _typ2, \ + .handler = &gen_##name, \ + }, \ + .oname = onam, \ +} #endif /* SPR load/store helpers */ diff --git a/target-ppc/translate/vsx-impl.inc.c b/target-ppc/translate/vsx-impl.inc.c index 23ec1e115c..1508bd13e3 100644 --- a/target-ppc/translate/vsx-impl.inc.c +++ b/target-ppc/translate/vsx-impl.inc.c @@ -132,6 +132,22 @@ static void gen_bswap16x8(TCGv_i64 outh, TCGv_i64 outl, tcg_temp_free_i64(mask); } +static void gen_bswap32x4(TCGv_i64 outh, TCGv_i64 outl, + TCGv_i64 inh, TCGv_i64 inl) +{ + TCGv_i64 hi = tcg_temp_new_i64(); + TCGv_i64 lo = tcg_temp_new_i64(); + + tcg_gen_bswap64_i64(hi, inh); + tcg_gen_bswap64_i64(lo, inl); + tcg_gen_shri_i64(outh, hi, 32); + tcg_gen_deposit_i64(outh, outh, hi, 32, 32); + tcg_gen_shri_i64(outl, lo, 32); + tcg_gen_deposit_i64(outl, outl, lo, 32, 32); + + tcg_temp_free_i64(hi); + tcg_temp_free_i64(lo); +} static void gen_lxvh8x(DisasContext *ctx) { TCGv EA; @@ -717,6 +733,67 @@ GEN_VSX_HELPER_2(xvrspim, 0x12, 0x0B, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvrspip, 0x12, 0x0A, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvrspiz, 0x12, 0x09, 0, PPC2_VSX) +static void gen_xxbrd(DisasContext *ctx) +{ + TCGv_i64 xth = cpu_vsrh(xT(ctx->opcode)); + TCGv_i64 xtl = cpu_vsrl(xT(ctx->opcode)); + TCGv_i64 xbh = cpu_vsrh(xB(ctx->opcode)); + TCGv_i64 xbl = cpu_vsrl(xB(ctx->opcode)); + + if (unlikely(!ctx->vsx_enabled)) { + gen_exception(ctx, POWERPC_EXCP_VSXU); + return; + } + tcg_gen_bswap64_i64(xth, xbh); + tcg_gen_bswap64_i64(xtl, xbl); +} + +static void gen_xxbrh(DisasContext *ctx) +{ + TCGv_i64 xth = cpu_vsrh(xT(ctx->opcode)); + TCGv_i64 xtl = cpu_vsrl(xT(ctx->opcode)); + TCGv_i64 xbh = cpu_vsrh(xB(ctx->opcode)); + TCGv_i64 xbl = cpu_vsrl(xB(ctx->opcode)); + + if (unlikely(!ctx->vsx_enabled)) { + gen_exception(ctx, POWERPC_EXCP_VSXU); + return; + } + gen_bswap16x8(xth, xtl, xbh, xbl); +} + +static void gen_xxbrq(DisasContext *ctx) +{ + TCGv_i64 xth = cpu_vsrh(xT(ctx->opcode)); + TCGv_i64 xtl = cpu_vsrl(xT(ctx->opcode)); + TCGv_i64 xbh = cpu_vsrh(xB(ctx->opcode)); + TCGv_i64 xbl = cpu_vsrl(xB(ctx->opcode)); + TCGv_i64 t0 = tcg_temp_new_i64(); + + if (unlikely(!ctx->vsx_enabled)) { + gen_exception(ctx, POWERPC_EXCP_VSXU); + return; + } + tcg_gen_bswap64_i64(t0, xbl); + tcg_gen_bswap64_i64(xtl, xbh); + tcg_gen_mov_i64(xth, t0); + tcg_temp_free_i64(t0); +} + +static void gen_xxbrw(DisasContext *ctx) +{ + TCGv_i64 xth = cpu_vsrh(xT(ctx->opcode)); + TCGv_i64 xtl = cpu_vsrl(xT(ctx->opcode)); + TCGv_i64 xbh = cpu_vsrh(xB(ctx->opcode)); + TCGv_i64 xbl = cpu_vsrl(xB(ctx->opcode)); + + if (unlikely(!ctx->vsx_enabled)) { + gen_exception(ctx, POWERPC_EXCP_VSXU); + return; + } + gen_bswap32x4(xth, xtl, xbh, xbl); +} + #define VSX_LOGICAL(name, tcg_op) \ static void glue(gen_, name)(DisasContext * ctx) \ { \ diff --git a/target-ppc/translate/vsx-ops.inc.c b/target-ppc/translate/vsx-ops.inc.c index 10eb4b9470..af0d27e012 100644 --- a/target-ppc/translate/vsx-ops.inc.c +++ b/target-ppc/translate/vsx-ops.inc.c @@ -39,6 +39,10 @@ GEN_HANDLER2_E(name, #name, 0x3C, opc2 | 1, opc3, 0, PPC_NONE, fl2) GEN_HANDLER2_E(name, #name, 0x3C, opc2 | 0, opc3, 0, PPC_NONE, fl2), \ GEN_HANDLER2_E(name, #name, 0x3C, opc2 | 1, opc3, 0, PPC_NONE, fl2) +#define GEN_XX2FORM_EO(name, opc2, opc3, opc4, fl2) \ +GEN_HANDLER2_E_2(name, #name, 0x3C, opc2 | 0, opc3, opc4, 0, PPC_NONE, fl2), \ +GEN_HANDLER2_E_2(name, #name, 0x3C, opc2 | 1, opc3, opc4, 0, PPC_NONE, fl2) + #define GEN_XX3FORM(name, opc2, opc3, fl2) \ GEN_HANDLER2_E(name, #name, 0x3C, opc2 | 0, opc3, 0, PPC_NONE, fl2), \ GEN_HANDLER2_E(name, #name, 0x3C, opc2 | 1, opc3, 0, PPC_NONE, fl2), \ @@ -222,6 +226,10 @@ GEN_XX2FORM(xvrspic, 0x16, 0x0A, PPC2_VSX), GEN_XX2FORM(xvrspim, 0x12, 0x0B, PPC2_VSX), GEN_XX2FORM(xvrspip, 0x12, 0x0A, PPC2_VSX), GEN_XX2FORM(xvrspiz, 0x12, 0x09, PPC2_VSX), +GEN_XX2FORM_EO(xxbrh, 0x16, 0x1D, 0x07, PPC2_ISA300), +GEN_XX2FORM_EO(xxbrw, 0x16, 0x1D, 0x0F, PPC2_ISA300), +GEN_XX2FORM_EO(xxbrd, 0x16, 0x1D, 0x17, PPC2_ISA300), +GEN_XX2FORM_EO(xxbrq, 0x16, 0x1D, 0x1F, PPC2_ISA300), #define VSX_LOGICAL(name, opc2, opc3, fl2) \ GEN_XX3FORM(name, opc2, opc3, fl2) From 2bb0d10aebf2018d98b9413ab960dc8d728b2f5a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= Date: Tue, 18 Oct 2016 10:06:32 +0200 Subject: [PATCH 16/73] ppc/xics: add a xics_set_nr_servers common routine MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit xics_spapr and xics_kvm nearly define the same 'set_nr_servers' handler. Only the type of the ICP differs. So let's make a common one to remove some duplicated code. Signed-off-by: Cédric Le Goater Signed-off-by: David Gibson --- hw/intc/xics.c | 24 +++++++++++++++++++++--- hw/intc/xics_kvm.c | 13 +------------ hw/intc/xics_spapr.c | 13 +------------ include/hw/ppc/xics.h | 2 ++ 4 files changed, 25 insertions(+), 27 deletions(-) diff --git a/hw/intc/xics.c b/hw/intc/xics.c index 7fac964fbd..c051eebb44 100644 --- a/hw/intc/xics.c +++ b/hw/intc/xics.c @@ -183,6 +183,24 @@ static void xics_prop_set_nr_irqs(Object *obj, Visitor *v, const char *name, info->set_nr_irqs(xics, value, errp); } +void xics_set_nr_servers(XICSState *xics, uint32_t nr_servers, + const char *typename, Error **errp) +{ + int i; + + xics->nr_servers = nr_servers; + + xics->ss = g_malloc0(xics->nr_servers * sizeof(ICPState)); + for (i = 0; i < xics->nr_servers; i++) { + char name[32]; + ICPState *icp = &xics->ss[i]; + + object_initialize(icp, sizeof(*icp), typename); + snprintf(name, sizeof(name), "icp[%d]", i); + object_property_add_child(OBJECT(xics), name, OBJECT(icp), errp); + } +} + static void xics_prop_get_nr_servers(Object *obj, Visitor *v, const char *name, void *opaque, Error **errp) @@ -198,7 +216,7 @@ static void xics_prop_set_nr_servers(Object *obj, Visitor *v, Error **errp) { XICSState *xics = XICS_COMMON(obj); - XICSStateClass *info = XICS_COMMON_GET_CLASS(xics); + XICSStateClass *xsc = XICS_COMMON_GET_CLASS(xics); Error *error = NULL; int64_t value; @@ -213,8 +231,8 @@ static void xics_prop_set_nr_servers(Object *obj, Visitor *v, return; } - assert(info->set_nr_servers); - info->set_nr_servers(xics, value, errp); + assert(xsc->set_nr_servers); + xsc->set_nr_servers(xics, value, errp); } static void xics_common_initfn(Object *obj) diff --git a/hw/intc/xics_kvm.c b/hw/intc/xics_kvm.c index 9c2f198fd1..17694eaa87 100644 --- a/hw/intc/xics_kvm.c +++ b/hw/intc/xics_kvm.c @@ -373,18 +373,7 @@ static void xics_kvm_set_nr_irqs(XICSState *xics, uint32_t nr_irqs, static void xics_kvm_set_nr_servers(XICSState *xics, uint32_t nr_servers, Error **errp) { - int i; - - xics->nr_servers = nr_servers; - - xics->ss = g_malloc0(xics->nr_servers * sizeof(ICPState)); - for (i = 0; i < xics->nr_servers; i++) { - char buffer[32]; - object_initialize(&xics->ss[i], sizeof(xics->ss[i]), TYPE_KVM_ICP); - snprintf(buffer, sizeof(buffer), "icp[%d]", i); - object_property_add_child(OBJECT(xics), buffer, OBJECT(&xics->ss[i]), - errp); - } + xics_set_nr_servers(xics, nr_servers, TYPE_KVM_ICP, errp); } static void rtas_dummy(PowerPCCPU *cpu, sPAPRMachineState *spapr, diff --git a/hw/intc/xics_spapr.c b/hw/intc/xics_spapr.c index e8d0623c2c..a09e1b033d 100644 --- a/hw/intc/xics_spapr.c +++ b/hw/intc/xics_spapr.c @@ -249,18 +249,7 @@ static void xics_spapr_set_nr_irqs(XICSState *xics, uint32_t nr_irqs, static void xics_spapr_set_nr_servers(XICSState *xics, uint32_t nr_servers, Error **errp) { - int i; - - xics->nr_servers = nr_servers; - - xics->ss = g_malloc0(xics->nr_servers * sizeof(ICPState)); - for (i = 0; i < xics->nr_servers; i++) { - char buffer[32]; - object_initialize(&xics->ss[i], sizeof(xics->ss[i]), TYPE_ICP); - snprintf(buffer, sizeof(buffer), "icp[%d]", i); - object_property_add_child(OBJECT(xics), buffer, OBJECT(&xics->ss[i]), - errp); - } + xics_set_nr_servers(xics, nr_servers, TYPE_ICP, errp); } static void xics_spapr_realize(DeviceState *dev, Error **errp) diff --git a/include/hw/ppc/xics.h b/include/hw/ppc/xics.h index 66ae55ded3..573b192053 100644 --- a/include/hw/ppc/xics.h +++ b/include/hw/ppc/xics.h @@ -188,6 +188,8 @@ void xics_spapr_free(XICSState *icp, int irq, int num); void xics_cpu_setup(XICSState *icp, PowerPCCPU *cpu); void xics_cpu_destroy(XICSState *icp, PowerPCCPU *cpu); +void xics_set_nr_servers(XICSState *xics, uint32_t nr_servers, + const char *typename, Error **errp); /* Internal XICS interfaces */ int xics_get_cpu_index_by_dt_id(int cpu_dt_id); From d49c603b37e6c9d025f58c09f55d0c7cefe88987 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= Date: Tue, 18 Oct 2016 10:06:33 +0200 Subject: [PATCH 17/73] ppc/xics: add a XICSState backlink in ICPState MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The link will be used to change the API of the icp_* routines which are still using an XICSState as an argument. Signed-off-by: Cédric Le Goater Signed-off-by: David Gibson --- hw/intc/xics.c | 1 + include/hw/ppc/xics.h | 2 ++ 2 files changed, 3 insertions(+) diff --git a/hw/intc/xics.c b/hw/intc/xics.c index c051eebb44..9f2c81a7f1 100644 --- a/hw/intc/xics.c +++ b/hw/intc/xics.c @@ -198,6 +198,7 @@ void xics_set_nr_servers(XICSState *xics, uint32_t nr_servers, object_initialize(icp, sizeof(*icp), typename); snprintf(name, sizeof(name), "icp[%d]", i); object_property_add_child(OBJECT(xics), name, OBJECT(icp), errp); + icp->xics = xics; } } diff --git a/include/hw/ppc/xics.h b/include/hw/ppc/xics.h index 573b192053..1468d6a890 100644 --- a/include/hw/ppc/xics.h +++ b/include/hw/ppc/xics.h @@ -117,6 +117,8 @@ struct ICPState { uint8_t mfrr; qemu_irq output; bool cap_irq_xics_enabled; + + XICSState *xics; }; #define TYPE_ICS_BASE "ics-base" From e3403258a20c61859ca1917bb86bc206e5846784 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= Date: Tue, 18 Oct 2016 10:06:34 +0200 Subject: [PATCH 18/73] ppc/xics: change the icp_ routines API to use an 'ICPState *' argument MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The routines : void icp_set_cppr(ICPState *icp, uint8_t cppr); void icp_set_mfrr(ICPState *icp, uint8_t mfrr); void icp_eoi(ICPState *icp, uint32_t xirr); now use one 'ICPState *icp' argument instead of a 'XICSState *' and a server arguments. The backlink on XICSState* is used whenever needed. Signed-off-by: Cédric Le Goater Signed-off-by: David Gibson --- hw/intc/xics.c | 25 ++++++++++--------------- hw/intc/xics_spapr.c | 18 +++++++++++------- include/hw/ppc/xics.h | 6 +++--- 3 files changed, 24 insertions(+), 25 deletions(-) diff --git a/hw/intc/xics.c b/hw/intc/xics.c index 9f2c81a7f1..095c16a300 100644 --- a/hw/intc/xics.c +++ b/hw/intc/xics.c @@ -326,22 +326,20 @@ static void icp_check_ipi(ICPState *ss) qemu_irq_raise(ss->output); } -static void icp_resend(XICSState *xics, int server) +static void icp_resend(ICPState *ss) { - ICPState *ss = xics->ss + server; ICSState *ics; if (ss->mfrr < CPPR(ss)) { icp_check_ipi(ss); } - QLIST_FOREACH(ics, &xics->ics, list) { + QLIST_FOREACH(ics, &ss->xics->ics, list) { ics_resend(ics); } } -void icp_set_cppr(XICSState *xics, int server, uint8_t cppr) +void icp_set_cppr(ICPState *ss, uint8_t cppr) { - ICPState *ss = xics->ss + server; uint8_t old_cppr; uint32_t old_xisr; @@ -361,15 +359,13 @@ void icp_set_cppr(XICSState *xics, int server, uint8_t cppr) } } else { if (!XISR(ss)) { - icp_resend(xics, server); + icp_resend(ss); } } } -void icp_set_mfrr(XICSState *xics, int server, uint8_t mfrr) +void icp_set_mfrr(ICPState *ss, uint8_t mfrr) { - ICPState *ss = xics->ss + server; - ss->mfrr = mfrr; if (mfrr < CPPR(ss)) { icp_check_ipi(ss); @@ -398,23 +394,22 @@ uint32_t icp_ipoll(ICPState *ss, uint32_t *mfrr) return ss->xirr; } -void icp_eoi(XICSState *xics, int server, uint32_t xirr) +void icp_eoi(ICPState *ss, uint32_t xirr) { - ICPState *ss = xics->ss + server; ICSState *ics; uint32_t irq; /* Send EOI -> ICS */ ss->xirr = (ss->xirr & ~CPPR_MASK) | (xirr & CPPR_MASK); - trace_xics_icp_eoi(server, xirr, ss->xirr); + trace_xics_icp_eoi(ss->cs->cpu_index, xirr, ss->xirr); irq = xirr & XISR_MASK; - QLIST_FOREACH(ics, &xics->ics, list) { + QLIST_FOREACH(ics, &ss->xics->ics, list) { if (ics_valid_irq(ics, irq)) { ics_eoi(ics, irq); } } if (!XISR(ss)) { - icp_resend(xics, server); + icp_resend(ss); } } @@ -673,7 +668,7 @@ static int ics_simple_post_load(ICSState *ics, int version_id) int i; for (i = 0; i < ics->xics->nr_servers; i++) { - icp_resend(ics->xics, i); + icp_resend(&ics->xics->ss[i]); } return 0; diff --git a/hw/intc/xics_spapr.c b/hw/intc/xics_spapr.c index a09e1b033d..b4e55012e0 100644 --- a/hw/intc/xics_spapr.c +++ b/hw/intc/xics_spapr.c @@ -43,9 +43,10 @@ static target_ulong h_cppr(PowerPCCPU *cpu, sPAPRMachineState *spapr, target_ulong opcode, target_ulong *args) { CPUState *cs = CPU(cpu); + ICPState *icp = &spapr->xics->ss[cs->cpu_index]; target_ulong cppr = args[0]; - icp_set_cppr(spapr->xics, cs->cpu_index, cppr); + icp_set_cppr(icp, cppr); return H_SUCCESS; } @@ -59,7 +60,7 @@ static target_ulong h_ipi(PowerPCCPU *cpu, sPAPRMachineState *spapr, return H_PARAMETER; } - icp_set_mfrr(spapr->xics, server, mfrr); + icp_set_mfrr(spapr->xics->ss + server, mfrr); return H_SUCCESS; } @@ -67,7 +68,8 @@ static target_ulong h_xirr(PowerPCCPU *cpu, sPAPRMachineState *spapr, target_ulong opcode, target_ulong *args) { CPUState *cs = CPU(cpu); - uint32_t xirr = icp_accept(spapr->xics->ss + cs->cpu_index); + ICPState *icp = &spapr->xics->ss[cs->cpu_index]; + uint32_t xirr = icp_accept(icp); args[0] = xirr; return H_SUCCESS; @@ -77,8 +79,8 @@ static target_ulong h_xirr_x(PowerPCCPU *cpu, sPAPRMachineState *spapr, target_ulong opcode, target_ulong *args) { CPUState *cs = CPU(cpu); - ICPState *ss = &spapr->xics->ss[cs->cpu_index]; - uint32_t xirr = icp_accept(ss); + ICPState *icp = &spapr->xics->ss[cs->cpu_index]; + uint32_t xirr = icp_accept(icp); args[0] = xirr; args[1] = cpu_get_host_ticks(); @@ -89,9 +91,10 @@ static target_ulong h_eoi(PowerPCCPU *cpu, sPAPRMachineState *spapr, target_ulong opcode, target_ulong *args) { CPUState *cs = CPU(cpu); + ICPState *icp = &spapr->xics->ss[cs->cpu_index]; target_ulong xirr = args[0]; - icp_eoi(spapr->xics, cs->cpu_index, xirr); + icp_eoi(icp, xirr); return H_SUCCESS; } @@ -99,8 +102,9 @@ static target_ulong h_ipoll(PowerPCCPU *cpu, sPAPRMachineState *spapr, target_ulong opcode, target_ulong *args) { CPUState *cs = CPU(cpu); + ICPState *icp = &spapr->xics->ss[cs->cpu_index]; uint32_t mfrr; - uint32_t xirr = icp_ipoll(spapr->xics->ss + cs->cpu_index, &mfrr); + uint32_t xirr = icp_ipoll(icp, &mfrr); args[0] = xirr; args[1] = mfrr; diff --git a/include/hw/ppc/xics.h b/include/hw/ppc/xics.h index 1468d6a890..6e5a113332 100644 --- a/include/hw/ppc/xics.h +++ b/include/hw/ppc/xics.h @@ -196,11 +196,11 @@ void xics_set_nr_servers(XICSState *xics, uint32_t nr_servers, /* Internal XICS interfaces */ int xics_get_cpu_index_by_dt_id(int cpu_dt_id); -void icp_set_cppr(XICSState *icp, int server, uint8_t cppr); -void icp_set_mfrr(XICSState *icp, int server, uint8_t mfrr); +void icp_set_cppr(ICPState *icp, uint8_t cppr); +void icp_set_mfrr(ICPState *icp, uint8_t mfrr); uint32_t icp_accept(ICPState *ss); uint32_t icp_ipoll(ICPState *ss, uint32_t *mfrr); -void icp_eoi(XICSState *icp, int server, uint32_t xirr); +void icp_eoi(ICPState *icp, uint32_t xirr); void ics_simple_write_xive(ICSState *ics, int nr, int server, uint8_t priority, uint8_t saved_priority); From f85bcec31ee578eccf6182be158d6ac6d9b90a4c Mon Sep 17 00:00:00 2001 From: Nicholas Piggin Date: Thu, 20 Oct 2016 17:59:10 +1100 Subject: [PATCH 19/73] ppc: fix MSR_ME handling for system reset interrupt MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Power ISA specifies ME bit handling for system reset interrupt: if the interrupt occurred while the thread was in power-saving mode, set to 1; otherwise not altered Power ISA 3.0, section 6.5 "Interrupt Definitions", Figure 64. Signed-off-by: Nicholas Piggin Reviewed-by: Greg Kurz Reviewed-by: Cédric Le Goater Signed-off-by: David Gibson --- target-ppc/excp_helper.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/target-ppc/excp_helper.c b/target-ppc/excp_helper.c index 921c39d33f..53c407576b 100644 --- a/target-ppc/excp_helper.c +++ b/target-ppc/excp_helper.c @@ -385,11 +385,11 @@ static inline void powerpc_excp(PowerPCCPU *cpu, int excp_model, int excp) srr1 = SPR_BOOKE_CSRR1; break; case POWERPC_EXCP_RESET: /* System reset exception */ + /* A power-saving exception sets ME, otherwise it is unchanged */ if (msr_pow) { /* indicate that we resumed from power save mode */ msr |= 0x10000; - } else { - new_msr &= ~((target_ulong)1 << MSR_ME); + new_msr |= ((target_ulong)1 << MSR_ME); } new_msr |= (target_ulong)MSR_HVB; From e763da234454c2bcdf065e360f69ca1d11d81224 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 20 Oct 2016 15:29:25 +1100 Subject: [PATCH 20/73] pseries: Remove unused callbacks from sPAPR VIO bus state The original QOMification of the spapr VIO devices in 3954d33 "spapr: convert to QEMU Object Model (v2)" moved some callbacks from the VIOsPAPRBus structure to the VIOsPAPRDeviceClass. Except, that it forgot to actually remove them from the VIOsPAPRBus structure (which still exists, though it doesn't fulfill quite the same function as it did pre-QOM). This patch removes those now unused callback fields. Signed-off-by: David Gibson Reviewed-by: Alexey Kardashevskiy Reviewed-by: Thomas Huth --- include/hw/ppc/spapr_vio.h | 2 -- 1 file changed, 2 deletions(-) diff --git a/include/hw/ppc/spapr_vio.h b/include/hw/ppc/spapr_vio.h index 40d0e5f6a3..0b025fd66b 100644 --- a/include/hw/ppc/spapr_vio.h +++ b/include/hw/ppc/spapr_vio.h @@ -76,8 +76,6 @@ struct VIOsPAPRDevice { struct VIOsPAPRBus { BusState bus; uint32_t next_reg; - int (*init)(VIOsPAPRDevice *dev); - int (*devnode)(VIOsPAPRDevice *dev, void *fdt, int node_off); }; extern VIOsPAPRBus *spapr_vio_bus_init(void); From 1f0e657d3f108c4cbd0ae16cf18de8dcb801cc1a Mon Sep 17 00:00:00 2001 From: Benjamin Herrenschmidt Date: Sat, 6 Aug 2016 10:11:49 +1000 Subject: [PATCH 21/73] ppc: Fix single step with gdb stub Signed-off-by: Benjamin Herrenschmidt Signed-off-by: David Gibson --- target-ppc/translate.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/target-ppc/translate.c b/target-ppc/translate.c index 94989b2abd..43505a936c 100644 --- a/target-ppc/translate.c +++ b/target-ppc/translate.c @@ -322,7 +322,7 @@ static void gen_debug_exception(DisasContext *ctx) */ if ((ctx->exception != POWERPC_EXCP_BRANCH) && (ctx->exception != POWERPC_EXCP_SYNC)) { - gen_update_nip(ctx, ctx->nip - 4); + gen_update_nip(ctx, ctx->nip); } t0 = tcg_const_i32(EXCP_DEBUG); gen_helper_raise_exception(cpu_env, t0); From bcad45de6a0b5bf10a274872d2e45da3403232da Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= Date: Sat, 22 Oct 2016 11:46:34 +0200 Subject: [PATCH 22/73] ppc: add skiboot firmware for the pnv platform MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This is the initial image of skiboot 5.3.7 (commit 762d0082) for the PowerPC PowerNV (Non-Virtualized) platform. Built from submodule. Signed-off-by: Cédric Le Goater Signed-off-by: David Gibson --- .gitmodules | 3 +++ MAINTAINERS | 1 + Makefile | 2 +- pc-bios/README | 5 +++++ pc-bios/skiboot.lid | Bin 0 -> 983893 bytes roms/Makefile | 8 +++++++- roms/skiboot | 1 + 7 files changed, 18 insertions(+), 2 deletions(-) create mode 100644 pc-bios/skiboot.lid create mode 160000 roms/skiboot diff --git a/.gitmodules b/.gitmodules index 9da9ede261..ca323b4d87 100644 --- a/.gitmodules +++ b/.gitmodules @@ -31,3 +31,6 @@ [submodule "roms/u-boot"] path = roms/u-boot url = git://git.qemu-project.org/u-boot.git +[submodule "roms/skiboot"] + path = roms/skiboot + url = git://git.qemu.org/skiboot.git diff --git a/MAINTAINERS b/MAINTAINERS index b01fec0a7b..280ee1fcd2 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -656,6 +656,7 @@ F: include/hw/*/xics* F: pc-bios/spapr-rtas/* F: pc-bios/spapr-rtas.bin F: pc-bios/slof.bin +F: pc-bios/skiboot.lid F: docs/specs/ppc-spapr-hcalls.txt F: docs/specs/ppc-spapr-hotplug.txt F: tests/spapr* diff --git a/Makefile b/Makefile index 3bcb0565b6..11f5154c81 100644 --- a/Makefile +++ b/Makefile @@ -421,7 +421,7 @@ qemu-icon.bmp qemu_logo_no_text.svg \ bamboo.dtb petalogix-s3adsp1800.dtb petalogix-ml605.dtb \ multiboot.bin linuxboot.bin linuxboot_dma.bin kvmvapic.bin \ s390-ccw.img \ -spapr-rtas.bin slof.bin \ +spapr-rtas.bin slof.bin skiboot.lid \ palcode-clipper \ u-boot.e500 else diff --git a/pc-bios/README b/pc-bios/README index 779192eb7c..47a913f9c7 100644 --- a/pc-bios/README +++ b/pc-bios/README @@ -42,3 +42,8 @@ it was compiled using the qemu-ppce500 target. A git mirror is available at: git://git.qemu-project.org/u-boot.git The hash used to compile the current version is: 2072e72 + +- Skiboot (https://github.com/open-power/skiboot/) is an OPAL + (OpenPower Abstraction Layer) firmware for OpenPOWER systems. It can + run an hypervisor OS or simply a host OS on the "baremetal" + platform, also known as the PowerNV (Non-Virtualized) platform. diff --git a/pc-bios/skiboot.lid b/pc-bios/skiboot.lid new file mode 100644 index 0000000000000000000000000000000000000000..0e59a8280d26342bc769f04e49dfccbed48ead1b GIT binary patch literal 983893 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ΞC1L03mGne&Y+u>$N)OyjothIHSm~(r2=D!#ZLwf z&|Ezz+#A{%7#cxy6zmKfHEqEaHOHJQ^xHuGfb78o*=5mUA>#f28aV8%AY*zQ_0tqU zcaBI{EM;J{c+S96v6Ml&$e)Im;+mvZeayF zy8{$9pt=u~UMyNH621Tb*U|0*@B8EdtS=!TbMTj^8B=44}2kpg63nn+-biQv*~sdH?^z1Idr4!E;UE zex288&_1slFG2fFG~xA+iTA%L;C?eGj6h~vv{;sb;=}v@6|n!k|NlM!Dmx}>GH}#C zVBoM&WGwJt1!qT4NzVvh{|sGM25S3&+C88)529~y5^NTz-{siEpaX5UEkJ6sf%XJ3 z&eVe3bK?E)6u7Jb^#MS2oCoV!7f_qh`~QE8aXL_+7u1fo{@+yqQj26Kc>E9AwpswH zOF;57JsAYN|D6K2l|klvu%1EGm+-NvGqK?I4fI@KP+Jt#9=15hP+&-gIWe9=16p@GX(s`Eb}0j7tbl=|VLqrW z`4rry0kxlC>jOdiOf6chRJ{LR0~lQ8MHw0WvK}r-)XUm0FCW{&ZzVL zUkx6&0hPz#usLSs4>@PxVHhZGy#Kd>%PNpuecEl%nX%xp4^Usu`+qA~uHiqlyaBDb z1+67%@zsIKgU81j?nBRH0FNtK#X;p9LFE9*T32g?I+oeYWF@BjZ) zK=Zqx{%EZi=zNcV8Lt}|IzV>8=HZ~`ZUl{Mf!y=^AA^DS{~B-~3gi|`O+E*Z{T3}& ze?aRzL173AYw!Qf;JGZ297vxliu-rE2cTgcF2(PEthS|8=X@&FPZ(7R&5@(G~32COr@|6c&7f6#dZ4UG&fp!5K( zyBjPHGSqbiqVB2AM`h zhK7lD3=$AO^G^8b$>0G}W9emj;HM`;0F=Gqrzb;%_y2z#kT&!Q#JmRVtWMSwptG;Q zXHbCq0eib9fXW3>7=hcg|Ib=@|2qP1|A5XBdXao~fu%e{hDGxK2bRj9I}E|&VlmbS z{{I8Di(hJ<^|1aA8u$GH8ZXna0iO@jwF2rl8PFWN_rFu{`~fO6e`@N8bcW<_(AvkPufg}8OtfdK4 z0$B&uH371h<*bMI|8wB<2TB9p{|shNO9i;Wnl zZS4K;I5>@h;^9YD*9z}{=fUY2G-d#j_h3DS7}tT0nU!QQG(hX4iH=PS8lbbRJ(x_u z?K;q1S)j3M(Eef2T5{NVIIwhT>G1#OOHGCj$auj28~DbHQSL#9ja@(d{{vzctSq(B zhPtH@lF!S){Z2^T$(I0H7YFwHQX6B?`7EF{HQxX0!Fd^UmaGSpIk?Sh)AS#7Clj+p zi&=q10z-uNzh~e!2Ba=Min9J4)CcrnJt_+tQ|eTKkE0@uyV^K=|33qEho!>*pP=*% z8oTmfJ!)Zn^#5P&eGE3RvxFh}+$Pcc|7r02I%pgWbWTIZ5eCMNB@9fUF?x{uLE{kh z$3f@e+q8h%aTUkDEdr$@@BgR4^=ij_@ReQE7XLo?=Qb;^@?)d%c z><&D={qH%rodhz|``o7b)^Pk|kf(`X6!E<;DFn@u@O2GaC zonQ9v8MwU*YO8twKLu`Rg52o+?*O>2@nB$N0G)XN+J6kPA2k1E(PFa~6#e4<_4_19}`PgxvL89Y7gJs8l21$?~ zKlH*>%2o%I=Rxf$P#X3AUkgqHV7GzFL2!G>)(Yev z@BcMmIf(h4ko0(xfuZIYLy5vM278d6nq%x+KxSFAFnopRft>M%RCa*QHO%(@_Yl0+ z6G?o7MFK;P_dm#d4kRrfM9cv&GB7~S5D9CB)}{a9WFv?skLIk*CJrF z%Vks~vpxZ>RR_sI+;#wQHa4{HV5{)o9%O%_=8ylNums&_o2vQ$f1)PhuA5qe;AOD$ zED~B6_`U!C_XVvr0kwN-735!e|Nk#rk?H>sbjJxOJVEUVixzKoi{yI@-v4id`x;RD z4M1mofWkPT1vD=4pB2@de^)`~I5hp=gQSiVbT2ZRy0uVspuMguzyS%G>xcTOBKdei zMFxWcXs?2HGXt9k>wd={ivJx!=l5GzpJo8HgFt0S&0XUP=$&cc`3lFm3^uk-|G!&$ zN#;}}i+9v&Nv*2Y3=#p23-~p#C@?TEq%bfr8Za<`szgQy1_nkC1_s6e1_s6m&^Rk- zejHRUSuFK-LiDA+K8J@%@;!-q_sifj@hn=r&wKyB1+K?I?Evrp|4Ka=7)11!GceTr zw+5{v&;X6WgXcw}k@`iCe^)p*F+A}8*9vY|faY~-)x9stYBIm5KWP!@(8S;ZvajZu zb%jNXw}-_7@Es_u-v5t+&p(3N#c8Ra4r)s<{08+A6B)qga(n;#2~J=7`?+^G%=_O$ z$UmU7A&~qt-6HuOkN5wZ;4v#u{Q@fUtsj8y{`fl+bZ@!!ga6OG|NpyV{owyo@Bja< zSU>px#QXohGu99OKL*XkTR-^!-24AO&|2dI9;|y|bFPdH&~lr} z51L;lg8G;a^B623VgL1cO&jEFEsGW(CU9CzzNg~-|0cL?0BXY^w_hN7yq!R6O2GF- zfcw8FW;lb|>PYHfkS9t%M3U2d)+Q$y_7z{xALGc1A z_d#dnS}e5GvE9FVes1i`oo}p+W!JjTM;xL49{cGxbR@z{T9>DQ^0i|9zQ2Q z{Co)9|3~!{mAnc#23=AQe>UR2_ z3@ncG7 znFq21vPR(l3DCV*Df0yQ>;HYOsErQ>jrYaC(lF@k1dFA%1r{wnk3i|!`~N}k{!h@E zmfrvW_f#KEIRbKH#nQ!0)z=vkDph~*f%Z^<%KaY;LF46r4?@>PB!JF&vQA*&3Xfu7 z0NpPIQwQ2(2vuYAB9WmWB$I)ye&q#lU$G*YMd3#cD9!(8DamMH0M$F-Hu2HV6`*rk zLFa9H|NngvLUyZAUApc|6>apPw@W#ZwvUY zAl98B@c4(`5ef3M2kQ<{8gPW&4FRgN!SRoD2Ukdzx}AO(IG#Q9yTJDzia_T77-c|q zcrY-8crZZYsE&OLc&ye6X>S(z-YZ5I?|=2+_CGw1Y9A>f;)mf&McP4)l=%YuHTQp4 zK+Y$d$p9KN^ZvILGUl)!lzteV!1ROKyCD6bG~_TBbpCkCk?K|!g-XrEOw~Ua5^7bo zD?ocyKxqULM}K5NW4I1Y3?ZO9oUI!exWcO;aRgHb+V=}pV}OVw@LDkiP+9HR#1H}+ zg97bm2F;6r?y>Uz|H~5UPH;K}pBD$;n`+wtOH+_G@jmeQKREs%>*6J>=luU)JqH|* zpftGy9FI>J5S00P1sC|3A$Dt%nLh;S26NK<~FM)B>MtsctXmF2GCiR1)%eGK;=)R=3<43cHlFKG;9@=W>;4^|j=YhUx znJEFvGnJYQETDdVt%`~n)Nd2L|Nnc4UUyT2dhcll$oL3f z2I$TO@LBYrdy<;||Fui{{}(i$3Ytp=^-Zj+pXpmi`Rahq-T=*QfW~*N6&RSTCH!)& z9xyOl9bjOzTEM_!HO1G!s@Rv&D#$j#%Fu5jc%Rjg&lRBZ-}^u0yi91i>;TDu%lsC< zUEcq5z->{`c#mTf(;84e&ij8hWWH93K@2pu@*{Jm0HjRF2A@3#8b1M@Y5HR6OaZ7l z=Rsw`kF1#zpfN=6|9imwA8y<`(27$V?*`U4xyW?C2fl5tzm0BY&kryW!92)*J zh`iX(paGgw0^Pe(@q%5U;`u`+@Bh2O>qxx+|C`a#$WX4`!tlaz9>WU9xePAaEew|( z=P^9dZeh6MIFFGUOGwDCv9465D6;L&+y#N0L?So^*;vbMY52(5y-v9sE zSSm2EV^PNpo=Zpqofq!s=KcSlNKFg-7I1z4e;2sT-RQ_r66)DvSLtwn;JcTifhXz}~){eLHT{>%IS-w76qj0_&En-FLDL+{H1_2)q2WR?mH;B$(t z|IcIqrRkYkGdZC7xzYRII`H~8khu51_29Y&(nmuw589uy0quQAo(U`GCVKx{2cENm zl?R}+b3o_h!o~!_1uCdN#sC^aVGw(%ITLh7W?ikV_cHYUudUMm|Dbl@OV4{opnB4G z4ugWM7XuF@PG%~A`d^^?=Rk5k^B5FfWHNA}n*l0wKz;_D_xMuN_JvF`0}rfh2CbWT z>1F!>be7kP=e8FhdD!0@8V-g(6&Y4Q^?d-X0sP6xumd!fZ_D)m?@JEb8?dz(FTLzI zemrED05#{wPeq0e5Pfz6KN%TjfY*0`_1H1|c*sxynjeDs0dyYGPez6cOGbtRFBUU! zH7YX*Sb8!rHY$Vf5NEISlJ}_f2oeFU>8{me-}2(s{|(@LsR7ED|1Ws|-ws~?^-_^x z2dI95wdWw~Y|Fvr6r|m<0dYqRH10s*f*KZf3J|~9NkGFO5j3_0axb|3s`UTwOHDfs zQ27fQ;{(q#D>5{^)VgN`YOgxZVVDAPr^Q2t2_UzE!V~0Hix&UNT6HfG(Adz6m7wwa zZQwR3NFF3+(c(Yb`~Nn`{x9&l!hgO{06tp^vVnrH_*81XS4z}m5CGjn zUa85T0CESYEdg>%Ma#(p6)hG_pmE_J;B&gZ!|M{qdC)TpTLLsdV~&-Y-;)wG!F$+t zfb0R~RnT3@m7Y0$p!{ml@c%!^?1~n!KgGTOe*@2J+A1&_CTi+3)M_#>gZd3xKL!MP z|NpPz!~k2{5K!y=|Gx<6?At;u@L4u6b+f$x|NB#^HUFVQ(|^!<4A9!GKalpyIu7)B zlT~Km@nBsGIu{`kww4w$27H>qdhbjH(0qHXt(OR>e0UiHJ|_XZj}CnI#vBFo|`= zLw_Cvqr<%aSD@$6F@V}}4)Yj1Dz*9_R@&P?@L&L+L&pQkKTtUd(Aj_>Imf2|b1LoK zLGxWxDz(}lR@(bNaBTYDQE49!5^Jc`S`HQi?HL25e-G9*XW(H29k&Oi9}m_wpff(e z{Zr7Lan_di46GR#7_GhsyaMeX_x{%co)-r7K|td=pz$e4nXx9Jxt4*!`X>X2^#KO1 z`Wp5v)pOLISnXjDu)g>IfAu|3TN`?x;lF0^STe{A(3r@J`3xL2TYrgw#+K{jABlMX z{{T)K(Db14Vm|{1s6Ph^SMUFuz~e%*ZZSw$|7Q{K{{Mf;Y$@>C?k{lva6|U$fZALy zy=E%dDljx8YBI=x&Q`AV^oHNn07{prY1NJoEQXXOofsIvXKY)v1cK(nn7#jR0=Iua zVTGQ*G1F$CC1^aTQtLb@ZGz6UVFdBv?u5=+p}L`l4_XFHgt&z%DN!>DoIjA9kzw-=D64v&>Qbv9Pw~wLe1}!gcSP3dW z!EFRZ2K2qJ3f}(;!1W)f|5=gD&|;|k|9?%UBq)7dfs`dHQTBg;+6o@5D{VnzSD?9A z>wBje>>n^1+Am;WN&c_Pki3^c1-c&wTz=@-Gca2J|Nq~ii2>rSmLPFRm~9Y*xC?w9 zbp=QdQoZcr{VyL}|AFcQNZ<5hD@Z-mkI*tO$OaULpfUk;&bVXK|0$sQ4Yb}7lGj%t z=1Q0$c>`3ACA26pK+0tHV+qL&1}QBc5N)&nAHn?rs69w`YXrr4|6dOtpF>Y`=;<01 zcc3%|8soBP3F-jV-_W$v2&y-||E~v^f3WlqO7GtP|9E=;|0e4F|9`Ca|36Qm_6OAL z^;!lp%OZh+)1oD4v-kgX;4%WOUJ>^G|Dh2nd|+XH4-(ev!1X_pS%ilGXzr2l{{J2ve-M4Jx-2*b zbk_x%S~2hc@4<6wXlmO*W8k28vS^V1kdVxv=>7jac&-pl-CEGPJ~Ve-_Wr*X+$Q(_ z|2Gh#{yz(vnt$H^*Mj};{r`I|M9seksA@tqz5lNT=Pfihi+cZm4^F=jeK7xpgn0k| zHvv>0hHA14**Y*dglaNXfc6nO%=^~@x?da-mmyW&|JQ=o|A5o%zx&{P3hHx!?xBG6 zC6*!1$b`1PKxqrs9)+Z31{G-9Dg@QfFF|v!(D4)R|F6J#8f6}PAVvELCS-rh_y0MH$m;6=>7k5sebeS|Db)WpgaOJ~j zp`;@DVv|KO=zf9!7b=oHSSpftf#ys==Lk;lU|oV3FNN-V!V=Hmb{90PvBdQYembgv7j{Q^l3i|4@0KWKUYwKZYmeV~3cXiU-i|4fDY|6U?c_cy+n&%ovV|DPb} z?6Vj3AohP=(A{pJv(Z5FNRY9aub!az1GTk4>*7J<0+4*M7;$zTG`u`m7cB+VNuaa% zVdG|?HZAg480fsmh8hM2&=@3AdQtcO{~X-50oeubV}SFA|9|iQE5Z369A-#o+JgH1 zj!g^&-v2Venx|0IAa!@xa3y+I|J46;K|5g>9!U1GudW z%7@!Ytbz5l;&_5S}Y5*jXhP|L$3yu4TsuIxC?36u3Xkk*dkSQGNnER{&zOl%E2h?FwQu zRiAhcD#v*seR8#Pptcq)o*-h-z7GSVVIqev_?`kM28KD{{LupI`z!_5e;y35JC4EQ zaU3ACAlPdev~LbxJ7CcgRt;%)Ed}?HpjNA31R=w0F`f`dwf9gl&Hy20Ex^0JjEv%1gcM7V5!tJYl7TQ@&A8q81pjF zxJ&UV1_y{314C`7H%QE(_ymIjTr31ErU2fn>oHTIRx7xoHr9LDOC)w}tk<$yjQ~rK z{fmPmtTcG6?g+ZD8hs z`ZOSS)P47^u(V}hw2oo{?SJL0wFTW9^FKjD2lZ(df!lxH|NrrL|9`m^RF8Q7|E3F4>o5{tIZX$gznDyl2j$1=I)mqXVj|D>dpt>&o^(%nqO6{r|r~O)`T?Nb=1(P#dOR z!b_yl0=&-{G(HvL{r}BQh<*P(n)ie5{bgXVS72cA{#OL{pFL<^?$Q6h^?Mmik}Vkw zL1Aev5uq5q_hy~d_wcWvHI<+Ifaa}i7C10~_H23oe*j+F1eFs3 zr2|N~EdaL>L2AAKf8Gj}mjK@%&2kug=YseD1>icV{_*b$?|+5h`W@sCQ2X8c|NBf( z-8doh9{7A#P=6KNclrN~*Zcoxa32vdz7o;w{r}e=v^Wv={{Il%e}&o&%{M{!y#N2Y zVAG($V3WYeQqj`Z{V@#h&$f@=Yz+;z5l=P z_5T0&1?0@xPvGzY)q&tKgntF#@(pAjXbjF_-v2w^|Nou<&0B)y|9^$W?-lR=f488y zUBvtUL-0CEkbck^Jz)D=BK~{-2c3EI?j>kW5foNXv!M4&|GMG*|CbA7pTP_Rc%97y z8ISN_o&FNkZUwa`Kzgn3%~Sxbud}XW0HOEMe&j8J1Ow?jJAsf%Y14xrPFo9Z ze=Pd{A2c5hnukPg*B5FrFgi3b=|JXn4NNT(oSi^(Hz~2c%FP~6bEST8?+tm`-^A4?!+7!E=Czd`H2VA&YJXUrUS^Hx+SYCK<0S=4+f_-Q2KD3_n!fj<|dzHI^+HS-xrX7Kx!;n zqI$jmhl0;P^k8680Ef5J|NkD$bHHnbL17HOgD%Qa!P+uf)%)LE*nYMOXc;)i``=t} zpA^)`w{QCY*ZQ7?fc2bc@Hrz8HH-q@|6lzC*$;9jsLTPeLG4UXnxCjO6V#rb3Kcs8 zQUfZBCTh(z@&5m@*8BepP4E9t96|e7EgB$c!h?A>xLgFc!I1iLj!jG+-v6S({onfi z4?ufR8$f$P>W_V{n4QQ_4!#RQMn%3S>X7EsG9@MOQ13VwBD-I9@3`+ z*#TOU2y!2M%@!zb|4jkc@ep@S1=o)db7q6n6x5s*;C0$idqMYsdN9udmx-Wto(;)N zC#>&9HF*D<15WF<3Jgr3a0Shafzrt9w+srPHJYF^NPcR~Q~;a*KM*`73P~@2AAsZ_ z;z8g(k^EzZ4a~FIH;{rv(&=^+(%GdbneHh znF`+jXTrwS7(i#`gY;S~wb(G%?*Dgi7`8-x2dxJM#kKdp$&ftS0J_U&3OKER;ud_i zbc2B@B#!@zfby^h^GtA?2adXg?Roe9#(>hGqr-z@k_6m%KpgYu)Ep-_{apL{|1~{H=6&NPK)Hla6aDe1s zb3~wdOwf4~HA}rKek^2Y@cw@TJhlN-4+>Y1dXSn*RXe^PyFq6M-2k_JbSxPdtu2wq z`J+7{ZH^h>{y!+szGP(R0QtF=12WI-*u*5_{VxK%{s&aX!p!#me-*sW2y{;+sJ{s6 z6M*BbCAtVyuR!OO5dN?Qo$veqKS;m515;9RR1`y{Y7HM~ogBm;*TH#P#|qSL2D=g3 z?ucIC{r`Uq+-~L572f}^g4cFpvHK{feTX@a6#d@&|9=VCJd*W)12uaE27YS?2KMUz z3<}AXP7c;l|NmDGS@74eWnVU$0U#z^PJm0|Tg^ zi9BbFm>-UD2CXXssV&t4^`HKO+CChh@eokmWzWErPPHn zg03I+VC_2!ZYM#Ip)3h z|Eb`zTYEl(z2iIv5$*X5UXJq^c7XcJ9t;dNpu6QDeGmyQ@L0?L%i#16s`EkpX;2yj zl}#2cu_}*-g7&>8g32fG`rO^x6*c#aD_~&@ z3fGW1Ep{OP)Ia}S5#9<4+t|t8|EGZ4TH13M>>cJYoPmz1&(H>ssWa@ccVJ?)Z(w3f zj*{q3o+Hr;x{DOFmK#*Bfa)_)TeG@)nv3`U%iy}pV&DJ&pteuN(p09Jr5Zm#^;gAG zGdGYr@Bf#?+U0qxa_WfEL~BP%)SLuH!;{)B>eyF!N6dG zq(t z&>dHxwW6RsbD;g9ATiK9ENG1>Y|Ibeeo@dEAM*Gf$ZRCHfY;?f{Q}-M4f9J)ri2zq z9jNRE(O^eI2~d5d-N{f7+OG+63n)EUB*z|xxySq8B5?Z8&|wo%m6xv4>W!c+7rs4zZ5(-G()=$e2$cl zb{lwYdW3cxXs(DMp=PO)2xw15%>unuAxqipChTEg0IkJ+$;eRg611KbTGxT{sACi3 z3h#e`;Qg;i`m#cnve<#r8j_fn_y7MpKzSZ?CX_`>EO?&)WKH)3aQ_*!M%z;D|Nok5 zY0z3!Mu)i!GEldH_sK)`JqMXv{q!K0t-=MyhH3_enx)DWiJFWI4YL^xKy4^{2L^sn zeV-iVjko}f%(0xEm7rg&31&<+m|NpN5G6Q5Ls2s9rVPFE4 zz25)NfycI>W`NxSHA5RTX9Oyj3RZD|_8er`D*R!nSY@CDa!0Br1AC(8cZQl3pmAWx zxeTB-sYOd%h($8U-X-9DK9Du=|CWHt6=)d_T0<%_F$Od~`mZO{%MBEkUqZcFK=d2% zeM~w(EJp{traG*2K?ip9SRA#V1 zu7^N*)Nvle6lj|9fW}J*G|j}+YAT6<(h4Nq_^$%>L&1F#jB#Pc1K$52=Zi!1u-HNM zfa-uVATcN(lwQE&SkQQfq?ZT(|9k)M1Gj%c{sOrNRIY>8TtVHG0&-Ku(u2o9b48%| zhUy2Un*$X~n~ycjWiSAZrGV}~g~l(qZwsnt9Gf6(gdlZdTnjinlbP;#|6dI5=Y!7Q zsaVQ>3>5D+3obBJ-#f?!GcRE&BSZbY+Z7=B`lH$v_6I=wBF}=;cJe(Z&^?r(c@jwa zdHTD;q9u+AiAn&I_P@iJkU0JI5t?5sK>o34i8}&m-}Hd{w;l`(Dz**`jP;!X4vusG z=YY}-s626)_dj8xI<&k4tt~>{X9?bi!|=lUpAWeGZ|fky0M)Mp((f?uzlyEG1JJp9 z2O1VKlpwnc)E@)6D`Y8ySRK8SytOW^(m?G55!TIRvpEC^1|&~dsNg8q#Lr!V6D zTMwS62JM^0?%zL43H$e#C8+NJ@oznN4L@%GdV<{t@o!TLx_?3W(1W!JG&h70Jjldaxw^j+O&-v3<9AX z3<|aKzbjyFM%c#?0m`RH_EjRug;*@$U_g?Kg}McjU%_*m@x|W%+reXv;r|&FKyxpk zz6q!d3|R^)CmA?E=7Y=x`6r=8!2o2Q_x~S)NPP!n^QL+KZwHSNfb@XONoY|pft95o zGra$QU5LdU+r9s{gX={keFkXyG9mi@oq>ks73iMI1s<#o67YCrhRq$+gVwwRg67#k zX&Q7cPskhw1#4vnhu6OtBJ1~q_j~$4`&u?g_F91U{ek=maqo9kh`q@7&BTB7{@(^m z{~J75>pMVa;)D7k&~hlGp^HJFey#%OZfy_HSc~_+8gN?!bRJ|w9RmYs&*Do>$o;(F zb0ISs1Zq8*m%Z?0;P7i;QGDUZpaIcW4IY<%{U6kZ`;R#P0a}hi@>$(ZaM=Poqpec9 z0=!pzpLPZ4PATa5Y~Z>RboYaHJE)9jFahlq2em)J`@X^BJHIl)X%gwIG|<_X-v3;| zVV_*c0!_{j2Fle-4U;vp5G7r2z$p-A-HIVY9P6Hml>yJr2dys$Hi9_4KNGO&1+{@1l9^uABuo4VN#_5D-tPnT*F0EjLFXRB z&x3d=&A{-Jk)Z=r4|)F!1@EtdmgxmJ>aYkz9aahM%OlbzLx9CXh6Zrj1dVI|{}c*M zo6z&i5}<2Zo55pbkaD~VQr3XR7p)l>kj57iy#G0a(`3U!h6YexEm+CH;LyY%1F{b^ zPLt5W5CF2v`~Me3&{|@UxWz(-nuHbw3y?fS?&C$M8=&ouM9`Y;n&yKHHN~e`{x~)< z#(?!f+Eo@73t0Yu^nvty|Nndvsu!sYNmTLv-z*54BPu@50_qEa*Xz~)0=07!{UGIM z6L|dl^)80U`n{lh%%}j`d#K;ZzzSLq2QmAXY4LG}27Az4*4_jO(0(Q;TdVj4Xnc-= z2g>&-J_#Bdg!40tPcaA}sc$Vl4qi(GQ@^MfvYrOU-;d-!2aAOaEeQX8*a}*sVad@s z0d&TDqx#&4nk@D$og54dpnXpI9SjVhd4Ed|rVA6*=SEm$fbP!*&#ALI%w^!P$Y78G zjdM88gUoq@&lPM*O!odi4cr%KXk@4f>10p<=Ye?)0-*T|h~IyM+p(Z{_5T0QfCmw_B_qGdO_CX|VhMm4WBPKy%EX`X{7?K><=0|I&oW zm&4jx4IZpj823MTuvT{dQ2Z}wzu*8Pe122u|6kDFde}OIe@3_ ztF1}7Fth5O?ym6uZvplv#4IKe(0tyDl}xYnTft}E!}1KPMN86Z@Bj7SH4>otLD0P{ z&~t=XEn2JsED{)8y#LJv&s`#kH&`SvID7w_32rAt?qIA~;QikLoG!fo1%T(MKxGwT zFLB}w?|&1(^Rl3L0nOb&;>8}^W&za?v+EfGX4f+W{I0?lJ(6vw_YD0OgIkl-U&!aU<{? zGWa~w+x6b1nMKp#IQ51IUMh`6z%>0UkJ$G;QAfx zb_+;cFJNE-iB;6HAA^JkB%L){Fi6afX9$=b&k*?Ap249e`E|u?dj=0s`SPQl!NOq< zgAO?UEEptS+-I-=$KR6GApfyK!mt)RF5vzDuMNmwAiqP*HvzW^p<#Bw`~UwV;K~@Z zkCz|TUMph-os9=tYvKL>Fu0xswfCP%-+x7VSS&$0c^*= zB5*kZVHbnL8XRu_e8KHokbck|Y;b#_?L<(XYSd(U0V$R-^GhG1tmyto>hvNT6 z&^gK=cRaI{LBi`TLj79;JdU+5OW~V@bX|Si3Pb8c9tkwI z-RLzJJa*rxIkyBP2b$-q)%5sLsmZGF)0Tn3`(Gh=tt}`%L2>25S`q-7Z}R?+bVnuB zUeLJrOU=0zhohK>K)Wy4QP6`~Tc_sJlDr z|1+3?)P(=PSqC-0G5bFQWBq@I3)TN09IF1Wz+nBKfge=1B>!h%4FAt&2i4mO(g*4@ zCI4q&LK5$Ut}~MW%_BqRXa948^vr%aw-ZuU6k<95vrrL~Z$RoAHRtw#_J3IapPQiF z$^YMRE(0jdv3mdiD_W2VTC>Ff8vmF8QwvHbpfE=s^T^Z`V5rq(FagCwsOHVOnObu@ zy#N1u(|n&n2UKRg-p^oQX~)0_x?9Qn|DU}zwIA1k=11Z2#SANZ3qb89@Oi%7d*`-- z@^tgPxg{|7f$H4Gcm|RB&H&IjsY$0j{LTfDPJ0G*Xc(n<|NqO0Bo_nSTcHZ_L#O84 zR>+tmXie`wPmq5az2<`Ndui013qA`BYQ9MQ;h>5d_`ab3e?jGg2Wx?e_y0dXLF3$w z_6#B~;~6YKeyr*8SZB$}z&KGJbe_fER*+n%CaWFjd<&3UK;ytO?HN=+^(wl*LGA*@ zgGB?l%?;n@2+HH2wv9ys=zR3a;Pw!{bO=h*9<2GMKNSC61f44dn*(`$gn zexHX!{r%4sp#DLvy>|sDAH8UqI{`HA1R5`>zyBe?gXK1OjS^@LMZ?m$J@xxFKuW%M^!^7q69+UV_xm?^f9ng-{1AM7z~a}SGYAd5|Cz$}|1o&~|HW8S`Ewm; z><)BZ9P})(6V?mk+6VCw^;s5pokIQIAE0{+6gutTX$jT4ecN_riUxL>=PSl!P;QjyiN07PR|1!bjzrXK*_mM9EwGBL2bC%Rb zeOLz?x2bjaTnFmIS~@T=g6eb7+3HRV|DQn2`@aX2_9m)=%=^Cq8efRL($K!32WyVt z55<2UA?>cy4B)W8Hy3;!?N4Z)0l6QPU!dtf1vEzo3Fi!O+rj()ua(~af7@b7lMEIM z7$jydWavOjlbwh(X$Bt8hnSTKPHW!(f4_aH$nfH2JmOpi&^UniKchxay0K7X6!2ip zM(puq2Cs7mjd#HMpx|f(xw%twZaXN>L1m-EJO&3)83Ap}v0Jnx{ead(6TSaK*2ja& z7f^W#@&`yCsH~rour>Oi z_9v*mh3W%SAUA;ON08bV$#WM#&%FI-aqJl{sGnfbvLDuFY4rZD2HxupQ|tX-792(( zzah@cf7k#%FTY;80&+qD4!xlK1~Y@R$^&p3Fkr z0S#?Cf!qihCjglPwXedW0VMDJFB!ZB38WV)H}gl< z+!>&__5Pm^?*Bo@7?>?utU+fOGkO2(1dr!I#hENxtQ9O07$m*_b%4tls5nUd1yGvy z{?`HC&j=cC1=qvL)*rn8^?>^okTjEl*!vCL-v@TX#;O^I%N}t&0br@oinr zmjSvP23Eez?wp(Pq8c=Yr3N+=q!&~t{K%ZU0CYANsILh2+X4m#ix!5j-v2egeMrze zBWNBPTn4QSU~rhnXagB1NZ#lDAJR7ir5lhNAaSP;_8-{nItB^Q-d(8rtKR?fz~eEX zIW7;@^Z?MgDWJCf?0F1oAiF{OEm~57z5lC&&)Nftf!3CT?FNtis)NHCWEW`M3^FeI zr4_Ws861ZHzf?l#Pe(y}9318`CVVFIh;YUDyoiCczPmY1^3}p2F|3%iKfq@ySP7umw@&5mX)uMrc-68?Jx8kSw z{}15#ZE!p$GaGpSQwQfw(AjL>|6hRHC?NYC=l%Nw@*l*{zB=CjWx;v1rdqlZe!po; z@-L`49NzyM!Q-Exy=x#pdH z|K_}?V{m8&k7eqD^R2By19)zsR`ZPkI8C-NOH9;a*6{xS0o>;YyAgcPV2U*)z2|`Q zl=uIC;5!IG;bGB|lIZ0zjJSKt2n0aK_cW>;yp`G27{Vo z+7;kF?}6}Fptu8-{}u`Ve}QPInPBRrGlM{<7J~+;ZgQN*p!3p;LBdjt!2qPUR>AL8 zrPk4eN=*h(Tr+HRWnh@8#=rnF1DjbPo$PflnHdDYV{mi9cg%ga^ePFc)D(MBtL24$ z#x-ai0BEkxgMonov=$t+{v*Lsfg$0g2ZIF2Um*X1{87>JLZha|xT03e3$li+!5{7? zO9h4uP~2K7fX;jUf5K9M0d!s`=x(M4(AqFd1NuC72XZEN zDMLjI$h}JF?gib~405jv0|NtS?hSMnL5!sXLjveN@mkFwu-hPEc1QtRm{~f2-Fn5+ z0qoW@mJVRI9K8i$iGgpLlpn!+i9KHQ)p9w5(`T)NKiFMReW1OCC!o$lS@#I4bHRD2<;h;C8yX#&7Erw1t{HnuqJ}e`wDcN z$Cv=R2OK2#QgiMGPna8TYfI(; zP}yQFk#gPpUmSR!zO4ca1E@Xw`ag3(qNV~vr49SB`u!(Bdtoy`btXv8`u}N*ms)dA zfb0U@Q3M*7lGSAAsMY)=@>6T>38-66AiKe#k>LbL9mqaeO$M&|lb=LD>VBV`yTSWk z9JqY)U|^WiY0sbu@}I*zh6$ba@I2n~(w;%WdL<;y)Gv7V3UnV8Xx;{LPGknST~gom z0#x2cfaD|N8-syGjNDi}7RJT?KUm#z2Ch1>=IF9zKHhxylW9>al`@eC3mvq0{$)Pm#(P~HUj-O>}n2h|q| zE&o4Mw6GsbY5D)5rXlt zlWX7y?X9W5=V9UfKMmZM2I;l*gy{``1>#$DLijZeYB0Oi+}=M(_WB1ws8Q z?|(7idd~tp_8Jc=b0F!L88%K62RaMB@bzH^ftPj+64oyv=GH&>_X?C2Kxw=F@9zpw z{Dam3cidypY?#NO0P-Jbe83_(b-MTeG;lpw{j&d|V-sTrn*4F^|Eb_TQRT1xe{gJK z$|-*dJ_8#%E}i<#`+q99{a60V0W>!Y6;I>${+|l=fB8!VWN{Q&PpLdMegJRF-CVi0N>k?#LVH}n3V z0v>Au&9Q*?D_c4+2v;m^egZn15mb)aEMQ=)vwqeJ2o+-fYPC*CNJpTUN(0DW zpuAnG#Rxhpt_RfK@nE_Jp0kAHpBTh=5H$aQ`jnu)C8!?&E=%ss-2sX}Sl#0NF9KYT zAeAXwpzf*g{+|S%Uj>&jNOf|hCNmSbe$!-Ns`NbB2bM>!o9!7SKxKyoG(FTT(1Vr% z=`+0lCxORpz0CXi2-z18mRpTslOHcUUeihXoA}1pfPou1Qv#bWCezbEcRoy$^jNN$%wI8 zP~8tT2TXzH(q3vZ2SC;|Fb6>Itrh^4$)IyoKzDv10H43E=Z7An6{`uF~%WuWf|p zs|-Q!e+A&O0v0}?`z0-&gTe=Nha`gtdV8wTlR?Fj;s5_ouf%(mTx@(VIT<7@PC(n| z4(6|*;f9z)g`SJ(!5VQ8G{1nHzODB&NI?7^3Lf78)qmi+=Kt59$Zm$V1wnJ_pf+0! zNSy}*g951jvgBlt0EMHigW-ZiF9yb12lrQ?eibaAfYxn->viy&!VEL-|MB4d57b`p z95y6RMigK%543iD133PW@_?Mf#s3%71R%=-v9q2_98Gt&V-(k zIrjp3+=1FJomz7*g6c-lco`@zL2VdtpR$30!6Mn_z)Y>V7olarMDKq!;Buv5v}IXl?m0%<_Ha4$E^4U+o?-h*^E-%K(jU)g9ej z@uD0w79t8B^MTGSYk=0tSwil~t$^%Dgx!4tbEO<=9`@bx>y!HO42X6C$+Uwx; zW1#coS~5UqpfG#?j|JDyptZK}u@UfE1R3xc4`^)%XdON{t^5}Sj~9T-9>;l%GeGN- zz-f#7#P58Sq6sRoD3W(R(k*cpU`N* zpaM!upz-5S&BS{aFBl9ePO|ZV%HCQ9`&SJ!7*rZ67!)d6o<8#ae+0ZmEjvEY`9Xl8_8fGvk)Fp%N#f}2Ef4%?z{)22^rDjf> z#S4axij(a3=ID(Ihvo;GT6TYyYU4>0!W>$0>giBKUcH)3CN95 zxeSDy1LRC81-QNfgj@nb4q_L0e885WfdOm}L=4>4vt?KS76a8;otkqmfc;&~0A5!H zY8zV|U|<7<0qD*bivtX-VD`UyaC!!-J;1;S60@jg2(VbnzzW$j^Y02|PA3pihX}#? zT7j9MHPxW;R@i*5{ShWc(7s=bdG-vT_2i)SAvL#*D;ko)ch`XTIsbHI0N?lK{eK!b z{Wtt&V1Slc;IgRx+3yOAmMl$3I*0(P0o5Jgv+0rcxH&d4tnmIP0ghvfdG?_5#lh=- zYaUxyc>kXYZcjkX1+N1H*#k8@6m(w9i-Qc{{Yv0|UrSaSWV|vQJg@xXAVUKw;H{{IE7s|2^__h#*|o|ARfx;pEVbyT*L zwPm)JwM4eB)%WaTt83Yf(Dh@WGlv+2|@TVeZ ztne@N9A1VTQ2f0Boh#7t7_|0|z2aCZllT8nusdHgGBmtMWT^1|XA5rYLfx%VpK=?d zmc{!&{}tiW@T zpgi-_o+0C~c>lKmj}dtP|EB@DAH^53 z?}-aiZh-SuOEze%n%#rdR~5968q}@>oy`PEy9{EWbPQf&P;IxsI%@6>>p3|Z$oq@D z|A&Cb#p>_h&}*mymn{XLwwm|<90rXb#2f&d;P@> zj2^5$p!=`kdwoG`_CRYmVC_?fc?>n6F<|hWJxdrELGliuae!RVnm=XmnmbTCA*B8w zU-MZ84p15UI+sBp{l5TX@_!BR*&v`c254=S_x}mtybtv=_zX$VxfM`<+k*0<_x~WU z8c>*m{f<d%U#Zm)@ilrBzXFp5=r$MM);Bpno zu1fF!|EGZ54b$)ae*(CEfvEovSqs1Xbp_OITfP7PPie?y0G|o!{Z9$p4|=J~AOP}n zMan@9kiSz}1Q-)qG}vFPWC#Gc$@~9ANIN_g)aLmQK9>*44Id%?4FszJtpSFNuX@Ao z6k}|Ft{(xNpWwmj1)2jb1fA&%+RN|#&mTOO3`)-p$qXFc|CGV?i>=cCf0mjB8*G{W z|Fh&M*ztNXL&i%_1}4y)Q>7<^0;ueFm;*XThJjH>lY!Av6MR032B-`JrFU>2Dw(;! zq9xbI`+pi_>>=U*PY(u$ibf9x4oeOOf%;XT{Xzeafa1gZUpTlg3feOTYWu?WAz3sq zFx8|>SAhC2wHzJ+l^hHT9xUbHaVb#Q0J`fKi@loO|5L&JaEpZhUm<->FKAbd zfw2L8euw8&aDGHOC#80OHmu$T?~khA=e5lHUoE(8TD`K;sZz6pAyLzTq1MiO8O&Z# zzOiV@t@i#O04^V(_cBR%|78Hr;aMs$u)x)}i2ms1D%l!I`adr4}5N1?osdm0pRkl(GGm3CcDEth8Bwi<`c0<=yycF#*O-lgp|*iR4b;8?rF)B(JbQ55HZpK{u)2fRGCj0w`v2c*%4vp| zA>cO73{V@#`@bJ}ToKyF0k_L6TB>|sfbaPJ4vvSKN^qYPoZmrhLyMNY1n>WT;QR@y zn?U9v%5#BKW z7Ng@_rkqAQ1`+E9aDP+YaW1rv1lE@?2NL)G?`sGObC4NU2@K2-x3PfEk_VqX0V?Ax zTJoNG|Mvy^ALJ%bTv@c_3w!@(0gsv16oJdf0?>L^(Ao|w2L?u~1O_(iy$qna5zx82 z;Pv64GyPxMF%*E>9H4%}OFM=NiKlq~vj>lFgY46@ z0j>SW_pd3HhU^*nXAh1;keo$JeoRdnTpZknhl*#`l*7frb$C^syb4sVtfm4cX9rH_ zQ1RxPD!4ef4F}4*pgq%$lNe1L<}v!%H!uj)ZCqUe9_wLXU;u?%{p1M@j&m6;s_%-Y z)ERUH)Y>v!sJ;iWtL~bYNZofY5zrZ}b!^QQwRQ{_>QuWcEL!p>fY*pdd5P3ldx?1e z`wLEcAa{WFS%b!cEL!qcg4B5b`wPw&aJi?uLHbWZ<-p|^Os<~wFi7qtR1TcaKy@G} zzdBB01m7_SlCx+jVDkR=7am?XPv zT7c3GG>#dq_c9*v{{K$~EQXYRy#N2>P$*(xsGsvtpnMJkm;D^jIPAX@>2pABoPP)G z8$fgI|8~fKVlb%x`%9$JozXZ}w#`~PR6B121^p%l2h0j)!xXbu)@0NFFq z0?e)fjeq{M`VYF}ZNf`?1_kSX42LSk{8eXONk7%uOO;0&I3xK@5yx zL7+7_|G;zKps=!NDX{eZ_ZysE!0~Vlaz~{_OFfK|&s!q(t1dV=&S9JY;)Cjz8V3J0Aliq4QOEnACpe9P%0Q4? zKzZDHuk8o0otA}fAa*h4ApB7H2c*vXzdN-2XMSOAS)}6quL?YOj8Io3;r-to+#Uh> z)BB$UIIn}ug_=3R`=1+lj}f@;t_RiKOd_CgbeP8kImbGIfy1Ju$j|$~JGd_GA7{of7T4g|RYd>$WIZ!g$BkRH%}JCJ@*-x1WV z@cthSj%QH*_5LRg_dni1_j)Go`eaGb~B z0|^TT8PJ~nm%i}!1W)~b5763p2k?Hw2MmnhbrkS3Q0>8PgtjL@?KQ|*p#R(<^;W$! z=!`%e>jR*9|Nloo>A?H{|0|HTlsC8^1M&-~Z{RSGK?34-F|ar&?!5p1a{;%Hrka3P*5TiurH_qAk@7Zf7B>1&2AfEd_Eb>){G$TZ-NLzbm+WK(wX2zx51$6&zWx8!vNc#X{eNbo#Ak{RH608re3_Wgp+_Cv&t3%LD{ zq!!%f!fsz9xb6VC9o4=FNLr|4V1T+A>@K){DyNasf-~4HAp5-k34_~zusnrulQX!F z08THUxtxC<;Bvqvmk1zLdSb89sZPXev~s`YVNR=+X;)IaH{Q{pI5Bbz`eh74EWN>+D&!_>>2k#FsTeK9P_Wth(PKyw?zc~mB zAJAOwPp$b3ptDjzWyMd8dEj+ppfOKSJz&vN{Mq~ezbTNkW`(%VlY@c5CW%3;BY7Uy zxqDE34H=WRjD^m<{Wv62CeIcjbA~=q!~f?R4{TC|k^1+|MNWX`<-DqpSd&As9M?yH;Q)}J}@Bg*n zel{e1u%>|R1<&PIaC!f?2e&Ig@d64XM4D!;@c#QBTo!@K2dEx)i_dfw}`37<`XrBvM-F}7&i1R0Vsbt z%!Quk12(Tz#ruCS*q^WGGh}%Ga{#AFP(5QERT>Jai$Uwg9p*9I0Oc2uIH(N@B=SxtTA5wde59EgQy#oBndl?x(XHtOX z5xoCbgX=a>cstHxfSkGCQaTe9Uf%zMAm#sj1_sdFv-dw|aQy>v7ib)((UyUuF`fZ* z1|4XfY7AsN#TgQ2u?zyB`v|~oodt}R@G-jP#}%k!bSdDn5o*5#=zarGnF1bD`X2=D z^FhqDYfJ#GSE&WJgVun~9|XC-Vkv_I==@!f-@O0VfZMiEv%vjyiShSSB_x>LUZs&l_aG6{IH3K~U4+&>p zaF~P4f`{`u0j9)r47`=+7!*Krz~29>z-b$5KDdmuXeqO@sAJ*)oiz4DA-bAaO2`@apie+ly!$Sm*wmEd*;SS?F4)a}+_|CcY3 z=Lf4@z`&5u!pQCYA97|Cnq8McXHTH1;a7rf%+h|kE<)Z|Nl7yY9E2hw%TLG zNPQ41a9#wt7i2ah%~gQwc90nk^Zp+|(Z>S5JBGvizZF=G_y0dNpn46oKeA!z+#8@W z7*ys#=58wtLFfGc)SCCh`#)rk3$*3|q-Lhpya(R@f7L+dtBu~k+gH%}YVf+oM+{=t z|L1dn%2nt(rbh37`rx@pP&o-Q2P8LBYrcf{KLc=jgsg=#Lfn%KT`TXwY6PDDhPBr~ zWgw_6UNcL%0yOsxYTv-;y8m&3!y2>?$@{+~cz#pA`TsvqneH%;VZ%#1h6c#^8zXr9 z0^~=FmWm`$U)TG;CAh2w&E41}Fn$2dM}y941eG%h$;=EMOcmfZ6|{Z?<>&tvEfE18 zOci^<nY9Bn$7Rt{amM?i>=I#SHSvd$)q`i~;!(6iyZ`6{{^ke*O2m!u!7uc>be)|7%eH5_Gon z0S{IKM7%=h?>txydeO&Rtnba|0F~3IajFB(OCYy7&SSIywMRNN=Szaz4QiV^%wssw zX$RRi?=X)MeC``)e}wlx4siTiJ1{U=TiOMH(g3Ips3!zfZI(84D6seBhb8fr!4~$ zcy9b(F1Y;ya;w8Uh7}-jP+FgzHD6+;Jp*W5IR|EUr)C2KXnm%`JcbBRn(+R|4zBk> zdO>all{KLIGzrIjE=t^i!e{o&`I4Y;^!}#2i$MXD9zgK~E(aGdu-BS<1SBlI08ZOA zE43$Cv{V*?&QJ0FZwd|{uzSIMoytkx|4qRCACO(%|5(9w09d}Ia@Xs_3=N?1dQkqf zzXuvyZD4ruuYu#my#@wQe)0Zq0&XL9+JVymsI7AYsuy~0o(Z@u1`(@C@c#er!Rz}B z4WRM`wDtp37eM4HH9&JT-v3R&?O%`>I4oOgr&}bmE&$zW*J%$qmkreR1?dCTb)b0- z@Bb!9@y`nOA1GWv=XQYIoWQ_fZP&oiX~_Uir;hX3a_VQ@0G*8rZfk(dvS_IVoy!k8 zzbnPM8gw5^8aV!{tHFC{PITHcFm}c>u!7e6Im~7A>5gY$tMz0rsgGhW0hcFp*et9S z7#KVDGcb4DXJDxhVc!DsLtXpg3X7J?f1vQIKYAgc<`{cP_&qkenx*U|)^(6`ox`iy z>_B4m#q3+^GC=FejKSl>+VdFd9OlCMmQ`w?Fo2{bKFGXLOO-REzjGg4uS3_FLfb)A z;okrMHB{$|L;4;qRn6c!_@63xTo5$Z1G?W5I7+Dx|(C z1e=9)A7IrRs9E6pA8ZzQEWIY!`=2Vf{sX0J$9aFj>z1nbvMG4~V+OZ-Z5I50U%m6- zv4o}n|5xvAJ_c&zfcgw6OaK1|^&7xv!$H^m)?2==0Hue7z5oAPU8_~J+FJA6T7q?o z)s&i@R>d_vAUho9F@1rgeVDa$& z`w`qm2KfQv?`mG}e=6WUZcPE$-$-FtEd}wnA-IeM=>g4;ShUnwdjC@a*K43X8hVxt z4A!8zsRs-Uj*}Py8cIQZ8*_;NoBsc`XsNaa&5e2gQwEPMLe_LLzR;h}z);*R zihZ2{;}=T@Mh1)jkn>SN?HG##%rELEdoVc6Wr*l>XJDxHVlSzm6~N#)hryv!o`JcR zgT17_BY?qiE`vd(hImSCkfUCsI|ECtm+`dPFh{*kcLt`~K+koZ?hMSe0iNJ@hnL2{tBOC5Nw zt$Gqv4m{@%mt$=PnYjomCktvnblhiP2FXL(4%M4La-h8D{qHe&y#^?cBFP^_l847* zUE5;tT3(Bm>MJ05?|+ZM<9Lpf7)m68$^5DJ>NUrV~ zXpX3c8#LDklK1}i5S(5>a*(;A8hP)3N?^Zs?`L2Eod;LHm%YS;fk6hO22@^Jv{ZXQ z(vm*7egKKrF@wURM#uY~B6zIP`~TkswemqCog5qjwGx5rEWJSE<}-xJ_3 zKOzrWcfjiXKM$O?LHP*Ojs*2DL4NZ7k2KDie7nN?pD}ox4P>wP|NkAyw-_TqW`X(v z)lm!zpniz={~WO2Kz(_Td7yhXV11N|r7R3JOHYIDk17D^^ZuU)Z$E<8U4i%H|4RV3 z9eyulC;+(+G%kSXKjnh^Sx|FhK=L4SK=voJFa~@7&jyc|faJmbt0k*J`=Tvi{Si{y$HE`XPupJ~dD>1~prl8w42`K&1-?yzJbOXKxJ0VY~_j? z(7D7njVr7j7#Lp0g4Rhef!E%6|NRRt8>|@_DnNdyk7wWFFpr_c`|n?HxP#J*MN93~ zhGYhTjARC8*jXo_xzY)BpnGTJRlNVngX?gR{vS2qGpqw3^T@T2y#MP$`aB8$zr0jr zssP!I7|&vO;QjXvSZ|{<14Ff^yoz-c17oe{K`rmUf5B5MN1vC z_dhxC90%C#)gZV3UjcD@9cZns%gZ`iNl_?GT z88{l|Gq7~jgVM*xgW$QLc*y(}XszK-Pw@GJ5}-9-p!2JKdV=Z)IdJ>ur5%HS^~wJq zKxYVn5)pXb0J>%iRNi~ADueEV2n4y)`akTPAZVWja_%2^%{8b`2I?0;`UDE#dK%V$ zK<>MF|4Rh#S*)o6k8^|96oUF|7AgYGl4*3XpT(`KHh&{ zf!lxHe}9APe^CDo6nCIK-Jt#>s1GtzYd+{4iY=h_H>mG3du0Q|?8OWVy#M|Nk2QhL zF@UTyQU;xe0P;Q~Y`t1eCc_8)PDTa~R;8Pub!(vcO^6s1gX28L0#I4%!N72!`v?Pn z^AZMu<`&49J=8C$Ao=>+>|5&FA6J0pJ3w<4-v2ehWrU^O|No(yY<7?~B4kV+ByZ7D zHy>11d;ix2w~wqJFes%zX7~VVS0p4iGI%g$fZH6( z#L2837Af^ zLF*A&H&{9|2>fJb5O~SSy5lD^g9K=?;!jW39iTi8+GhhA*8!)2|L;I&jKzS%xP?KW zc?ohD*K5GTc=_uJ@H)m+(D_~(;Cd6B&;R}e`x`mDLF;`$cSC{7Gf0@%Cqu$q16)3# zhItc%2U9w@eNj^hPOqRfQqV9@htzkF`5Ft*x)2X0$i8PJv-_d(aKQUNWF3h2|9>6U z3E;54014}V72f~3!08b*ZUZ_y;H4F8%!Z){WELb%)$jKHuMW;v;IW!zuR(1N28#v; zri5e`1`nn*aGe5b+dDQffbtd0o#1g7P&|V6MS;TAgDC}EuYk-3xewGovuLS*Vv)>x z!27>7xE}ES{|B@;{thTlInMh(0TQ0y;dP+nyuSyu=Yhu%pkpNu7#!yPf6%d*K_2ct zsM`{j{sXxW>_@2kK+ds^RR6!&WdEO$!Taxb@VtQXJq89_1qFusdmjZVHJhJQ-|KJy zjjL7Pt6&1H!>+&QB?6sifR?NB4xssa&{!5|Z4zwnJ$M}b?>BJ!9;Dy<|Nk>^_dxeL zL&yIng72n>+7IoIfzSSc%yB{P>P6ajA>h!&;PWDx;Q%PiLFb5i|340HqeAnU1E@^v z)S52^s{cS^37~S$rs@Abik|5YLBUy%XjoY0131_hf14U9Go3~Zo2 zP(sTBCGY>K(DelWQO-C6wIN`8e?jU&^KhX3BMB`F6l&_FE1>=>1hsu$+A%PI%6(8> z;r%}e+$ILOA9P+0*lpmstcD2h|0>}8@=}qZ0(D;o!x8VlPr&1U3l=gIK=p7~v@|rp z&J6>#;Xv*Hl~oBX3lwXXYW(p2p8{TU3fjL`sU`jpbQdQ`-h;6NoL|A>;Cs};ciuC4 z|F;8=e}l{cxf|pckb3X`iQu*`$juJ({-=QS**Z8dSAzDwY6Mt1HvJC(jje<9LGDFg zpajvE3?B0XjnzZyVOhjI2~3c^u%Iy`(D)E2zG3@bpDy3#dMJoD1H6iEJJ#Xs?;~ z|9E)W=P-|P3U>1vdAf5_%ov^1Uutt)T9NMns3 zz5gqK%LwoP|NcPos3c;~5cKRi4_1l4p!OYXuEpL7GIs*%D_JjK*=QZr6aZ@P!_qgJ z8=>hn7F@Q0`fnh2)TD#k3ZOlQ(DdG<;{9J9ti~pRfw3aF`3ZPEhYe`_1b!y=4e!7A z!R=p=|3Lj&iv-Z#YkBY-S@S`Lg7T9LjE+qVAv(4UjMjU>`#>x}_JQn$mYd8LElma9 z|K-7Hq@kWc1T-I7ll;K~v?rxfnZFOzcZT$JgTU<_Q27N?2UVl!(DXk8)UOAZAM^gl zl%Hf^a%f`E!D7z@@Beb(Gy<}tQjjDg`7=L*o7 zm=-NfyCHc%4jljBJb-y`Sc~`Hd*Ctx6sIuvAj+Uvu-}mE0jE8X9U%Ll_PqA~|9=Kp z|3ZcWgx+Xy*#^?<*aY62^be*F6jv54%~GH}$B^>}#csgE26To3cu(*D|Me{%4vupf zHh{``4_2{MQ2QojUIIhSUTyFgW%WJwV=zBkv^2XnGBa>A9A;o?SPVWFmDBsbEI9vz z+y)9KP&>x^e=MXe2uYs?Ab)_|12P8`UKTCQ4c`A{!D>M16qIK`Y1M;O%ml;+x62>@ zt^l8Df^q-XpDi{C3@jk^NM|oFHemW`3&>Bfx+SIM0R!kfC{X;@>{ABq&j5#&MN9KK zXkF8Y={Fhhyeg{SV!&hj(7cDkZ!%ytP`@>R-0Hz9S^%p5Ky^B(p9S_C%Dra4?_l*8 zwEU=9pC7^kHkXq|G3@kO@ zJhZ(3OM%DLwD*9{;r!oXuk`;P$UWAUEy6OvIE?&Rykb(vd8?quMov|&(inD>80`3eS5n_8!QRs9>s zCT1*USj!>r|5D)kA2b)y7|$RO?#cQpRFgpubRN3Hy#FU)c7wyg9kd3&r4wSOBzP_b z9F7bA{|C7nbZ?tQ3*!YyIrWzp5{8Tc$Yxlyv>k=&2bU4v|NlueJY)df*9omFS{1$j zOM>fv&|L>Gy`>rq|Dku^{c2zThd|{Ulzkt1E(A#ZKkxtGJ8u73w6uZl zcY)NAEp6_gdI+MvEe$j-3T3y0?y!flmxInOZJ5u%6MnBk!Dayq1IXX?_mo5|=5d%n z!ue((RkQ?cu5xAOk~FT#4B0O&5f zg6cU8;I-tS@ig!MzhZIdDfa&VPsMtl060B^*SS3YT>&aLz5oBx#Gz*`=-g3@c>)rc zZu@l-ho0x&|Nri30PUx3c?`W%^VeMLYCGh-|Nor;y2}*g4v3$B6++bho&yS7L^yRs zfYxS%)AT|H@EOR6^!zgurVgU_FX-G=Xqs*L=>1;|+@JCO{|B^p?}7&_{}Xt<2Hl_S z!O9O>{{X(*x(0OD=r71!qu&2Nn}W_;cWh!P(4ND+1Om_5V+a zfX1#s^WxtBc);zJhPwryO z9>T4BGvMJ0bt|a7<-y7)`a|)*qMg(KfA$Xl|JWb;|Icp0|36ki9g{%w2KEaWnCu%E zSgaEa7?PuE7`*>J1CRe&-|JXr&A`B9_ke-J>VOFYsGdsN%1~p~z`$siz`zU{qhbJ! zi9GON34 zb_UDI`aX>)EgOwL_|4|}n3?4jRQZHT6u$Y0Tp_xGdv{xH+rz>(>)cgNma61Ch zzGF~n*w4TM%159*brvn1@{saf7(7<%!N3sFaFC%SY$jAq1MIw?+4n*B8vp+V?mvL;afhy>0;OY6TiE;WW$^e< z!+r)HP(E&`XW+0nARqyn8-d(W{ukWlg`5raA9OeOKahJYS~@}Hs|Tb_%7e%c&@ru& z&IX2><=Pb$9qLK?%NXEiusJj_xH!yXFtIuG|F6Zdug^i@0BIX{J^;Dh`@hgZP-TKX zmH|=k?F1Tw2cON2p}$KObQS`VIz%4=w1$;~X<5Z`1|^FF0t_Ck+>W63F({5f_d0?0 z+k@i{6o;U__W%EY=LMnhrPF{CUtQr)cY@0ma69+#=L!#2ZX4t<1fA_B}1!EDi{8R6GZ*5BUwQ^P%nlt*85kq!)DmSOwUA zSR1?X{{!SZXFzBEdjJ0mItv+;jNx+?p!O%o4i8o?OVFJa$mtk8EKt+&Z?K=C?r{M5 z0Th2AH(9iF?SzDjAb5-r+!n>`LoM%h7!=(u%I*RenRdr1)Y(z zz=M?&u_p#Pw-u79ZU^gw=yx)3fYL0qzftHo4?HLH&!VN<6A}jeV0VM&8$1{o8Y*Bmyk0G-qR;~+zY_uq%$asf162|5D^I&KT@H(IoGL(gR62al10(uwwb z26pJW9gtm%KxbUMe$21}TIPcGE<@|r?u*|4`N4Y?VClnym19TsJ+qWr`w#CRV|o8y zfa1=grH2R9Cj})C@EAF?pW?yF0V?ARLF)vqEl)Fm=HkJ5Ww&+(=!}q;k)XL?2FP6S z|9=mmVf~=fj)Bqo!T(1fI~?aRT(Fj7Pyo-*|6_rSW$k5PaG1j=P`xze2xuIjV(DV0 z>TL`Op!L_F`EF3T1PUkb|9=8&>e;tCG%=h2-@Vwtz!e?^p06!{sRNa(P&G?lG%^%~ zbTY8juLP~ZWT>cUVNv)on}GooHjeWcb~M^C$bjZ~wL2NOCfYH`ILu|x0F6O|!{7h| z7icfnOgjcficx(gI z?w$OPK?XGU3|VW)b_57EF2{r~4tXq=T`i8CHhoPpvA z;$~(@S>wo1@zM$-UTnPoo&nE)A%%AeXg?rm&JYpaKVO3C0nnL;(C}UXIVX!X1|Ht< z`FB=M1_k|1n6|G%$hg zu`5Vu5j_V9vtOY22c7Nh0UjG$@c%zZ4QT8up+)opNKK_C|AU!!pfgH->VoFMK<7Au z=1VO#Pg}fx$-rQ#!2F{AzxO2h{|s_aH-OvP7-jO~-=O=Oc)b6f2Dg78bvX;-9$0AE z=fTPXYAY6k+tdGleFfR+*u)TEy`Mn=+*ba_0B)y&_R&Mvt-|XDPcg+Q6VaMeulownd;}!{EWn3_kb6zUluzJ5YOf(f@yTAU5b+PpAL??3Dihvt#=I z&-T&(f3}DI|AU_630|*YtMvb`trO_%o%j5fUOoFk?gNcqTF>dZW_7LS6=>YiYHP2w z)s#LbtKw(!RzZCNR))Pdtps{^TE6dXw>;OI44u;h?JN6dv9vD<)GmdrvpfW8b3)Dp z(SW%Zy!Krak**z^m|VR7o&=APgYuL2zr*144>}tRR6c{!hWEcikoNxq1_n@H1~h*S z5kCTM$AQ+ZfyL`#=U5y8mtA2m)$PFbTD5cqD1U;=MNpZDsM9#X>jOb|vxWU-x2t;f zNU3@!gF>xKa0O_+cirL56}1t;72f|j!Rv28YwJLBv7m8j(Afsw{~_&vaC!Ro7C6p9 z>k2_>7i5=3ORpO!t$6?E0Jr}@`^&WFg6lgT$ex=2PhMIutbnF31JL=8770uY-hcl< z%B{r=3_mIuRyfQ9pCA6uBDr^l_diK+_`H^2SW#_hmI69sv*yQ%b@e+=iRib3*X&FH z-8Trj?|af;2A0XO3>=ed8F*&=Wzeu`VBiPswG97%v+k!XgMy_jg8}Fs!h{wE{-3f8 z7C&Vf3_$63@?Qo4(AtREe?e>CzAc5clNn?h_A;LR_0Cdj- zXiU_Dl_A7~fdSlh2IWZ)1}5+v7=+CME{j3!7?8y%Z4H+Hpu67`LFYPHN1bK>eQ4g&{|Lp^hhk@pR9Op4~*c`C` zZ#|!-C*j!t|JMImCV|FgKy9#!W6e)MbGxAY0E)|m`yUv*|GR+a&_Q|~<}oY*o$m+A zryzOn|B(IkP&v@Kc?Fef$CI>|f$uh+0&)jv4WLC!-+D+|W(BWF0-qh)^#32o%@!?v zo!5zVx!Muvo~j zq2d_$ESi5cM~y@*TKdlYRAiU|)z<;`PXYtmkB1BmKN%T1emXKt_^HUS;C0&n3!w25 zi{JnM*F66v;{6}8J|4917ZzR#OF?}T6}e? zGZ_@BGZ>V@pEIa|&e;XUf%m^1;Ia^;4z$(^q}QV5JwH?qJk9}HCvBm~@W6xRFQOd) zos05d`STHU-Y9(BzE-*dwBHs~2Y}W_d;dEE9)p0VS5R5I_;rQ%KgeCl2*367R@5o4gV(=8%Qw(I_kW=B-J+%636dU} z!Qtk?z*vCf{!Z_IyTN5J$ZpVjUF$dlCu=!_F6(&)-PZdI`Z3*a;OPDTKWI%F%zR~t z`Ap!xum=O90O+g{upQv^(Vqrc`^p3^|G<7{ISlr@_kRcQ*apaM(0*W$zKUbV7CJOB zK>9wQb7moC)PTm6y#F(S=l?+JK<#zwcm~G$NcJri$0jyZ94la|RC7J|;~+yp#j)H( zhbD$QU^jr)-$Kj)og>NS{htZ!Ur;)))|}A=ZVNyDT~V=A*r8(S2PRN>+A9423A&2} z)b~u)WcZ(``Tt+dQV$DAzsC_gwo{V)!$KJ0m!ac>n*;Qojs*2M&0=q1uf> z0TRy>SU`6=fc>m~x&kVu2Gt90Lx9HHL171012%g?2PAG7z~vn{Zs6n3cHlN6ByRrO zfb>D*W(P<=c&ra%2Ix#aHt+uo;P?lr1H}y@PJH_yaT5E`p@{(;Uf?y+V7(K?Ans!T z*Hxf6u~qp0u-bA(7byHeHE4cKo`yHdb*LFFoz zu57AU8o>au4-)^F_Dxds{{MRes(q6@Aol$O?;S$;c@k)hgw6Z^?gED)m_p0q%5s( zNLb3S9ul^;kbO~U;4-8G>_%{YfR@$&{(|Q}Js223Yl8oQ`iPKr$yV@MIH>z&z-9G5 zgC2zYag@!_v*56lMG4-2_ki2ysPPFcv;X~pggr`HwE~xaAU8P7`wvbB&~o7j$RD7+ zy^!=i3Dm}7^Zxe-+%5o_4=NWxWp;HWgF<~2O1TX!Bf#Z0q>OO83@yVZ%R=(iA8;N4 zg>7}zj4nj}fRx)QOMftc+A}pvFGK4?YjE2RS}uU+#Xxx#;l9b;;BxxkZ?ONp|NncU zy^Mhw+&=-e1;Oz#=_IH>1@_ki24<+gUPIjT8@&F<`~QE9`eooTEpQouDBC8RgT{zJ zdh6ZcegUoJV)Op@8(jWlmJyRd>s;8q|NREXKWe^(?Cpkx`#%d%IDp%6kAGJrEM;JZ zq$_K1-G)8S{#^lz1F(A_euL)OUts?u#3$c?`0p2ZOadeh3NwqA$=^ZkFi=|b{IIq+IP@Be?NK=S<~9keMqi zwHVm6+Zg^=EO9*sGPmLc`>|SeFOgaf<%*x23>=mW4F5s>7f|1>V&#iN6~|s23R$XW zQnS>!qGkpAmKVnvI4m0e|F7uk?z1_@U}v#R0&=g9gZ?X!97xR4O#*V)qeIxMN;TJG zm7Z=4FWnh9Dm4!@DF%B&BOn&dyN}k zKV|^kmHW>kd5W(0zn|dxzUNMaDZ3~sNWYk5^b`@lhNN^oLeXtZb80~$MWocF&1{hw<4#lF z?l3-w_y7MLm0JEVJ|}36L#0+YjL!wS2fb1&9>(Ve%|BFXrNj83@pq3(Ezlir3?TRM zdjJ1#QK>Z@CeH^d1EBYmfaLi>ZMaIUuA#tMs78gJghr|y=TmnfPlD;A03P|G6cn6yUWvhYgGO$#E+-C$z6F*fMEG$(Z zcU(aE4wfnm7T~m{;0IFgVX4C4fW!|#&&!r7|Nm)sG6*@&Ww-%Z>+&+BQd7L+MKS|J zE#@7lpt&>9SP5v#3beKbAMRjaV8Dh!>tR;dBs17qB+G&Gq)jq|4ai*}+9H_&>_$tK z|Gz^u6Vy^Q8Eg|ZnHWIpBWseqL_q2+TK<2oXlc+$XyIX~Nmc@j*(5XATO==lnP+d2 zyaCJx&Vws-n9Fp-{_+3+7771H^St-xKYxE&-JvGwrX=0FC*2u)Jeww7)vXQWF+0 zOd*hXdG!JmFF4|41_J|Q3IhY<83<-FVPGH$3otM+fyyyP(0CTOu5W%^vC$5+2K6uR zOZzJ?An9HPk-qI1B9O!p>D!JW!GnRJ1yuf^n+5i#9q10(KRcm%Z7e+*86fF1?A1?% znILgQ9)u706wn_9Q6oC)!_~GtvI)f{F20mw@8L`~SZj9DZS(3HHnHw@7Y44hLBH zfc%2U=cs;x=IyXoptgyn0s}L8m_gIR@0oU>yLf*$TG}G&A5eH%+Cu9R1;1C`|Nnu) zon@mP0|T---v57ldjJ3T!BT+%RF*$M`1k*BO#l9^0j-M!-E9O<`_Oq0?WLUjusL7r z1ONX+^G~D0T!t9XoRLNHxf>n~shOSj|6hRS1EBfAq0#>T2mMY4HqbhUM*IJ7EH(ds zhMtq6Vo`tYg9k%_Dkxqi-~az+^8NoGCffi10&?R_`~NRMbth;X%7f)K;;cN_oGi<$ z+8>Jl8DV=XKy!WF$qYMQ++$$)agbq$#Q_Ee&{}NAc`PEJx!Q(ihCLv6g6?;4moB^Z` zRJVfEHp(;XvDEng6S9VoIi%q}!vXC!(0R_x9+n>eKZEw`Yj=U~aOSA>WZz;N&%oH} zr43qR(opl<&!E=J!UA-Ef#W=830Y0U9kupeA`>|c?@Typ_@FVK;mAZ!!zY#w42&~9 z4R3(zPD^D(84t3%*2=rW;>G{ZpmBWdb_Q1P+%7Y;-e7QhW$_qNXVg5f1F^yN1&Cd% zmfmF zAwliZ7Yq!HF$@fhB{=X01_nlKcmk+gtBnH9r~J>cRrtV=sM+=aG**$S`Q;C2>;klJ z7Ic3!Xm8q2MTQBs3jF^QH7n#HYPgv}W9J?W3_Z3A-$CO`{~_Y_U^YZA2k6eeW2u@A z44^Y@Z58hSPt^SW8KN$}AyJcIKSZ4ZL!u@J4@7)HeWK=n2hbd_P4ag_*6wss)Lf z4B$4It%4vpj3D~nf&B$h5Amb-|9^9A71nM`)C@Qc5pU>C)VvS~8b1g5CsA{O2t>R- zAW@T32Q+SOs}SUwsL8JY5ob_J)KqH%osj~X8wTYQCx-tFpmP+oS21un%=>r4`~RPe zMtg<>;Jrq3{={f^GBAVFx90y}V6nM>JV5zyqb+FOmw|Po4FiL90t15w0|V$TPezb9 zNbJQyh8-{E7#M1fIaOLRFff4DH99si@Ob}S3mzi{-;u-e4Ai~>6@!co(6xddEKl!3 z&oBCCpY;D9Xuk_+J+?j5|9^Im{{P1^kNOvM7b2)Uw4O87&ANI@ignbKLTk$@z19*_ z=2(3fyz~e7c*$&^wdffaf4UXH$d5`n><%2hTr( z%31G!d%)uj5cV!`zZtaNA2e>8kgRRs{r3TQd;v7i<=FH;!G1pjBW(T2Bw1~RUw^eV ze%}Y}k6!{Fy9b@OSCbEO&l2$39a{wkrl0>AIDYosma9y$~484N5n83ZQUgYE^I4<5(#{wD_Bj|J)%gXZ`^ z=TL(5dHvPy#~+O%#ziXu>8+( z!HR)_!SVn@gQWulOQ)^2MD2+-gIY}o*t!2PVJvKRpg080wRkW>fvwVj0kod~2uPg=0}D7!KpgaSLGY^(W4}U2BQG}gu0J`V>ry_F(D8E}DWT>!S$oRq5 zgF*hKG6RRDR}({}7ypu4%^(p-9qRY$#bXAJO3j7?H78zbRcbac)jSUpsnz(X1(COZ z1=0t)e+$fa2zv!OE5eE4{|2iC3~ctw42<2D+7h5KgSwT>%PbTA|F>ZH|KGCV|9@)` z2Js&-FoE0&8qWl|3FK~T28IT^2l5{(S{PXD4#+c9W-};+FfbT|_AtnW&tZ_Lu4ZSk z^k87D=WsKq?1scD;{A;M?m|gKxtXU$U_DH2i4IfDD&*Fa#c3T)Y z>b4q*RBdfgs@v*Z@oV#64y%<6%vD?EJ?d7i5~+B#OQqIpk;toN28Bwm2BjaO{~Bt& zoGX5Y{^hXrWMHvc$XrnACGSxi8YEJ2wfRZi)5ws`eY#Ue^33_05TtDw#_jHM$ow)^&XcioEZM?0J$4t7XwSBhP+CxtB#qi zg8~C6AJvLFi6nY4G*~=f_)xPnxWd-Kf#JuCe+`LV3JgD1{N=FZWMBmCC9dR<_ek_& zNC2s~1l?DyDev*q<1a_8sh5bYgZu}O9$N+nhM%7Q8XBD$OcFU97%Dl~k5zgt&;Yp$ z6z@Mh|8iI=FzDB6GB2~$V32?5%)n9e*Fnotvx%irlYdFAmlrr));tJ*1(E}ei-FUf zf*&m1odKnPkXfKS05{_w*bD|@%>booTTKRAOHQ^QAoD?Uq@a6=;o_bUaqw7>GkDy| z){=|u14yl{f&&9&E|UFNt%5r^e}K*Mgvf*RyjsYd@lu|Fp>8XrZiCco%b@EYnICwt z+^>P>YhK7YZV#6G;I*%y_A#_<2=M;*3_QP3YwxtIQnN)#e3GL`^mZup1%cUN)AV5P6Urk@PHp=$YS{sHwRRq%T#Ip(9a~ zp%qOpSRF{OMFK;L_df}6J&k0}35Yq&%!!(8VEa=wnVHed0ILC+0Ue98vE*cU0n%p) zD&HO4VdHTiw}QpNY9ZrsApe2IK;=lH<{xld2+e%3JgOchaQ_yh2doxu7DT)jF^*?r z$;AZi^SZ;v_7Gx7>MUL{tN^>2fq?~l*C^afh&b3xc?J$!4h9>G7YrLfYHb|~I1;@W z4uJAft%E(1`4D-q9;i7;=ChJuzDJ^$0;%Rp6K}rhghVd|2NK<{K)m^a%!yt{NOeCW zPV*6A2@ZeIo#>Su3@&Ku!E!jlo)b+iIL^UpG2+&VBhgEdfyA)kBEftHGR#*b&3pqQ z-Oo4yoSqpN96;qesvQtH)G%U%+`;R>Adu+AAOH%ZR4)h{H6K9Kf%U@Ujep$R?0n35LB4FjZ#VeK_pf~{E&y27WEQY4;02Xy%F_5|!{~0)Jo-^23 z9A|;0hX#=UQoZW`Cwl#7sC6)hmx&gyAZkGRklX>Oe?WIgBisQNLsiEL8HYqs2N6S4 z2Of7p^%pBx3{4$${2ozeTfAZgi=n9lhaGZ$uz1A^7DH194m&h^!D49Yz+s1`4lIVM zjtz@{A!2CizvVrr0twRGtq8B4Ho&W!b8J7@sAiapV zWP^;yqQntI3`N~3NFKC#Aiz-Zoc&nM1C%rZ&buh;UqRF($AKjmOw8@oOL#tGxByD4 zwhkN}iC!HYpmd0u&mi*1`Non9+Fk&)`Jm|!E(Xf`P%)6XwF=?zv<&7W<`h9~7;spk zmLbsbLnL!7xflY#dQt3yilM3lm&a)4LBvqhF+$P_ig{2mBy|?A7(GDt+A=USV3sEk zIdHfj!V+w*tpf)%4KOsIg(X-XtOpuKmRztoGURp^R1C!}4B&KP%fJEdOQ6OpL=J2& z!Y$CUMS&sFi-QLguc=-O>Jz>GJD|AiFk>(D>zl)VPDFLvu zWOV?w<fHTL%z7%h^gF7p0&6TH68R^k7DO9#*y)Xd8gHFLLt{A6>0!7f$(HiNB# zph2Q019QT$1_6*bXpA9MLxI6o;qKi;&AWFk6Brsm;+=8Y616FM2DM%a&~bf+5>Q!G z>t%%KZ^kol!1y4yyr^g3uykYK0PQEJNrsM>Fvx@Rb*+~YSRax)0~B=%nCdK+GB8>k zV`2b}ML9A2F97+~B6;dI?|(PI<3G^;ke&5P8E{*W!)GZdBka^vj2DMkvbaBf2-!*XhM}#*dj%^hL7!oxZ$|2^T6F@T? zoOZxwBise{yR8BvbD|~#JEXi~fRs5<`z<|Xz-qwy;9>$`|DgICA_i6mGhYkhF3|c1 zkXu3XDitqX`XFfpCWk$(g3?`MJc9`+J%Y+=OHK)J`U8)}z}*28Lt3lD30aq9>(Brm zn?h5M#V?R`NT_~+h=KirunU}~395tI56YXBUJNX_><8WD4IZn~WL^gHE6AUgo=|%k zknP zoEZLJfa~Fu0Ov9Im>42#z~Z3rvUtG229mFN$-K={LVx?>I6HCoQ0-!Z%wj2x`HP1n7(zGCDD5wo6&%jZu0U7%Pr6bUMlM}=LHPF29 z#{1u8@SF%Jec5_3*n-<93QnMW0L^FY_KBJdOyG7G#JylOAhS^QfaV1mh}L7tB>+y3 zwqU#X&qMMYy8^^6c$&7g^n|Dbg$>L;gkF%HMCygKV{9#6C?MI(a2Rf{76TKw9Ru~F zB_~83xK75<3$hnUFF1VcVQpZz9pLseT(1GxUa%c#Vp!EFAe#r#i>l56i+K<+tm;tA z!=^3(i+K<+RP!KW;64o89}qEAbqQF^gNR{OhvGhL>Ix9%LCQy4OD?DwqFsv+L$oz* zEj^*?K%amq|ODo0bLBmtxS-7 zkE#wLhNRBo6%)AJwPj$!W0Y9h@q%c!r~987)TvF{V9RnZ0oS(3#2SZ&N~n})HJ6AaXU(ygNUK2 zgSZ`49as!a9mMUZ>cC>C>WrZNL3STR3{4%_Kd5De5m*dO9TtBWfyL0&f!&OnXN|yO zXzIXjMpFkCLsjR5#UBtcG<9G%qx!=MEQY2I>}FJZoxoyf>cDPBQwJ79QwMf4nmVu; zs=6R7{(y*~sRO$i)gM7%F*J2xH>27c1QtV62X-@>IcMg#^)K!-aM&DUu(fCdT|3LN##Z3~bgkI^|A|_laeH;RK8uqO zH8ls!ULolNkI_Tc$1$+fDyU<~f%?5j>cL~?XzIXXsOmT&`OpE`Jct;YI!M|_v6mAp zhNcdZH&NAr#Zc8j;|xU|L=06O4>;ay79hEA8B9zM5eCb6!0}!4K>rn}uVnL_!Peq9 zR16f3ka-i37$goE%#qsgJYX@Da_0mOIPPp7Ffzf%%;9Yih#ZRg7oclcS=NBdDTF%k z_$Zn>a6F=xk33*8GYVb9Dvoq^AuDJlyBi>5@f91R)K>fQIiF{o&i-4L>`n!5Pd#|1W4bMfeqA01eL33 zdcg8vJutgD1;B2!bzosZ8yf}nE5UMT>cM5ctpkGx7WH5`H1*(l1X~9N4oJHbrQZsc zLsJiSBgB06V@P8TAoqaf!0O@QqyTm!B%C-n;C@Dv2bb;e^rZlHr>z4+TcQ_36U1G} z?M;Y0YI;$CxD}=S3K0XTL*yL=up4a|+B_iTpgB^$g2;i(CwRUx0K30d0a+bH3{4%_ z&9x3F>cC=X>Y(mKQ3n=7QwMfuEdz==uo$X32Q2P`h@q(iy9L#K4q!1fbzrxk`qu$0 zhNcee7F72+fW=VN1z>R>L<~(G*e$5;3jm9usRO$O)qMeAF*J2xx1hQ&04#>8E&+@C zAYy3hz-~cxUjkSRO&!=RsP0Pui=n9ly9L#K31Bf)bp=@52N6S42X+g{eX#Pz;#C1y z43z$n#K3L=m%p$w#V-OHAkUDt&6#&m=*(wxYNYpHj!_40h zd2s%Q>rnvf0hfK~Vkl*?0Ty*oF%)$USkytqP}BurQ3n-6QI~*49aIcOT>(NJBHSQi z4q>lA>v_HZU&)1qJ<^z;eWE6jV}6M60oRAN3QVA}OvIQUc-#&?Pikw)g*4^|*9#eY zLk(}J7>a)&V``}CpkgTMAY)~y>Y!pM>L6oasOq3%DC(eNTcEKNL^y)|i(HpL>Q1o# z369Z%#)hru8-B1zp8DT9fuX_s-(K+gO3+wzebzgJTFn618g1}CZ4ZWc$XasH-4k=5 z>#}VbK@up2>p2kH;N+tYAyB)8jJaxDPoV_Sv) ze-bs{*+b@8{v-E~K>EOH!1^HJU~kE}0NnqxbznSzRM&#kg2hqPdM*IxcQm(v#lY$y z=>g;xaGS|ifq_3!lNq|FYX14Pd|6I=lnV z`=h!YB8Q^ha|75vXy$^&(A0tbgQgBFhN6yh1K91h4sO`&2g`xgL&C()k_$3-WvkH9 zk*L{$zIN2k(i0*N)&mO*&K2M`ysbk37CRtvDC#{|U)R@P`H-l|58ms98kZ};@?bqM_j|4YhXZO@Ld4M2f#);P z)Pcp&)Pdt1O&wSaO&vI1(bR#((A0tB6-^yj3`HI13UHss)`1yYJb>k3>McF_!F?C7 znehx9mRb-#crFMME{rH@(8OTo*lIE`VNnMcLsG|#MIBrWNgWFob#O5xb*xy_!NtJp z5a|f)SL8M6sha=m!RZ1`4O0CKN`K&WE%gWB^$J`JO&xe05t=%%7@E2npt2iH9as#k z4$|(ow|KDv++Re@o5I`ta5->W2B99j=C=L-iaM|unmTa*5~&XhG7l_3=rVgCf(bR#((A0s`Ia)Y_ z#n9A2(>03wz+!0Xz-buGUa%ONI&d0BQwJ79QwL7hXyFVNLsJJ%yJ+Tt#n9A&(=M8M zU@cC=X>cD9iO&wSaO&vJxqO>(QS3$&3-3Ly)Xy$>%(98p;T{QC`VyNbU(=M8MU@O1yvU*EsI|Rj@o=|n5z8YNb25?%kb!fy=PeSBC z^#`=QtLgo36Zm{VXnPlQE)Fza;cZ>G7)T$qpJNBwGY2Z~q3uh1P@gbW6S4;xT=ziS z1JVnL8-yD{V&HfH*Ut!bU@?##pfjIA=RkO{tg3*xb855qzm3T2KR|0}(e^p996+)c zw08(B4>AwxW{@6mezaAX)9L;Hv;=(r6)SB2)ylo#I~Z!Eq4rL*wf_q`pOx(bsQqu< z0P16G1n=GKwEh31zUv!mALH@w3J-=L@R}`4I|fGU|Ij{$9i)!|Ia_2U;ygI$nGVo1 z945Y0X0QOA0rkU?K?8Ko^UF*I0ni?|7oH3pehn;&FB};((C?st`+))ChaqB?02Td6 zO|ulJ=&r$PmIf95I4H~lofiVSJGWNHX<4m`m&i|LhK8DEkIe^MP(0Mj5oedRUdV%+g+FN8n&IzkYkb70DDPdud`Tu`SvZnyLyY!cX&Pn+H zzvh&2MWxnFzFN;<(0S(q;Q2DOi+(jHjVl_R8F+F%7#8VwfX`3m0k@w$FY>)~W{|Mt zVuIB74ep>lvmidCUS9y`gWCnt2yk$m!ysdu&B)-y@P7|T59t0J(3v+LEK62^ z_>S}bf6-q7IuD&e0<@+(Vd?+>pgW&ami`BwBf(M2=?uBU@!|g;HU}ISYE`@|Kxb5g z&W!T@|8E00!WkGC85luf%g_Mw4`|OZ*gwfC9iaW_p!JI{wHY`oHSH4WSAzXupuY-y z#+XK}nitspm0ImbD!p2m>Q_SCZ>!0`Siiyp?0(Q5YbS>P2S9pY?gxb}h>yqp|2-HO zIBL0^E5Pn{2?o2{`~TlRP&b1qixwuKn$_AB6)o~AAUD@4D`-_}xG7X>&QGY-V&4Ki z`-RnUE`x`n7Xv#et<-7;7}RR9msDn^DuBkmYB>TdLN(d!>N`9@_ge_qEa3l8$-U?p zC>(7L2r$&9M8oWE0EIos?O@BH1Sm~dGAnd|(gY~}UwVMzn++V_pz{Nf&Ifq`({FL$ z|9^`G4Ez93`&)q=RtKG&R3^Lny zE`tIneM8R2G22jaQalB8eitYm|4{rt5p)g$C|&q9uqZGvFo5o52Vv0JY9I_sM<5)) zz`y{)pt>7`L1)r|@CgP624oDn2NjM%XUjnDO>o=*KKsN0bf@VCl&OZU@#J2!93210cVE^FXtb$d4oEZqzylgUfYL z{zW>sADp(dTNvtVGNda&@ecM!D?>df{wr2qY_{|`cf+xXp~6yyS;!)R$pEwt8Fbb_ z!BPhOmm23jfX*fXon4`@l)=6-WinsQQw=kVmr%Dg*uMg)snwK%tXEd>dj+~btX5qE z6 z&SO-8mRB;`D+L&A5*Qgk_ryBRV=w@P4aja=21W*uddGQ;EVc{`EH(+^44`%6Aax*d zhk5^RywpDT0klW7ra`%)lA+tr;v_UYK3O0OJ^S}*I0T6O7)O3sXyN;XjWHQTA?RB%PDrgcRnJLJ4b$bNwreU%K*^CB7k z|F7hn%~z?(rt*^e+=p5f(P~QVQ765SvxW85ds{bH-a2f*j zl`59XtAOgf+H5V6pWd%CessUj0Qui0ffXDk-v9s0*d*|R&TRSu5{E_ym_o}ZU@=g< zAf>Sb+AR$KL1_#W|DgO+vrN09(yiMMo_0XvRvL(O4eF0nx;L~`dNLlV)O2I2cpmFi z^W3|l(lh5lrKZb^T6OD+O3(HLaQL``!-peLQ-Pt<4IDNciJA-?FJ7GcVC%rZTCuVz z2Q+V9(-mA{aU2pi;JHDMa~~{TLE}cj{*^@wqYx+zK>4VaLrLVP#Q&0lr z7st5_1uvb?eXvzvU-SV zv^8baayf~-cyT_XqP;2S$BXkB;Pmr!vfoRta~~`g6h3S<#T^RH5JT2=@L{gPH1Ids8#j` zmrGy|KnYNIg8T={SBB1>nmd*?wmdXqrp#1-n3v#BC#REnLm^?@v zR1W{-WZ?Yi$pLD!{Q#ZEWT~vv0X~n(fq?;b7L&yThI&w)4Kf#0XInZ8bb#FWQww4) zD7-8g7#cwOekzM}{#0h*{He^s@Kc$C;iobW!%t-ahM&qJ3_q168k`vZKS6glG+iOJ z6F}#$ocmzO326g^@;p=xxD5>AgTe>X90rb;o}jeMmH{bC{9aXR9bl>Sa$|OE0^K>! zz&KL{d=ELe44>%&K8xuKIAWj#=&Tq_Gdfr*y=t6^HAAa~ff01hjpI~?Igs><A1EhCwvc+hFRYGlM`y z#}lPSEe4hP4sd(e0(2%ANNs(mg9E5us%Vh~orTX}(ZVpHR!c#vlBBb(pC~n|GpN*e zfz957FgpNjc1R1GUBwF5V-;QUDxmYOYu$rHUTQH+sMK_00G&f!tLa<;KKq)}y8?9P z^-nE^381tG%D>poy?*Hq>Sz4_U$JDepT#L?8PZ@5I`dk>(hXWppq_Uv0kQ{n-ZiLB z!d9Mu!UJpAb+RWw&jVKg#jnFW1`SJ11};#TgWCyO9wder)I4Q83;Q~4b z+)|5y3ltV$b2*eNYS}%tKw*L}JYF1U0H5gvItSch86-SFZE}z}wZj9{J_nr#>cKM2 z@Q336K+yR|pf;mL^0^z{|9?lmj6e6mk_+MnP+1HIP!sUmI88s6ASL{BuS1F$RT7_h!_-CfHpNKZ4f< zfcVh%U_EHu48&*n{~vUQb0zC+K3E#ASpb?>JomxU1F9D^uK`N;FChH-1@^B%<5zmC z7#JMqFmO0bVbFN7pMlG93PVYK`{N47ISeKB9gizOXN5xUkC~AQ8fdV-$H1t)kD0nl<#b^LJPrXo!;ebOEgU*5_3=E(%JV9d_7A?~nA$N^T2cJ&|K0_KbKf*Er zbgn;JM;Zfz#R3LaQ2Axiz`$6O&Az3kL&G4HgU!y;x>PIkU0{N`#o6tFCyQY3aWD&4m0E+-<|sUFayU-MTTC_}k168CJ_at3pFw`LXqo=q``@&wp!oD)U}^x#X}2-6IL>2yqTR;K>Nt<- zgLWG;v%|dqXFzgLee4!3)9tkQ!t;O9f^Y4+h2nR6C~a^!_*XC&+Ct?HMM3(x~G+2Jra3MI%EwXdNT2@h6Zu z-Hi<8`g6eJu{H>IPrK~>Zz}kF!pZX)azN=0eBTbz9ovpgOby6&PJs`Is%$+Xj{ckFGeh#7@DIDcM<&HuF zINUTJIDzw&R&WKp{p?`>3RGTHg2vQAae&lzwp3tdo@mdI0~u>OZSkU$fuW*>e+eke zy#GIM_5S~#2gwbo-v6e6&zFU`fekYE3p&5j0aV6)@B@o;!Nfsl-!n0R%(qlvIPue- zp#vQw-8d8-1h!A8GMd0x|xtLf6)gP=R%nI(w^Z3$giL=D@z9!#)oGYl@`+e~L2T;C;js-V@ z@;@lgYqv3i^1Fz38zYnBJcbFNJnt}%(FHY}W~h4qn*^Tg1-l(7zCip+O%8`j%^ysb zDDljY0&+hnjx7}!!EufpX2|gZDlb8IV7xx~|HJEt|9?Q{HJ(a<%(g_bt5WMY=nfUM zygtLl``;w+T31;90@({HXK{rcDDQ&o^kC^$d8v$)&YZEOvl$WI|0aU(2t!S0{}15u zkN5xo21wz@Y|%2K)%)K>=)FluXBEXVEfaBP^akcLRay&KLU) zjlBO&1m6+&q8`N71K&T|XwSf*-^l=qy8!F^h7RC!sQjOm37reH0GR>0 z^8uVzTV`CGXwSd_D$Bk9O@N%w4Z5rLZ#(#mYDoBWv2@xS3V`k`aGduabk2qZYz!Nv zuC`~8fQ@B?#{6E&Ge}r!K-vhPyi}_ZTdq(c&y%`=BS2+ek-_qHmT@5 z#O%<-AOPx9St|VhQ#m7(i!ld;kBRSyL?yy1O98q88L| zd-Sx?_S_xN-Cd6J7(xmm?TDDyf6u+BKElccGP_dc2VeD^M6Q~a#}$_LjNo#zrosPJ z^*#0l*7q0<>i>TNkGI!9__u2IF9rrsUIv{J@4?a$Q>ewjubeo#d6Lj=?h3B>pz{2u!r&^@PU z{>Z9-a9s!CkM=20e{6yJV+}5Uc(Amqg8X2A=>LD~d#4#dcWJzS%)s$7j)4Jm?l@?C z4%|LOD;pdjV_6I{Z6RY>9t;dVFZQ38usFz22CH)|mNE!|&ZP4G|LAs$0_6IClX8iR2*9$&Z3RJg%>-snbhFZ;_N|61IO$-X&e|^F2pM{DHWrbP_ z4316zTPii5E%N^VzX9ZL50$@E-#zyNWN!6;R<25WNII+k|G2`^4wBC5ANaqrw1b{~ zr{Jemt8f)5URwV^Cz6`v2d0&S{34`N|cb`=VjtYrW4< z<7EsYo;;X8g2M=u$3gKh(VhWxcL|H70;hn*0tP# zCGlb(gM-CV1`cRi$OQB6Gbq5+SS)3bfXewo`7L6Vb!>YE6agWRbCy3=?mg922p6e{O}q)!DZ7YUW~K$6pd z%GpBYe30Z!pmK_!I0S`%s3wCAC>|}f7{UE$P`v%LXUG7_S!zMf?SqOHK*V?$AY(y( zuYTGyR6xZfki;6GV&Jk9s<#6w23{Kr6`KGR1FwUHip_wELB`1yz;-Nvib2lkhKQ|z zh(Y(|Lc}&e#o%qjpY{wppkl~wIRF)dr_-PI3@4ys$nLuU6+?F44X7Bh`yN2WklptJ zBF2XtRv(~Z$nN_A6+?0#Bg0EO1_4V?K8X83`?+5JuK4N6$oVpkK?2t2w`FKxhmChw zIxsX?|7Ya@j~B@?2q2FGK<7Z-ytHFLZWF-w+*&FyG=TcM5O*Nj0zd7+b0cp+cSgLl zVPL5Bg58@Ax(mevygn0Bb~YmJLV>npLG7=Zs^B#)44`_&vaz~>vNpPz_C%CfkA&Ks6J&70N+dE ze7VB=|8H3fMTQNa_Mrz$!vj!zx!(D51?YY?@Bg*@AwAN+@khA278CO3?h(v4G~_TdKJ`f2tUEL4}A8Tmy21g zJLuk?{}CWJfXY?Sy;YzwWYGC*Ap1dfhTmhc1L*^e2@x|M1fEy?H=7SO_6%OrD~~$% z1L~tV%wZ7d_{+eM@SK5h#$N^o(E1;cSZ6E)L!uW0)67@~hDr_aU5}vqZ&*NKI!vt z4yf*aeHY~J8+(!5od9)r2B`k7euAZ)2(7!iVUTo{*1#s1`BXM zD1iZFrla@2=93^ZL3tnC)nJ8gA8Tf|Nrc?RA9mwZ}R^Ce+rr%r@a3)Y2vVh6Wxx2WB>O<&5yKHU}6FJ4Trx@ zfbMn$J8xTBuYI4^xS1s_t-MHGbVB{{D8U1QUlQ*hlCA` zZx0SzOASQ(9wHCp!{y=ae5gE>50i(U>jIj0VP;^kfSvOKj~^azdkZvg37TVi3HBQg zq`d_?lM}*+w6#Eda2z4pfe<@ke3)N(!EG*7GkGCxE|3{uGkGEHEf61KCcG^OH51B* zn~BApylC#^MRO;jJqR%q#)p~7hsB+IXzqlz3!(0;^$hr7@d9!#4=n9ia`J%nfcn3n z`9Jize$Y6I2TOS-cwb4qG`QVVvsb$Uw8qL(iwWXp(0am^koJ;AGN?}cGqZRlc;3YX z)bLq)pm7lf6Ht2xl%7Fto=Umde3qV&`SW`4 z9(M4&Hi|y5dR%i(ur?Ve&x6`O$m3X=pm8h)6YzYyCIjz8(A}a646GCF|AX#2Wq{rz z$_Q$Yf%dJkr@vK1h85H(SMVLb|Fu^! zFoD)n6)XdXj|X`D4a5KcpmD-Vwq`$Ao4p3K?v4|+tp*B@O0FM#FFDVBuz=3jf%exG ztYTmSxy!eSK>=hQIIN!_+I`@4g=l8I)P$~?;rhX6iL}lQ6#v-Pd}z0T$0HTATNs!f z=P?Lqw=gh*>NL=rT1$ujKSB5PYPT}*gTx%?GE~%@bgrmWXHs-%V#ujjC9hI(tn~)JqV(w|ztGeBv=VGe`NOXhPQKI#84mLp zGF~*F7pT;5JyNO0q)^Gx!er_2|8M;Y1<*Qr7tmT-$9W7kAismw4}$Ur%)PMmUIUtw z1+6`V&VPc^|4(&@A7SnWt%>sf|NjWs;ZUNsfk6$F2PZZ%aCop3Uj_Az?4ADqw~m6e z=|F8$>jMl7p!3c_^PMlF5aTqkxzE>27?LWr{y%hRV&YiP0v_)K&0R8j|2+b}m%gTs zeT)7)2Jn33OB)6WkUu8WFf6I`9Aqd0jhTSdfz*5dKlyS2Obn_&;TR*VolxZc|Fo;)B&HwMdl@)DdO>G6 zgY?xeeGRee|H+jg{a`*^KLbCsodMF%s=p6Z<}hus-Ul|L1k;RDo(%^XNlpZEV$oJjgb(Dbt>98)kr(jSSb z|Kv#|{orr}oALN}h4noKorGfw44}Rsk{P04`$1sJ;kdHlNq6pjczryhd! z9Q|AYllT6AG7zLE;TQuuNF8Vm0LYIZc@GB0n%74dmU;jGr(>xJx*wg*4zf<3amL~r zw0KOpUE%%zgd!*&z;T;$8yq(Y$5@f#@nkJ1{y^h?pfv%Y`1k&Q{4G?E9ZW3b7>iZH zF$Sg$2N{aI|DW`9oW$@4CGJ6HgZ%yYcZK)=<7+|sLE#D05Aq8l?oV<;;+|oL1t{(h zFo5qQfT{KVfATCSjp}zYusY0R*kY@|;FhSVU@%dUp~PYz0}n_YXlx7QR_lcf4GB&R z450Ax{(o|+rGf&3#XbfR>w63m76%jG(p-v~}z&$e$qly#N1Q0vcOsY-Hf5ozSS@!IIwsEw-2&*cce}moUEo ztyhHACm}r;1gYTAw&5wEieF(XOHbojV$8-j?e+m@N-v57n zRY+!Fs7aO-s7QX{RFN#d1hj7iYA1Ysga=FB${&jV9YK9w`=tN>t*cKn)Z8p0osSrsm!ng+J7{#c3@zzR`~yab1VbH<~Rn1-!=>kjrQG2MI%uqEvi<)rv*Z820F60;`g5@M2I!t>(B0@z_ZAS%>%Q`ao&F&=pF2!JmvE;{@e>oEofg#!S7X} z1_Os<6NAZ%{pS@xX$Cxw{P=eTV!Zp=%|=Crl2R=O7SLUipm8lw`w3(w_#XFp3>l7d z88kq3isL*63y_~d^*=1UC&vGOGco@E2M-1Y3++w@cE`E@A0UMrD|mmB0s|9BJt+L3 z;RtHKy#d(+s?$6e7%qV2AYl!@;~r=Df!e0fy*%LgPY@s0P6FM3zJS32)XoB}9Rs-) zbO$%mJ=-OgnxH-ugThZ6aDD6eQU)@{S#y$knf{9Z|G{lJ4p9BcAmQY|AX3ZjV^;Gt z0CY#U2S^WSzD0l4|Njp2{%!%859*JA{08#ZMEU=3Cd&W+FfsoB7f`#@`~Tkwp!K7m zyHuSR{?~xkO2PQv|Nk$rP-HmZ!IJ$1o=?~r7_?g$>K*4YJkV|hx9gT@w}RVs7TT@g z{h22~Z5q)0lfyiQ2JLpR+6qf|Rv}B}b2loz{~xr^4eE8s`Y8{VtX|OA7~1$G3%Gm$ zkMli@g^u%q=TRZ!d`GS#jq@SqgNc}@3->%=XBo$65bWtB7wqX~2buo}*8+`EK*lJu zK=Xb?%?E?##64ItLG8dqd+2-}cpepLey;oeIq-T>>w64L)%Q}KILu>sV#&!G0kYTD zp$@X{%EA2=EU$vf*7SP}wiZhnL_l?&_y5PbpfVnohZBx5FoNnaP#p%=16TKN>r4Cp zKP=;zBtZNAL1_YF2kd-!|5u>?pCuRMj92Kr?k7QG5viJxd)-0p;Ft0Le^}ZvF}yy- zz)^n>a)$;e&DSb?f7NJz?hfc2(uwxx?ttsf7(~74*u)s%{a61fsO$yBr6nh1e8JX% z;X$PrJM`R7P+t+|_kXD{aj-uQFfhXW2=zZ~{_QSU{vbmMOdb(7j|7p!Cgd1{4Jd3t zG*}NjZ2r!Kh7AL9*nrBkS_l7Eka7oFeuD3k`v1fF9+Lt{ZT(5ex`A4U@2|jXl3&2W zPslS-b0K&SX{u&@K%yqU4yYdw3Zqa>_Ftedni$KF^P-l4=V>HlB(7Q-FZ67~l`VQ+22aN=b&xbJZTImB>F=jK!-tAa_G1<; z42%^m@@y}i85BU`H7!9RKkXTQfYQ~E`HbLoo)#^$L?+sU>jcJ$_J)66B!ljpSBKZ- zKkAJN9Of}dK*vRyEm~%2djHD>kAK(yy(HrOcRDzHL3fqe9s2+G#eRkdR@V$1ekw9t zcxi9=qNZHB0(7r^#ZqR59}5{yyvPKZFAg5(uBijHZI}-HzHj)!=F$IuHi!QIvuXPO z*W&rC0E=U@VnO%JTeLh3^Zus@zV99+S9ff4g$4M2`G+N-aaXGYAoCQ#YxO|#76%vv zEEY1HuxRns0m*y+liLf5Tc{i}R4+e7P66x>s2meiP7W#;iKLGaBF9hwm9vG){j+$$ z@E??hAa0$N3zY}^4{YuOP~FD_>T5Dtv_$nnoJj3Bf5KxyG8Bf|uXmOHO1 z-9h)1Gb@4WOOTmA9T{fWIxsQ(c*w8-)E4{c$k1Txz|a6%b5g0rpirsFtmOSq9=wk0 zr9C6a4zT%_4h$R?3mDieT4t4l%&F91Rsz+pwd&p#p!LDt|K!2vEP~u(0dWVTMa!&i zkXrA5^5AwnM2?{W5`MGhLFD9M{{LrjfT12Lw;n17_J6~DhBsin55WFovS^ug1SDT^ zOhE${r!NjNoB*p?zyOlJ0g|^k#w1X2oI#=D7=x1cKRNI`21wldpD8COTpK}o$$^1s z(to3nN&k%^CjB>xnHXAz6|Xip&MuJnoVMivv}jT|Q08<|XuH}aS$Zv?vI zn#od=fq7!QQNTobBbSNxMn3g-FNuKs4w`GVs9^MH*vIh3`j6p<`oF(KDwZl}c>kSn z6l8D1K86<-2N+nO>N22m;JFv593xb&BV?(9nZ;5Dc5prPcLI3rb-nUwP(M`AqT&C4 zP+jHy_aN9mu(H|v?=A59TxfgxjxE#w|F%y5|66i6eX#U$y6}^kVFyU;r!&I@h`7rG zOE2dGKbaX$K*eW3#GMN)y__EWWM;Sk6<+`<%Pcuu6n;80toZ57u;HgO14!QosQe44 zz647zSB0O<3=e)fGu*IMVi2>`x3*(wkda1~8 z15}P8tx3}G{;LV@553rD_zN882@I?jEwf&E|I2s@3SUrr&q9&Wz=I|63#i}*uTA2D zv~|GhTW0fkuq1-k!4-n~L@yQ_8g(27ucu=7{+9t>S7@og09tp-@zS0_z~Uqabgshe z6=;27rCJLU$Q;n#cu*hHqGh%oXwGZGeFh#7-}_%iBFG&t;~4}jxj4Y%$+ikif{B_2 z;Iknibv#%Oyl%u+fdO>?6!Z*!Fq;uc4R~A^qy}>SCuBrnzX3G1 z{t~>V5^_g0sC)vQTm0fbSg!%d?V*|s3>L>3C)9dE?`nkHCoEy{iV=KX8>p@a*=_NP z5qu65m=7@%d}lPsJdnI4bYF_CfyY?R_rSvy>K-^Be1;cDJ?Q)^>jjJxERtt?d;d!VuWtq0i?YsdKWKgU z4siHD+i;-%8Ys+c4lsbujwh`xjeqUAF+b{tN7%2aZrN$a*iZ*cVZ#7-XFn zM2ykm00XGLgRD~ni#=d{y`RBBe=h@r<6MRw&>kqbU4K`B>xP$2%ehjjn4dJg( zz7~5KL_p(lXnIU7_JYRg7#+~WWi9qH=vW+p)FVjduv+Y8Fu-od$Cr@w2bsf!r9aTR zXNwms&~k@?0i5UL86+%Duz<@ln+IzeDq#0IL&U-NGTS_00pEQB?%zVhAAs@@%018! zad6(XdEfw74=NKZj|nQ@fZXG4^PmOp4yb}2g ztyamw(1I`*a+iqBgL(^8{TyKX;9&^u*MR1*zd0?s4+-bynxK_!quPP0hc>A z58nSzc>e!CB5ZlU<&DjQ!~-BPi2r%O`^s$@{vS=`=wSez0RVU33+Nm%XdW392QPS_ z^O$gZ!Ep$;_XQ8+EIzn;=$tX!osc=q#m?4 z`#*z(#c^Kn*&ntHb3Z3?>;dn6Pv!XVA(5kiAK_l;{4>ISaNHuFMy>(UTFB*|4-xyfV#Ub zG?8Qe4J3C%=C~2=Mhj4b_q*Q$h|Z54dC-JL40uC4ZSZ`!jh8@T<(C{y`cIR z>JM-@+bRfQ8GnG)`AlFnp#F8D<^gz{1EL>#Pm_X}V4|iVwB0A501F38PRN~0whm#! z;4uOR(4H&?R?xUPXbriABEtj^mT&`j+ZH-5;lUCHTI1#jS{n*#*S>E4{{ytP)BFEM zP4N1E@V=Wlu{CMzTfpnt6ByXN|HXpW|3k<0L1WoApt&T6d7!at_+ChMiL7*f3dP5}4sI^)mXu+(B;vh-q5sI_C?5^Bp~W2pdIZwET-hk*q& z_Eu~A#td|>Uj1J0ikCJF9H4O~(0CbmOoD-B4dO0E@L1Ukf@5Vi3>=nmOrSjr;5CAf zc=CT`&-DMF-J$>gtQ8m-tR?2mvwFb5V0CTIZcsSXtDUZ>XE|H}YO{O)ivjx|th+Xas^+Mc@ux;NeX|KEi#;~?iCT525tr)|)>^Um0FH$uGxtSq@8 zYaQV0cQpe*>)SbOy%_8*xnSzuUqQ{Vv(%CU_lrPgfW#^_Cpc7U7BE5Xn1;!rs0YUj z4)stuP(ER11obOH>)~G7Gd#ez?h=xZf+1rI;CPrT?fowb?0-<0LffA?-v9rD&VU02 zEqEPEMJ9t%NX7xXfD9+OP%RMcW*4aCBp0aVW(QtZ&JkQu%j}GKeh}(juMp^7FCV16 zUJh9Hdg*}9iUjTZ((eM#O~_cZFa&`1tAfs6TByRn1KQ^eaxZLd0OU{@28q`!hU^6g zt!06UgJ_EchX3edHp&10y;N?SV9AMmb|2_W9cV&xAf5F2`y$qvwZb;o%O85Jk>9#pJge*ih7jA22=5hlfolZ+0v>|P=cO$-w% zo`KiQbb#iTDxNbp)UU7r?HRAARKK{OQmgq$$a7Y$O3v0J;B(3}-Ix-dgU(+*qyRdD zE0lwET`jwH1;|e}2N*ajRr)?Fmbt#~*gW;FT3>6h!78;mteXfXZ@E*hAI9^8$2yL_mM#|Njp2{yzbwy_s4JtRbC{weH|Gvyd}Fp=N{9{Qv(I zEh-t6Di6-RR0i);1lO}Q4dI}3>li`yz}yR>!E?YRVi@LUoS`CYJm74z-S$Z-sR%#wRR_VpQAk>Y+ zrqb&}O3ew&b+!zk_9gqVnhxg*(78R}F@m_Z36@+;a5sDZ|9A4GUE7Bm&L3+)VF8&3 z52ygS4?JGO#K2(l`2Ro9da;-6a5qJuo}tAKKC7)_F=+lxO5~;I@{CF^<|nmY$`wC7 zmuFP0w9u$n%EDF4;U%)6gMsa(dfNm`PbP5v4!W}uWG^UeK>i2OP`kktHhVy8p+IN% zfzmGM{3cL1f#{HxDmo!c+5Umf%LbV_QJt9czaVbMZKi?_D8E#CJ~#(58)WWJ9Ol|8 z|Nr-rv+V)MJ&yAjCZM_nd6p6f71nFxD&$ zFsR8?5~*3vzNOYfVIAl!fsmJMb~ecjOtoI#6}29U>pGp=RcbxGD`qOUgU{dtg;~u? zjUOO2pz|DRy*w-s>O3q!X%}1Ag3j5p)%^dj(X*`uTBf(f8f5UMeV}N!G11PP7 z(~MQ=?Onp&Ysn1!>>K+!XJBL4lwI z1Ioi#=4>sz{|Xs`ps=&w z_y1p~Z94e zcrY+dfSzG-MZ1j=oYrma{{I7&W7aDn=Zn-Yc=xJ$CFl$Z#vCLw*)3Y;UGx6u58nTS zNK1?+AisgmkpTG{*Bp!o10xTrS)j8r{K4mcSSm1p=8-$l&%Xef2TC7EXJDj&+S{PA z==H+?FHq0HSY(0CAGQjD44^rW`cHW_SJl|}ozzE)719OY_|Nk{u z&b$Dh-vbWgmU+dXbm0BZ4?MRG^BZX0qD9NR6;L_w{S+X7c>n*q5;T|Q(7*uN@5cbj z$Dq6b@{b3L`x-2EiNMUXXqgcKT6+V_H|SyF{r}$^cp7Gg%u)S@w#{lnA51(jbgyFu#!A$IqI^ERYy=Qan! z?1%qko~WPcXAVX9R%a!Tuiu(~JF;lf3`=@`CKJXkcQnNMK^{{+kJ&=Wn!Q z-~sJ{h3*YyoM~SPDjOO+Slke01Jo}bEUut+kcr^^{Cl)3YVI0?&msWbE#UpP8a&4j z>cfNM{BJdQF0s*$fup|j2B_^3(iq3U02nf zcUFPp6Um*9pm1r7W8i_drIs|xF>rv&&-xCqyE_`~7#Qk1!EUZWa&rOL&8@D-K<=(y z#(vDw-bJitm2m~=TuJa4wtRPAZJehTc>gnOzsZB}S5Q7=Y!P&Zrl%VNXn!^6{LETS z?TVU{;4_9H@(Q4{;2>vxfcj4!EG{LM4&bvrK4ALWg%h{GE5Ugc;qNL>sJ}VtyTJYo zXq01MfcP8iR}+|DLF*{1Uot3IYP!gQ{8np+bQUKpZXA%^=zIZW4)(ZlP6fMho^l0f z?QG2*WAM2tkTg^YKC21rM)2HGCAcloXb(%Hj1n*YGbDif^2@>FLVFtJ88|@c02)_o z8sixlpy_Kt_&wG-?Ro6q9p^GksXoG>P~FZBJ|DHB!%n3(9=z^{>7|y!hw7CMe3hDq z7%DZLm_TPz{sf7way=Hl*Fmp-@8b%P`Jg^grTT-uT2JeW7yB71>Q`v$)tt~0fs98Y z`eoX47(i!T8i4b_|BtGmGz(eB%OLPFo}nWAo`pdT*M~KTbnLVQY=#!h48K>PzV1Rb z2DXW63@o+^C%|K$p!1BuW3ZkOb)dc}$ZYTb|961G17+PZG#`M@K?l{}ptB(@l^Isq zKW1REbYS=oDaeHz+vma@E@$#USS1j92L5s z|BodD2LqDa3uHNq1p-jB57=>pK0=W+$mTHBZ4^C8?=J|v&Q z&$C3)hjgwc6N9DPbI7@pcHa{q=SsFsu)sK1vTXuv&z3Dig8+Cui~)4MD1(4y-2ViS zn?ZLZyf_6qU$kw4#R|wd05u2nLFZ|{c^MBj6XIuv20@5^^H-3wJi&4h_cEBjs$cHm z;4tt1ix>56H=t=$#0IqfXMVei2lE>6-kcZpZ4aPw5;pTe^V|vy7A;_T@Lr#n@ogVK z{X>U&j1?feExDLDKRI#whmhdhQ*+>0qQ#g z931B|hS)p({|7qH(mv_`U(i@IXg`v50|SF~)USYWHm99wVS}p*sn*fhlK>X|w_6n??6B1_i4N!T|xt2>`SAfs8gxztl05q4?Ho+2U zZ{JJ#wh6F(a`g@NuRv#7>Vx(vPGR71n8Tm}YO^>_VYpJCej9YI<(2x3+ZFXLm!ae2 zuHboa>%9z&+ItxpAm>`5q!swNmKF~fSn#DW3;6jHb}<$YI2b_X04P1y%6W;rc(FXA zQbX;Dr6vPM&5J-S&{?J4|Nmt`{S8SM4h@KNa~T*EKz4!hIaCcatRUyJdjJ1dQO|xD zl%EXhH9+g8{u{vaCkLdy1(h+NJZYKm{}-%mc{#uBhW;8*8O<02+7AS}OTuw3V}SM& zhX0Op89g9(YA`xzgYMFp%V?q9&cNt6m(f7G159f``ydNyj7#J0fG4R)V zMHpCm{r_L*@VEA9_W?@mkECSRnkpa2aVIISQ4IK;&3o;lODxUE#sYy%L zvv|(HXvqOCGp~3sFl2zvpa5;a0EHi@e;=}(%_7l@;YV$@H7LAVDweV*BziHh*Jgvx zdidW1GS@P`T?w?#(UQ4c$zdLY&z3F*rutP5pnUiPmiKC#lPf%!SAyFmxbhUpUQl@n zx+}$l#inJ;D}*_qI$^^K@L8WO@VJ7Or6DaWb{;I&55aXXs7-p;xT5B_bw#bbbA|Wc zwc!2!H8r5MqzonXM?P18@|E}Bb>O~K4S4?yL(Iz-1_?;qG6Wdf|Nr0U0$M};QvkF_ z05pbG-vvHz8{9XlfAPBllpjES15mrRzWH&*OC1J=mpKdqpz)v=J}7s&E%0Emo&t9> zv>x+du?C&>zBN)sAmS{iGLfb|3lB@0G+9|G?A@7pP`L&DUEs?@i zi-E~{0ZO>efQRco(3yPy-+;<uS~i}61TG)4#scMC*&23lTvuvmm*4fjfDxF_GP0EPPuM7T4ehWnGBHC5oV z1#ySF!~b6%3=G7EJ0m3Ae?KG;?)#9#y#poOpXj25dopOR=SN1Aa0iQhc#9G4&X+43 zn;2}o|NH~5jl&l1pgtDpJR4A$cPcW1+ZeS9|5t(TJc5L?IcS_1RCF*lK*Jf-2Jv7q zd-_B1zaeZ4z@GX4KhXXHs~>F@puR`l}pc4~v>Tj6I1g3gYDmL*Ky{~vck z)A@u(3wSzT0y#g2;R$H07S!LVR%PX?bp63s?Ul$?vnsd()Hdi?$WR_`&%UQ(Y4eks zrQmz)T0m(NWUu%C_YYy=1LeDd(y{mdM-OZ2|Cnw5!@vMq*9kf&8??r-UiCD%JpnrR z&HMi^Q*byUjY&Y$Z;bb!zlxxCFg(xg0_8ad8%SCBKjNhYB3*;#aX@_J@CCW4{=vVj z`UlT-K=m4^Yy^$LSST`F@L(|ojnhNInG;g~gZ%HoVmc92r@+b*(0Czeybd|tg2wJ< zDl&l12Lg>%yC99smyf%+A6u27u!KWp%w8N|3Eg9db5 zkpa|?#5Jyn6lNfEHhBNDhV*|9GL(V#PlNhbkae7YzJkxcK{|H_w3isP)*5mK&d;xw z3Xn6GVdHEddqHDu-v4{=g4SuG*>%eMpB1EUhiO+Qx?KhEvvz*=g3j{s{{MdlsQ>H1 zVvIQZ621n<*cY6R9)a$eJ5K0UZAEh&t4%&oA)$rx%OcLFWX3&-?_o*?@{c?aT8Bg7skW>}v2|KEef z$djD1X(s6GPe?n5(fj|sw|L4X(4JQCxf*!NrhVAUrq`~ZasbpWfs{?JRzk|Ad#<3e zX*O!v#E4opeVqvod(5&a!u!t;aQa6po51^Xz5f$kHi63h257kiN=p|!SPXqYg%Wt~ z8(J=Tuo!#=jTzW4W?+KtGXs@Npz2{#Odl+tB`S1V|s$9O&8p=HRgng!n=O(0qjVKXdR{D_k60#(~yqn^%I$0?3*r z1|AOvjw>$~G8BO9wN(%h0ND-NQ&6$gk-?$`bk^uWrkbVR6+ad-6nOtD2d^1}xP{{g z-0YV5b3yZqNc>%(@%)sf42&KOoGCBk85+QAL0|9|hlnc(xTtLK2$r}MHP?3-N; zI{*Fme1-|ta~KrB>&^F|uQ&hNYO#j_)RsnDZ~iscVh^_U=3hfC_JG%$>!YsA{t8;R z58AVZwBEb{(pRYgudf$DxNE^~@BjZwe$Qu^0dd#={}y|&tvCNX5#%=P>&-uxTI|8K z-u!c<#U5Pi%|F|A+-K;t*ux+KDw9Ee0F}!%#~4gPj@_)YIHthh{r|J1#U5;H&p$I- z?7_PB{H4VnTx-uiodu5-a-yw02kq_PgseTcbqIj(Nr9?`jt%@d02}K9k4thv)`QzB zw00zFG8BN)BV-H*v}XmnKUU%Y{Y1_G|3Pw~H5?!|SPj@dR`8lvTZaHkn7N(y44oje zLG!AXT&xj}^H@wkY0Oq(Z4mPQ5{SE4!E3}p?JLl_DO-ilD;nb&1QIp*PJ`_GsmM@Z ztH7`rwAK!EHx}r8OpuyHO@6q%{w~ls1cQyO0>fsg8iSXL3iL72p=u% zk=CMv<)LfQ;qFFSiw;gl(6#6c;jbF)83d5WM?v;ma`9<6&V}@YY!wo~^Sq$^3C?%m zwc*gU>I#4UCu%nQ2IZAh&Hwd@njde;i~eaGb~B057{C^(DLaKLhZbmG}Q2;B}O? z3TvIb|NjPuGg25Nc>n+R$Kn8^8|oVN_k!5hyTAJh2~QsI__VD8gHobq!w%5AIl|A7 zHSV?w2|S6KPSAaREDDL54IhxyK=mJBNYq@s5)$5wO^KQbkag)`e?!*7gWQ^^$&w$|sQ8TrGyh z`dtjnp!*JN7BDbdG;kDv?z#rG?NgRAFefZ!X7c|3Fc#u}*qVBA(L_yA=$d*lB)3D? z)GH_}Bx+t41Gx?4CeXPn;PSI&Aup&c1v-lz6mQ=D^uY7~;C5g%avPj=iT9s(;Qh6r zvI*3#0G&$&oBM{&yEA(K%K;5>GQ612paE(JfzAxD0Nu~>FAv|xLFrGXKk~9NzkH!!y#d*GT2;Dn0fzyU z2b!~RnEP!(%2Ea!z5hR8#G*$5p@)G3)Gh<5h3eDr{(t|h%>sV7y%r4| z65jvs@3dF|*{fW!l>LZB14o4S|NBcpVipY?86Yu`8Q%ZzPXyIV7AGP5QbGGbK>h;x z8RS<`zOrapz~}u>7rg(s(Vk(&OGbu*O05SPwhI6Mf$D8gyrydM{|B*aIXx^u>lH!i z15_VcLif9Z;vHlzx?M1PELs*=dH>Ua#D6@)0?_=B<2;50kouQi3=Ec>Y~VZ#N~d74 zc!mX*oNPBlLYm_WmP zGbmmh=Q5~(+;7PRxhu(5VFE{@rm!)@pGHEceu1o$0)-orU(&q)X+!S+0p~Y}8e4}8 z;5rTFCQDAp{#{!K_8*}70xTZSAo0?kApz9hw&Y^WsCWr!bA#*zx#^`nLxv?6V+XQ0 z=-gOPISQI92Dvd&lLK_#YXB%7K=}n!mqY!x7&c!93PVdy#t4VGUsOP9KzRymKV%=V zhb1Q?WWOymTrD{v`+sd68W_Opz-1F;4=`xV476_;$&Ce2_pd;9C)7^xUPG9DpmrIo zjRlf-nEQDJs6PR6ldS^-e0~cgXUWM3Zr9m5C?LWS;tq(o0z(sWThJnbfyw%AWrz3Q zSW{4+3Dk}TwV}QLKYR!ZOG_@=?mGshcce7Y0h){S{-+6EQ;|Gpjsw^Y7<-UEU4i%& z(oP1I&!F(ez6bfaBy?{vL+zbliK;!;Q2GBIR88p_K=*7SY8pEsA463Mw-nWyf z$-oGjF9O|->o|wu2k49g`z8i4>pAlcUS!Vq(r^C%!Eqi#2dIDRFpuGe%^?P{7suvX zH0)=9?YUvIXjwSR`=16lJ=i)ih`schZ(*z8?3kz-06s_gB^Lujs-}-;Z9s5EqNa;S z{R;5B)SQ=E3>^9^!Rv!N?Ef=>&mypBS-2mxP72arSBKOq3E(mG7@H;rv4)oUpuRkl z_dg+UA0OmiklQ9?&i8Pf_dlg!4+G>37;sxhJh2hrfq^Y=-#Wj3^Dqh44`vo zK=bYep!Ni4|C;x|)T^Mf1hn_edJY3e-FNmamY_N1e@Y_teLEN&=lyqiv4?>Zq`vk^ zb%o_Q2FBWR>|4D5rGn$u`~Uwt`kml&&J6TB8CdF6yDJ>#{RfZRfad+Z|D}S@#Hm}d z8Z;lgpe}Vbh;FHKoeZKu>(@b9jIlw8fk8)ufx)qf!KYD$fyLq&10!f|x@M&Y=*~&- z8B*YT9an0B*Y7(qfaXjY6dK(b7(z9`VZ{hOOUBE^V6H0zqxb*+4<@oRFj%Vn|6g;| zNCdQ}zE)F9q-Lo>0BG#NVkrY7XdOwT3j<57mq$RQCxgOE7X|^)9vryY>I@9pZ44@* znhtuP{TQJ8m^-;ZX_J95l!MKzmeaceeD9Xm|NkKKL25u}&4Sc;|Njr0BLMl20rkvT z*+lT%7xJ02bCoMPRTx;IXU%qi>J!jhx#L`h3E=Z(4>EwtF9z@brJ|j-46Mxu87e^X z;dfZsu?%?V82|Nm|P%>g>h`+Gurj(~{6yuSyu=P}=LnD=)FIITe9 zPXiRE-v5g%8xAtmfW;RufW>N#8T;1oYCRqF+`0OXJocI4CPIUF&|BDM79T{pG z6&V`pJ3;$>{s!1Q`v2eJ00XndbN34t3mAAT8W=Rd^M`+X!1EX0|NrW|z6(0P_iqi_ z`Mo<9*P^96@cF$3ptE!#=?-+pE;!x6&+n}PxeJuuKy4A&dA8pF3o1cr4OtB7{N5Vx z|Aki_Cozhkq*ajFpm+j@cY!5HKPdiTW`-PNu}C<^z_#Ha14#c=NLppMfc^a5qDWAl zf}Y=d2I>6X2K4iLL3th&x8DDYRBi45|7+AlUz^4-1Jp*IsL0S@y^vu7=xkq5nF@0k z=nP!YxxOuT|9|lQU-%Hd?giu@h+jZwDTC7tNDt^NU(j3}D7}H$p!kNQhr*>V6&X4} zWg_hCCQv=;*u?O~`_Fyw+8|rRxxN;lbB00tjj)#$c|Sqn2QELL=^m8E5oJX|sN0I9$@Bam&IKoN+6h5GF7m&Ze;RMz1{lDNSD6ByF z5fomayaUc-;4sPuofp{va-;YEKj8C55oZF67l11j1_oyQX9A1E_pe|-6S(6osBVC) zY5I?JCh*TtLT3WwIRm~0dUkyc(%JO|;61R(S|T+^ohx1{|IesY5q|($)9N^nA*NzE zBj~ImAH5Zjwbzc*7#u8K{QqC`M8nddiNT~&QvlTNai};}#!{*I?Nr6F4^5REc21zP zvuqU<7-~5@0xH=w*8Dj9AAG(&XpJ~%A5Fy)W<^lF23m(waje{>QuBirL~kk+NH6F< z>55|vDU}=y3u@VnLG2Ngb4~I15j1WNI-frS$&WEwZ469~QyD@)`!Nw`-T%*UoX6nd zIE|sDQj?(pw2v5^7LG1D2cEy>f}Yt5TBqp@UK0vgd#K?4>ZdxYe=0S^AA33}UzX73N zjHOcT<|8!y6QKG#Ao@S>f!fy4GzX?Y`$Iux0BCFhdfsh=b}Iw3rNaN8;JXZ385qIx z^B8zQdlf+O0W#BJ-v2M!?V$CK|KEVZ!d8Jn5Y)~Fg+wM@+vjSRw6%|+n{UP{x3i}%XSL*3|oc&e`^jKiM(|Cp8+0wne)G< z((|SR*gu*YOrSl`6tug=6_CLe>|Nj+Wk3tEMe;wyC zJgHa>+k*~XCm8}=Ul{`O3%32?uyxF!F$>V1c-R_iQ2P!v77W@W4$B)qnGyTL!R<EeHD+?G+62j&uL7v2|cztYmk20onsw^IRFU9&ZX{Y>+`hd!+#Qo-$D1 z0%Rs=uGH3nkpZOEaUMg7tpiwI5X5(w_x}ONub{Q16~}UxfcC?K*j|kXmGBnh$0FMc2SR7;EaANqs0i+)^ z#sG>VkXvfCy(>WH>VnSX0m(Ve`~L!3--y(#Vz^M75nWNUG{B-}DZ>Su0}c!oOIa8| zXOmR2urOF8Ge~&<|91l#WMB%k|KHM?VU?u<=-wNihcyR`L1i|0oMkB&15)bx9OwNn&|d=%f00^kh6}Ym!4PX`Ss1{3i4*_dc-{E_0ccM#C>&w?ios#o0trjd*$3YL|8`VrGAyV#wz#8K z^F=_Vb`nReOXQ_mFC!7qdLwWkGcYhRure@!;;Ck}c11`FhYcw0ILu=R0iTn>z`$V9 z;v-klBCk@*te{oMDIj0Ta_o^s3j;?e8{0p}CWa&0Z49iS`nuLr!OU?ULxAI41|8^m z1}&Bf0t~g93TB`?8$joA+c0o2fXuC6U_ST#I& z{|G2-K=+5#FNgqzoj|RFmq`8U0MMOFA~h=+F4S-{SJY~1Sb*4|c4}=(bVbE61{O$q z`qL50+1OXf)udFb6Q_7f?O!>Atln|n|10%N9YE&sfXb?xmD&~H^yc{g!fR-nvpFEZQ0p380ZMzw z>8@7Ay8;yEkaYK3032YTw8h4NHkQaK3K~lU%}2oRC7q{SVbj3LShHKZBB8~G88i<8 zy`vO7t_Yg9$kk%ltltH`mqMXoJ_AEd3xi2W%gwr)7KRHIEo><^Eu4%NEjG>;3mGcB z|M`N)#wWj~g(l;J?Fsy1l7VuklVKd}GN!bQUSpHCpjk5F?JK=l|X+$xqPGP19{3*G8qglvBJdi~>XZCSKznX2HGSkj z>#sod2xvW+<0R%EiC#<$weg->khw-kpW4=;0eSB!qoqy43(y_iP7KVTaX`r4+Zxc` z+amBB-b;H1i|P{_*{bicJ*ec+J5;Ha^2AmFa_(ZPru~1=8I1KOy&>mOd3sm;w5j-D ztMCB4H#t?)o}vDpcSZd@=ZfEVDt@53LjY8Ef#y9e6&M69V=7*N+7uu)P7KU3Sm%Mk z^X#zsVFo6ce()SC7xWxfh5vUGHG80IX#O7nwPPUi&~;}Db3P|({^Nk8&mVUZH4FHW z)PUPQwhI6MCu)Yn)H$m*X#Lb1gc{g-9S6ol%{~=~T?|Z#nkr2o zHI&T9+23Pg1f^rpoQ8Frfdpt?4Kk4tC(yOS4c`B}?t=0Q$bB{o92h`qEan+Vg7Pe=KCM~mV+Kl} zm8y&Uet_pcyukS%UOpv&?lD+2)%zb8c>ddFfdeFu%rlSytz!Y10WvFPDGP)5KQHj! z2B;mf77G}_b+-3EFL2og6_*38WdW^Y0qOPr=LJ495-KN;qz9b;q2hc<;^6#mvq1I` zRE|GkDR&ykERZ|A|9OJP`fL^)fcaGiBo2~KS^ED&!qWc_y#INE&;PJlu(1PTh6QuN zQVn*H8j#wQr5X(0|2)C#zme3iBrJ8{hpF-Y=h+GhSDOV3KS0bdkOJui$=9cX%fSZk zf1cp8eZXV9{|dlmAE+z`%_Td``y~Spn?|;{E?uK&57&6SQ1n^#1=l zBhibC!TbLo9>~6K1__H-kUh9% zV_aKBr!r`MH_QOE*V3Vh!REzI_+EWxi!eR zIRW1PW6#7O2CCn!CFTcM*R?_RUH~9LF)@Z^Bo|2Ve`ul^B9(N#xpDg z&oSFGEClaw`|}SxAKPfxR$UmRp8s5oi<(6Naj1=Y`s&Ak7ygVli6 zLV(uDcid-K2s-zz=9EW;eivws^8W}_J&XQ(|6>Q={|#~fU&vWA381~b|IUEN6z4GL zRGbnAjUlTb>1DTQS)Azoj~!gLTO|Dd=l%cR9PPc}^DjYdUkUBKkoj=X8Nr}7tM~tZ zHQIZ@bJ;f9dl^_jXWD_z1^|^EpnYZD|G#y5|Nj?ZG2cK6l1|J=ZHoS?Y} zkQhh~5*}{gdJ8Nz-#`KsUJ&&z;PemL=U}U_@B_%aN=^1-6-!eUDwZBx0WG5nykYl@ zG5@cCrc3y~KG2yrpgrfHbOGDf2iYYe-(eoZ4~shRnH8##a)9B8MP1tj z@BeQ&i#x&h`kH{us9wqX06eCEe($ke8|b`I@Yp$IY}Nf$G3cz*CI*w2AUTHr|Eu@1 zKB$yMy7zbi=o}hMePH!i?mf0tU|>re+p!849E@!=82%Y z!4$yvBmV*A^O^Rba|=Ov;r|ABT)_5`G5`4sF1w(2nt|3Kf%YSU_8@}FnxBpg;QoMi z8!MCjKhSw1Od;0wZJ@iA4WRwa6zw)vM$jA$(%v^_ix$usx6I(PF+3QU1+?2(nH}db zOK7*TvN+89e*;vOPgG{ed8v&5>|759#uG^9vO~@eW(Kzr8|}e+OhNY_K0#Hpc%%0} zW^fy^(H^Y~n@>U+b_CS6Xan6N#9%ScKnjvCoxo`ulGksEHq^H@Sj;mJ2IXg{Jb2v` zR2;PD23(I@-!tF?&EI+da{`xbVEKg%4fRJpS9t$(0GGF*H54Fz#Zra_P0XBOf1E?>+=>5+gyzcGA{I&&Pad5kxfdyi(BiR3z3am^MZ5eVb6&Sz# zv}Ndk?S};Ig+w}wjSD=7{y*d(c#alzkEe(CpM&7DQDE)@wc#vU7-YQv*{6c)M>KI+ z?|=5t^S_{B0dcRK_dk1Z-wsJVv_EDq3o-{(MuGZ{4xql{K6w2KD*LZ_|6>HJd9m;R z3z&Y;xuu|S6YqZx;P#)T0xL7fuQ>de;{E@>%u8E_4p6_>()0iSpRo)b4)gwfc!98s z*`j3$qxU}sa32|zS3&uEqJ3M7_y2z{kkqkTv@9|4{>K1LBcSvRs((Ro9IDA)7OKf$ zGts`S#{2&XUrPm67EoORYMXd4|LlP0Yv@@JpmHB{)(Et`Zv>fDsKvnH(8QpCINMAH zTu*}J5;Yk(KxTu^$^e!79?U-@;ATS4!~m6F9?U-ug3F5}$o;OMGQ6fry24tnt)k|> zF}U3UzRz)|b_McY!HI~ym@MA^mnMSmIcZ{OX|x09VMfO$@E&|7$0o?VaG*9jd@p7f z>OOH$x`yr%uL1252iN)kH|_p&q(7{P}OtowF?9{g`$O^HM^HGz_g;eb+1E?M&;0_` zkuPR5F#Kp_*a1opp!(8b9s|!tTgZL5;4rj++ye_rTOe^z{k+kJf#JnMh8>_gcWag! zRf5K)L2>KY#B#v<&pvP;p;P()2Wz{w3dmYWMjKnD|9@XEp zJ$}?`fbVVP_{qr70TKh%g%0x=R9-qVRMcug7m7#u)#6nK5%Gas{>!w!~?O^gDz?f~CD+(EvTesFQh_#Y2V( z;QAfuEG1BxQmbXDW$DGh;W&>8bcPWVq%DEHo`>1#IPV`vqy7IMpmmoH^B6oV8h98W z_qna(EJ%fCqp`%m{erGVq&L1H2!0SZk z{axTVm$3%4w$O1N;}lRhBKse7KQ1VIKzZ1Mfyo23ez{hYeTx&rza5rd42;^VK=*_H zn*dEa2cT(f1vIT~fTpz_FgGKmvlAHU?EhLz{l)+PgU-2ems6_*h1n6E!D4(?^S>i|C3klHL5gYyO;Jj^6&jIG^=r(e(cLiwd8{~Iz8al?n0!u@+?4UHn;9{`=nub;~FRMA~V^*`+ z!qTycK>?J0EEyP>Kw$(*KNF$(!u$W9H;AzMe*qCz|5t#{qIF{U`^5YIKLu^bT3Qv* zoy`vO{g^yV+vxcQ()BiW2 z9tK9W8eSqGIZ)nsX~n<*DHnbxfX=Cc+`0UJ4agiz1_lO@+d+8=6gCs(|Nj7mJE+X? z{{P#+LXlCxgZWbnyex(8W4Bl!sNuo<333J!Y~3vA{KR@`a6cBb55j&w15^E-&lT2t zE5U2VV0+m;nBzdxPN4k7XmOCCY@!`#EEsf-8w2FNvc<0}CfYHuSSko=OtfR*XtZZw z0qv!oXwSgn{eRcqg^CPi77eT(pz(@{b__h;|5q)vXkbmKNM=x)P{$wu68HYUs@I}{ zMF1)WzL(JZ|EfxhdyxCopyCpsI_SlIh6xr+88{&M@kc9|e-Bi5GcbVUEtZ1zxictu z|NoH*l~V!bW2hW>EwuOlAHEj%7&JiZ*go`2x==L z$$`$bW%mAO0zT^tNgUL+%<) zM~eoY6F=%0c0l=t77e@%Kk66`K>3Om4ZIvb>KINy`GOV=ybeF=7%o8hj1~>N9zW_B zZb10UKUy^Kg6w|)$icz+)tkHr+cGcsaxlIkQB2si3+C^IOmvz=hTa{{MHF%g|uI`2Roa z1OI!Vwt>%G2A%Z=I={vH|2tn${}05sJ^<>k|JFs+=L|NW`WLi+!eJhR zL8JZuFVJ?NibXAG4CFQ|sNFI7{{JtN??c8IKxHYY%mj@ifXY4(=C>(uw?g~>U^S}X zvW~%n`3>j{s6fz}PN4QEsND&*Lj$~?!hwMq)Nh&T%D@0p<2a9jW1~9wJlhQ(%x`{x z`v8^F;66aDlygPRU+apR+s5ECxZ`K0NGWk$@%~^cU!CGU4gOo1=${luvegV9H@OzadI}F#S6$>6L`H9NF8$fZWRNA z!yE>I&Ugj}(D>}kcu>6v68q27X%F5p4$WUT^ zud)M_W)SzUe`18+zkc|01?cQZ(EaP6^~xZ92zBc#q5Vk~P=6Afe^C1U41c`;Yy^*y zfb@av1C2R>?6ZK~3xD`?g~d_^X#KHX6QmC0CUAKUkrRQG=O1&C-2}P|9^@tv4b}s{ z6Mo%OsK3GICfMRShXZ`xDm-jZ&e#C?DO8hv2gpyLd)-0zxO@MN5d_y6wG14n_q_k- z0m*~%n70u>FLMiVP+8j~K+P|Iar7^}|9nS>-}Cne8SjGL(SUm_XgP z!TT=*q@CsP|AQ?PgP1+&uDAsZ3==)(dsxp|@(5&JJ*a;UYHw-HH}L+u3_NZQb*BtW z&in5Q@O<=-dIk>AxTviHY^}kPk2VPmOh4@z1ib$|0{a1^7o-ln(|0b1h#apzJk@4xRMV^I4UI2sxmN-XX(2!Qt1djGu%j`Ny&(Al5=o`B2) zozG~|veXs47UAzZ@L4F{|NotU#P@T=`Qy;|29M2v!-_8hd|!Ku!VcIt&5L>l2JgS~ zz~gctcZ2#g5V3vWcm$2lcrZT)-TwkgMvM*6u^C&Z|Nm@2dsv>IX0Y^Hn&rX#?Bfr` ze~xyC{{OXW`v1=^>Hj}Fr~m)#l>Yy-WBUKk_R;@;wxE0K4uI~fGf@BO2)?8H-%E8+ zdSlc8)eDwhOWUlbEXx4j53<|x{qh=1 zuVqS>=a$d=>Bz9cK8Zohx|%NombO9l+KXzC-VMT*eZs1^@qBGyMN=t-!!& zmB7GIwUr?uT!MkY%7KB=N`ZmFih<$3?SuONmIoM^K>BSK{r?Lx%VMd4srTQd;PESn zSsai(JkL)vyi{b=c<~%`mV#9!=-gVzCZQDXKWo8bgx-JGg2&)Mdl^CVBA_zP`|mRF zd?ctGg79a6?@NBs$S?uCFXid)3edS`H8s)|76}Zj-hbbK>;D&x3^PD=wfCR<;JgSP zn+4sMa`%ju(v#3qXBK&{>8syDO>~ z6hP}|>OC)4c>jHq3(A)kvly5y7BcJrjX8tzr1w89@ZBz;Gy^*G8=Nkey{>?!&9jiS z`39`U`~Sa`mx>HKKw}G_b$DoMzk}A{SH~=<#9)kp`*~>gZ{a9-$21bzE!E=I-e}nHxv^EFrL(~NO z4YZFHBoDfq9^yAm@Z8>uhYUMl_SUs52E_$C)b1VLe_w;uymVyP0kR*o4&8AcgAbbh zU662i4LSdBA;S*P92~?B4M_WcA;STfy%kGKQoR3Zf!qHUa~K>f7J}A2F+ke;|1==^ zaSj7${nHIZIB9_EwwI0!H(oqsxBz!=%51QEt!)@wtrjpaRC+O_fZPu9>rY398?{~m zKYl!9xByzW2hxe@Be-Akl_T}Je6*+dES3tg2%{TGBTV1wLf1vGIZ3kJ6BYyzv%n%kl_R<3_xv1 z(EO>b!UBdL4;eXrIx-4aEnr{*&1cqfcvt*n1gm=hQOA-~wL)ISQjyW1meWbZGL(U_ z(o5dM(v*Se$BX|rEFLl%fZJg1K_Zo=3<|%w{@-}%$Z(>P>x17x(R77^JLa7^Ew`7!*M1ts*t2t=1*D0u<+<@cprnVTboW4e&neFBUQ!0F|$n4gw4yzx;G$Wcaa=;fMF%iQsx3batX+ z(=Q#HNB{pp&wBi8@qGCsi(>|+77G}dELt9hdHOXZ?SLHb@^x-uv%d@VY^$ULBAaNY4B30&qJ8-!s8u{ZO-*t^coZLYM{715ytPFC;zS zbPSGXP(K2k_Ev;K!f_@z&LHgd;JH@s|KAhzw}Qrfe_sIU0i_*CUAf%I`~QzCATdxo z(xPQWN^@V9ct@4J;9 zlWi-fc>kRXj*Ch43_K7$|Nn#X(S&-26`(Wzy#LMuhdt#GM*s-)E5Ai z{h)nhpti<~{|p{K;~5-&$}@QUv}XwT@t?usr9DGH{mK=f^){eBKLbb{BnE9mD7*yO z6VG5#srkbRboK(sUXU8FU0}Tj9318{aQv2M2!QyBfd^b}fZJg+!Sw)Gyk*7qMr8(t zpY{w2jmiuvKkXR|8kHF|X2mmffXcp~_6!={fBV7t7n)XW!1@+|*5j`@>-~2wc+D_W zP5~^}vf_>hvl}>nfzHEqXky@)QP0pZ%buYVG}q?+XES&WY@-CS9t%m1lJv)^a0@qgVPMe4E7RR zr~m&gz1$prI)mHp|1G`TC;W6~m;suT`032B;HNXgil5F58-6-7?D*--Z~&s-v*D*R z!wCr64aB|xVY`FaA0TYEgrCj~4}Ll`ynygM1%5g++yJE|@4vm^G9Gl!56C|a|6%90 ztat#*i_kVQoA=*`;Ia;+?!|ouj~D-;aRXixx#DllGb<5`=l}nE|9uD!AE-Ku7yqGU zHCWwBRU~!bdq8pDW}oEh`Uz`n%qLAAsA4AUTj)>p3gIXRLwxwl7{X zaJ)DP>L)z__eo%CKysk^`o&8Ii5Djs1ib$~fV2^+!RP7xwP;b;;r(|4ILtx*2KO7Q zLFTLjha0HOusQVqANcN!W2*#h8W@Ie6JwpOW4;i5_ zBFqqAusF6V)uKTFWCpknhq|Qz$&3>3|G(zI)_Qv|yMXP2nPIa4bPmj_ewzjc7Vket z!Sy}V4AA@?wCq|n&-?$c2(Vg+JHU3q%&=I%2y({`iv~sp?>|T2VfdpSbQTJ%{9AS0 z`~NQyuv&;2V7p$=t?cmr%L%UoKxat22Ax|8u74i#*OW+CfYPh?-$~$n1F8=!4uI#C zKy4#AkX&^XGlTcvN#J#yPs>^+M&r^&d#Su5B^2t&_O}A~zA-z5|sRFYOsTUVzH>`H(#L^C3e8 zs80auL;rMSD6lyIHkZ9pi$TGn<<6@gj0_z=8$stYGAlvN0+&}W8yOm2Ffu^Si(LR( z13jx8BwyLZpisfVtW?3tpis-^4C>z$)T(<|RCX~adH2V7YdusB97hfJ86v=XAF%&`v{h#vfyhq) z_v0;YF$sX=D~^NjC}yfS#-L=;GV2CZ4LCi3#xX!@ES9eNV$rhd7euZfJk|yl2iFm+ zd73f0hgipzvX~XjyFzG8dt)A3Ub?;yyzG$UT+}0x)$xXzIXu^u>LK3XnQm z2JjkJka-Dc>JWZEz#sq#_tnK9HQs;w!Flw>eTD{*8I}y-I0Ko{4w6T56FA?1`&$1e zRW|Hrh_E=o{sY{$D`%YH{g)B!=7#+Yp!FCmQ1Kn!e;L7P7AnpJ6~AGzlz|OAF8r4f z9A}_C@DQ^X%R=Z)sgN;L-U%-?88jee^xHL{b`|Iz0Z<)_>ka|$|8HABWiiMI{*Lh;xL0lBlG_++FjuDDKhjs z1VD4l44`p$(A~qJJAgp_=1@%r&^|taT=xI}_1haj`_6bk^UI*~s%#!GFxGcjfYxC1 z)OT3GjJZLXiRG4r#bv=v~hq%$GoS z9t6VI*jGt|@81E9btBJt)Y@MN0IiXzv}RCnoXe1*zng&pbdL^boZDhPF9X>Ag$yO2 zzC6es-v2_tb!km4`&Nf028sIA+Z7g#3?-oUjt8?HIF8ZhF+lU|j!g^>-hXC5#t5M1 z)*t;`fn+YYe*-c1{{id&3@q077+64ehR9HVy7f94>1Fa2f0EMkZ0%(oIe^F3d7Ic0K$c@lF5E|D1|NpQ4&!Fho z#2^7``&uM2RCxd82CvZvothUjnu(nIRMEr$*4-h*0-&%>MTuG=J0J!F<666hPoS&cwjbs0z9_ znSmL!F3M*vg9138K=0MHNtoY|kj%ggn%f11l|=*3oSOaG6$tbHd<5H>z##Aa|KC)o zT?*jw?F0s9@Be>!p<WLbk7%f4gEc1@cmk# zb`+?5fW+_l6pIEP7f{;u{{N>G5=Z}EXwPG0sK5WY0@R1He!$28N}r&-4Juc?|Ns39 zYEL=L`+oq`28EQPe@dZZYwGWR2&mutO9ZsGxq2^yLj9aypncAW^{CJ}4-e*Zpf&%2 zpgT)J;Q;!3b1dS|l)l*485Y0G-$OU_N^ky!I8gwrGxW1!(_l%?;xU zYlZ*+LF)uy>xn>X$UtimL17QhcTu4E2*@2}j!g^?y#GuA?~w}cWV5U1I$WWs$;ePY z!voxpt=00bsElV&sIR?U0a^!8Yxe_Eo~eS%vkLvC;Q4U_&{(HMB16e!MTQa&W-IW# zT00{r@8gNoW5fK=D^!{Y#|& z|A7EdTvY!6hm}bK=!`R{xf2o@Ky7kUs5vU2GR=A~0}Ci@z5o9Yfvk%-^8%hvp!3zB zx&c&wShTEuYy#E{nw|$}GE|C5>xDU7b3+PTd z@4uJ9?M84IBh52|%5KLd#tGhkCWFVrEEX^%fYOBrvjw<}0IlT)`QK90%fKQ5JQkq< z60_9wJOG+Igs{CpV+9gWwgYH<0Lo4PjU7PQ0YB{-EWH2!@`TJoF=T-9i1mI@8v3yo z97hQZKHmR-X+q^aAo=gd#FzGvxqioa3^I-J3@p&G5(m(JL(rMb4s#hyz~KetJuz`*AH_Y%1LZ`jYkf?Lf+@cmDq{sTylMGO0L@4pwpZ7@Vx{uAo|{~4gN-12WUcIaMq@K}gr6GIPZtpsQdisL+n2Kz${V%GQOCxFt3_n%|nwqi|= z(=teWp0==m#31(i|NMgb{}KV9x%T@1(vvLe7$iKHeZX@o7L5!IHOaq3K=m4^Zt`IE z0=Hkl=f0)fuCPdCXz>1f3p^$SvEw+njSfox;Qi@}3^PFPgRMD-tSOoRuCu{+hcTZ- zl<&|mg4M$yw^{$6p8%@AK=BU^ufiXV3>Dsgj)LRqMI%Fn#eN0}u-$)efZJuYI!?>L zbL)?PSNznPU*P@c7`TlNsuw_Iln3)k#M&TeodOvPSW^tOW1{z;ZQwYElobpb;CM@5 z;IL>})8PI0JlG!e__A5VAO`X`=xpGbs`E2`s?1LSjV(50GBCX81m%(csy0pkLH#x+ zix#g5pnAvq&r9&07bNio;4=BoOK^IIwBh+c{gb~IE!>TuIP(5m0Up-`k8w2p|7&q< z%^ZuChhd<8iTB@Tu)9I)4M6U&dBh+Fa@R|Z`E?cv3>+`r=U2UCncoDGd+~IB--{#j z+raE4^Si))Y+19?`|mmM9Fh0`{|fMO4cab+w2Q%KA5Va_*FbAoYFea3Kzrsu?LlZ5 z7J}Mo$Za?8f1cnzC@9Z>>MGD!prr!C|4?N%JJ33IP#IC{1zCFmNhf{a{11vZ59Z@r z;BJAouR&qcs5yTEw4KcevcINNNd(Ca6TSa=g3Al^xPqGn^_K_pv6rAWh5aH1G3&ka zCwTu01kXo6-T4EQ7GM9Lzrqr9HtT*5Q2*o!wC;wEkFUAz{pTK7&r5p-0Z@Mnv~K~F z7C~h!DBXGg|97w;lcB+(iD5-SCIgE@6T^Z|dj?5py*vd}W`q3T{r|seM?C{*jSM5G zPP9m7U=B%Uv-AG{pSPo)0krNEbe=C`M?JXB2s$(5YezkUC8!VR{r}&~PJ4!k`pypw zj&m78I_@)Abo^(q?AQ;Pp9YPqS+uNqRdMXwBJaOv!EJVs8=!WxfYxNsv}cg?{{L^G zMJ)q|_n*Vyxd2EU91{VbUEjdKSd;l-o%KBiklmHu|Nl>bhbJ>+T_7Yat<|td{{H}) z9wvJK*$*BUA`};(GzMy?g35vV{Sx5$EKnI>(X!SAYF4A;90u@OON(TN4DUY&!0ijr zxDF`4g4)uv4>Lr}e#{VQ>CBMv)0rW`(wRX4)Sd*Lh3LV26eItG?W~uEw^v^}GdOf= zLG}YX%wy02`zL{c-J)f!gZJOl;QS9Nlf3_)0gnTL%=TbDD$uctfl<4a!2xup43eH? z@4u(Pa~PoU{f?CkOjy(`_x^ht96lg5pz;f>zh&(kP@HvYGBC{4n*ReN4wCPLo|V2) zYyK}JG0^x4<3_Fde~`qOXKKy=hs0-@sWtz<_utck;5orV3}Oq8&Hn=`BNi;3{|js< z*q`h8z5kwq%o{FZ5bIbvAKV`Xxy7PoovHWVQ{WC1=nVFbWAp!m^mie1K=}(CU(j^v06r(?;r}0y^I!h3K*Ia* z0(iQEmI<7;~cFbq6 z0O$An;4!?z2`vmPAuVin-ha=5>p75q??3y%H#xqDj*Q*G;{?DL*T86IM>;2~@xGjOD z+ya?-0cs|!OaiYzM@<|5CP4grum$dCXxi{#KFA6#;~z1If!05P{A+#p{{xG91`g~0 z3=-ad_JYe1aQOZIcNY}TFSX{c`2F|)i=VdtAAs2>8908Qn!m#P|If3aG7%Ez2mZkA zf|h?C%m-!?unSx-LG3F1{rCR^sC^rL+Wvp>QfvN(-zOOuexI7Z!TbNuL?pW~%32TR z1Drn;{~LnttM&fp1x^EydW-P|tUd#;2d`z20F6m{|Jegh{~)(}|No&|kPcp(`~y<= z{7Hr8IS%jtKjuQ&Oy2*0OoYgP|7(%_|4&FAn;n$@7PKD;%6h&1?@qCvQL82 z7^wcNDU+_K-+u$tuXV9$`v0%)Is2Aswr@)HuIyVZS~f_4+T7lMkAdfLAnyC#Tad}% z;LyaN0coSH=kfk?4LnZOY0n^0-+6(-aUNsK>;Is3_x}}8_i}sx|Nam(R<_WVA*;Ug z2dFN50&)vT-uwUeqY$%ySHj!{aueu$I#7CaoX24CGM+&I+DFl`W%~c$lH;^Rr!7O? zOAb)q*6~uUW{?Q@4g=76u8|&r4vmaAAZC8MTaeBm0J=YOzh`2Qc;CXj)()6w=CpRlL}&EMVwx2GWO=zSre z`rjgf;lK5NP`&)^Vf}yhE#CkCgT~1iU(IJo@c#eJv8LqWI_oIVy^jntK;d8WoP7%@ zPt`01h5!2N;5O;sBjENQxPJTp+tH$dfyp9)p~3tAw_Yfl+57)D(EXMSpgV^_XO(u^ zGelbLXHcl``~W(4&IFc!L3Y%i_*?;r-}NdW^Q{gr90S?u{r3oXEll@)hRE6X86vG6 z7#Qm3U0`sW`#%5@mOpR8%t39xtWSjM2hVMR+Kn&c88|@U2`)$Np?AY#E35zP0?##q z?k}xdwz{J3=w|SmJnz3J!DR}_4DUZX!Sl4<|NlM#wT(Js8S=qxC{SAp)Ys??aB!Ua z?+D0mpzyP3Sw92h9&i|f#HTfb0KQ`d)TT$Yt-iW?|NnahUS{w>+DxGF z326B{(fj|Gsi5-=KxM*At@$4cG8sVog>?|&|CO<3jngtvTMC-az-RYC>c`)2K;ocs z5yVG2dycUI+TI15&BP#P>A>Isn(qObF;ipy4^SCzv2;V}MvwWwKx_}@-Jtv63qkp0 zqsRO|pgnOQaZuSg(*x430JSGTX&13xyBeI%LF=_a`2gIPZt>Oe{#y)gb3n%iplb>? z)PmB4_uoU{Iu}&Vc`)w==VR}`h2Z|Gelz%97Vx~4Maza+-v9rD#=RK9W#`{QaJ$NS zKDdtt>RT~bw0Jjw*Pb*#t^keWdjGu%?qeas?lU<5Ti;`S;r;)6DX2~Y)q|k115liT z*1i6WXHfVFn%ivIu{@(zpwP@K0I(Ha$1~_8_3j+hpua*wXFJ5Yb z%EI7DHJyr=el#-#Af+>K(guwWdob?=jfFbG<}pBH7N9Xv>%D9SP&*=DKW1=fc+B7d z9TNkOV}Qb?Z0$R)b7aXn-KSK0?!oi|t<7@A~2f%RxN(Z2O&5-nh z_Q0`u|NRTDGcomU;_&{vADm91dMl9hg3g%W_Wt`9oVKy(RrCJ4AG~J*s<#12FK90~ zkN4ld;Pit_~X zGBmt62$>HBg(v7t9*dSuUEY5$gWH}jLE||{V~>!2dL7vRkg?G1Z@`fcng@fAhi?a^ zfkaSVw7z$m0hHEXG&5*4Br|~H20EWo0qVb5v@o!H|NR3Vw}h4-7LatZ=`|!R?*r#$ z@E9o4oCwIRj!g^+-hb-A?JAoE|Nn!|^?`*+!cu=ZhJ6qTL>QCUG)FI^DbEK=?+H%e^Aif{S7|sn&ilUv?xq&dxalA8ISy-#_3y52`mDoBp2x#feQ4 zC>}SrSR}Ilc!zUK)PKcI5igLx~We-9l~tjUzF@L=8wZvTVE5=_% z1+UNJ0=GFhUdl5t{N!R_m}tk~F?m0OOs5@#E2u38I!hi_c3RXia-h`{T(B|=45aGZKNvoi+vuN3p18-;iSqp1J z;+>C%^-~2ZxLwsy&tT&H zZ#{Ue?dDR z(EUz-e}UI6g62>hL45|$o~xEEGr{R4na#%g?|E=J53&bjuLtwyh!=GX4&MKNM?&>L z+ZkK-fzFu*wTr;v`u~q4ME*Z`jf+LgmgnC8|F6Mt=fnS?bvFzNOaFt60;t@vRQUhSanAo0 z)hES4XW#KyD*S)z{r~@r>XY&?{u}TA|2wKrs>ArNL3?JZPwK597b^ z{{KIs_#^|PW7Gc-ONIaMLHBTg`aKZ0{{qj|g4W=I(_PC}e{dLp+$DpuQ;5*dvEU%hp}qf476ne{h=ovliTs1jUI5^M;BS`xyf2m%ad%T@tmn z8i5Xt4A8W^^_}moBp8o);tF~rPfZi*k1G-nnaUMepNDs&zAp0#^wpV!nJq2#(TO|Dd`3&e8ylqdPSHf6-{i zAOSsB=gdTV29M@C29^5i69LuL3c54#2i5J2Z}rBnMo|( ze?NiyLp2rPwh?#?32J8))K2jF(0ZA};I*irwB<1Gze1xugG2qwS0a=5GdMu}_$$== z|KAmziVO|4mN(Z~SA)h({`b_kg6-u1t&6Gvt?^JfT>*+`h@S7Jp!{FG(*2=h)8Cwi z`wR}CxB1n&Pp^2)yhAoC#Z++hxJ=W$s2j{%+4<2a8&2OK{87I>vL;wHTE&Bftc`q>N+%wP~I8gfzwl5e|9$822m}G6aL)2Pghq?6}wh*iD zJFi<^+xgFG>(0qmQ+DpKD&ARO6|~dS%5a;JmB3bis9Qnfmm=UY0$M(R_FIG3X+`&D&Btz!Qs*<$Dq;hk3j*HUmEr?NPy0F0L6p%-;Ln%zwtkVz{`6K0{Z>nGw7$l z+E5Pjplgf4<=T#;-hVfO%YRUw@cy?HoZmrx6^91!_{Tp`J!sLg<5B%y_ATCjkAd4l zpmQD^=l%EaU|@PP^FM>DV-qBuLE?5NH`E>AcG1ND3?ATh9Q6zry#Jm8yA5yRC~C%!u$WHzjZ9l6<~KXG1a_$2i`wg(W%eq@S>kVqamNc z1T^*qYM;&2XLRuX`wraxsZ;5O>S54;se|To9`C>JzqOz zB`j)HbqwaLU|qpm!SzQ5=$=?moO=H~ z0v_K1g(+x1F!(&OxeNv1GguE7S4`Ar@bLcsOoeZoFa~Wj7`wW{OSAfs>`+FE%7I^;$ zpU1@tvHO1qIBx&{E3j2K04Y;edRH{>W6%MeLsGq$g{w05!8uSl11qyU7#KvF_c5qU zjA!rw$%Et??lX9R(j{nLCL~?11Gf<{%cFPTJ|8rFM1c0PLc-}Vxct|j3rZhc;xLK_W0WSSm1p`m+g;GXIP2i}?%^7WE7X-hYpS z+vYFr7y_XEGL@Q4DUly_3;`DP3^Txe=y?nQ-hYpQ+aBKke_sLF11gU}^93*C85Arv zL3@E26lygCFM-#0Dl#f~FfRiQ%YvF#;Cp{TeP+X&tb>H^5#Gs}3;{xi@$ppfzc6vh@UyUM)(t_7P5 zDOVPP&4BmK{{QL(hsB@8;4}#8n|LrUL#zz}tqoOS@Bozyp!L*X_e0l(g4)DjKkP$V z3;Jgfc%2&9%>Q5ag8Tx~3z{>Bg>}t5B@yqxN5Jhfh`L{_VEWG@u-hPRSPHun4Y7t7 zW!?6!g%$}65wJd(_n!seG!JRpFsOj)FwmHaMa!;D-hbDC{SO*Tg_`XGa@X(23<49C zL3!&xVq6P4p9qQ{P&~oRZ&=Kr^HP~XK)dz-hu1F|KcM3V$RD6~7bsD|*6$+63(U>le`>(_3pBQZ*z37l%=^!7a9F+m$FR}* z|GyoU_KY5&b}(p73)JnPHWfI|L3KUE?gij=Y+&~P&k*( z!OC#zPAdVQ1D5Z7HduXUO8}k4@lpeHrU%0fP@MoWvzk+0#nQ_;!4`DJOalXhAxms^94bYIA_w*pM{4JIC$-(=YG8E5Ug( z>Dq?|ke@;NLG3~BznS1UD3JRtT6RyEP|sijlJowX1fKr_?>TBw^ZvUB>`z!dWwDT91NiQjzfZy84eE!0 z##}-6K=f>K@&3C9>}Di;K=;I(c>kLNb{j~oMav#L@BjbKc>lQxUXKYn1HUnzL7-ES zVFT#CqKWnl2A1{=pmn(spuRjP4S?pc!S4N20S+tB{#)%X1{TM8412V@7+67bf1q`^ zpmq;PJ!nmMqcVetq9&-X!2bX=zcpQ;2=X7OjDv+5842+=t3m|hr z_lN!7&*%Xv`|K7$&lYm}{}0qZwc7eH%xcPBW~-pRf-hqkIDW=627qZT28N%u3>=_# z82GFpP45ksUVFnp_iNZH{r?B*gFwXhx?6hfHF~{=LF1<)1L%BMklYMQ&AoEgd;kCV zsmQRv(iY?|4^X}bjj6hT>PV2emYSz69Op4!0JWimHfS%nMa$ka(ApL2dkg^;&lwcF|1Jif zz4Ur70|zKRz5o9+0rfo`=KY_8=8g`~n5X`322eah%fG#q-v56sk&R~HvQJ>B0>yE1 zwGcynb?`J>2L}E`FDHju&)`X*F_`-5z)P^W|6R`@A*;#1!2AE-KMs@rgX&q(`LPA? z`&^jkAntP!0_{1#yq6BtM(|*see;Lnf5d#SwVbFLpXs!x*-p>2) z19000+O{$Qja`D~4jtz)xYR6t4Z82Ez@~wb2~^jB%mBBQ7cvxh|9u2*Goa7sf%-Rq%WsbiW34UK%_<2}*yEJh6AD_n%GR`VXp?6Qmb3_6%x!**{_s z^Zru=E`O~5FW>-`|Ijgl3Xpk-_3(@q-hUFobwu-F28LSuPa>U~3>={H)?prKZEF#@ ze)s?za&uMrUejcbF{&a`Ln z@L*tA0zKD#4ydmP6ZigC1|ARhU|?tgmFu9h7%d$b7$(Lu_*gnHC~S;p@B-~ob8G^i zQ_N&t&yWE+Qv_tD_n&FtvI7*KpmYF=Pf&T_{r4VtYzwru4y4xm&vfuUHc%hkao&Fy zP@Vzp8MJ8Gdll4%@&3C296q4AEl|1kQj-m|U-!R7J!lNx*8$f&m-qjF(7DE$HSl&M zD`;&3gP5h}0uE50tW%kRqo&2X0vb0QGnyH|aqBY=w8!TkYz`N!9g^l}K-PbQ)&|x| zSAgQodOuSIc&^~jRIocc_AxMk+UcPCKeSuHXIT`0#$+AlF_bjMG4QGWpMYeAby^{ zr=gC40n|?i&Et6g|J?{O+xt&Gc-#}DAC&gByFll{f$qime+IPQ)o~uf7VS<3Hph94 zETDYnFprT3vgUUIhxI&$3{W}a{bw?GE+1r<_n&-l|4x4~0|O|1I?Q8;0I9LQ$5i3{ zX9{>c3S#eM@OmOp8wna$oUk+mu?G|vzb}H+g66Qj|4c#n|Nno37yB6m!28D<7#J#+ zG92;#|7#;Sp8x-c?!{S90MhIIXEJ!69<08efd@2}236k(iW8_B@LD7N{h5&XA*cl0=UjVS_9$O#GvB+Ck7m@NMYsf{dW#{oYedO{~e$;3W)k}Dr|o% za|3jp0IW|B&I|t+HGt9|DBVKqlSc196T$umttA8d_5bf)ki7SwN#OA)NZ)uWVr~#^ z{u+lWH50*c=)v#}+y(;W5768as64g>ow=jw^Wmo!TLCB! zSZadzA^o#x*_R3F^SXe`9f%zN1sl+rE8zV|`$|D`hoC)4KQck*viO73DkQ&8zR*z5 zzyPiX8bEU{-zP%+nGNm_fZPXa<0I_%1hbjicrNDOp_7$~oU)Ij8XzBH|4?zBysRAkk7$hn(pD9%&e_ymwg@I{C3Iii(%^iphDwk)fK={z` z08^m4EhN*;4phc_Fi-sYL-D^LXr9D+4s;#X9tP0acPl{S0giJSOhD^%U}xxCBr?=g z+A=73F#Y2Mtx2eU*_H$<13_&dP+!h*9@7#~8RNmgr~^p@d>-NdS?n4$85ltJf%}-9 zp!?+*p=-DIZTJ4O5}X$y{>}imkzskv`%eb=TuO_D3>`I9>{~$jpxWhNMoJ3@tM}h) zurjXFp^0J6N=Jq|(0Vn{T20V;$eK*%WtE(63L6y}rd4vbf#_M4oX0@)yh=_srHzUV ziz+$YK=d+DSXnG&m{N1pN@T?`2B!M900xJ-4B$J7EkWl1J!fEXV)zdZchDZSjgAa; zD;_e`RdT!s&(qesU9PA<3R*9{Z^BGQ2GIId4)4Fy!DSLCy@31%itm+*40VvU4+BT1 zB17#&Yw#MY6))~EFu?ApacpAB@ct7HZvTPwdH+cVx1&LQGAJM1j{?n$)Ks!>sdv6y z5pH*oFa4eXYyA<>9M4s7ctXaj{cZeNyv8xx(TB1EZxTIGm4w)@=03>-5Z8EW)bfX(EX(a2B>3ja<< zhFVa$4mxiUvYvb&Xb&Za_upyYJPC@|nTiaxpnD5J4=DXO&Sl`KbqlTl$#*(3Oa;w%f$njvb+@hn-E|GxBiXT#VFpyM&WeK! zv!MDCK>9iz8D?VB0}BIC8U)?#=s1soXQm=U&5VZ(wV=2GxeFX7M?Y6swCp%6gr=}1JWi)1&=vfOV}7&eSa7R%FkBU_IOW6rm=oV#lSRaURh9 zn_zRB{{IEd*Fw$yi#}Hio1e9Oz`$T_*_UKJ=RLo*#C}1m?>5F(*B*vhZQb|DYRbNU zR>eY1RzZ$Stqk|eS_$myf|fxUpz}jP{c=bh8N#~s{0Sa2V5o)&n#WAW>Xlw*ty-hbV}W9xOTiz`6$iQszuuPfv{ zq5BM=vyT|T^QT~Q+`#Jt>r}fdKy$WGwP5!(%wvGuXYpqSxNZXZ6EqhO8sql<>jR#T z1-TdGFVL6=$h{!{h3{kC=fTVkS-%JMqxWAMuzTyC?ydm&0c_S^SMXdz^)c23Aor&n zV`v2BQ*b%=*A3jy1!qvV;;<1i1Pu!b^UXtkYsi{Sxp8mP#?A;ne_pv zeuw5+Fa@g5L32)^J=+Z}ix$A#3R=ShDq}$D8QP{nIXB1q9}l>F2h#^u3pz(9fdO>( z8Y5`WwD&(Aa2zx$GL(SYETA$OzCT-$p#tQ8#JB|mkN2Md$aoldJzN(eOri5*9?YFn z!Tk%^y6Af83ecP+v_An3N6>m%(B2);o@r2+{A6S(0QEIMKQPA3b@BjZkP5||v5<7miYM)|(_aA@on4-l31_{u5IEzGv z0uQEd;64s0oE+x;Ujk~=djJ3D2y$;jJ!r50KU0uoQd`z zb^l{5k{LjEF@o-E-r&L9ffxs2hNNc?<_Q7evh8XWZe&Dtp zD6G8y|NW|v%)kKBTmS#3fcKwPa2^f+&t7Bw|Nk#YS^9qmSnc0+;J5&`mxCV^!~>Q-iHi|E5~^ZC9rw|Ja^H+z+ka- zzt;;H=;fXtnc zxo81m-_8C|P}=hT+Y7cAJ&YWi7-PKu_=3|9$b3*63e+b6_ig`rfcs;pd!F_egXT;@ zVe9>;860*E^BDxdd3XT>X#EbO_dgD>+mXaUd-jm>HU~KWL(Ks9VL|SP_UVw$mM{a4 zh1h`lN#MTRnmHi9gZgsbe;qqPWiDtg4K(I%(c%X>tDo8X&ob~F147&vwC{+;`_D3P z-3!V$pz#e*{CY5b1dppj+|dLcJAtIJ-Lrt@i z2&mm+ag2fSB?|*bEr*tf;~WMaP~XO39s>s`Ty@kK7%h(d{|`Fj7E}h;ya-%Z@%#{z zr5C8r`X9E(0c_1nX9j^zE(RI>4sg5BrBRuIqrOuCv<_DU)W!w%k?K1Y7(io>pz%Wx zAH)W=S3zaYOf3ePMlA*j(7mA`yFl_F8f-X}24)YjhK-=U2wdzJ9HP4MJDqb)tIy5mffcKAZFgMh%bO4=aTu^cR z;)04(%|}9>vuf2m53Z=xYCV$hT!5j{%Z;g0^N<2aEL4+qU9Gxx#Y^Y^7PbluoS?Ob zHJ#q@dyHxo++V#^{%>LF3Awwz=0W%?ixvh6P<(;n4-|Jlp8S`nbq=mTcYAFEgBqxQ z1i2ryZa|BZfzgAx88q&h=s1z#g!U2!X2-b<2Ws|dgYTjOogZeA{9mGC34=ndjB`cJ zZ|jPhTgDZjHSpCZ4}rtMp@{*Uza8f>bZF0FU~gE=z%qL=!yZeA|35+FzS^@vb5RUA z+H=5kO2sPB_-~NNOO5|4940YjRIhx{_fzBlidy?15m0!6?iH+9%DSN9>14l`p8r== za{b`@>G^-f%lQ8mu)CaU7P!9x@n35GUt!4w2?tQPfWiROb^!SuF^1JtQmHA>P^tL= zv}S1rG`TQ?_TGT|vIz_fps@q=umYt!bg@q5|Gz+K3R>?o&xD-!#(=I46viIRjXObm z4;CC|V9;)35CE+K0nH7A>(vJg0v1c13oKgpPXhJNz5jNA%Wuf|PveEfhZ&d_Dl@Ru zA7kHAtIocqR?QLh9_dbEn-?DkYzyumcN_Y+~ z3t2#A45*B--Uq6G|L}ss8YB-A1I@{S&J=`>F@J=KgZr=t7(jZNy#N2cY4bn;JQfYo zlklAX08|fy_y6B}!R9S}4PJkXX5K>3_%%omvU%3~Ky8xWtq3^{P?-&~3uIm{vUwrT z8RVdLF?#?19SGB7^MHXLD$ZoR57d76Z3>gKc)%bGl>?b4i)T0D#zsg|JPLOeGDR?umG8h6ds_x;+4qy zP~G?|7Nj1e4@nQmjS}Afe>q~21DU6Z$2?vvdO+sMc>n+T5sMsy_y32V|ax_y3>p__uk$zz(&G!TbM@m&oR!rokU)ahRv${r|^CBspaBW+I!1>fax= zNP3Xdpn>=QABjkE%t-F@L^co2eY!9`HV+sSpn5?5HSzxcLl7p16c!BD_ZTd^|9}6A zY$mE3zu&~7kIDQ0_k&o<3kL81-&caoItp2nk7iacsJuhg2ilMSdg1>Uu)R_+H$(PJ zeUE{b-Hfn(rQos@d=}6ChtNLVMDM@N;5lc|d^V^I2bl@dk5ooO_V{-wS2VORuz=e4 zurctL8VnqjS}P8{)L;;(^ooG(p_^E#*}_z-$xs3shXdW$TdC=q0h)UO)dPu|91OLp z-WA?|4}sflAbWAyso%oD;xLaPz*6=9f6(|ZXiOE<-f@`6U<0Z%Dvtht1oOv>W(J0r zDhvr0Eer|`nV@p=e;~+gP}>LDd=MYQZyZd^YL;nNfZOj&5Ab_1SL=fMI`F=5E#$0R z3&{EoaK9CFuNSEP^kDi89$x{E#el~{48Y?spf)^s&s);}e-_CH#J&H(&oKXI(Q-i3 z`>(YxsO|d_wEr2YUmuceU{sU*Nd&ZJ2(lO25xiCo(od;^wG-iS>cL!93R+tMYI}g< z7c?$n(Q?4XB7wmI+%CCeTv7AOx}sLvxx)KTDY$@P5|Nkd1 zX5g@tXPEH&F#|*Wy;mZ?of#y4Co?EmIx}eeZe|ep$;_YuYBNke%)s+fo?*sMW(I?o z_6##X=L`LeXPDu^Tx9}JchEC=LG52qUFyMHc@bR4KW1R+RAyiW)w>n{7!+!rdjweT zV_*W6)u8+m@*H$F*_XNCyntFiGD7OxFO48|AobAv2oeY7Rc7!1Us93eK=lYnj=_2! zC{27p$^X#&1(Ij<{{ID@|Iy53@&5k>SN`Ym{{IT zFAbpcZ9YTFf7J2@8Xlizv6eST`!k{O%Jdq3j@Bo{xuwvxG@x@Pz=rP9&cA_-k^cX<7L?vW;^1@%kz)kKqxb)h6X9tR zA`Z?g-v2*V!u;kqkKqc)?I6E7&SN<7B9qYpWG`rqCTNb*`rd)NpfLgOzq;W0ACTIY zv2ZmXKz9zl)?{>O_F{0bu3oePGM8Qi9;X871Kr^TS;uA!9-FjOWN7%2`TyhV!weFj zGi*U>K>a`OzuMqFJ!l;f$c*1786>Ljv8U9Z{3J3tjzPxzPcdWGG9 zd4fgDfgI2px)&!IK6(GG0gpp~_RKV#VsHS356E7SyS@J!fX9Bl|NqZ{l(VHd@N@{B z*RW(@-~iq8ZtKAC-%^>uqtdJS2`nxD^km?4V)*|Dv`@%l0cg!Dxc$#yk<4)5r}F;` zKb8OA_^JH=!B6G?FMcZj|L{}!{|^tQhv0E3Lg^n=--5+=I|z5iB2#((PnOL+hPANbP#zl9|yeIRo|c3LPhG=S2E2XisvepvXJad9H3&H;rVXb*MsVg?S-9un_A zE5UOd_02Cp>m*eg?HQo!ei$UePqKpMC>bp^e+X!IGO#<$Wl(vspWzdzeg%!g)gJ@R zjU5#5{#yl3Hz2z~Wu*smF=9RpK5klc7i|9??TVVa#uXv+S?gXOhOBq>{{KG_nnw++ z|Nj7uQ!!Nkm-n##&k#^+_d}~v>ySdFCWF$(7zT!!w&1&>CwMRy-2t^>y#N3I0#BpR zvetvS2z38#A?Q4entM>Y7BdKd=Vbo>`wF$I!ZQAcKy|C@vFc;&$0|MLJ!)1MS6FH? z1c1t)N-x$0wX&XC6|cJcUfMD!z|s&XeSrDUagyX<&0R(%4W4bZp26G(YJukHH6hJO`F8!1q8a|F^Js2}uK>vcJ~B z9z3Q48_)U4f*8*Mjk$rwZ$gf;*n#&s&;9?RmX)DI(Urj-l>cj%2AF~5>sM%i#<0$4 zui*dhF!%qFis#BtYB?B66ge17YB|`qXs=*UcbxlwjjaPCLnVjH3(%Q^wd~fQb$BJV z3<3-ZuNVaDS2}?9D~Q-KFfb;(VqgXF9p*8_)SP7B@{;+#MWtrW5>PwX)`5W&l&`>d zTXzLlfbts14+y{ztO9uuP(6}Nv|1tl!u=Ie0J1G94 z=h;a>?PG?T3tCUO0yOtrtI58_iQ)elqLX40M?%I{;LjO|Kd20Apjw60ABC#;vNHdAF)NtK?~6Q z6)4Yx=XCy-fycmK%wsqJs!u(bZi36onq&r(kmQ?n9t;eivm-4)Yh^&;0m;kx6=27L z#(bf98C(v}N1RpiA{jL2@_Q~cU#WyYVXd=h`5~a)!ocD?EE1R)y#GuB_sKwew%~4nmS>;F56bjmaAsqX-f`7Y6JWne_?Gds8% zw6?M#^FQd0Lj#cgAp1aZVbOB%+)U5^zd+@u_umq5y8;^44Ia#S8lb#rF(0&+_T$W# z_6*Q6#1C{{2Vzc>k%6I+8GK*3Kz#>fJlx_10}D9+g2$j4EI|E35Fd2Tg?<}oeJ6tn z$Q?618Dw61G6;b5L)^|FGSL$<4h$Oq1m%HBF9s#=|Nq~B%zo*~0KWUI(u@5_$T0@9 zS})@Y&{=>WvqA9!O2ZZp7+7jvGA{$&k6Lkz{TOK81*8rdHxnW185mx2g2&65dtNXw z);td|u=HZ!sClYg0oJ#aLBWaP|BIKN3=S1b|39i#@vdmd0`*lsOa!$JK=y&$hpUZ@ zZ%h{CMi1tkP;mdSR=VP)EkmQF=KmL#o(vN8tHAZ13+P;Ta2(Z3S6H+h0-fit0qQT- z+%~QNEL<0noQ7o2iTdJhvdBfG=tl{3q2Va>bo>R<(|z;O$JcgW5MQ=3=Eqy z8JIx!Z1!Ye`TdfC<98>6!0(j|5-;T$I(~98D1d1X28N&U3>~2UB&hA^!JPdAp5CE- zN9|UI|DZC>gE<@22S{|B%g|8qn?a#wzjlT7ZO|EZ|NqzD)3B(%#{il`NCEX1Kx6JT zf2=FK|38-n=>_ctb8KSps9*KE!czYK|5}b)A}_KSCR!x_zhSA&paCk&L33^Odp>~X z9b)Q1cc`Y_uBdLG4%2xO2_RfORiz847AO1J>25 zIT+MO8C29f^RRen%TQ5s%)y}M*yReaoTi0EttN=?QBiRVlvn--{BUH@0IwfQy46};5jUt$#X${-v2o-nHeNN?F`U*!bW8V9?%)1j&m3U8bR}H?H-_bvp|ZsIkjgdlfqG{2R8<`JQnFZ2SonN6<2*(BdFN$xFz(5%B&I@Bja5 zLF+4Kg7)!ZT~nbC-eV4_(=rfeKcTH72DKNF>|?@XA1}zhjkxUt_qn0=`9PBjVm~!@ z|FPh<@9$iYeYo#n(gT-I5c|>*bp_Oap#Bro?1?j)86JV=l^Pa9@7)CNDLr`3`)?k& zPYNn;k;_?7xd=LE)uQE)o%i27@O-!T|NjU(pkoxEwZ)d2rx`q$(?DzA810k(|FZ|J z`9fRgX6N+(A7~vI=$>mkrvLvydG)6wV+N=VYy0T`U(ou0>*_;Ot)mRot*#wfY_;{! zMyn}@u3Hr!dTJGPK-0?bu!gmzfrFL6;b_bEhC871?HQ19%ftPk{0~`opbBnNK*vK0 ztQ-FSw>|Ka!A^nw18A=y=x&JNIR(-RQ9vv zfY)z(oo0Bc$e8ic3;A3UK_Blwy5PNd-hU;)@d2M-|Emk0vj>?A+UEsoe|i5^1FtOr zomm1p(-|rTUjG4J+m$B`9{=+GtELGWBdvS3y8?XXZ|ma<&^oUg(Eh9n$i6J^zd2z0 zKw~kWy><2nKzpv^!Rwzv^)YB124cPrcpVjJJzGUBXzvFD8)%%+`)>}ot!1--Nzh_0 z<7&{EPN20*DNCILAnPaAfcIg8%!0Q!|G&Iwv5;YgMKc3<|C#sSmEiSYps`$w1q`e( zb(NZhDV3U&n|>;S*2KP?Yq5}F0g@i@`1eakh6SK|zL3qY^f;bW=~b8lD(gXa+JoBB zpz|I;dpN!SzYK-i!)VdSu;TYYh8-5k49q_j88%EvWLN`s^Zys2pf%SpcXmY}qU#6Q3DRflz`%&C_opMnj-QGQ zCw@9IT=4$?{47i#C=NjCe=0KE@ct_W9wVyBlCA*tAwX;0Vd_9?UOF<|sP*y)`02>- z02Dsp`;X@`^g#B>9s2G4ry86WLG=n~{T^r!toL7K@cKlMn`=_pw}9;P{{KSrB_qR* zmk@t5AcYrGt)`QRttJB#%Au_q16<2`r7DA6KByWN8QOa%5d54hwFMnmhc>-h>cztNgdwwK6;Bp*P z27=c^wj9ny$jN}$W`fRR0?C8KEm{uOK-?e$UONL4uV*`4VbOB96(kRp1MlMo$${K# zv5?^g=>BYooD_H+j`#oHkiFk6hg-e>DuMGqSbfXkd7%EBOftg>i)6+M??17SIH?1b zP2ltA{#hg+UIRK~8>AjI_Gr;^XsY*LMQ~pOrDGQ^5NGEX^1!e%CR)0O_$vX8-Whj!^-$|8hbdgT_QVh94k(-hZZm*G<_vG%$et zmFV^V04QE6Dl?CP`t#M6Kb$~rtG5iU@cyd+_CGAWg7&#W(yBPP?5rt43D=L_|Nr!W z!o+$31A{f_tPBS5nWPRA?HIn;K44%3)j^=VXR-8%b6xY|3h%%2;B*RVdpk5SXT1K$ z@WT7gL~vaII{V1dfr05|86#+a=HJPnbO1U_Yykt~Bw+m!b3)t$&L(9COa~Gn7okT%jAU&KPE3^_%qp&k!SKkMv=)2 z86_q=GRjPLWYn0vkkMfBLPnFxj*Kop6G7)zNrKB3a2f)YnUMR53kUEsTa!DdK+=RRJ_F<88eV=w@j z1-kDcj2cq!v`oEbXWWX&>ag9yLN-esK8~~|K}$g_AzLH`T`bZjNtv`-haBl`3oct zny-h-&9GR?zyiL1_fHq3+^}O%u=HeP0F4dSDTKdz3F31y{s8eo?M2Yo9H=Y++xh?b zP4EBTY~+71oOo%+-~kSkmIIpgFMo-6|CIrkf1tI)pn4IMHyh@G*8D!?{e7Py;rD*X z`4+$A83Zg^j{~3kF#A}b^KoUC zGn{xC$KU}PE2{O<5^3~e@ThMK0G*|F$5I)zW{`ag=sX$Fn2Zf5{k0qs2ia$r^#7mL ze})9B{R|aW#YapV?HC+DeXWUhkTcsWHQzm|_4F`kjAQsx>*-wqDtEm9N+Z&7%Ms-t z^$Zdqv%LRGgWF>-<}+}B_DyW4XINm-!XOMTBmXV}hcBodXpsQAvpftuzy70~fwO+= z4v;%vfb@a(yjv_}SYh>_LBVQ2L&HRS1_i4G24jmB2Brz~8B{=RM2LCw!TU{LDl&lg zyn*&!RBD0ReaDk(UwRn8+HXJO88krm9)k7!zqj?*euj=;`@wfS|F?L+&|q-@T-OL# zwD^I?D82u`a|N$|eZVlm;s8T~#R3LSixz(cNPNH3w6tfKVDo_GRl;)t5l}k%37Uhq zXP5x1uORBKM%K4K2B$lyICMVosv~Hu5Tp+(4xLZDs%ZmSYX@4t2D%%*0lI(V|5ZVo z2mg0~)F(V=+5u`?g6Ak37@+1|`B;0r7-kP>JsQ-!D>p%N(;&MnIs86==Yc_GSOWtK z#C`W2Z62_J{LYf_9DL6;2O>>hnTzChkT}e)R*-ohw^%G-0Exrw%C&)nBa6iX$o^-D z9aln;%mM9-hM8lFWDZCiW{&EM{|p+9_Ruvz3mCxnZGg-QdCp)~^W3`vZ_VSO|dJ>HYuiOC-JEdw?P0mpzff0wfNz%MeXH%q~eJaTz2xGa{J-5{H^| z3E5tdIMkd=7m>_SK$vrBCz3fJahN#^(bU7t=|mD&K{BTh$sCY4%$!Ix^)Pdg)4v9i zIhsi3fW%?u2qKvS5{H^|@h6fv=q?rLT>iy}NaldVq2^pXiKZTA&PF8l1_<|DoQWn5 zGp7;B9FTgLIhjb}CP?N4BAEjchnZuErXFUF;!Asm1}o41FD!!?Bx3&{B&Bn~zg zbPk&L{|m_e2g!lWu9g6e!(B-A{{OY)We|hFqE8G=p#CLjz8o|*SLZyr;w2XY!^}1A|S10|V$TY|tD9bUY1AfyB|pKx4AMAO8OV8_R=^eHFe`W=KFDH+<>LAOYHg z23jju(-I`&{dXpKPuxqiF~kLl3}ujYXwu+5H)NbG1Ti-TotLs{VBk+^VPU9fVLt}7 zbE5bE|D^?)3JjojK}GWNM>WX|7ebQRTSAf<_ShsVFrbgOf#!%qlEGuNh;>BJF*ew^ zs7(U{H^>gq_!86}&|TxaHVq712`vY}=Z}EoA?>e!UqN$j^^YYgU~_#L$qbATcQCks z+~C0+yaF7Upm{#%m?6~MiQq7EW{`k{5vV;n3*0A0cQ;%=)U6)OL7+MRK+t|h(Ej(D zUD_3(vAvp`20s=zGc2g@{9^`9`v%qj*pGqQEcN$piGbRIpgmt8x?WYn0wi9u^l}Bb zUHJchCg=_e?fncAp!>uj`%;3A!0m>vQ?Y4aU`c4<0i|V7-_-#W7BK&K|Nox~ayuy9 zAdhpx&49We%?$K7RV2m?P#OgF*P(VdHYzi)fYxw=!qjmt!<0@vB62NJ&!Gk$)MW-giL(u&r@UUQHV93b?-JA9w zG`FRp-OTVGbQTjRe?i8fj#NVZHqrY}2KbDZnq-L|A;~OuNO=;nc9w%_nFn(K=nSYr zP?*>^FmNW%xxrw6fPuGq4*Rj>dpZo&_t=juNCxeZ|KAJRg9=JJAh&w||6>T|r$YA$ zECrQue`CRE1k}&^|3?tSu0fKo-}~YRDEvVBAZGl23u4!#zOVrCA?fL_BuF2K@BRPx zSrEIX79w8_w&TxF8_+#%2N)O=S|q@GekV4b*-F@j>F=|NpW= z_3$UO2!Ql(fZ_%s_vfWe0|zKwT39S#u&8KhhV(`M|G5ZCZx#ps{|CiW$T1cLkeNvO zHiF7yivvsy2`xWBX2RnUw7(vt4`e6E4rIOF|Nm5i$|_L$@?iEyn(ejX#D4aJjR90b=Ik-xVM;y#N3D2#q5aQ2Zpc$S~9#HLgI!@2`s> zw?O+i4NyIMA^vw@@L=}E@IO-ALCX9(X|Q?F{MhLI|HofYctGOsk1aI*@YDgmur)OB zc`A@UL4NdL_Ep3T;~#TDX%ytvgryA*Kk6A)fc)V7|L0NcVf!N&5w^eAg7hKhSMUEn zdlC9}K*A3kCqGP)^p#@K7YYd{P&)BBfu2ra;RH%+u&{Zl%&-D9XAN3I53&=KMnQ4m z{r~$(M40{Ngvr&U{sxC_$Wj(NNS*rQ;Y&M)6`*qiL3u0D%gH_=nE`xHFle0qryauz z$GHp+ApIcqNaklE%>T8rCiw@p_;9jGb^x^t8a$YNU}vhq;{@)XdCK7ZcAz*&So;49 zlHU?uG&693>T8P@1{LqWkaaYmwV|LsJ!t(iR8H0V?kRUp4$bhna{uh8iTG_ z%D@6r2igbW{dXdGd<2KQqW9m4;Ipk@@-_D?jUtP4+ALugVH!O{u;gif4K{h z6Je;RKcfVa1Ep2(|6h(;+W+66y^`UB<6MR_6`5z0K<={i{J#N|#zVbW?6kYUatkUo z?Nq9t+Nl(3F*1Z|?y7TaV&DL|4OGU0)&~@5>7G2eoNx zRkgwS3S#e9Q2yrur)N-`=J02*ocI5)rJ!^G5kKqzQVVjc_y4c4jdq}QPvA2M7+=~k zBsk7x5Si)8@BrjqNSgMzFw+ySU(6K%j|=z!P2&0_?e zyOw}3>u4mzEI;s=Bq$CW?HP8IYB+%U2s|LY9t?~M3+)*e**g9IyLdmt5=$>vjY>^< zm3l7^t=Cly4Am>;RY3Wp*2+r+biOXAUk92;f0@Z309vE?!V}S_E6Gp*$Gu|{!xWI8 ztoJf7g4`0mm&L9gw7zFK=)RpJ-$8By&Et9h^#kw80j*c8^>JDTo!7UpWPsgG={)JB zJi`WAO@A9l7kDtcoq?D4 zY>;*VEZu|R6qeROar!czApz6}ezA%HzJ}SN<;XejzrNu0f1rMs2LnS4I8N^wSJZSW z1i<1GbXOcCE*V^q^s`yC9F6q;>kD503|jMtCfDx$*Ow7AcaK=(=jNb2kAcT=E`y9M z)BnGqv-vDJTs3MnJhY(okpavM$olG|n?T{<{nrOvM%pSkFeGX+uuQaP*a5mH?Zrt3 z22fan_F{nch{4j4LlcraTaMm>ngN~*0o{+f`98xUkQtyfyV0Iu35fn_&#Q~<@j&P!*86(OC6EI|IO)$-7))KY#@ z>GhD=w~0ZaqD4oeCQC^K)E@xJgJ`H(U<%Zis7Q8Kg2vTE??1BOJ~(8af zUkkaf1~Lb;K}x!0`-->|2Tl_ zBdA{{crZI}fQJ*b-EXPz|EmYHvnR;z*KZkSK-L&DR)E&QM zv}R?ZG6Q4{;2(SNIE~&u1_sa>Gmg_3eJr&Y3_xzERq%UNsoA1XsWrK&<3EFj{wmN} z{R}D&(-;&$eg@5V%(Q3F0L@`^#xrQuY6gSOVb#)ZXJGHNXV9{AVE7Lz!$Imm>&h&> z{{IJ^Z&s@rVCmSzaH7_e;lhji3LMT3?`Kx;wg%n3<@=E4tgE;A!j&* zwDSL}Z#4k*Sq&VfF=#Z(GuVL6n5gw~0MFk{jAyWLn8zScbBw_xT+J%znG64{E1+q<(Xola0yM7<+Iw25d9ewUE2e0F4EL@5=-4$vpPM`%eV;t^m*)TJQh=uYm3f0iC-8>Yvnff$j_G0JncYX#;eJ zJ1AX(&Zq~S<6?b}=N{~SXGnQM6wtkbh_vsp1!NX@UB~m|{uT?Em@FDNpz{O&w!-u{%=>>qdoK7K zBu2-1|4)GRfcCdMKb~l@fKkw*fu#df-+KT5*NCKN4p<#%|KjuG#b7%YFbY{TuuSm& z|1Ywmo}mFW&gT99KVqB^n*U(&2Z~GN`+I9v!0&TOgtn={=Q%kxG0eadr!BBJ1D$91 z;~+ytO$R96TEJ&JfbJcJ#$5sEtUFNL*?`XAIfjTkP@Gw`9B=jh3puL?6mOvV5EOUd zvzw6GsF3z48+c6$NS*ip|0SS!t?7iuYlGUWAB_wRFA_m_+y6fTS}W|qZ0`Y2$I$kv z2eTdc4s=lY;{C@3yfz40=2yIa%rFB~_Cd-eh6GSK1S#9B!R244J%i@#`wW_(HLDJD z84Nn@88o15&>p4$(D_%DS{)iMH5dv&YpFo#4b=Xwb?}GgKWlIqhDaxN6F~k&*-r!= zXYgRQ69t{Og;Y*9RMfdKg;X=yS=#;oU%M;20#p`M*D@%8%5=xM3>?-67}%}nGe}q~ zFff4EqW!S~kBw>12A79C&HEVwtQ8m-L3ez-jAtKw(|08DM~1Zi2()|Br*va68fH%y1=qC6gVr{8{nRnW3OkvqPiS z%S*)O6a%9r8xMFcy_UgkRUtbAqhk|;061(I7#M09!dL0<1h-pNI^!8M>$^UH)&NU@ z%&67!0_Ry+7{0V;;Fx`%K?7d*90*?p^(T03i}pN7d2W#aDbGRYZPg@yFaVv)6_U(m zSF0>x0U5ish0L@6DF(+Y=x&IHU68sNvfk?WMo`-H{_6~G|A5YA2Biy>v$&ySz8=gr zkUik@l`Cp?Ygc&x5dpWaL1BZqU*-4>??1ud`msKfp+wP>!5$i}X7#(l_fbOEr5y*| zp?c%>VulN#vqnL61*A?t!3AmyHQ!~p&}hqWrDpzzfco1E7wYdRSb)-B^&JKUhq(+E z4SS(}NWWbH+6!yZazYy956~J^@4rsqbt9nlr=Yw63O5gC8xByrtp5Kek;!)%E`ZMO zss6{HkZRq)P(S~1Mg6=V4vzEwUjdJif!YE8zl+wtybU@>oU!^pgThZ`@O%McO)e{> zE$qQ;4chmYSTjet0<>4a`;RbqtrlvSoJjTl69f*c`d17kid+o#kowobtbTt0s1AjO z$%#tu|Nn2iKFn|dS_i)-m9j|qkgcw8Q750m#FA#nOa3zyH{e*(elYhE%lTmaSe zh;(q09kf?Tdp-k)<6H*NTAE*$Uh{gY|AX@IuT`Kj2ejVZuYm=0pH~S31A_{viORqL zIzEaafPsM_f`NenbekO;&)}iwp*Zn&cpnnq)5#4`wSK zO9e*IzLGnZ3XGur3s)=^7&Sn5DO)Nq8i4WxBz>L)sqwK?U}ONDZDy&!C;-Y+@Uj;= zPvyaE83?LZL1O}-vbG_afy4WcAb8CmsLTbWd&hYUa~ka!7(&(9_El=WSJLieUWHdKz;_*eYI*PW){y+YFaE{yYj+*d)xEWqWB!~cd_ z2lrJC(DVS>pJvf=GSvI8Jve$%EPA4w4(} zEfz5HS~Rd^c>n*8<=j3C$o`*tX-NBFk9LLk|IeMEeH9K(;Ij=u<82E(m@R5RdCdF& z=dGZ$;Mny41?Wr-{Ur5t$joz|iQ-AOR|)KxwDaGv`pK7h7GZrmG&PZS6Skzs^Kk zaM=J#f1qT5bbq`#xcv`G1K_*lz+v*Kw5Archo8X)G|uY%|I=EKTO6Cfcd#*l+LDfQ z7o#04+lH&`Z7eFYHp!DhvC1&JcgcB%?1Wg8C89cNdcUO?0)cp+N2f>n3OFV zIA?&;O~YLVhKghCTs8MTSJ)h2;7>TlP+xJZ`ANdD|Np)Jf8_+J2etUp!Ngr*~Tg zo%;Y=iwa)rxAcM*C|!Wpr2hE|Zc{_|GhFfh!wX&)2=c4LJkZ&Z)?mJU(tnJ*T0wDa zU43DNbpr!~wZs4apmvEhgZ+Q22Mml>*DfkpZM|S)HRVFGRq=&tNZHOip>}b0h4=s8 zSHbJA7BDbbv;-AcBrsHY{|SYy1BIR+ACzE`z)95)l3$a2f>ltA77s;FwUu!0^+Cp<|{E!vya?JmC5Tl)gcE z9#USO0^L2lqG1mM19+`?0s}kjOq$Z>@+ zV<~x20~)htU;y2<>HX&;I1EAg8DzJ^93~k^{4$Av#?~O^SLP!d8wrW zgFr==IOy(C4od|F(0HPOr2+#-MKTkE&7uFGb0&m-)G#Pm96R*^9FEP8D;i_KeQL9x zHVhix|34>!_Q^RmFi1ed=(qQO@SUWfx3w-Z-gVn1yd zEG&+l*0pG0*Z^wVG|Dh|)OtCX{fuF7@c#dq73v0Yi({wFEgBehfaZ2U>b(DddI|D3 zxO`AH;B%Y!6w7ROGPSTrykfSNTI zYLBGFvD0-H4Gbrc>}f>U69KXZ+KxHh>HYuj9GLk(Y8Wzp?_o%IX~U55GKL|cQHH_b z#UBO@(Aq{&JiNHWpa6;^P#^ne3`2peCW8T}j{0fCP~rX85*+^^zrXmy;PB!Og9S(} zXkQOVulHXIaG(3dABKn*cNhY|a!XcMK;^*s<;5R{j2Cwp62NjTi(zu$F((fOCL74w zO$HY4zZT&0kDK=}FxVv(?GS}kysShc~m?c2zz*d0)v<^`Smd<|KfYQKwTO>0}KzhMt`18}R zEfz3<*8V~B%6m~Hbv_`wLHouMH5nVM3{UHV?5$Jpt^oN5tbYN67|5QVHVgr_3Jd}u z_g88*Kly0`y2ta~NhGrvKz7<3U@)+Fe%c&V$5GA&mZZ1MC!xd2cfYKz$ zE(@p~Aa#{$Klr@=zbiyiy8`4!kXsTp!Rt6BKyCz^3%(Pap#kI`kX}%_vS0N7-%lHc z4C}q8OX`=uuJHcFC$8!Vomu7kQ!5^PrU;|lNpZ+{}GH2|d(kQ+hfz|MsQ z*#mLo+p{pWj`RMSK+I)huy}rE1~|SJFo4z^Lc{#+LYP{Ic}zVZH(D%UVzAzOX0b&B z2Lq^21~S+C|9e}AT}%uhage%{v<8?NvDSOfY_V9tC;(D#(ZJFG(gTV+@Bi;vA^I2v zK;mfnRIT@(Icl+h5p0h|0}I$ZE5kFFy#K#DYjdEX0i+k=W=4jZG~)`G8t?yaUfLXJ zU zGb8^02iaq>fI;4(f#CEOLJFJl;XRIgNi0;*3dH6Jor96RR;QUh}TPc88IV>>`+ zslU`>U;xccfy6-edjAmz&)Z?KC&K&xKNXM}AU}C9O$VoumoW@0K=xQCFf@Sdu|3eh zVEcfmdf}xF!;Y7n z3=EYV%1r7%D#BW zFyqBRh6yi0@|n^Vpfj5hV*uyQc>n*J1ByE&v3uVCzed!aFw_J2ug+~UD6KPs!UMc- z^^X`h-M&<0SWuGz-dm;vi$_pj(xT`^5PD|3{ah$>G36%}#~w0)>Zh7xpt|n`CseP*i#rS}Kw~^0`#|@Bf$C6@o6w0_>4EOeAEAbHU}64AbaP|zw-X` z2rTFQ|KkVnewjZE;JyuLYzEYRb)3ie1T-#Cu#$n@p^0GwXiqpK@9Tl}f$m)K{{0U; z=MI`X0rA8CZ}hYOFTmja`yY6`JtWyTDH}!I{K9tc|DRZXFJ@r)-OL~{yO}`& zG%i)Cc`Rw7GJ`-@90T+0W(JMf&J3DKK@1IHE^Ky_oEbzQ;{y*PLE{&Qe1GAj_y3PO z8bSBrc7n%rV0PT{{{L}7qcZ~!X#Rildd+k?jD8M#2?DWLHW(Eg>D zu?!V;UXw(A#WQ#y(#l14@BbfTK;Z?B!v+S%x>p_sFKt2dltCgt?HM>g{`UU=D$`;C z1N($}h5*prFy8;)l{VaG2mpuEkbxvQ_^72b6{yJ=Z3H=HVUYGOTIzT$=$B zv-JA^qrOW6G`~J0WYvd#Axqi!ReH#uPvvD6A%`GcZh80f`@w z8R%h$W>)}db}8t9%J53h2j@U`g6#WAz&=o1y?D76T;GAmfjQSEfZPQ-6AI+7`VI{T z5Z&mxHU%`N80z)nU#*wowU8w*{?#ni_z|*{y$-aW0yK{R+9O!&rD0I(%Dx3O_gl-Z zunx4ICS(Cot$TH)N%z^%=A2a1LQ_f7}ReXUZ$R;E>A`dYk~YI$6|4f!dzpa5E4o-8 zfYMLJsb)Wvbl|z>1?+r9(47#VGZqV0f$sq}c?ptx@c(~B3+sc5C$stB_X{+*zXHoa z&t-(^gNi}Ul4NKQfuHBdz`y{?3!z>Y_tkeffZ8sgbLkjBaWzr-|C5Qz|6fdW{{O~< zfx+j+%QY`7-C=1m>=kqlUjlsp1PA*T(D*SdEI?=5f%JpUwgZ^~Dx)VV|9@ktz`!_D z`9G*#jad#n{{N>@ea#*HPRRTu=nOj#1_qf%_cd1vy%;z^bC4i&LE<2Dk}d9OwP_XmtMnLK~7kVnFj!pgY7t{&Sr7A2enLUaJZ6 zE6AT9Ghya|!VeTD-v9rzfbRPRt@qIG0-ewO{|rb!NROog1FQG{e-A)@_5T0w3TS;3 zhz%Mi`+e~L2TM-S`X2)$&>R#vEHwWguz$cHVwnIslZ$-|Xx(J>f5`r!%4`M}{f_^j zJr^l2+t<9P-D?Bf(H^#wGQmBK;dQqz0abCf$f#`0R{(9c-Nm~URIkEVpcnk z!P2pbA)?kZNTk+_eG4euU%D_bSZe-10J2Me71(?akQj*VFpoh6RA+$FFUUXOFkt@w zWFj*pJ%Yjjls`R~=p40z-zw1lAkZ2zP~HW(sa8RK6?%RLiG%Lc0MQ_~ zBIkdQUqEFqD9wWM2S^<#%t2-FMt4Yg+vvIGN})G6jpu;Wfz*T4f#XvRJRc6a_l0?* zIs*f!{C1qjFaZ>&pfwbrHoC~ZFdvi_E3;sF;kJDT)T~h(QzK559lsc{Wfr%WW3l1Kl_*2qUBPk_g`i3 zxgVf(0E+90_6#{53=A8z+gO+!=P@qPZew9~mwShJ?r?~W54hJpHADgGoWsQtxsmRXt~7f{Z|Rx=6o5u=7pt}6nKpYD9%CrN=*re zO3fEcmRvA#_g9t*EKH#AhOHF_g~f|b1_tkcrH0=B|3l8Q0lWQ@wD(^{@cIXs9#DME zv|T#`6hoa!^C)ooR{_tKS1%1E1W@d`5w$t0Tv1WKY{WntW0cx&%;ZC@&I^094PIB(z|vW zBctOyh7Cw*eF-RRK<)&UD;6!6OT7OoK;s`=w*CTzy$1v11no9PCeRt^+HH*Bv~Fwn z|IbU!H7~4JN;!ba(E0`MURAF={?M_BF$c*^c8iwFhTeY_z;kJcw8Urv@*C)`0g%6O z`O$-ckq6bROB22SDuCxdEEO0){hkg>1xBpt!%~6yMNNzMB$*b56wsVLsEkCu%L8-= zhxfmtH`x4Pt02e#9#3E80jl2&(A==r`>#BBKGafykr@;|Ft>o#2fS2f=m6yxOV9uR ze>yXCILu>cfa`C$bOn<3M29*Pk?SaAtbmuR)kJ-Q=07@gEdDY`Z$NnlIZV9&|9b;ZGw}6j;-LE<3tum0-~g3#wzmKO zAhmZZK@4s^3aYT?>h+oAK=Nv-a3Tp3w@)+o>aoApL(0Qt$ zwWZK}R%p?PewO1s@VR)Pb}MK+05r}3I{R>=9cXNxfdRBu7F zMeGJV+@R|XYdV!HJeb8I!Rub`8CSes%pd?VtNAZOL;Zh+fSM)R6(Dzc|Gx*BgIx@+ zXF%)q|AWr_uKwSkQLFh2bnm5%r6(_B9i2niDo}hw?ewwqgtlEA!d7|z|NjEiX9BGg zg1ZG4E)W0z0ELbH{fkDkF_AQ|C;+oX~7T|h(9z#vYF%FxAV+@QSeV}%Z!#suxn3z7uu6Ycg zbs3D7@@sF@oMc`G8gs67v#_XN76Do>Edz3|!#su~8#)*m7OY@ksCdS|q-I&N9_S1l zOAZDmCx-u5JQx@T-V(t3MjC39qbod^MYe$Mdf9#wVHRjFPQ(4R383@RH=F>k zo3Vh$9W)(zFpGfh04=m%{QnOqej9D!V*oEIR{n4TrSJL{4+fB&!#sv7pzy8v4?ZJ3 zqvE9AgNjw`51?o5?x;Ayq*!s1(V^DeOT?jxVFmOKzy+W_R3+#Rz*XRW;e<-{iwi0> zAa?*(dbS<`tx2!cbYn_*F3?aJ54r=;yCVEQ>$>{?))n=4*tdYjcp2dfyC@l| z=g6zn?|mfl`|p|?khCt0xK|0fJ_eMYL3!Plfq@Zpt^}w~wRC1=vp>wh1WVtI$_x`g z>*qmh+qY_g)5ITe{DJNZtyARiV5$R;S6b9Da#$=-U;vFZ+uvtk@nEV0w~;{gtu2EH zgJql|2dEznN`s*NW}vlpP7DkgjrI&vEajBJ{Wm1>1ejSCb;ck&z+;Us?HLMe9Rfh> zz8XO1!c}TIJ*m_@!~`1W`)Q{LT95fZ5qusZ`>|Be`XxI>0S{)OhM!yv3_o5ma9DbQ z&OQI%Q|VcK4Ac(--S-4Kzw4(41E=@@|2@d*M!N+(7NGz-w;WWSX}2&ig3_hKJVpUa zh5tW27#KM~_e6oj9Op6o0gd;(bY6R+erW(`4elH5HU=igxeQN0dAnvQ`xc9*PN2I1 zpH#e5djc9`s#W$9dC9rvMkS}ZLZue_0+2Zl^BDH%uL7S>wdQ5=T7!y}YELTJoSuNx zRvbITRKG03!Pb+3<)zoz2bK!||5myzWpbRu&;VZRHjkkKWJaaN558JX=L&Fou0S!|y1?lIlg^eYC z&~62Xaf@~<_^!>L;BanbU<9=lLH!}nIhkOymx0C`{(ouYT$=(upL*{97ZtDMLGw|9 zp!JrZy`L4&Ss%P~K7XU;xpqZGR|DTq=kt(p#S@Uc0=nk|RIj3p6FPv)i#eb;g4p?g z!b{GzC+e3uI5^Dt-%@c(?FqhcneYAozX3QPpadj5;NxBgKx0dw zGN^u)0(h*>()Is;?Ntm+zH=EApkrVjc*npvQO8+eX#k|h;svxH=wJ^TPXpbF%K+-9 zgW4V-H-r6vJ~oDC9yt6M{{IKv)rlOApg01xYd|#AYhVhRhh!jmh_L{ahaBfIg2!Az zYC-LJP#&r|Zd_5bgnbLN%$evok3q!N`Tw66r$G710CYCF4XBS^)2>{B)Q4YT(Q-u# z)V}uqD+=EK2nsv&y+`2W9_Ap+En)j`%*tL|N4am*Fuwlb(* z@cJL`|Nm2J9)Q)$AghO}od-%Ipmb=F@c*yloc}hUvaRBnvqG&V!-a|tXN8LApt6qX zNyV`POqCo5m_T>%g33P7J+z=Tk)SrskEdsE{L})aw|}5|?k6aW!4ZM7-;Tjbzmw6x zgPE5RbiO|9o@h|n54|fId_K3sJO&s0#|$i>KFo{#!B!S6S586vBMjan4k~LvZ831W z4)vb!HQv83gZsahDj&dOquQP9|3P;+fcA}4x_;mT-MawN4-y0IFMlzg!2^6h_}^gg z{ugK)Qp5f~#D4Iaxt1%x!0t$3VD|ni4Br0<>KDNDg7&mqv@kGw{|yAM?FH?*hM4m| z2GyLa>L7E#S@Qzp-j`Mf1@OHubCg7WvaA7* zpF`?t?k%9U49K34Q{a8uETA*zYq=Oo6uMyR{1wdVSAg8`{{r;hmlGAQFz$Vkcbxlw zLnXV*3($STp!1GFZ5YRS3~NB`FvqzJ651;T7!sZ{fcmbmdu|#)_ryTe_1HRq7G>jV1- z44j~`(VC^d;q8{11>vti^6+-cf$&!ra}nY3`^cIb-v9r7NO%q!m;K+9@Em+^4D4Kg z#s(G!2JNK`+zxXYR)ES7P#Xr+mI0+FvIL>3p(C%VT0r~euGJ}LAhX4a;KF<69|B0ZxRy-IOB(%F2bU^ajT@0Xgrl560 zH?-%0>*5;ic?>L$^B7vR=YiWHE#d#=e$;CIF_;Ox#|acp9?YB~HpvVu4ava@A(<>< zp_&Y4p#3CJF_n;H7O{|I1~bS!H3MTsCir}a1(sg_A5?mMSY+!3x}RI*M5UK_O09B$ z9;lrV{$K7J$exXmweK^aYv3n<(wRl_)e`SN^5AwRI8Z?488okIxAOn@VCDebdzt7s zmnlQL<^O+BztM3nQ;enC|Nr1V;;I1f9#V&SOdgdQhnPY4S%Jo3LE{My^B8hKbI8!S zr-Vjl29`n(2GBk$mqHKl{E?3(0|O&eZ2)MTDtsxMUClG=3h>xR;{O}3k?s~m+$s3a zqtJta#j%M&1f&6Cv1-Bb2Uj5*!R8Qox)MRJ? zl`WN;{7Y)RtSdn6Kk$10I_Zk;Oa{*C>gFf))xn^+|M8-k!NX=j0|RJ32&f&Du$0lk z`>!AJ{?8s;J4iWdae&dm0#uH!3XZHTf2VS25>T_8%FdBg8uK)kMt38*2sUnL( z36?fPJwR#H%`VWxNiNXC%?{MI1Jya8^51bDLkeggrsF(@C)#ttY32zy%_#pdn^6NA z>jL-R7I-kT-FPvN!2>j(4!&m)Tvq#n*KI+|=^9jbUTt}?GT6%d|NjVZ+ED&uwxI^x zUfTdVo7&Qo5i&lO5dI3}UQqsox+4JUj+l!1>d4+3)@TKWIu#5fN#X1L8%1D|Ke=>7i>Z2t>5L_#{*P4qjNK=rNybWM;!qb39BEJg*;SQ4mQ z0+pRFl|g5-K;jw{7WymygXZEyYF2t!)GzY@m35%@_!W>_LF&PVLkUor*ETSyc`!2{ zo!AK3)Bi*9zaeOR0F*AE?bj2Ia~MGVLMF#~pnI?W|F=+NxX{?hz){=WsNliOd;`=6 zvOB=Q2+AjRkN^Kkv=9KT^H!*1^I!nUfy8UsHZUYwDlmY~hp25sh=cY?*ZhUtduz3Q z&5MeCtPc{c3>frxGl2X)!=@e@-&{=K@hnh!f{m3x(g8;Y$gK#!GtQ~ha)0R1^#2LS zoi+y?KznwMSu`*)fXXkByI(E*zv9)w{~JJKX%@+AUc7qvf5&Ua{|8BHQa@({Xx`jGdyW8Tt=p06RVoUVUJsZZn*Qy08NTKPxG(bZMV}=X6Lb#4{grj~ z|No$|jOuDoJ@W5|<0J+HhrWLu)vMGSpn7X+H7|qq03E1ar3^DKqgL}UNNi2@D#Zs- zbs@Eyr$J&fz+*uR{{KgIw?*xm7vBH>&V;&K2Rya{+Gli+^+BcF2R}0Z>FC)UUbV{r{cjOZzo1ED?9&!SBKZ zkFjY%`oo~~0qT=hdb0C@#kpYO?yo@Oe3o+eFErY(%?Q=}un%;O2FOguxr{YP=CXmt zU_fh$K;;amPJ0=@_5iqTIfteqtL&j77~c(H$NgUx)!&ZC*b}6UqL0O zyb4I(R`dTqOU<x;t{g?An4s@?6V%-gz-8GdOkhMCsEY1}ctC$ojjx_s$?5%0g2b&Eu7d$o-zvcxf zFIB9V&1Z26niipMfZZ)w^T7QTlHYP*eJZfMUJQ(&u{`hp{~DmhIr#iFPHmN0sMFvxS3ze}ScC3KZUEoIF7Yyof#Ihk1Go=ds>J|q2fl7$NUGHO z|Ind{NdRslMTQcKeGEJx zbzt?6e^*#9WM}}bNpCpFP~!bBOwdw6fx%)QgNVfe1qQGhsQpuI|9|oR7y9v~J%fey zJq8Jo8KAr9K>h{wL0@Vz2!Q55L34k&=08DpfYgHYh8$zlNjS#fFySCW35Z>Bi~(|1 z{lCy&@YqHas67!>2`UpoZ4AdIhCANB4}r(FUmsyu23i+ytH9upsHp(jzpb%&FIwC! zd0pZCFX$mC9KrFqpx>9gu1Gk>2=+I~&))z4^MKBG0JR5dCp0Q}F#U$L zznB}?7#Q@IFuwqmlc2UQsNDpjL1h?79VmZ+>MGD#i{SoNy)^u68}C0k;Bz!;Qb2o@ z|DOTv1qH>G_y0ec3dsx%HOZ0!70EB0Dw5@wfcix6ybGOg2lwxoe!2co{O<@KtE!Q% z0NMZ2mVx1?B52&3fx&SuLjtJp=Qx)k!cy)3|C;^U6`(dBbghI-Mb{zbn%~wHpmoKd z`W007I?Q9xX|w^Y$NB#Y)Rza}t7pT&Qm6sW_d11I3{0TDpFQ@81W&^D~7S;C|i)gt`B(gxq4Y3;)Mpr9F#*x%wu!e;xpeJ8&9MIb8u- z^X~osgDRx0@qdZ-EC$B#{}L9Uc~ggZ3_rsEv;6?wy;Af1he55TMMZczn_bQS9|pDR zzbioZNLt$cf1usTAmBI`bT1(TW388mS)qrZphFYGgHlfhMo?OHX!`H-qJ}}j+ERc4 zl-6sKPl(QeI^7qtu=FXl1`c>l@t1nsW^@n0%4SiD%t-~bwn2aUah zNS{{rwP7Dd&zxRUg>Vx`01mp*hJ3(%Pxc$RNWcPvQsX^`ol{KjD`?nC} zKF~fSko&y<|DOUHWAR}6wgw!)ps^knjCf%3{{Q<4R31!$;sG>{=fU(%6*(S2V}hV{ zI>>PWikq2=45iv_OrSMtE=cQkFxRO4`2*hn0BYlc$_&st5y%=fCeRwS674o7@VXsK z1x7O0s9n9`{pSyO{|A;eYNepC#8sAq)}(YQGL%BgIM5y!=o+=F@4f&00gr8h@&>pb zLtUfBHX&qc>N<{JrRQjs4j)2F?{YoGDqM0&u{SfKX^=G0fQY_ zKlrSd_pA#JGL%^$iGk`~Xd9-?`~N>#O9dvZ>yEtt`OO5~I|uSJl3i}ze}044o?zPb zZYH{21;_sH-*Awj%=`b}t(FQ*pmk?6AZhIj;%-^!+&I{dmTU1IOrOE$pW82HU;(8i z&|0DwdxNdK|NH`{|CjNg@{dOXRIY&fcc3y5BF2#c5(D$?86>PvN`d?9p!Gc<{UGxp z^BUJ`KxTUX`32tp*J#i1qSEex&P#g+2}@6yp72*7Js>d)s5vzU%#ikWUR&z@=NC9X zgVb1eLe}}!H#`ID1KZX1xWc04+Bv9QkU0{228rq}1_w({hBR?HLw;#zZW+7&9tf{@_ECTVct?*nuu?$;G$;qz>fAP)!B~a2kwfka%g& zu)~szaRrKca5`iB08$S+YXlqyATdtH1dy1m149$6e+_o47DOC0eqfQnz~uc$3tUGa z!uP!+SRI!X+zl}MExDvtfXqbVgZC(b`5-$zrNH}>KyI)(zyLa{L?YoBBX~^-WNi9J zDQHc!#R3MoieoI0J@DXi<>%8E^$Zul{rtHMDHf1>jTpds{@8%WIKl0#1_l>U+<@|f zMay+5@O?4lwXr z>|x*n`5Rp4LEI4wZo?m7;0K9;EQ)C~*?$1Z^TPH?mTe>b(*!yo|C zi$$NL#U2I;&>R7pd5ji&7!0uM`Sui){w+Br!TAByh6Lvcc?JoK7n0!o0ID~^bD$ux z6O!P3Zu7ubJmGo64{*O9B>qAYvZe&I#stJaAqhTH)8@gZ7YWbn*^$&i$GGiZy#%Ry zA?X20PjEhX-#gsC7n0yT?g+jN*qyZwF!eHEH-h9}{AZA`I4%QrpDlx;K_Ul3UL^OFw}y^BEWXaz}*Vf19qz|!@d4Qj{g%OdYHo#Ih_9^=|OY144S)T(A+J9 z=5E;9MVPyJ;qHcn124G#f&1$OFW8MX51hCvo;N=Mg&)MNyim8^|DMRPml5LD?{^b9 z{(nHYl^4yeyl8IaMRO}Jx?3B-aRLuxUg&r<-0d@9@=!N{%LH473k-=I3_BohVg#`h zKyHGn0hbfD4BGz_Ij%E9)cmVY$4-*^eR80v|L?XRk}-_`e<$rbuo?3rjwxabt8iVYFP3>-Dp~#$WdSna$_pTf26#~gXT^iG~|I-HCS%UVdKz%0A zxDBXX3!7g6_mz|xIJDbXLHiQUfbPVA?%%1sQ=`_z@TEOz{(7=7l%5~UWNwn82rQk zKfq(||C}^zGXMVp&E_{r~slA^5)7e;{#7%^NzFUZ+-AJilT6Q<34vPe(?E9}gKh z?3x(Ftfuf~K+eCrWnTNFy5dC%$i2%rL1PRx`QURiYU~a$uvjzv|8Je}|9{f8-~(0* z7}%^E7#OQ17!ty(85pb*7#OV_7#OS+{{OXNU|_O6Q2!rf4#-@PnHEcLe)j&e6nq99 z#7s^NnEzfXGR}DM95hyIRS6nLa%>X5;{AKADad}%m?J2kdjDAi4nHWLv7(GYq4sfg zh4-H|;5IBcO}AYCTu}iNUj|NVpm4Bt`v33sc?Jzj%^NGgVc~V-hsE=oUOy7S_r@Op zsj*)9}gK;{8VIk zVF@}D-k(7Ow9d+L-oGv2Hshal;Ql)(t{vyGd;!G`Nc^WFqry)`Mvb3}j0Q0Oyl72X(3SKlaa@2DkuBdypyP_^*c17Ls z%@v^WdXU}Vd$U1j`u%wgZUE;P|gzx#&st(@?jXrQQ{w^S%-_84iQY1oi7c=B8>MU;xSeSjebQ zvDEd6_g^h=IsvHx+Yg$bh+z=+{;L5_Codi{D!gc9H~_K(Y-a)kGsusiHJLviGAelg zc?I^X#X?36kQpF5y#H!|_cpy$WYj=&dkB)-&m-La3he*tl`odyb34@C8c=tG*WQ8b z1ltX9H=p-k4RAhu@sLsDMI*xrbaz|HFz{R1FbII$ZxzEJ_~Rj?hWDSB;Qo)rLPi6S zc@RISgZ=+fk!TAZ-C;m zdg%|9L`{YRHA_!dfb>_XFere+1ZwVoBy$}=dcpew6d66d|7w8Olf78T=uzc@Y_;Rs3mL)p(Ru$>1F!9U#mH#!;vu8Ki$;bENMXxfCBXOu z6sErz87=Ar8h-qE$Y@X{aEQrDfPt}&qq)NS&kM-@r-h6TAa{e@>it&@ytWl|H#p2) z-hb7=V>_=E89iP+WOR7Z$Z!MMo@z^oJ--zhJ?bq_fb4OowmigSZOOn`uW=e=54iqE ziZ_9uii{P%7#SO^9T=EiGBP@V#{C`VG3Z!YF)&tp$*WjAWL!|GDeqD19wbt$?j>R! z#lZBF>;H}4n*VQr(z^8=1`&&ej1r)}D9GKQeJkF7Rl##TFBURNfaACYGLKlP`hf4p zLPiPizv_*kvPpjzcr6Qfk15&37~xTVnFdVb;ew9SV8I^1{vr$1q0~3Adp_~Khwc;-ykzU`mF!2&<2(DAbIaUbHL}FLG|i@ z#6WW1f98Y7T0m|9iPfY@L*~K$%ml}y{iFYXA!hM*fz*T4c>kFLE;pfOX@JB)a^8RD zgYyK4Uy}+mX9n1OBsZCX)PmG_|Cs~6Hw|iz3&6nEsvt z&g)RKSgilAa6*^`(E~CUqz@5RGr;>;L2(V5F9OL~w5$k)#K{bBoI%*@!1>7g|DPQo zwRML#gVLD0_wO5Eap;-EB9Qg9x5B)Ce*u?8pmYLi6IrwvsM|gI|JVD^T(BEK;#S{5 z=O(=82kq~gP|v^sQs@0=E;wAl;n~2zFrl7-10uc{9G*~dM$jGiP;qcvTbeU?fZS!V zfPvYfWrfp^dIp7`cEK4SH9!9a8%)|4>@ay=u#NYhx!^bjwdo-0|NjT&l?n9>FDCqF z;CWFOY~cN8CS-q@GH6XZ1Ha>32Iv`4x6-};|JQiQ%%Jd7o+06-GWah0jF-*~656X6 z1RUlvh`e-WF!&kIQ1H^3!Qy8;L&eK@h6?ETw*qK=lEWMZi5LGF3Vy~jWc-w8DEMj5 zQ1RnGL&8gYhKl-?2S97tKxa)bfW$#!pnB0^9)rS5dxi|q{Z*BkKb%14>;JT8$N;GU z+XdEp19Wy0$M1TE3W&cLL_p;O$p7AdW`OHiuz1Ug?TyL|3P0@`G#Zr|R6u80HA4Jh z(WuOz^V6Qep;4K^U{*cD32@nG&*0(xrw=@51x<%GU~?8QFj%y#IP3jq4tS3=R1S2e z+CPhy6?Z(CT)}N6@HlA`1ILVdh7%3*88{m485m~8Gn}-x3pS`%K3yTx!oUVP^P{GP zeT(-W3-EdtP}>?L=lv%LT&{u4aBSkRuyy+X-_k3j;iogh1PD8H!B1y~8KAWkKb;vs z>=i$q88-ZMX4vu5nc)CLO_;$?XND6Hc1XcbXK*|Ezol1Lz)xpzUj$?(i2dNFGs6pr zx-gKs8<4Q;0hc{5_61vk#*V;#Z@D!Klz%|&UhutIe;$J8Kfr44GZeh|4~>Ha1~!Y9 zTkC6{S&4wohxY#S0MbSPnRTBb;l+OjP`?Z`#|Bb&1xX#aECksFI>XGO<3jcq0IoMc{fD3S3=dw~GduvLQO9`< zOOWhkw`jSY20CZe`_BW&+PHneRv@+3dv8w$jU|BAFui!mzyZ3y%=^!Ma2pAvAEX8( z2U7FmC4%pyC*l0>~`yKahRq;PD(S zCg}Vg=>Du!1?`oL|0mirOmUdYumE(P_fLC<50(nxeES1*9_UYdMh4JWxy4H+@VrXR z1G`rZ_ZgKQ=iwnEF|J1O4(f6f8zL$XNz|F71Qd0C@9WN-0S zW$?b@FE92pYyg=BvcuxoojS1pejf(ccTn>{=eNSl>-GNs(+8vnRQ`A{If3h&7yB6w zAepfeV#Xo(`2aua89-;Y!pzv={r@KiNDtHuuwAeBf$9`?@O&(&-m^HszznHpAM)2! zNrUe@_Wm;g+}4H4GePC$K>6SM&jfIr1uDk~kz*);%7M>l1;@_=hX2rZ6_Z8FtX!x( zxLpI*`v9~So(Z%Tl*ytcsuwB`b|Xk0bRPx8?93fdIdJ`N!2nug%TVyLo+07od`Ow~ z^B_Y-ea7tyP(AvCk)gom0N7miAB+qWDzz9CEL!fo`kBZu<7Xqof=W$hC5UpzHYeBFaazNZeP!u2a)Rs`yWkiJxC6;FAg+s<^880oR1s+Gt6kX z&(Huh0~Cfw!0Mj={{cGJ-}_G=_}+sT{~3OO)f`{|#RZc^%bm+mb^pEp^nu%KFBlmn zSSBzqfzIED*$q020kppCXCmY*8A}ERo*#_hvwK12aDc+gqUFvu$#KCm zCdUQOnHU#bW9iAjWU0x(JUK3S!9=^@o{4e6EidjfET}lnpiprP6uy1nzW$5*3@bo) zdxHH3ZcD8;2bqgd*9&g{zqrq^q0VH)kXzIZACZrtQ{}fb)H0)<+0JlHO87sX1 zFo4S*i2S{WkUbc@6JBaEz{WE)KxGGLOc&G^z%{N5Dtj%K{@4U^2dF-?XxY!|{ig?d zm(&{(Q27Ot1N8+hTJG|C|G5d?Bjo-6hl+(FlYs}*CD?u%#s(ni0>2>T4O$zAjLk-~0dn#G3jKp#5bH9!wX{fY$Ax+-(NhGpNX2 zQUCvU1*i{A39fMx#yA^OyP07XXn&yNJca;EX9gpX{h?lLpnHRrK>N?NI~mS9%wqtZ zwRg@^^S=?O-Bqi}zQxju-Jw#`ETtyPO9XTm8fYyN==@BOe$YBmnxtJ=@zJCoRJFC?>L9S0;C_bM-H^k5OgML zqbGv`=!`N88m8=A^U+q`z=B8Aa}vkg4oFMj~rj1y%(T#{!(+L1n7)Vc>KL& z;IRJx|A#FTgP5f!1BWHYN{RYa;5#Tm>jWA+m@e?V)MQ`);DW6 zAibbFuU_A02m-Ac2h9a}|NoN;3x#xQqdvO9*!>GXq1TG6Ro(Cj%QO zK0$u=U^-_DTH}Y524p~K0MxGlrGtr{4B$J9CMq+4&gW#abz%?$`31Djf1)x2xW8uo zpWVZH0Rw||0|UcEt(5^FH50W~hJf11AofqKl@YV||NrxQK7)aEJ-9!|P`~mAXb+Z$ zr5yvK^?wEj{Z0nuT08bF4)gxsum{iEtV{s;#ryYZa2*XgXUY5j-;EHlQ{b^o$a=H0 zXDk{RGQi^he?PQnX2_^dz74v&2Xwa$Vh)FufuW+aO{t>mn3BaY1{RBC29Al!|Nn$^ zy69E3xIY4|&7INA5HeAjfgxn2fEDPz?wXa%%VsM7|KY>{DFYip`{|A`a7+cyTm6Tf zO$82KNLZfv2}%Q?`Ge-e3@qV?+3dXk|NaU;10Hs*N)dqSAgd8x(_oj%xGkoXwl5T13mWubRH?g zL`8-U(0S6JHTD*X43lObWSB5fk)g+f$pYNRv)IQVWzoREVv)#D;r(YicxFM?Vl?9-54!YkBR4#+^6sUXzoz3vl9#Vcf&S5YBrF~G}w$|QDo4oQj2!iIA2>M7V<_p^_kRXRjYR`Pi^Wm~j*6v?FTDT%+}M5ZKdj%wY0+{o*!ms= zNAp2W8 zpfPXn|34kQ|Nk$5?r#C@W!zA|@^!`QlMI~o`#cyN=lxq?KJWhwho*mLAZg+rzxVHl z;J!FKzM*$MTB`p4;lXq=6LjYzD86T^Ffdp@Wni9ggn_00zgR&{wRFXlKMWk8y-J{U z?VxfDbibs1d7wSuQy4&H2&k^GXkci7)E7VIg8jPqHF*6aczzqFKmS|- z>9@Ye!07$|$5PNvtxc1k>R8Hj9>f^`QOM z@bm;~BXTe;^I$sm@`vJoMo<}I2i`lrlELoK|Nr(*|Nq)8`v1>f>Hj~wrvLx!K=;l$ z{r^`}AzcAVQ=q!g>N~rGbv*-z)wM_i>nL9xtF8BDSX)l z3<5tj8907wg4^K|KRp=)EJ5|QCWFII&;Kuedj5al#PI))r9Feh?|KG--}MX}ptclf z9Q&s|cw9xo(jGjXYXBM>_5S@D+;6ORxeT3CXal!l>Xxjos3~OMQd1yZQK#Bn0g0Eh zV7G$qe}jyb*EWLMFQ7UPbiXcW51;l*24=^(3@V`btOMz5xd%F9lG*#u8Svgv>jR*C z@(&`}aX``BGB{Uhe?Drv<9_H>m9cniHEO2Pt16;`e1I+A+w0#(iGz zWss=e`=P0RFZ&kI+>iI4GmvqVxeP20P|Sf6jp06))`>8YYA8 zoQLi$`hB0F;inxaUTVPMP?HCB6SzLVpXmMj4p#*YF922h>S zu$O_uVID(7oy+73s2=dRiRF6+Mk@gZiQ4zn1Gw=2Ny1dQ`ByTEY*%1a(hhxfqqIU@r@t&Y<&P?`DCYh?$h zuT{Uw!vWkr&I||uje*uAdskE>^FP4XzX9bZP`e-M_D0a%p`bXnXu1ChR0dllfbN)u zw8=naaq`nfl=Z}uU#y(q{r{6C^voQdS|6unu=P-&G7r=Ts?@Yo0iU1d#31%lYh{NA z)1eP=e?ZGCSlwWM2-Hqz5CgS)tnaOag=r(G-DBzb{~zegcgML5F(9)&m=3M5Xkg%g zl*u2z7GyGj&b*%jc7Fl`t3}I$An!jX!E+kmHita}iu;h=_S24`1JviR)cpTP8+4xj z-2V%p<}h2dJTUV9a{@fi0ZJDzJ15#POz{5yv9=(C!NIZVKX|MMl)f!m9`JepIRPFw z1D#z0ax2J<;JWwV{||_E#XrOy^U!ecU^-|Bx~H@r6po-i3loFbYl)Q+FSSeJV1241R-zYqYL{{q#~wOk;x zSVFA#g4SyNa01=;?7_gI^D2~q!!m|}qc$=~q<&KX14ymuB~Y7(!Qw?CLj`DFpnm2f z5$``Iz~hoHqZuMB75@LL)O;ZTx@-EUHHZ(s@6*DAfkmNd)Bib5lm0JgD*FH7MI%Fl zMFIm0c>cU?aYfzI)fL`le}D7ELWTvPwg6}j2vpX3|2YmW|6y_I{r~;e7Yi9ypsG0r=~px`G(gRnSf|=u zfu;sr{#i6IOn|D%tz&IQR|8%nV$r~`0IJ5b_GvY`8t6O*!v?4tRnVF@kX;r_A0{K* zeGKe>@ST~U{nh{9{Y6q&ilh!QC)>bq1Y+L1t4QjakkocDk^MFYbVhqUeNb3F}sRPIV zOKFA(ONameKxw_w>xDqAmxIMmP+E6jVE7rsVDZxE{|`|91?3M*2L{%Oo(vJShl?w` z|9@!o{{Ne??(yyl@87#1bB&D*9WN3YCZMMKo8UQf@Be=q?2{P8tgBZtSlwn=0BQ?) z|K14>OHf_wIPZ@LYB|8b11bj`8^P;iLG8Z(mYNUBtu5IdKx-3ing0K?^m?$slH(CS zXq?;9lH-E?q5uDWIx;l;WCY)l{tu+)ry|1yTP3jCCzc!!*)266D*SY0m;t&U(vIo> zKhRxlpgWUoAN~Ia9#gsZP{hjcp{|v{Lwn2j4+HggfZDmg8zAo81uhFfXIfbOW=Mee zeJ8k_ere4RQLFjJ40MMCxE*H7U{Svx)R+1_1F8-@*5LjBH=^tmg7leTbqH#G_U0jI zor7Z&gNZ(5OhE^9wAQeF0mG zjC?jNbX~6p({4xbxJ|8e1*n~G{eLAxM=}Gu_y1Rx&@@ocs0kT2bDYNjndb-32|p_F z{&NUY{wXp{@L<~Q0kQx87wi8F(DAFC;I=0yEG=poGQ9u4I0_0s(4E8+Z5bj!XPJS* z%=`Baa9Qj9|3Bi~er9NVJpBIy>MpREFh6_$-VSc3dH?^x2{B_kB(EtlGY~{Gmtr;HUTJ(LFGQoEXR2a0my9whq(+6h&r6XxbWj3!;K#g86Ny(WO(sYk>SHn zM}{BX|Nk07`w-y%2c%u`=!y5A1Ca7xkzoR;o$SH1v&Z5f!-e{#uPZ?FG~WMTU&VHI zxd+ouPEfh=x_V^+sEq|0W3Ybk|39dW1v*#CaUR18NE%>RV117v0o3*bnGbTK_wViC zc~x7c|Nj?q2*`le1Y2q_Fcxb4|L@quPy=d@Z1fb6d1=p(uu-0Y<@bID52Uh=0aVsC z$1|{mJA=j*pU(yLu^gHhLK^Nv`a$)smn$q<9)s>gVFtO$`_F!G+g*PTcnnYg)}P|4s#s zpMvtE2h(;F@BdF{djGx)ZbNwg|Gxz8Cg|R1P@V*(5zrk0P=7Xh|9^TA6gDq4S2jTH zu>hqh@cpRZKIh|P@89PPLH%q{KC_t5z+sWhAc0!WJuv~vc`$9e0JjsV9Kd3yFPfbp zXm-|l|2_+Di@#K6kg#-Skg)#Gz=36K`VPomkpEHL^Y{!%+=FQwq7Hz%ryzs>Kh*CN zLFG7PjPLPG@84&^ZIOa5eo+1pfQp~={{R0)!3q>H(0tF8ilvL0p#8WVpmQrhWB3)x ziRk7|z=rVEAv(z;GUP?vdRBhO2fB3=ixQ7|z={Fr2efU^u6z z%)kH|gS2*FU`)1TWJ|m*RxntXEQgyK{GL1TM1-v2-JLhT9w z+Xb#qpG@=qvkTmZ2bUp#BfxbDXnq4U-tGPWKiGVbxfU%?c6tB*e+8-z+`j;s2O7_B zsAu2-kEw#!d_dPrG=RqX-p@p;!mXvkSZ?6O>-P|37)^!N3a|$AtEUAH4** zyHRsxfPE8#nDv~M3}C-@N`U%jE}$|B!>$IEJ| z$(7*xR=X2?o|6hpJt!_MTApfo|Jey{|9k)c!RW!jlT&<(0dzKFNbxBK2Ztse(ES)} zj`MgzKxSEL@}B_d@6=>q0L^JQ&SQY}xmhh*p89$JfwVy&VFg)N2=VXZuf-QyLGb}v zD})kepfP>WnQ7kt-=!9xYyhcA0moCz)18oh-%fD*A1nrL4?Gk0{<9N2hXXPjHty^F z|6wYkPxKIU?t}qC&(n7AKRfP%$}!ORfAJ|6kUaum`Ie`bz5oB8QGAk-!LjN89H`hA zQ2kVViV38y2bLE=_t#*FZ)WiLd4{@iH_n#e^AUiDjMe5fYZ+;Py9YtQ;io{r|zvMjM6@q%`7yBaN_l|9{I1 za~C9yJj;TF>vnMZpL~ZQM1S7@|Bmyx3Si^$P&-7+PjZ0#F9XvLNi)y-y#H(mubU}{ zgd@8A2Jb)H!Shq)C&A%|E`QPc&vx+mXZa~mm~;L>GykjipY7l}$Af|MPWeh9kQ)?W zYCz+x7A?=)Kyz8%f3|ai!nb@C*q$3U3z$H83flL-9}0~(Mu&L}OF-j5ulF+ufbw@o zEvU_X?=0p>qQ7(ajN{bw6^{a^V?@EpYviw1@%ka)Sb7jzD2MP8c{l)u)Zfr+K^4ub+{ zJ`pN56XgE-_Qw^VcBVzk3qep>2^vp_gxgkdpDcV8n;pon+Fc9}Dq}$ND-1GWoNRWM zn*Yl{XA#zFUI?hvpVI3;{BsBL(+5wvdDp^3o22l6;VljIj#Oy8LF?a9({~e&`{lVANfZ`Pv z&$XT&;P?fF=TBt@ipt!!r3#v1I)cpSeau>wTyEkEWTC}_Xty^XG{<8(V zCd2#xzbhd9mJST;Ahj_6)*fZw0&1JTm;)N~eq3u&^M8i-|N9@k|NmR!{r~PtXnK|b z>GA%5w-OX5AUiBtUUGr%L9kR{U_&v>h9LqxAN2Tlg_Rsbg7^Q&nsv<072dyBf%{s` zdl*KX(Fy<2)vj`nesTxOtMl zlHr_wCo3rb!p3UZELvWLc>mc9F8^&37|tP=$2JS>e}Lxs6OvmQy#If4g!Ee&p=J83 zLWp}efyaLu?HJA^YBF$mFfh!hpL>A8aULT>{aotKw$}RI z{~sOi{r}@uNZ*io3n=_7THaWCFfhRG0%Wylc^U2fXA`*X-Ux9Q(?mOlGv5FItpS-2 z)&s6nUY2pUQHli;=VFJF8A*$D3cAna&o@c#edBP2W_^J^9@ zuh>C$c>mc5j(@1TSwQ#6*ffFmdw}hjMn0z5i?g``_vT1B2xO1_p@!<>0y| z{V>DTy63wqYL69z_H2Rb8|H-M76$MC?=M2*02;@yr+EMWSM$=2VFRShWH14ZN7^(n z2v{tAt!9w`x*vWKcwPp$=RzgK|HEV4cH|G)SD8<|*4Fa95~)A;Nu)Nm zKnrre27GO+fJN>98#Q@SBHsV+BwFufaM0e%@dC1j?RN<1u5r+MuAhty1>XO!34+&i zfzJcFnhF}1cnKE&zXp*;-{nHW=C=eSY+gSFySL>{s`vjtQ$TY&ptVn+JK#ZODs1iG zkA(~cptC1|fZ$ek-8^F4+OBZRKwxOx#Z_6J%UQx$ZE)u8bkR`350Pfq;DaANX4h6A(f7>>-I$8far zJ$r)gdIko^J_ZYiNem{Su`kfsq#(b7+choE`9S4~_n$T3@jtLw0|V4wS9XH^jF=yV ztcM4O(Q|9>KWo74U+@1PGC=)oP<;*>;{f%yUmpBl@bcmRidT&P8(t~??|9|-f5NN8 z|1(}S{$Bt)6CQLHJZQWM{XF>E#zqD7doR5IKU@Op8#>PW-=N*ez~(UT%LK?6zz6X7 zGuYiN&to8dSqpAoD zjRS(>06lI&X~2VlQQ`G|1_fIOhKA~s3<}kISe{hxWmTw+4S>uQ&t-T4S~q5C%m2S& zKLby#<|l9)qEeIP$?y9N7N9<3{fgHWpuPmCA7s(;RvT1@c>h@mF8>?$Gl+o7JDUX1 zc-EV_4gVP=z~jUTj92PUeXg*zg|0hWz`$zJz`&M}%*g2d|HV>Bxf)pj>ce{fe+jMs z8GJxx3#d%;{{O5Ml$Sv1&Z6aQ9;kfs{sU=OS}Oei3JMpCI*tdRu<`zXArLgq2o94v zjsxER&o8u8`2PWP4xaf z7u-KWjjy-Uy?;Z-B0%HkFEs@eAan8ppgpIc@7jM=zgIBP+WoH2HV(iK_<2_%D1PyfA0YAZ$}-YeESPDMp@CamF0Z7O$q0c^R(pNYGehttWgO5|NJKW7rES!RI$OF^JWaNmp3US?OTU1R7I+TwyK2 z?qKzU5?2Hrb|DW*w|3^@JHuw&v z0854czftWzyBFk#@MUav7A@}z8WuC~fYT`GF0?<(z~dhl^BF+r1E##R|NoUQ|3Sn4|0h8C_^18<2aWdsZ-Cen?f>8K{<9Q3Cj;_>_y6Ca-v9rB&!_>NKVJWU zfdif|xKQTeXpmAu2dEm1Z8$6ii-2s=0|F155{U0>$`5$(^FT9Kex!t1W z9q1l9(7rW+ABz7cdjDAp_P?!y;R4V&y3GOx@VSsS35E-PYOUPi!NdhFx1r(x*!%yr zhtPP}fr`EH{(tQ(R1B$I`R=RtpC#ZqdE|VDp3gvO?4{<)27}E1|7(&x1(4*yK>(8n zwcEk#vpAT*>$X7k1*}ihsI~G;LUJJkv@U|LdrH(~V4SG6@{ITY#|JIIW3*2{Hrg|s z0i8?k*u*#k)MtgX;ldfb|397!RdW^`PT>C6dm-;XOThUGs*lC7i4ok6hqS%lJ9+EX1%o6WEi^1ccHVKU9Y!-me=VVMs4rllN z|5y_022UjQbG`p82G5T}?GSKmV&p-R-|zirF}VDPmf6o_qm|ru(4ZqiahAy9_~fHb@Vs{6(zkdJ^FM`w)2i-~0b5 zP@V|!{(s6B7KWfcocI4zw%)%Fg4Y;$|NqzH{r{A%_wR$?I>P(^zX#w%1KJA!Z3BSP z3C!=HJP&qX%Zlx=JOl{`e{h)v@-OJTisb(d44`%5AUA^Yln2vnNShE`27XBK{u2W) z{~YK2hxFH5gql2lK|Ss<^BIZV!jYMXYau@OA<8C4O&wVQV(k5TeN)W zvPfWvsM)PuQFG6@!u$7Ra2W=jONEZzewgF^dn4E_pf=Ow{R|9~=QFTaJYZn2dC9!& zcRd5BuKqjGouaS|384*3m~zER}2jG?cn}` zLBlHsmiqPwp#Fl2tS0#Gf&aA{ULwsW88|@gHivl(Dxi6852l$bKzE&3dV$(e>|2}| z{_lbM^$Dol0Nf%;R+sK`8^e^ z7g}$F=j8G46`KZ`e}J!Hm~jMj#sp}u7-+vxqdfx)v=4>6Z)^u>-6(MMD7Kl8zU#*CvsiikLx0?vD=adcGG`~TOqkT{wGjzdr!f!d-TOw$qfRm1%} zT@&o*TImYVS_kU}<`>@oPe_9Nu0QYpKhXJ3ps)bd_n@;JQF0hKp3$&V+=Br~vj|2_{5|D&1UwDAAGo_i1+Ww;BgvA+)f6!pCDzyv;%PSpyi_WVg_ap zrfHykfQ6288P>=oGr-nCU8vtLB~oiIu?`e(p#G2JJO&5EJ{<-V>;H@oKzHdu?3n~U zKcUl>ff1w@G)4gtpA7D6TO|Dd4GI?zrfCWr0&rspS@c#)&ulMgs z;4wi+7*0j3nS+**kb5hpyakn$pgk#|G;5LkvC8}R8gTii-3-1PRz$lQ+%7!<@`DEh z!w#?;6Bro4?mWQ2l3e}&zx95`2cZ2U)(#8|p#5;5ums%=xzL^=3^YFCI1jeRZz6d8 zSEoHByg~Oi&YsV}ID0+=>x+7Zj7DXK2&i5j@BcT!WB(v=@BcTz`^tXDGh~3%+V6?r zxn}Eopt}(nDyr{+$BjB*>D!{^<1+6*v%%>T)Q^XhsZ#vq7I<7?!G4A?P+u4{R}I>8 z6|%HJE@3GHBj}!Z@BcT!`MjnIx?cm_ruq0A)OQ8lJqhXSg2uydf%o%4>S_iVNIU#G zcr7S63|c;^g6=qh?p3V--CGOYtD55d{~uxvJ{zQc?!h$aBdF{Em+|$|71n!KZ+Lx} zApjEA{g8P|J9wP=ytHG;sNe4a+K=bZX~)0{jk6e#`#|}}q9rQ9`~OYwI60*LM&6J3 z$;bQ8Oz`**NUit(YfnLA8XgP`95d<|SfO@;#UOca(h|_RE>QmzUJgL>jR(^t@ZGPV z@~%@E<~~N2*NYhvK#9(IF^CS{y%8n?*I3-RzCvjUj|RA{~vg%{=Y{+ z{eBJ5c`+QIJA*)d632NAN0e{<{}6tU#jbw;2XJ31{2z-QXbp@-6@vgMPHSqVL_l?m z2jf5R9xt%ExeO9D`+fw}%=rXbb0*-y_z&#I8U>a$Ah*=YUlIYir&c3)5_pZhrbEC+ zTLv!BIn)bn8TjfuFM!$w9xtjHGNAEl1IrH%^B6$qIQ@r&>kV)@2~`8@voKqvGJ@`O0*zNd%FzknxObe(umPnUy^m3jx*(0^ zT7b*ZJ=);0RLEMvUhq6^Cp4WP%F;e?K1P(K6E3{i3%bKu0CZ;>hs6Q`22dUWms$V+ z>Her?fUH>ot#SX|3$CY)?}7SPpu3_TI8`L8r(i8hq4gltPrN@A{|7d+Ft9kzWxOK) zn4tpNHo5>RgX`!05~;QOu@0JUUAp%$ut3I`87!>h7$1Pnss!b!n%T+~-oJYw>0gF{ z5p+%>*k8_VMH`!%zSDI>&`Upq}+`1?a9O&^a6)jDNs$T=nz8=Z(qKSN{mG zn8P4Yoywq4Q+Y_lgYh@GkF(H*fe$p!lj!yTL#^g7k@}ax)9U{RUIXP1Se>)^4+9@4 zj6mzSKw;zky9erjP`UV@p)-zw1+>2rG*8{VkAV@YR_CQ0L&QQ42EK(H3|#eH4xn<; zrZbMAK)VYRHw*@rUJQ&g;}{C8?}6*C1t5J6^FVun85k@Q7zDh3Zvyvky#N320hPPn z|Nq|r#UZHw1TPOb7#MOg86N6)GJ^6@O`{5fK&Te@{&dhjz8p|m57lI`1GPhBH4$wE zSp5o`XXw;~l^+ZSptKFjKi|!-L1m%!0tQA8 z2BsBIJ>8)3KP0vLK@!%VH!Cn}aQDR}?C46dsoZDiIjAp0#^z6y9S zFp4y@FbFieFz|G@Fz|GxFz|xL6S|i$2td?)dhY#aGPqp@;)lDk*jcoE2Hi=<9xldW z=ly3gxSp!J&kmlO0-vGV@>v{IM^;?|oewq{eEt_mFX-+;idSzaR0b5b{e&LNuV z$-oqLYJ!y2AI1mue^!Z9hA=3A#wKmO7?>&}85F#Kw}Z!Ny6YJj^=E_E_V$3n0~8Jx zEuU|C|Ct1CFM#xT|Ly>{?-tx+5CWwEkpJqnPFH~Xs&yTUD?n#NLB`kH7`*>q1g~R) z_?Hnpk7LpD`4_l7@@FErtzx0b@Bmb2doXof0NrEfFz@h7oLLByQ~pI#gBT1j9MEnk)O&80Wa+tB0%RSZuVke*zC!`5YEYF z2WscOlxIkoslmWBQ;UHKre;K?YcMq%H5gbnYJvJ||KB5tv2E01U<3IR zCbl_)fn#$P_)hHzklC9v7`QfPF>t};XKFC;%+zAwLE`hy)MDU;*}XZ7fp2pr1E2T* zf1tBsq4T5{z~fnvIA?&ap*aUG!@zOU@YwQ0429r(-fbS>(?bQT@8z^i+`4<$gGqqOl@c!KjS*HNrQ`81& z|JO5cc>neSkCS@;{}(k@~-!v zesElc|Aw4b2f4=`l5fNRgYtDhIQ@h4)vKNcuu76-5Q zg5}$OaQ@ex56QFgvk~QWZTusVTKfm!dK)ya1=gE-8)O$W&-R1MWLWwFrEN&M1Fbtb z2Og_{q-6$ZdG=+B_y0dG3$+-+ay8(2&!>3h|Njn63C}YGe}nFq1dS_z=6XPV zsfk(w2Hw9tz~v;U|5X3~kq9UsdH-$!uTw?pBUym@Kwxw285n2UGq6I_mI6}yP{jNH zX>hp;QU^M36lxY&4AkaFlu2j7`}rVd`~;t+;r;(Kc+MN_x0Wx5z5o9PjhjN#Gh_`t zR6X?En$wW+3UC?r6?A3{v?^v`Y~X|RDM0DAQB%MG)E@F+YU>5{FF<`I$2klspfVUV zR$x76|e|9{~HrT6;(5&|Io zwVIv+Ab-|sGF+Icwfdy@?`CjX1N9p~?MV-&wiKwt;B#~yOs#K0=lFr=qz*BN$?syQ zu)eqQf^{9^1CU!leX^SE+7&f7Kx2eW;QGJT?!~%#yH_G0zku66p!0fuH-pm}%4zAf#W9s<^TWsouIX}|CfY6ZIA<{V^ALvbmm{pQuZy7G|k26{U35x6Esaj z>!Yukkn*_)TvvJj{|~DFp>cT{Tu(sa^1lb9J~{~=>wv`l*B(%P1P?P#1_sdhbEoF& zlOVr?#+N~SOHIB2&^nbuEd~zXCI$si`^tl<1#|~yA*f#sYI}hC)v$34@86B!@&}xz zSAy#&6Hs}J)-IHRjcb6$BS8Ij@81q!eV{aL8Oy*3nn%&7j0I9)@+ zhvARSqW}LO>#V-6hpe-z1+S|F?T3ei!^#UkGFBe|jVsioNLPTy6Kb-gagHN^%5l(G z0;ntpl>y%W&w~4ppfg1*>OuRI&OplS28M?g^`JSuGvM{n77YxmEb18|y#Jp8*AF0f zSv35IoFBRL>xqgM7SNgd4Br3$DuU01Y%nmfNN{%YVCVvuC2;jizn+JxWd@z!;{E^6 zNAS7laP^(wwh3g+sM!M^R*aB5?ZMOpiepFb|4)(UUiN^?7V!ClQ4>IGth|3O2DdSw z;!GATQ3e(X43gfz7lYSxL&cdbTB1PvycxZJF9x3h2ny3q&DAGBY0YsSLk{Tt77K*i zz-qu_qzw!V7RgZ$yninTrw@=mOHJ^-DgP{5zFq^3Q+od~1=oep`3CTL^PqfT(em|; z_n%HkpAHYtI!|Q(xn)Xcp|ANlHwmSsg(<%hoX9YU*&04}&$Lc$8 zm({gzpz}vK>i2no`WrG9;57-bFz*1TL(o2ydX~fB{;~HTCvZOul>e=37#QoT*|&ho zpn6ar_m2~}z5}&&LHWDx$mWWgbm%YZYEW4MIxiGdw}!j0fXZA`aC;XT zKA`>i9t<7eJpcMXXss-ZU40Gc{#(!*-~S=-xP;EhLh}1JJJ1~;9!w24!Q~<795V;# z*dD|G|Mp7%|JMKgU11Fx=ZpIPKU{*v%(|ZOf%l(w@Z5>DrF(<-|JRP7{Mi``ACnAN z7|Re=-*o}h*K>LGmm$Hrfq~n4&j0__b3o&Cj3J=%&ii*Qc#IizXA<}htnB4E3;56&~|J6==r~m)#6&N1W|M^`3 zDucjdlTqJ7k}bIz7uvwbB5gq720Hr$ZJ{!dz%=+<*f4Q3h)2N!2KW4 zJfHXf6X1TIr7Z)a^&Ex@(B8UAThKc9|7$?@z{Ub`j01Xr#*9E?91#23z;!Zc91v8F zgT?|uenuS!JPKY@39w{l|K~!J+x2y|KGa$ zGW5pG3hCw z@exp%TQo2zfX-;~VEhLz(=8eqDnRyl|Iq`-HE0|cbmjwO{U2yO3Ij)->*NYhTJ`>8 z4j#*`U-lZbc9#*9XF>VX`;P^<+yj-tptFZS_CUqKuC!`Mg%>F?a`9_CRf6Tz;Fr;kyE)2;p&EWD6e2;M)XnjghCCD$1O$;-;Qy)3K1D zT)!36uK3@f-3pqw_}>CC_oEISV{eQ?>An-i-x7Xf( zY{27wHT4W8;s0;eW&a25ll!j&b?;w`r4J{0|1kyUWr$thZ9sQ)LfRiSh&3?K`4$hR zYET{r@z>OUSuE9Z>&3=b*o*c>kUZo@YRtgNXpO89W#mOdw;Kt1m#> zJ>}r?4^&oy+Qu`rR)gn`ynk0f+7by2j4u@#IzVj&f z5Z$S{`XMOpK+ z7=xbo|AXMZFLcen0q6{1aCj|s@33h34qAW2?ER+^oNqw&2-FV`z5oA*j(LOTI}U>L zD9Ap?dH?T#+Wg-C_kr8`Xy)w!&97M~GHmc*s)F6s&e*^V$s-<2Rh*!4VdV25U&ey- z2RII1Ix{4I<~=&K7`XI18I(Y6kXlvtEsk>;G$3KXa0ldea2urMhpI)gzyj|-Q^9RG z4+aJc{Z59JV7X+01)zR{eka3vhk5@mfb>|j{9yKAV1TTBY5D%r`_EKxCbn4c|EmWB z}|m@h^~B-oJ~%ZB3{jp!xX6Jn!HA;5JU99fJfk z{XqAG|2PLatD*WCgAy#yfbt5c4QK()JKq2Ig8PV|vf7~ul0G1I{}lHAQwMGfTR#A& z9q>L^P=DE?RHc35vf?P`SuZ&@i7t0JJ9EVj)98MGN~e?>}we{9}>G zP~iP%F1V}%l_8+?V*P-DVWu5}p!fgX;QAOe_Yd)B3AlVlPe&jatf3V zpy3VL+sEPkrv@BXjrI&2jqwaDp&m_gp;|6_wO-B@puK9KvwCy27;flyDKI$9W2|^x z&j8*-(Y>32%lmgBI37UZQ@@ja3wW#_d}hMWjo!a|z+-XE^B6?*=YZ-p*xfciLFMBU z{kaS)9p^C==+9+X?>LX)g8p34Svw3L8fG&HG*mP2fYLK4z9+8~SObak7VvlzB+h4p z>xY+)3`HRSfYR1WMTRnqmS3qa85ycxJY=YQagd?u#X^QQ??2Vx^bNX86QmYWPW{q^ zlv5MHmzlEfoBJdgpNL=p#k3)ddQ4~sf)ZzWx z8k}B`>~V(L15SGo^Z);!s3oulwAKWs4%9EQX!+FzRSRC{2O3A3+yz#b1JBEy$l>^F zvG@Ofb3kT->Q+el`5$1R$Z)}fsYC`|uCT-EkK&`CaV$_-0-E!z*{5CM{r@UBjw}`a z{{qFK<2;5fpg9H5SReRo70B5`u>I{47A?Qt+CO3t^ZuO&uD3z%vi`pse1G|m%+((( z75;w*#p&_nBQ3w(ynp9_?FX-cS7ew_tL$Cj!BlMW(jKhlzeP(l zXbnq%_y3)HA!E(|!Ta_coBm%xGAG*mcMdrHg5&uAc5uHMWrDBM8fk@0@}-Nk?Xdm-fkBt8FC z^!`%@?*DlI|DS_={-z}Z^NW|7pmNoD(n~qe8R4vVYBiliKxaBS%t3bVUuW+>W#IN7 z%x=(J0myHldQ%@xW@8A94@mZ)ivqekv z0*eHObnoB&uyO}v4oDm{4w>QoyC2+!1my!uO+M(j26rQ<59j?y4qP7D!0&)uGsmLk zVHl|I4vx1!n&A2ol!ig$Zs4)VmcR2s`3{r^z5l3z>wIuNX<%4okt}cklrO#iZv*=m ztPc{`%f0`UfcsS-z23jGz;mkJ|NrPh`QY&#&>jkSIKszUbHV37f$Rg-IoAJoGJwXL zAo?=F_0CHhh6Kbb#vtP@O$_)lLbB*;&xB2GALCxe6e2J2iL8z{(NunXmTXw%L_Nc?JcW z1jg5(exJ<&h6UhoYG7bVNM>fJM-3YR?QFEsXXzrkqW2XivkAUJ86sMrG z#NhpkLSI#27&0V!XjDV18D!A_n$U!IS0wZ*)oms3X&kxIk}uQ1^Df^1|80cw!Eu0XuZ9Ox zCa4b#$rIrI%uWW-x=2VpmkJJ3P~3vjBdERlQ)8z9Xdg|ZEqDzsJ7~>e$9@Jb?N$a? z$GHp%+N}&O4s#evAmeNd;Ir;Qc@#V!+48>_lrFsgw1CSwP+Wn`2Dx#f)=m|WKN~f7 zDuBf`L2dV)8s7icfcx+s3=AIHtqkuS=KY7A3&3pA^54(PInXL|px2bUQjb)fld@BbUX?M6`f0;)GaZ357Fp3Ns2ctGWH z{ayAg-v8G?(&2t^|BMF|-VXC1clmX0QW|Pk`E4pneXb&&?1CT31}N2h{I52_B=gRQUfEq~CEK!yHig3%M`B zzz|dhL*^iJ!SyI4ev-jq3W`V2x=)LF0t_|@3>$vGJShMYo7}k*T-QwQgru3tD?#aG z1Gp{&&6|SSL^cTw3%vht0Jo_@VP^rZdj&bX|E~wvS>FGDPlehAwilERLFoa~ze&UB z|AXv(sd-YMR#Qr(eu)Qz2UF@(kUv0eZIB-v<}u8$e)|7^NG*d}{eLMDh}lVvpgs{u zZ=>c;iSYjnYM{CibVru=|KFmZIBV3}sZ!th0=zzR@~WMXG^@2!1H5i}E(6EpS35O8 z`d@191dp-7=GH;xLC+oH@c#evB-B1|9R}*7g8bsalsds80X)9(1ztWu+se=~b)xrw z$a&eIxB;zMMc>Eh{kt2SZb5DU*$Hy9rPof-d2Ec1^Zq~S)B@j40NWP`OTvIpcQ?>`aXwv_k(|8wB(f$#rK0gZbng3?!`GDF4d#S9FulNmS~7BlF8 z)}@2SSV8p*q~2wiYklDVfA2rp;I%rSd;;3H(ooN!13D7}wB`uBCd8J3;bkr8>=ou^ zFJckrVSvm5l@}H*jJn>xQNnp3fiwx__bjBmc?=@j^B9CcW`oY90F7ya>KO3Y-h75N9*h^jX{UZ3s9gB3P=Al%Lj6538?m39 z6?A9af7o5EJQm6SA9(-&w*|C@7*x;ARA%^qw9XV9%|NKpgqLUum{I0B5(JZ^+K7v$mn zTN7NK!{-AIFeq6pbzfl7!ng(GKkq-8;I$Cob7~g-{|mCi;sApRRLvdl|NlYffNt<$ zN-_ZlC}=zxnx|lMYoPIW*!)_}e(efS+K1-1#70#H29V#N^KIa;u2oU0c&W<30cxw& zv@n>2wA`!%owZ%l!f>IWg@N0m<^R_opg9%LS&zTxL&heW{{I8{)uM$-+WU7jxPOPm zzdYW*HNgEsQ2O>@N<`e#1D|h76ol1vHM5i}K<=%%V_f0=|1dZ_Egj(FRW_Ck3|#h$ z{{IE7U$NfnzQ8h;K><{5HlJePsGkSAQ-EOus9kC4#UKH?BfyE_{|nHb29Vvg&cPKP zObK7W;h6wxuQNq@|BeCo$3SBO4owV@KE?kf;CyB2@c%n#@8;xr3=F^P7(n+;{RjE? z_kD%{iP{~v`K3`~wq|6M?JPxTX)C!o40A=!Yz z`~NC%8mWH43TlI%OXXnL0P5Eyau_hww>_=^_nW|d8(}8z|I5I0(U9@^|Dbbn{#k(C zz+?(ZZ)uS6A&388L1#M2HKkjse_q%p=qnJ zp@o6R`%fBpOb0Y~`1-$~0cgC{Qd7_Xaz;9X!ApAv0dN_4_;Us9%pmmhf_-;Lr7*e^#*Z@zfajEdM3L5|0qg_#R*SMnQmvx2r{{!$g zisL*+0qr>g432XdLE}&VED{(cELxcEc>j(Brvs?_|A5jisPFiDKLezF5zoLec|L^6h4=r(usJvIxRXUo%mnZMOTcXvP`U@5j}1zfps=xMVfyC%I~+Xj z1=#fBd`R1tWvNYsdc=UgNy8>&Fu71OMNG z<~ywq{C@=+XRaRY(B}L1KKO)IOqQZq`b)J*aV#;1(zSp0^YyF zA$>ZB|KA~T`hUaZ`wR@Ad!TF%{r?ZjhxN~YS6Cd2*#KI{18Qe`|Npzw(&7I{NZ9`e z?|FxWJ+qeg?=Wz`2^=5CK37=mWz?`}VRnJ!(`4}YmnAr#{zt5NgN7HVzX#F>s!J_e zm@_OA7$ji%())KfcsvT!Z+2*6fc6oXo4kJ)gX<#DI2S0N{(j6LVCf}j0Lm9Xof#Nj zdJ06pTCxbx! zDhUQqJ_p_Z1}Z;5ZnS7&UIa?BQ1?xI$;rU+lM7@I1IJ5F28N$p3=H1CL%`)QdV8?e zGq?hK`z>lKXnxH5|6Xu=3R;Hz0k;Jk7|vNF3p#lJUkvHLgU;()z`$bB67#_#fg#fS zcQv@J11?V>;-K-pDDU6Z;69Z1|2^RH1#0FBP+Jr_PWR9L(Eq;{EzC!)@3}7kt@8ry zF9nU;S^op=5#a)tJ2s&8nN9!yS}bMW0~)&n?eq8kBLa@=n)(}B*3}FW9*jr8{b%jn z3?D3#85rxEABlkO@B^K>2nsV$+OcS1KJWcI6x@HPsRr-8gq%;XkI})Rh502Uog{$s zJ7jJs5_}()MFN9{MGK3J_wP_hT>#m)2^mKM>t!*6>IIiiVEd9m>(yD^ynhFS`?sL{ z3lfK#mG1pJ1U!CNQweqlvRRE#v%q8ZAU&Y;DWAptVgN zjEBK}xw^%xD?AtvgX6Q&{y#X3Ypp)&)qR%|X|(_UrPlJJp7lKj7VUiu8lCq4f6O&w zV04)GAF}rcRHuU1@3WkTjCBiw!vy39$lU-ew=51o@A~{B2=1?d<-q$3SRNzEf!hQi zIg0~ezrO{q^8%0C3nJQ8%!ey1T3CK~{|*F?zj*)uk66FJ4Qg{UfX~T?oz>#O6b@P! zSqRGe-76Wmp!2ICAbUW4M2i+S7SLV*>w709y#K_3>t|5e?)^IiT&IH4Gl)NX!bl_+#j^Aqn0xu(4mn5)Xr`2U3ykr(gHeWAyU8c z2WV{;Pp!O1pkw2I@LCs;|14VAlDz-KLel>N2GCh{j5Z03*S-JG1-F+#Wv)XL1Ehb@ z!qx{#r?KGn4|I<9zeP)|f%pHp;IT(&ewP7-jradqU~@rXYSF^B4YbY!)P?}L9W*vI zQ|qJ#s4N7XLjV$csmZ_~tI1$f|KCgG_p6f@VEV;L(7X|NjW4)dYGJ!=kt`VD{ig`r z4h6LbX4-+qoo9pdxcC46(B>EeybYq?!oUJ5>tSIF8ZWGARjvS;2X^UVf$|~LvGB1}kXfCYCtX191=$6%2Ndr}ZdZVq z5eTkFLFa)$_(9-)I>gPP8R+JM%tLa2B* z7Ph9&1Lkj#pDmKvZ+riV2KTS(L2I;s2TTOzNl>_h__I%*bOEtvp9JOWKyVy_=JB9z z#tJ|A>9|&~`4^KcN0@a%=+BjT60pSAgRLD!0laS+K$T{~YkX6XZJD`~N?X z6F}Z(Y+wNG%lQAlQBx4K?h@3GU;*9JZtL{_ucepAkD4rxbv4QCC7`wfNCOOm+6kcW zfuz*2xI(-vQvTfcP&M&-sTZ(ai*x*`Tm$ z)I1phDrXR5_v}Bte`i7Z44VJ{!|a9F=MOFuAoc}eoc{sJt5A1O#F9_vShR3xdH=}+ zn~fTV|3e^i3@1Tn6@bcIR*M#nNbf(9;5GwjECU)=;4lV-7ZG+fc>jT{LqN6b-wUW+ zp#3*6yViUEi2(O!u-Rp?fPu?{DG<~bDwKcBAPnl0gUj{3{_58EPNsmydu!@`iFh#X z0k1={sAu4^Siryu5tjmqgUeS)y%LBq{%xtCz~I3Y$O`If!PY?jRAeZCu7!iH5&pX} zB$<7Oe)Iodj`J9%fXd!RO~Dn=xC70%GTJ|ASm6Ete_-fj$w?#nf#6V**pfm z3aa_n&NV-t%B!aOqgWzy+?0z;+&cl)ZwS>7ZnuNhEr9Y9C~tc(`6JQ>bY9DY$?q*_%o~*6K<#MjdnY}> z_499U@Hz$W|Gy{J)U$7ai1~o)0?-<6ka-UC7-F>NGBASnW~)V!esq0?1l~ z|6gn%<}iWIfPjQyT!8ogso**W)DMI8CBfz;3m&m(;XLU5Ckv_VH3{6t1ntj3kAK)0 z49Jbp@}<%H{}k{(KWG~Vsg1$;8RFJVa6E(7kRZa>4}4#-_y1|&b}2L+L*@?tPXx~^ zgU&4j-OB_DPtcsS_kYNlRNnvpBkp>I)*GNY3+f(Fc?Ua_2Ud4E*nrO+J?Y{7+Y{Um z^Zx(yss7^s|3LFOp!qFOKXjs&;0%O1uU1fH0?H4_WfrKuK&bJAmQz1x>M#EP)nOj! zT;|_lj!qWSQ_Piy#h3sg&xkXOo+ks%1%TEAYR?0&MXJf~Y=EX|#yiOMvG;EeaGM%hXU?#w2e+&LS}XvqFY;HH z)npK^N%j))VB7{)2U?2(N?)L`0Qm`=?pwH4SR@Nx@cxqy&KIC?1BC^se70y%U;vfT zp!DGVew}?UP)z*^}?3EbAtSwJ^G>bB@)QcVx>9hdvsWEVz z_us{?p<#j5PX?K!Dd6@TSKa(a6&5o}!6AS`!{LAb8`mq=am>C(#e$E1hTFXr$vrjUpg6^HPz86;sIu8`o@3+1u2rlR9(q==(TwAz0A$vgr!R10@ z1cQq$LvTPMho5h)X^=>5Xn>xjCIgEl>@IqTe@hxY8Cam_ja+H;1g(V%5&@O{p!%a$ z^OQ)X8iRtOrUC=#eiBgK2AYp>ocAxs<{85QP?`eOQI?Dh4HnNG7(j6is$)U@ZSVi< z!0l8>nE$f@kIhGe&94Nlw*c*{@%}9Uj(?Cj;JOoZukgHoGM0=C6F_ya&4PvnpnCA9 z#{ZWIOB)zL>Ol6v>O;^yK1lX~>w1uVj`RLc@&5n!N<$|DhxLDG-T(cUNWJAI5l|e~ zbSjB>FmA~OOv3v_oktM{J(aJumR|F;HmzqF?WJb&;a z?hn&$;r~Cek%7a5$>Shs3<$Ol%(~(K|CiR_y$2m2dmQF6*nsK`$a>hXnKd=+TOFDh zG(c^-Mz50z`dy$tKLdClPNU{Y(0w*fW$l)7!w@kg3l{q@nB#CjU}^sFfjT!OahBBdoVCMfcoa3v%q7cTo!@y)I!aZ3-mifJwg3pP#NOEz{q01=s!4rS?~2%2jw@AJ`cuC;C>z` z-+}nx{h0L(`W}p%Anjx&(E0EuXIMHil!Di&&1c8~?dh~gWGDsY(OP>ikryW!WL~^v zP+7>ypwp?zp!eex1B0a_L+wUJhSr&i4DCN&F)(;AZUWc;p!ju|_rIW1k)gaZo*}Qk zGXS&>Fu`I01DnNshJ4UoH9ae^dhl2^D7?Y-?IZ>T{hi?TOA=7EMi%u9@*a$vz~v6e z&yAWVXMpNYhk5@l=q+Yo0ELyqw0|2M=KcfSXT&xUbXWZUe-)syEzsHUwG$c@Jeb^J z>z|n$pzEJOaRJ)jZ1I4B!Gp$(>B16fGy9^AVauC$6gPsQj-tTWc=cETH zZoPjyL)s4ez-u93d(av{ZDmj!<@eE>3x1zuV1TLxk41sfHYneM+Np@WD~uA}zj?v! zpO;$TyH!4b=B8>j)k;8Z4$xjUOU?iPEx8y3KzY38nRNxIKLa{H@1+I zh+Y3fUeqxNSS(~Hv1kxr@c#ejAhc~`(5T2z0&)kaZR#+W0ldD!Qj@O%R387nBM@Qf z6}RE1CwSe40BHR^D4sxb$e=wa4)gx~v3~GJ6tp(b`oW!R-v9r-0p)3M8J{e8$D)Pn zz4xC)@VGrFEqMR`2O8U1;KAgIXx~BCpLsC3fX?}Hv8{K4n}%448*5@_7c>JBJhK<-Gf`okat z8kcRp&A!m@mKpQsXd}furu(?h4R&A4s1E z;}P&!q}3e;ORGN&YR%OQ3?O?zZUL>|0GR{Y&tkEZTMJ^wFAuRvOzfI&CiRDZiPRrv-=Z*2fB~cqWTyw?5pdqpo(*wV{XNjS5U843DG^LJ9R|j!Q|}vL-D^LXpOV=oYM@TczYQG z-j}iiROfjAUkX_-u^5z&8J~dC2)G<<;kE+Ro1n7L`;Qm6y#UHfpmN;%w>^0MhV=mk z2J33U8KC$D$$`=xXuVIPJ?QLtka-LS-oG8deGsr&_dsWV)-;0Z7?67K+J)ct;I;#( zZRq{m0X!BBZS%>1+yZIuaaV)J621RG+LfR=D#v+@7NGJ8v3H+)9%zi;`}a3+Jb>1G zJ2o+jSl2ViSjRKygX5)v!J$6=b_Hm!yv0)P4WM$-gYgi!t^k<@D(fKa32rsenGB%( zWU0tdQIjbpqR_$sI%d_90G=2o)mV@9nILs|L+>ipRmmzLA2<}5b^sfPr zTOiqg7RhdKJiK&d*zwYafuYt5QfGqh#qs{l0WMcT^OT@94p17jNBn~alOtl?6Len7 zgUJC@r!#v0f4ft^8QfO@-NOqyLt-Lmo&4+Sn+qWKcQ8Qr&YYa_IvSED7T;pvslW9} z1hnQ0)E@(t0}072%-;Xo!EJR=yg4)>*0))-aNmIRm14kc8L;14c(|bD*bDDJG2rwA zYKwr%F%Kq(5|EkR|2x2QRiL^NR3?JM|9=ZOtUzh)r7c4ONDR_{Y5~U^s80$yKMu6V z19}f3V?r`}gZKY7a2|oW4cr&8XyMU^x?zX+pJ;HO6zaAl@BjZ(pl$%`gStTmWS{r{ z7Vx|ulG;6JZUOf

Ej#3L}JDK=)R(g6%?f3)mekJnfKhiUzlHq2})btsj86r5&sf z>K4d(LI0b<`(!}lNvLjU29GO3-LM0+j}+t%P}>r8u0TRED}(p{R`7T@)E(eGFHm=Y z#?N zlwLr7N=Rm61kINdd#4TPJ{!=z8Lt)ppTIT8?*0G$hlYC$EcI;%Kx_Cy8umf~{?^aypwfA9bAcS6Q;{(|T3Kl86)D^RDsVi11(Vxr!IwRA;%7{V0ih+UQr6B`H z{VMR8k2bZQ0RgpM>{~1i7#OV#83gJldoa`*fc7f?zw;`HfkS^2sC@-pQ@a3kj~bt_ z2Loe7ql`d8tv&k|Q2C?Z0aC+Y5bD8dS830nV9UX9Ak>pV&62}`q2|<&fLbl~Ew!3I z0w&4`B-9*Z-vZXxwt&I%00V>L90rm4XFmcg4=^y+|6e2ms#9M~WMHt#XE<=`yU)Q!Epr%Vnr2c=Ei1+_C$eiyw28OyR>|5&JgZDhUrmAag+VtVIi-AE@o%{l^i! zCKuE;aG1vcTBid(e-bq20~+s{sC9CN_y6ayNOMI(NOMIOEaowYfYOuq|J&d(1V}!E z+FuV^cfgnI{U;3E&hh^LJk$ICb3r7tn32qSU@?zD0%{hxErZ>xP;mL@{r|Zvr0t== zV6l|13vw2eF+AKr=@jJOADJg7fYxJx{A~eo&vNfSq2TdTP{|F0z5j%O`^BK~EzrHnaDPL`9HHv+JeVv@ zL1T}gb(x^CJL`Kw8lZK%p!;bnHN{hE?Yu-fR)W^g*@M$XqdkKJSUk>4q|=LmN4twb zq|)u+layl&PN2KE8|4{fLb=%Y6}mHk&ifOvPT97|#IO<01nx&(e#51H|t* z$-onG>;NA~Z^AJKj*4Rp3LyQUykL{ScmY(tBrLrE8vAESNDg7JLhD{|djygu`1`#71cU2;&^lbuxF~2%j|Y?aoZo*LKxdTvw`hrH@cv&1_77-Z zDX6dM*!2Gfq-|0SPH&*_fz;Rh+d<}f{|N?pX;lX4E+7BNH z3Qy2EGN3c@K>ZC+c)nBtuh;yCyvEg{h5u2*OVGJKw%~N}(jKx77PMCOH|VSi0MGk^(g!FH z&D0VK0gt(%uK(rn{`D8!{)O!GH$$9l1oI$)8-L_Si|$18?5&VY3R3u>RhG-P&y2s<7THlhk*&49&NouIz1V9 z7jiQ2)kXwg1KrID@_$1;gG^2GA(0973^Jgzj6nJ-HN;bDWt~JiPB8Fjw=oDg&Smfc zow-`;WngA=fPppP7z0zStAV9s6N3q8%mZ{^Nu{QE2WUO)LJtN$kh!3;9Ap+~Yyu{? z;UxnfC=R^;|5*s?r|LKV|L8D}aR}1~fXs#YX`v?rUwzjHP&=ljVZH3NX}n9$*0N z(~-Z&z-sBh{G$HOCy_=w2Buog;AtRpKxZ_*jA!5g?Mtyp`2TmJ7P!pi0F{Z}|NpG? z{{QcU^*shga3A^q|A>W-3>BU73}T>hX;4|S(2=2Pp*({KlyA})&mgc+k)cJq3v@=o z|0SR{mUb5d(?Ugt8pzo1e}{#N40WNJ>@}eM3846dncu0&z*|4ZOT_#CzZQ#x|6gC) zGjM>`K!e-{IkV-DBqSaUz->@az61H+qD8>jqL#tH`;Q;EZ{hv_p91JiUk@f@#C`XKxfky8?mf(5;q5cuL+*xP~ z8Rr4nWwBIXHmE)Z*$uJ_v_|N~eFl(S;IagKz8JV~|1b<(HvWDM?#sMXWY__6Cv1!n zB~DnF{LrSkJk+!TP}eU*3N#z-&bnGi!~3@`cs>zSmUe0ig@D!ogT^F5=cRz`v`7G*3or24`?n5w z&JR>qI5aVU`zE0DV9_G*+xo!&@7{lW!0`_<*Za2~xL*h=OF?1a!DJ{9zM{o0e3hHs z=KTyJp`2`XTAd7>6XO{KX4*4|IZkEJ31w%qvt(dktmUvUD`aQVaBO0bfTUxFJC1W0 zwt&(x=qw;mT?29#XwRF)QqKbxErN0&cXnD zhyPC|{AZB(ZO^~~D&Ky`gT`CG@6}%nUN2k$%HyDRm(8R9|7WTTg?Rt}_Xl#9DT9FH zGzJlE@ICPVJwSC3===&x1qLDS|NlXA9|E8=BVm4m_(#AQ;vaADcm!zN7~Xb)j-z`p z>HGdr{3i&CN6@)?p!tuVii{Z`H+cV_2p)$8wFg1>z(VG48N@(ste1?886dT=xe~`F zmLJ}~zJbFBlrJG?l?vuU+NT=eHachx9jGn>*FB3F7(nAuKQeBf0PP6_g|kI1gN;Rt zV5|2ZFL3;W)&SciFbP;YGJLREz`&7^9KhiHzY^Sb`0dDW!(QqCKYIodCs4oK?f~Nj zy9Nd>y95SS(6~6LOt!WZ+>k86z>)O*0z=ZZ5C*FS42(%r7+8{u8JMa+iKo~pF^JXA zog`vqcyj~jPIB#5P+T$cAfrZ|N0Np`qeUE{op8YWBUKj;iJ0<~88nM(2U;vF1gUW4CKLFHE z1eFio|4YFACs4l=!Y}Itjcw{TgZsD{b+MB~K=Xdhji5cDUnX`2G4O)=4WKdKn&jYV z3xgQ=Kz7z72Z?kBG4O0CV&DVSU5<1Ai`1M6kB z*!1s<^?%Sg{|umWFjzosX;2)ahQmJ=@BjVabOcHdj`RL8faEPT`4V1#WRS4F%fJH~ zH@92#{~st`Ky{;C)Bk_3I~f>YXED~_{aj%!@oA#fR>2F_mV&RXz6*Y}nj-kus+hOS zDoBW_(++(0-+yo(0G<80mw~0z_WvLKPEfr3ov<L1 z|Nk=qi8;*sZ{z*{pN4iPgAC~YAFBhP{KlvPI&%?PZ!1{cXJ7=&DKIdD#3A+d1<)9d z0_eVwg>j%dHSii}P6bp}gW?jD-!~~Tlz_(dEgBh0K;@Ek6a!;@6#EvdYYeQNW{^61 zqas6@_y3=%4cGqv>Dc!FH)w5gO@TCMZx)C5A7k)1-GYM*B@01k8!cd91f?s`J?yEP zObj8%n&fJZc~^k?Mc%)kf%}x+|Nkd|&S?bIn;<*A|NrEyDFm-cbgV?HQOXVCE`!SAfh+)nsHqG8f#x0r?Z=evls*+A%PJ?|hm2Uu2;@I1V@+ z=l;J_chbYGPy<{8e-0?@5#jKI5t0V~TcGoJhO^g9_i9p?RK0o^T+FzfqPh*|&Mpqm8>KX};v|97O$Wilu(nZ5rQg6kyj z|NnMaC^CNVVA6_!m#YGhF_xT6hIjg%g0MR@Cpv)68w2mT7ndus*u?|03|%7rOoEdLeFL5VJ_Wc@d`9gK;u=4Jur3GJ{D-^36KX zI3{S_4!Rj0Oq!D5e(@s)vDg1^X@Ku`0-cSq_m+nB|NjeK-)Bg$zW0BDr9DGJ{mK`h zGFJpthJ*T>pgPinNmB#dRYt)zu zni~eqhlBRBA@&}2f#*&@eO|{VMix+6)~I>Q0<@PIH17ne??Ce!+AA5D9p*9!fcpNR zvEZLJ3=FU5Fff4bMt7XcAOM;pfUM!ur~#GD-v9rd1?}4a^><#{F)$=*GO&Q|Ujv!n zsd@7PWX&~$0H|*YmIL)s!D|iw?}6&S2pWfTZ2G_AcO7`25d)}y1T~8hWY$7uhA?P( z1~Z58r#;wBp#9QYplX?r)H*me!R=%MtKAE_)8_wQhk5^7y#N1q0QuYd|9=a3+(GAN zKx+^|h)b&%uD&1faS2j-@w2YehIL zT7*IOEg{ZWgpNCb+z1+T1f63F>g$8XJfLn({E^5|0p8aNIEX;(~CWT=~| z$j}5@EAZ2i;Ra|NVWBcZ2sG|^KTpI5sixc>j6>E}ua2ARbJrh&%qE`4ALGpgaKDQw5Ei#@8<$J{~b2IMCXCRGnmS^%*vT7gPpBsQuUxGU;PYnmyBH)v>th!>GYEmgT)&Hf#bF*pO`|h|2)KVRm!SZ8 zd>oWsLFwN59wg1e-0l5a5!?oCv}X{3rQMlYpmeJU?mvR=j|aII)Mm735q{$RM;n~R zKy7xApCDssDg_`KrM!fuXHeXFFe$$Tm6@Qvqxb(TaGnB{RSwYn2I()0@PqQ5_a7~A z{||Hq7NX2l{sA6?2e0eR0@pX7@N#VW54qpse>ynLfZPc+%NuGIxXlS#(+UqulyR%w z`W{Tmo?y4tN>_L=_JRAOkn$K*9x^b1+~C2aTml(~`UR`2Ux3yDy#9YH0MgIA74Z5# z=zRD83lL>LXdmbQ1E4id7T~hJ7d%!1HCqI&tiNDT54wx(C#c_p+4P?w0+bG4-@6rHEy>XEdL9Dua{9j;c2dXc@<3iy1Qpg#HA`d|A zMo8HIXa&_JpgA3IJVV^S4piQ6W@ZQj?bEfG$G{9y>%rIy-kSz;2WZVY=nR?qd5Ojr zeHjG?M$mXMNDruAI#Ww%iuZ3>aG&_4BEt!gIk2)6q{gv{MZ){nbMW{dsGR^F*E{^V z!g~Mz89zN4I6&iRFG1&ZgVt*OmIbFlP#k*y{}u=d3r2~K`~P3U>P}GHL&_pio{WOS z{mRw{{(trUqXr&VZnXdZ1GK&cw9flQ{r?XZ4WP3Iex!oz2D#0mMRbbyZ%J^u>HYuT zQqX=!P<;Su6G6(U1ci$yAIsfQ32&A@BfhVdeGdF?fw6Mg*E7YL(m$r z-_nr&js5?ZAUkK;fc6;6fafN>|Nol-5_=uPu)(^9VTT7}CwMJAsH_3ik24Y(N>7??q0f$4MD)4+Ron;1Nxeg~Bk0yYT@w-S;k z9`OGE%MvQih#Dr}13_kk#+JN)OGC@re|HwzF@%Ba0foUrJBEmj_W$32#2|gjU#*aM zWvJ=2|NjCS&L*Aq|6fAc0w6t!nhcDf`~wvSy9Xp5s>xsj6$j}BiDT2t1XTkv6Ql-g zCaC^|ioXD_x0}c405TuSRsi*7!TCv%p{!Gpp#;>g1dWHzwEF)a)Sm5F$WY?J*a2>j zEOdmZv1MSE1hvsX^HQL*ED|{q7(nw=wNc)B$a7TQ|C7OO3edS%j!g`I7VKk)SkTB& z1_~$d|G#8^?}5xgf!Ze)EeQtR|C7P#85BQ`O$<38aqs_$f}pm-g8l#BESUfQ6-4jP zhoE!`D#syZrsyh*WKh4%0-S!J@dge9Xng+j{{JHrDvlPPUmHR3>HS+0yoL=@PX5vH z{{NQ)w3gdp-oH1XFbdUV+W=Y<2^G762t)8Vdl{%K^#1>E4^(~!R8Jo0J~wb$`Tsw_ zLXlCxgGojJUQWTs@TB*G>*G4<3Q*e|G*<*#mtD{TZlC*r_Kt%3Tp&M#>UfJ5(UaDD zZ#j7XQ38h-I81&^fak&%+A{=!+cb+`S3ue{5|I6G4gbG3+A}0T(;LqV@Et&3T0v$) z+GV02y?={>=b<6xM?AQV25Jj{=Z+WtfAJb+{`eQ79nTEuGkY*eeFgagA%!uz)<*xjJEmqQZ+ zq@4>sw@A#``;Q`Iyf5MZe@Gug$^vvZSG~*S3J=Cs@OaVW{R|1e??c)Ev+EfGX3u8` zw7z%qg7rRz3D)-*7C`(b2JWYT##b%v88Uv~XUKTzajW8IJVU`xEd~Zq-Sbo9Rz;_l z&=lx+yaTBH3(^azi^Rco4ag1PxN^jM*2fEwKJVXR;4v!D7zXG}b9kC$L#)|{tk;(W zo&6IC3LjX%sOGkDMa^H(c`DW5@nX=rUdJXz@SHtbAKc)jEdxWn{pkvne)t0h2GCvi zulF)AfaW6{=Q2n@`{5f9YsMvBK=S{4TWHy7Qhbtu1#~uiz58X*{RNEGsox)g(g{S} zKV6VIhj|PQ77719g3bhnh`)CPi962wzo7UO1EZcT1EXUTg9E}0_6Gxa+vpj4Jgk++8z?Z-hbr47!nAH+=(E*8l`8@&G*f%7A%>;;8wLh{6a-v494?HouxVlDxj+ai(R z!NBk(QB#l=VmF5e$W4xO*b<;_U~`!FAKZ4gXpz3}!N6eva&MxhATLyX3rIak%yBM* zL87K07gRg}B^h72S>D|!Eqfz*HXU^(#mWs4TE zQ=l^3`;QEGZIcHB6X<*y=$(2o;PM=jUYVfxBSwMiKd}8R;-a8Fvc&?1FpETnbsmgO z;J9C~kO6Yu@KO z{@4!&$9ex98Wu9F0F~q3|KHvO`KLZgN~9)J3fzaCkjStCRPR8?EYCpQ>|@c$u*ISd zG{#vE9yf!;BZCUeERY`W|8F~y%>$YB(vl&e-tKgTwI-;q_HTpsT+m(1|IZ-Is|BYO zhLa4g+Z1KK1_pcLI`na618{9&~RsXw3Pg zA|nT=oPqUW9Gh4hyno$-w68&D7W@wf_jMrVNv!q$|JMO@XP`|2vt&pMivlE#6oS{c zf#L+3=NY{JM3hR1$f*-7aSj!3Jm@;6&W^w?6q`c6tGBS z*i@_K1zzto)ARo#@Bc5LV>b-oGbX@&wFHJ+ptd_GuR#0vpfd%TKm9RMA}(6Ii`5b=5+H2?2~<^La`_8j<3WRP1e7BXzINEYg_Xpz0`{YM9! zcENG7fZ;!+Z}oo)XxswiUJu4<@K_-v>={JBYrFTouCQJS$_xLOfcj7%y-@c$RH~kT zc9x6dx8XQk%X1|AO4-1x`y+ z55510gUdEVT8aSkp=n73YPXX2|2LZ6|NmUESilg4ng(jXYhpVdGVJbjWZ2%R$gmBP z2E0IN{2w9>NDD&Kz=V#647;FdVJ9>#>;R>O1rHfEAku;ucz&njAj3BNX+gUYl>eb= zVH?PPP+CAr2P+mTGHmEx$gmaE_OIUc{89B@_6Lsh7?$XFI)LKs1T1dt6&P-T;y2lH z;y=uBDp0xj`-=5F24;&!h8>`?%!9ECzP`Y59)k-)yb|2@g~S7c4ybPk+QSFxtAWZ? zkY4ZqUuvQ9JdpL$uTFx;a}Z-zJ?Q!@5*c=Q|Nr6&(f8W}8aMyE|Nl#Yvh}_H|BHac zwR9~gyuJU3g4c$D zm?^^rTJs2HTY=8gfwJd;+J#W|1<-m92wN7k*AJQ{RI z{}0+n8{omj`vlrvWNhGo^{;qAcbh1J$FmkOh`ru>s{u4u4;s?~&)q-z{|_`a3Tmrc zTgow8OLz%cec!EbbxkhNY7aw$)f|Qh&|UD3^B5vPbJrFL3xLj}y?7-+{qOrZ60wRTc^_4}km6q5h{tVzBkV!fAvC8UbQ4y1RZ zJwwPs+yDPSV|^Zs72x`)rWo9oY5|9=8LH88|e-?lh9i0JX(IbH<>tMo^u+ z(T;(k)1HB8rX2%Q$9@JT55{tETLL5oT8BF;lYx1mJwwPwJBAR@7~`*f3<;nyP0$$a z%NT}^pK%NspuX5o8-|XTF$@Wyxz1nn84`ZR!^IQ4|NmP8k279aoN4mPC;k6tJ)a@Mx>{c3HE3V57qmU41!_+{0F^NX2s7j(KzE#a{}BY&3oqjt8m;GG z(+4VV{_}wDQ(wr%5YlmqfoZ`i1_p~)49wv2H-UlO`;Q>Fy$qgLI0c_WK7v(G%5Bix zKS&R_y@aL*TxLMRM7|jkCW7Gf1_}%B|9?PpY~XPf%lc1}Wr_x}KJc@8PN{(;xbfyx_;7Wuv2e+0l|wV=43`~no_|3sjD!v&yo2teW! zJ#H=0?qmpbn8%QV?gohcfoS&ogUv*;AM789{eL0-n-=*$AUAmb5dg zZ-w8Wb6#HmV~Dh8`u`7NAp%r>fb>}3XK47n>XreB|9j;v@LBf1Pu&8`|2}yu zz|x*!!B4GQ6(ISaTDJ;7dM0p6;`J6|H|7lYTGtgv77|DW|<#pN&R85-&r ze*l#|2VUAUYyhPb$9W77KxgZ{Xt~t@>brpUohKwGFnIqD0Jjk=6&M0RcA%$sL>@=a zV?MBT4*xA$KzZB;-0y<;kqOi;1)bH!Y|)~4)%y<*I7~el7#dzGGcde#X5avqW6A#) zfaipi88SfU!+`ckdH?zk?$3Dt|E~d8yX19+1$MPyw|oEpF92G%3ECTPu~cy%c-`i& zf8e+Rx#vec!v@gWDTtc?|1Fj(iGliVP<7z?1{AJfwVAhOfbI|g-~oZ z(M|!kot4r+YYx5t@PPLzz}7T?(vJsYA-K->{(t`@XwKWQiJ{^3T?S21e1YuRMs>wEuySlTggfYuB-&SQuHg$KC2{e2Xi-a&2wozo0TdmfB=@UR8#_j)mp0o3pJ zhuQ}Y1CV<``NpC}sRPpX;|8aH(EeRW+fRVW`@a{s4F=6C2N3g7UJ|f*G4DUz;IS%j zo!r21%OY9mfcJl2a96xO_a83sx*A9w&-@0o<^Yr?A$9RTm)G|gI6&bB z+7AFWuO)th_kS;N*$WA;|308F@&4})>5oJAN?9xg`wukV23p$(%DRjV(DE0wJ_xkF z0~AK^H4^_l!Q}*~UFF!s06M1>+Q;$)x3@s<0)-)H{SY|L{=0+gRghnxaR9AbIAQ8R z>k1k`YbHFHm`y-;f`Q5Bs=S6WsgPfABs;(7N@PnnE`q68Z<`h zIFF$PbnZFmo;Qn!;QMh|ES4r50EG!?j0AMn{!4oX3DDU-pnDB}Dl&9{?&tfd$S}eC zw>|hgNYMHNh`Im3@d_Ge1KooI8o&R2pMm40me38*+AR?M`<2j*-!Bt-x> zbsKp9IstBL-RV&L%p^$(oaK;zfm|Nk+9XwVuP4<<(F{kF=6-hVhmL3Ibn&ECKMf!Uxt z{!q@fg{L2eRB-xf`v2b=biPHsbOmS+31l7Q|9=+A$|<0I8Su38haD2W3JgyYHJKUe z=X*Ff&S6lnh47g`e22LV68SF~p6GY7GC0ly-vI&I7ZmaOE&~swzogs=>hE~}VF#}- zw^+cS08TgHy-7LXG66KN2wF=3${&z2Rr#FvA2x8AW|P41Bq6!^pZEVirQkFWgS?K7 zslxl$F>rZk@5CSmo*#(1wZghu=mxm%|Mdr)cA)WgqkiQLP@Sg%TI&dv2hab3=UL`4 zSU~Lp&0S3C^kfj!?*i>1V-R@h$)Hfb4;7Ai7S&0YwaM_^#wsK`+D`yfLHXe|P0PX6~nh6&#P z|5ifFC&-=C)u6Mt#lh_?aG12HFoV*i_a8}con_PD;tDFq5?X=-y#I)S!xh8_hixN6 zh4&u`aD56A^Zp|N-s9-~|6j&TN6;Dk|64%)n3;-Tb_FP&UjK!isjlJ)DxVCw<{=*9H|3JdB6*T_f0S!w=&|WN9 zSUSvOuz2ao0E!F7`uzb8ptD?lzhuyW#LI8++!-`pRG?;o&dm4&3V%pE{$B%%N6>gL zsJsP*B`AzRVf*_b!-ScN3>7mK87jU1|B;1;?H+Ktt7g#g{v!%0|G{lnl~3TX{r_(X z_B8YplK++d{|A+yp#5OrvV`$(2D~hRt|x`0cU3EB*)h@k4-2^N_5L3ZPKOY8F!(^i z>;Hd?7S;5SWELgwUq8V0XH6!kEzY20$-u%0s$W6(gjggC-LQ0K5O88(P_bxWcw&*v zVB!7W72H3BuTkb;UItog2QELD86-eu%u5ih!NBlSnL)x*lL2&YGh+QPbnP^(ZUfCn zgW98@dpbaEq=aMv2J8PX8KC}X^!^_WZpVPr)2|=k`72m|2qgAX>!pDAub(sF<?s1C&N*+6#czXfn>U7htwjVDQ*z zFThr7`AWpPmO-Pw>XyjsP6j^xISl-uxk!aQ3<4Gn3<{w8-fF5JiFh!kf!hc*Ghb+d z&&Nx?U17bKLBNAC9XuXgzxRU!=$v;;1qMay{{rfuJqnf#40=us3?1P3Tp+*z8dn6x zsrP>uaNTPIp5u8bVDo@sgG~eD3rhwDkA&v};4@+^7BDa;w0Jp!+7aIW9U$!%n0ip# zttC;x`@bW2-VKtT|MkGk1D)64{r@j$KW2q>18Dy5zfW&G1EZzZ|4X5oYVD;YRKmL9STS;=MxT@wJFUkq8wW@pi&x&&0mc>iGlrwees`Tx&Xa2Wz= z+kp0&Fo4=LptSK)^Q8nRzCm>_sD0!8+YFrdu&=2;0B+lZ+oy~_5od!z)4d1d4^aOv zu%<@30=(aQH|T!1XmEK62}_0r)ya#Q!sj)}dH)swubr&F_Zz&wDx~%RUv=_vCGXz? z;IX-omQ z5p<@7HMlHz$;eOvYVRV>rdK@&4&&ed!Q}?1Eeo;_*$$As-v8~uYaAhM^@sq7U3TF5 z915*a=~(gb4$XnlYOV=}lM z3Ob|ery^s3_y0(6UVzxcpaXIrNKZmb8L02X;Qikg9EPAU0Ev75w+Gi5FBKUxK;|Om z13~M<_kqh23q{5T5616^_2JO9^q~F&3GM`k36eX(W6^oF|A2Hbx_awpg=*xk7o zye1Fg&TkjsKEPtIs*q3XQ2B* zA?E&rwSBN-wFyh(D(u<4ngrYQ|spe@84qJasc9% z4-o%@?$}EJwP!xpfGq&sX$K8^Sl)mAUl@Act?&WR+G&`5&~`K^d@PW{#{m&OKf!H& zQ2c`Y0$#%gN(&s!%e?>peE|uFzYky9|NjAUYs3EkA3$T`HV+s!SaSTl0XysVr`FFK zpg6Q>U|_b?Omcwe3kRn|lrwoCd8Ezz_fPPAF=)OHWVZ+7C&ZdYsNX<&ACx~pbu*~{ z4Dze>JxG2*@}H0OKgfP??_cl0`5WYpMor-zptNG?B@Etw4;oVgiNDkoK49qu>05)u zAmRKTJca>vhX^QMCfb3{cKNpuY3&&Nju8*WkBy*xaiI1hWPIf33F~{p8$ja;*7Fz? ztU+s&e!T6mB3naQyyy2OgXEU=RS;T_ADqUvI%}u-E?>6zcbb=WHNzPQTuP zG43t+$emuG!x#~=W@V+%A+0UDq9{SVw$Ld=gr z>o*U^58$(3L3fCGFz|upb}n_0A|tpnvF z@893SZ3cK5xZwX+ix#y%-oL+t+tr|Tc_8*I9|YI^Fd|D|NkI;zxOjRywnmt@zb7x zUZRBLTMXX+O~7kyAZZ4)-pT}=PoU)qQk|<_>izpGv|Rmt()s}dBPhLr+~L9aP6gyQ zsK3^F|NaVgH^?n8KVY#JJkEt=FStI(ZtoXx83)QQ2)A=EdH**C$1}_fkej^!n}FAU zLCpCNz9RyZe=J(m&wKy=0v?k9t*JqeTMx#!lAv-18rBCu^(?5ov9x0l0G0JfWxNAY z86SZt<3EGPYe01vKfeC~)!U#j^ZqY&5R{HV`LKQ&Xy2ClKTw(mx%DTg9|VfK ze+&k{Uomii>I3iJpTYSbv?c@Yc4kPw%7gJuC@4LG%5P9P11i6*_rb|GOb1ue}71&4bbc{<8Dultw!S1<*MNmYxiZ6XO^Z9OwRDjk9$4{7Tx@L+tM0gG=-8;p2HZtD~v;`tM}Z4U}F@BiO)LFEhR zF1Px<;C7M()D7UVAZR%_0FRG>&Wo^?UjMujzTo};>s*Na&%yb^ z`~MF`Xt|1LYeUDmpmqC1@BcpF@c~eng4Q^J+U*t%4h$AcH4GqgXOF@CNKiWgqz2S} z{gL_eg#+lk0MOVQxUHe#?fv@$Ed3XN(gAF*J!t&GW&r~W=pF^{|Hfc7pfnFM+oDCI z%KO(-a2*X9H~W9Y(t)87H2zcT$-K-WSr~Meu7D*ogMkwRLytuR!zGJk1_$r|M&LRd zqz)907RiYhynhRV>p^f?uz-Qtq9rN7B7wo(`!^T3KMxgWv}j2J^?f|Oe{+G;2~?cH zq9qBm-`LChH)K8sD$Z=tlDNSlfx+ARHz#<^!2ADyg`b?@`ArMZye4?fj533Tr6#B? z^FIcjH?g<*8KL3c=>7jQINU+$6x1e~{8EI&gYhL)I|E|_w0#C@mx0=3&~`m|?Izre zUr)hxC#c+deNRLHWR|6-h(P^5a9T70@f$ToI6!A3f#$+r%m?-392hL>j$iQp{S(}e zoKScCi$wwh=#H3Ba2osd6kOJV+~mRd0%QCG?jG=3hF=_@^oDTH6R=)Lo)S?2*>9;S zq5v&F4>Z~z{{Ttjza&8E*kXYLgGK%E3lp_O47`8;0M|P<4;Z$B*3yC7ybTP@6{!rM z`-Lxo#=a)(KmNu0zb?28fVPn=z-g&PV=AcJ^#1)0+~2oU`2Q8;u3CHcE#AMLK>F5- z3=JUvc`!bQwvUnyc>mV}*Jq%%C@5_^&ij7`q{jQdHaO3L`>!pk>Yz3f$UIPe@BQlu zcn=oJSO$D-=ox4%v=Fj>4KzRV^MmzX5f1A+4A64nF<37wd@OAlB%opA0ty>Ym^6Bc z7(nhbU@(BVMdV<^90mhWI4QI+FjchhKgeidVD$d|9~=&r3jhC4v}Mo$`2pMpKK!|2 zqSh}3?_ZB$ec}lojL$lt35&4-X}>!x-a!3qNWGv1UZVl71O79B&ieX5YZ%mvhEY1H_IDC0eTDLBjp-G%e-DJY)mpR#YUXwf(ZiK{o@ z^+KSqg}V)!<~w6*`)^iyo!1d6tN8olXXg=>Hhlqlu9fL&u3J*{_ z6efQW)b0hI~#9+=9*qtiztBNwSG4^&j^6( zNbBFnFL?hK_5|4lIv>gV*CTM-1XABUg!F%${{MgJB_d#HZ(&fs3cL=(=V!cy!OwUL z3(&kEC@w+je`<+H{8Sea@c#7(+!h462~OF7;r15({dtfa*g~`@;I(&kvxnNl=>g{`C-C|AXAq=q17d&66CUF#ymw zB1jzU4^8lS$)Ir-9{p7o1`hKW4B+h?P#M3}s{>RAdjEcnRR8@}1cjXk1A{`N)^SjO zpAppGZ`3;e1ynCV+GD@|LfrxL{{&FF_F#OB7~_DqV;+OzJrL}VD(MQaKV~aefb@gT zf&;gY8yFZsdCL3O18}(xazDsl(0fz1K=YP>Wh?_n{eEzthDU!t*gqPeIvccZ$NT@U zOpux0zaD_cXF+44pt$y6d>jJGhxIE@fWkqc(f;@s&^(pnJO;>pRKFg8>ln~{6|@|K z-2VWotM@V(ST}&i5B$OT4&+Dg|AMR__x;`vtFJ{YK;Z)JFTN77@c#evA=DkYpD#VF6C7pz_6*!NB|1eQ-Sr^}j{^{u7}5 z04{@HYKjP0?}e;GahS(Y0@~y4!N8#LdOiaKh;9A<_yy}Z$1hmagVG#WpA2Mv@c$8z z9p1n0gVVnU1H*u|z(`iBK5jJ*Hzef?d}zyKOMfcMQH z;|7Rv8F-$40LlyC`*cC&7bM@FwgBY~P`&`op~`A9Yyq8V^;4Naqf;4t-&BCZJVqAl zdkhwkbafXz{s&E~7NGhT?2g|bA$`6F3|o-v+L~193Y!E*a9!*DUkzMWLH7xGH0);p zpT!I+yDeHY1*{kR|LXnw8Myq1+65kK0=35=cKk%-_rg6fre%@87?`Za}o*lP-AwW&+RWp!Clf85mZoFff3|-$7^W z!_K<0bYNiK2ompNU;v#NTlTy&Ksb+sX%LAEfN`uJQzK}ZBhMspmS~+3iQEu;xX`m?#OeP$M6QE z)}oQ22$VNG7`?#lBGCK-)I6m1U;hg%9x@bw@;hjM6ewST+x@>G>rp`Q>Nt;K3#grD z(W3PhbQWj#ZBT!KfeoY++KSg12d>U0aly9z-G~+72y5*5x8#$T9>lX9vq$- z+Veo`^Wo(NNL`ut??+%afyQjT|Np-Mx~~XyE+Udyv%P;m0{8DgYC!uky#N0P&;5eR zUW*p3L*Bn1f!nE|F*<}kZAtKXzKRSRJQ#0J0Y@Te3?Eva)?`Xo<2 zg0_7@^FJCOas93sX3#mXAU4Rq`du-gHUOxv2wDpTn$KtS{{QzaXx#z&oR38V*uRMV zEJ%GnX!<^9ku2f?wX@OtzcRQCgZ43*ELxI5WBC@|zkY+`8kENo^Ksh#FET;rgh0-c zL9FrCb_T6m2FCoDY%0uhjeZLvZ?mwC8V?z{3zak7lXKf1*+nUP(u+YMRFgpt zy0#B8{|suwwrF4V{`~;lMzKj?I0uU7gyh>g-v8ynrfO0$FSPAGDtfx>i-*7Zm4EyEDLTlK(Q`eigdi zkh1AMSUtFGLOK&3izp3c>WK` z&Hudr%Yo-QKw;|G^bfSx4C>~87m)nB+WYrC@R%HuUIy>~vf!}*s9w-sdZ=DGa2o^U z28Vh7X4L99Ed%v=e`@`T0F@OpZ9(f!{(;AQL2Vg}7M;r=H+uiR2QF7ZeHBod0cx*# zFkVN@@k9F`NO=`;=lFjG@OUyfzQJ?d$)GjQncly?gZr3Be);76`z|<7p_dQf1P&^T zpm&kK)D)?(W%~c$l0&2dG>>BG$ska_0z8ibI>(U#w1yazpCI>gN`TtKA6{xQ2!Par z?k<9w2c|&z25n3x0n`S8mo>jGBl>?@A|0UdP|)3>mI@4P6SYJ-K<)76{~{eAJ>I`A z!{_I-|1+@F|3}HdhnT4p!G-~cY@6G{&fkQE=*%^69>F+oaSnLA2xPwp<5k2xVbF04&^R5aEQXp3IfrsF0}s*~ z2E-oX7F`L8WRV{4-yar&@-WCh-v1@RZ6-+hd*usgPNimvc7;Ww)zqi_EZS(Jk@*{T{q72;x@>aDNq4 zCW6MvLFpaYUts?n{Qm(QrghR4FgJt7szBjlk*vG8`y~Tc{S)>r-oI~w`+VRu@?RWW z{^`#L-!CAeJ)Z$Ie*qsKo2d1xz=MIo0cyr^@87q;X&y8O4I00Csqw1_)Yb&gQF#0+ zaGd-91gOsU{{L?#q}=(x0}?-%L1+JhoD83{2J7eeRbi_DIzRssc%46Jjd7<31A`Xm zo`Pu%Dxf`#)(aSzY!w(lV^JcYenRrz|6d)aF%&q=V@PS_VBi3iX)nEgHGu9?sbA&6 z;4p_F24wb6k6#_2Gt)rh0I#cmO|WNT5CfeRZLPq-@VfO^pS8rV1kgQnpmn(r|LIA2 z|Go(>UqNB)!2mip{r^|cx#b`?g632~cKy`))dA{Hz5We8@9;zQ|A*jnt3hGtF!%os ztKSR)Rtp#yUWPMpytH6YsFey5sd;rtq<)2mgTovKm6~7dTP#f(7_GiD2-MH_V5l_( z->r4!bv5`d&;rn%tF>|LTR?4d(0YJcE02IsO$N1E4bYug0Rgpk>|5&RJz%hc+?B-x zI@b?$Huj6@3=B4vj0Y_Cf$qo(fZve?vahB?Nu++>g8=XU(%^oC{x$}N`g^BD>gTX; zslUm-#c|$$@II=Sn!hS+4l#(mIQFXp6egha)GU&9A2+OIVDbKa1FRPm1~0uJ>Kcyy zY5|o^HV+sNSZbzBNO&H=U@5_%0n*p7ih%_(pJE0cuL1Qtpn5xAs{d*L_r=wJH9*!D zUqJNtxMAyBL^>dCB9RLHP6kGwd7wK^L2HsBX_t6#wR2EH!lR{|)nLCt9N{&faiPlMdh2&oG|ZCubfuZ*BF7PJltq~812S@2vV zD4m1+>%n*du}&IV)_E|V2bKGYp!L=@pmIOzR|04*%lp?EuwHQgtr2A28`(3zYJBH(ok%H9>0THv(;TV5(N2!Pg4gYp-6EwwU(#7kxd z0npq{{mb7KFF6?uf5tNy`~-<9Gf4dOfbfbUkc>fm#w<$nvGT0pv7WE7w7A<-v-oIag`+1=A2cco&2r9cl?G8{G<-vIF1GqiW zlKjE@zbK^b2|i2k{}qtmq2`2p|9%DT=Rn$ZLf|$aXn#Ja&;jo$g3je>H#0DT%1Kx} zgT^bhn?ZM{Gl1s6K>Zg7P@mKKKO{YP|2hS3r-1wlO$VU<94H-t+XRp_a2h;D1SA-{WTnd^Q&~_^00hCoV2lQiJNNmv#)GyCFgIH;j#-`HPhS3=VVuZ$UE;TxNRz|B(o~ zr@~?0fAHC;-oH+O-3ZE)9*n0GUfMBe)ZDoxQh(xeh0Qa@1E4v0i{}9hpnJ;dt3AML zL_zgIxC@Kj?+gabYUeg3@BaqiHVmj;0CEr1onGF*FM-GWEEO0)@ea+d42%uX{OZAY zYAw9YTo0P(K(v{?e;o&}9e{tA`StN+hl0*R~R z;Q2sM+Z2?4Js3~T0MVfKv-khcy^wPF|Bd=puPZ?N=|ST_&^yOLcffJfue1QIQR;#E zA>aG=MQ}O*?dt%oIeCfw-tZZqaW(k8;YW>;?+xduWpl2mdF~|wxxU0@(kcyaifw1Rjq|U|VDS!FZAbT;?Y*G+4CgKLV9s-oGGw_O1VmRDjYJXm5|DGPqv^IiIl}bWf4~ z5AWYkz~j82vUc(*5l|a$gQWuli={k+0ciaMsIGe%&wyB`U=LZR;KcC%g+)F1jP`Th z{{_MM*P@;w!=iyp7@6qeV*! zsNM?k{`CSppAQvhuxLpEjgv)t|9SzgdqL^JQj-sIe_4w`He{Tv8thh3x^Qgzw*Yd# zwE-_^ZJPJ*I!NDOF(?iGYXOOY@`(5Ec5wL*j)xWlQBZh8#M{8@aw_T>AZz!M4HUe8 zp97DBgVGCVj}piXi(~^&@89RZ`4$wXaPb5NCd~Bm6S1xkExkbIc7DwOrAttrhNquj zhoR$13}Vo>>;}+$|4Y|jt7?uLSAh07R(dcffX1`IW8Mr5j5-<&jFue#L3vIAl!rm) zdH*^L=?lQuLLBRYNf;tPW9OjzWx)4FyE8DnOlRPLiT!l{ z|KVr){~sXpLHZze{J&GFsrCf4N26BFO9a#|29;G4JsCJAEdR9vwBPO}3j;&L5(XYi zumAt+yF3^yUhw~~u2ffhQuEA8WFqUY9krYR z0ky8|TR?kXKz?+b!ysVO(7;gN1v*Rbe+B3+E${#T5%(Cv!WFc}x*oOfh-F_9_^c98 zdWY;SGH9_#7Wv`*`ypgL3cSC76Pyk~aqGc&GzJv+7Rd&iynmkok4J&d$%K~y(Dn@| zZ8mEDS^-+a?!kCuBWTg{Fu0x>x=>;B)N3MX{d*FHMUkAbU zh)n{MgiQk@1L!OVP`G;kR|b#c*(WeEG}LbsXeit!@yYU z`AMW!^Mh8S7XweF3d<8qP5%F&K1!t~%ad9akAO;528CLCFOmAr8xECL3Ygn%N3xpJe#Kf|3PM1w4^-n{?7%@ zC!liHu?cdm$D-v^ILg4BEeXNUIt{~^}KurV-z+R~u5B((huny&_r zRfF1R(EK>j`~N>hP#+A`<^tt!*jhIbAEoVuG!Fm@FR1=T@Bb>`ei*212c3liN-LI{ zd>)OO;Jb|&L3dj~(wL!+_wSRCF|UOGKRp;23@q*cH)wY<)H}?D+-m|VYb;s}9U=Y{ zW%2%f4^j?6&g^aQU_7)2;@{uk@e5Gj02D`1eQBV5UEcry27>Oe1g&d8PsbjNhZsTW z7S#3!?dP=q|7!+ljmZzt9_9bP!F!m!f9->m>xUS`Kz?b|{B`0*BSXbYw_mG3YndG9 zGJw}=Cj0bOk%8`cWzjoBhDT!2c zvOKZmfRq`vnic`Inoc6N42%r*oemD5bnGw}adxcD0nnY}hKr&0fcsvc_V z*ryHJI|m!1DujfMGI+iK6b{72^9ite3mowb3Oi_=IYRt(2V4(<#&tk#J`ctN2S95! zVDoYy_27BF79&xpdhj?lD2}U-!t&ogMNnRGX!?J^`~PoWXc|E5TY{CN&~Z3K`c(qw zBdEWofbt+@ZYkBkB7q^*`_}{H`k&FFB^5M}mgfEI0XUt2(g<>TcbLl%0GV$VV6a$f zWCWRS-T_Ycpz#$@y$EU-S>O9L17zoqtX~_f|BL)U%zGR8S=2MAc>lf)ZWlnx>HQl( z=ih+ZFdmHB;5bCGqZeuic)cRX4yd^Y5cA+hptI`MAejO7^9#_r*90aBkT|5z%Lz`m zmI{oZ@r{2L4U7yH$ws#(+A$b-|2_sTk8Boz>MKJ~n~Bl;|DUxWyFh!Cq2i#hVe_WFpGN7UT=0-xrx!f%*kYUrr*iN;K8^LbQVOR!#qZg?k5a<-AfqwL3tZ= zzL!OdF~9Ns|Nran{S@&2eH0unpfVa921||ELF?I}Z15S?Hi!QIwKx{@6f`#gW#2_I z%fS2hQE>VMwRb@EllLE0a2W;)UxQ@OJtvX^1<4FMQj!^-B_y{oc>iYshZpF46^ADH z95Ay*i*dO3?<3%TC8#a~kHv!bBu4~*=GMIbL-yN)!U%L8G^i}_{?7>R_d(qQGNZ=( z_mM_WzY~=9LFJnVg{EuB$+KA6~9O^Da1lG%!4~NEUT~rt68` z|JlIxDyVEnF4y6Dq2;*;;~vnx$cgsg`@(*G0Hse*nP`3Q*AI|;LHYm3LWTnGUpv9= zTG+S&NDh7M0Mw2HrN5tAzdm^X+68V4yjaLk04g^u?nBRi{e1#F_5&&#Js9`E_QApX zG#-q5AnX4gF^GZO^7`Jd2iE_8U9jHIpaG7nUpv6-bZnKtbF&|yXGO_CZRAO3m~`EuL8FTIchzF!RJ$f^g!IY6Wk_(g#jpSInMjPr(-{ZM#p~! zkB<8cnxOcw0H38~eAN5*A@F=zr#*wlOvqVDO(326bHulmo>A_06x0QiozmzuwzV{@q! ze%gWV`d|cyJ!C)0zdIm5LCiMMgqVE|+=c!7FGy4AM5pDhJfZ(3>?i}3_RZd{({~$LRNo06BL%Oa0H1f(V$uW29|ytV0`pTicyGPQKB&LI z?ca`h3>qDE=wbHfFDR{m@(A{Qa({C`@*a%45O+a9=ifkfS+tlu2aWr}^WCq_;BuHy zz5|VMg2u-{{pmw@Uy&^^1B z%nT8;4>Neoe$3zr8gu^1%n$&oFKV5GD?Au?BGw7Q>b{5nf7m22TmhAH3CXR{z3KlO zz5o3Om#LtBChX2DixyL1aN0-~P4WJH1)L^9c?fL2vNyA|(T=u{J;Bj)$7#XCj z`+o;ij(Pw43!bk9`OTum6mX`p=P{d+&S{Db9DP&w1Ek3quH>(>QPeg)S-;IT&2e(zuB!C?hH`(A_DK)*u( zG&cY}qsSDrChP$;pO$F1GJy7bf%6vlym8PzkOd4X7A>Z4Es_}|ynkN?j|*VW2fq$_ z|NplV(|1zx6_;n!yHI+fqh{k@j<|384lUwZty z@iYGa4=}C8!0=P!*A4GqTi|oe;CzO$m+Th@JY7KRG!MpYp!84(>T6=!y$RBuVqy?O zviHL8{r`XbjQ{`PrN^%eKQ(?`fSg&i8Jspjc^JFhKT-B^q2PkKfH|p53WNY_2mB_FXR7z0G)~B{c97r4gKlqMkuxrq*u;?|=Wm z?IVkN1_$rohrxYfP`>wI+^PeQCush)N&5fIBDs?RWRJxH7SP%L3_mh|b3olV(SuO| zTy{XzwKBlecrYq}_a4}Q&vN+!kNwt zoS^dxW;!!)StK(U%vAn=(NckhVWaZ@OQ7{1GnM~e0hK=+mH%G@%{k6g{(obp^8ef5 z^KF#>-}7KJ0gnX|ESDGle*r3!L2aP=6HLoM@c;@Z#2Sl#iZ8+ID;Rfx-0S^c6r7hp zWq{*6h6|u@c&YgtdLI#J&iLP5m>)swbuEsq)39h@2$+1BK>#$KXOYYhVttQW9h5gc z7>yzAmqx||mI@3apfjYVs{GsF{i_TzfAtU~&bV%>`oAqT^}m)u#?O9pG%RE&0L@2( z?t%i{QEhRIVTt#zGO)W~c7x0Z@6BvrTxXHY6y(8Z3@$4mZLHrM7Ih#oS@1Z5MKa^R z33UtsFC7_ofZBVtUS5@;vLAByWF>fgf`uaE18n&TWz2vXGENOk3*P_#EwosWmS)jl zU|^BptK|VrT;Tcv+CD|-6#<6Ay8HAwy09ecc_cuZFc%X6v)OLm6zr(n(#G>KJ(D<-( zM3@^`7#KkQcAU$AGEWzhB47n_n?(x)Q%DP&4K&;vJs7gU`|=>}%z})sD>5|HB>yw0 zNM?WF!MITZ)Ne-#V@9|gHK6hol%GKP2-M!GNDctzTpCVB9bP;@=-I|KGrH6SNHk?o%BA#U}$J)c%Ry ze~cjUsmOq`-xHb~85^K!5$p%h8HLTtpgre$Q2n4YPga7;M^Kx`qJcploG(D*wcs-` z{v+xaXqgE!2b4E0l79=p&H1$kJiiB;19_<>daAw?++T43x0B~ESm<~D2i?~$W6{8% zXOX}Fy4TMTi4EGn!XEw@)DQR{3YwRh{8ID;$XyrvLfg5%`j{~s0&3ZQWIR(7ckK2?i8W=!#G%;2`J_cfc^8WwtE65&;28Pex|Np%N*p6@deE-JIrJF5R$15Iy()tw&M(_>~GZktpHkM0V=EQ zUtVCS|1Tv1atm~g3wW#>w7y1rF8EIInBtcV%nnTqAq{&NKyz3my*wm0KY5 zK7SH1`UjrCXWWl#XQv3`!1i1+{h;B)N3BK*CN5 zIqXzGZPJ&H3>Ba|*^%o0E8f2#_Xa`3Gyoc=9u@}}SU~Ge5n-SMZr?)3Fe*UldZIO` z9ml`|4vYU@BJi-N28TrlEKeYr0iNH3nqdMmV!B?*Bu> z4swQl0t0gVb$kEb2p*FH#UE%62h>mVU|fah_dxeofby|Tf?P#H@`MgZn;WT&{{Lqo zDEz>7x0vq=No|k=^}Qyn{H+kOltIq>_XhBIF{mu`{{KtVqJg0hoX7wFJP67g-oKWE z>w557?*Bi(BFQg=$S(tr!GQLMc>n)-6-mAkDi5tILF+MoZbgy@m6^p*yP*5umqE%u z(ESVle}c+Um|IMtW`X-~76}a8-v57QBAF!$l?RUtSR^p;c>n+DiID&C6)F!N7qv)W z;Pw9hQxi%4DpVevw=5DE_`LuB1hwCx_WuB{^FggEej(;Oq2-uG0)qy$44vrx|JOoL zp3-k-a02!9EfN?sz5oB}%}8btsK|W&2-MyKtu+Uk37f-$=O0-84Xbi>U+&3iO@|NpfURG!&1$WoSmCpf$ekdwKy4?GUX*qdx;yKj?wqe&k&s-V z5dL4m3~Cn0eUcEj6)1q#UqRgPVZ1C-$CjeCQ!H{-1%J) z)Xo5vDc=9T?X7-%2-LPn@c#d8BdG4SXkbY6{{L+$sNT0|U?}kZ|7|8B9ewMC>Sgr) z|E&?^He@$J-D80s?x4H}wSS`b|8EnaW`OQ41&z(X+j!ppzyE>jWdN;fWe{uB{H+qI z^S?-;Y$YO1q-ws4*;kPi$2F{{u8m zSktK_QqclB@8c(U-3Tmwg2EQbZQwR=Z3BZEsICU}neu8Hk`~MF> zYmdR}Y#Zc~KxrtU1!O+td@&CO1`*Kw04SV5_q;nyVgS{%44}Fj(RW&66Y9nCC{&Z> zQAizw4a{!vIdcgNp!J?tpi#q&vF-|KJ%;r`hK7b@297!N7%Up*gVq-?utW0LcUI8c zPD4Ed2UMIHBK{3L57bc4AOYI@2AYfV{{Ia;t_4cx9*m1&eKz=-d{7^}W~q{h2jgNx z^mYKaZ?%s>!FnM>19E%dr|tib_47Y~(lVr82kqrVIkTK0!24GgI6f@x!S_6J)UW&i z8ein8+5aJ+Vkv_{L-qe3p!JJ2$-hLPZU?tNLF3R4P5(Do|7YL;wQE3gQ;<4!(F16h z!S5}oS&5qd8j}D2s7Y25sa5f=fSCCe+-AU+{y=HZgK-gP?WZI7tR(1}@fOMdAAs6{ zH8+hbYJOW+)Ji#5AcukX|9`&Fc7zDDeHa4WThP%^|NjLjeI+Er;_EB8&I6@4khu4M z$oXI3b~sYFfzp~|6GMjguMBW|uhahjpN9JXKPD?Olz{Hiv}j}~0i`|A93*%?xsjpN z`~O#P`vcO(|K9*@A2vYl`TAc0(qHd-xuQPhc7^xaYX& z%*}>U2A+^)mL)0449pWC?0F%{%uBrge*wpD!&Fe(bYQ4Eyt%^r|JO!PItI-VfbNli zwtxPE#v#0a&4QL4jNr8}h`hC6N%%cBHA@8n2GBXs7Ju#kOuov%11d``4*dVy%Fe(7 zT60z3Vc_667qp&=ff2Od(TU;z3+*ljd&jxZ{m9_`gcdU1zn6o@A3%Npx!wE!XYjfU zh+8Z`rM zzg4V)EOM<3&2LxNV0=oef5nWHOaxybp08e|3UFu=Q0`8 zk7D=!y$n2lQQgU)0J@u^IulG+G?X%kG%7OG)W6~@Xqd_%V6DKwRg>XiQT>?xL9HkI z7CmJKhMHuC641HNjfxCC70DNyDw5?@YMrGkYLYz+YLcBRCX_Nj^XMn=co{4X!SVF} zGk9L4CJS^g8{-_%847hrHiOSI^kC$H%Q-eN?6GuU;Aq&&AmT8I;ef>h1{OUn28KF~ z?h40A3>WGBngasRsM!rz7ZYx}{+KFC7^Q940YLu@q-u)bC(mt`%qB;xLb) z!}|aK|N8U)|F8cE=J!}f{r_(*@&8YK6#G_(rhnjltspmAv{>Bm{xt)f{`BX8$2)d_ z;}^W=)#9u7@1>CZIhBD0lm{ zL2+am&%mhP#lTY=4|2o5Dc=A8*A%~GU<8GGP4x|n`p0|)4owW8`YHyPh3!Z1-tmU33?iVpnc5@8;BfH%y#!o8fzGu7^%<@2fz~XrgZH6V-xE)< zXt4zM6}*2h0mpxB@CUt64+lL^nyU43u9z4KYG?n~(C=d4aGduKbl31dP?&(i*P_MJ z-TT*c@R%(qjBDeAE4=^znE)*lm>Yy3W33*Hb9sL#{wJ|~{HaTP`S=0c=5MI~{{~V% zegKaT;w~SP!DHIQm5=Yi^&igiasK}wpnL?{SK<91az-1Xe4K+g*B?HAHHQ-%7K{G> z2c3BUYNuE?|9|j0nZW^cp21J(`Ruk142KfE6r>uh85lrq700;@8c;C_5Z_@ALq)FE z|NHt~yA&MfF-3sZQh6{iY{=DOc(32(AmK3YKWLsEH2%bH(PFj6`}ZR7+y%s-~WGq9%hQsD0!8|CcQ!+!^P9)I#Lh7!oxZ7(EymLHmrMW?H6r z|6T;1{{yWLwRp(T09x}7T03CTz`zRbYyJPn3Np*F39>%TqQ$Zi+{gUA2o^sbAV0&- zaDdcb%njbZlECE?)Z9iSb0K}e|9{s)&4r$kVL2DHKcM3vLu1E6h6d0bQK0^>b+zRI zaJ}_=A-MnBsmRc1=>S>J7^=y(uhP>(XQm=UqX)xWaJ`0R<|FU_|3fSp7?{xf#t8A- z4^C9|R@~q`2AX4Km;>G`fF^GUT2BdcBgkDKH+uhG2(EuYVT~Ctw!0HG85$w+@?$B~ zJkT8XKTuw_Xt4^1gy({*pnA~z|Gy25_Wxf%;*5&{aV6 z_#&N-3{9Xr4?t^}9p^DXkS|GB7Y&JY=XxN^7kU zfBklZdHfb-GgeMji&eSd0_v8{Abg^{uYv_vmGG* zv_VQc-!h?QoB*i>nGI5(&;nD-#sEnle;+{Fb<+`R6j@Q*bz01z^+VHbL2Z4gMy zg9b>Hpt^WQ79jIbIvQ|Gxy!mz88PG=R>P38_0|=h(!kP<>Ba0~G)D zcRq<&wAg^|3ugEJJr_Ku+kB5f#9o1cKfL<5RkEcMWG&6U)6?qb+ybcu-LJt8>c@Eh zo(sN(t>+fk#n|$iGO8vdl(?DxVy?@UEms61b0%MG=f?Tpq zf?RT!G_wPC2G5O|u3@YCL|2;`aW?-~wkV}U2wO)YBmxg*!U-<=i3=rhz z3H1ydh&7|Op!SmosDChdKZ6LQ@5;geQZu2Rfu|r@g~9v(3$TA1<}(O1)Pwfhy#R-A zqdfyhp_T#z=-ge)OG7#iM5iJA;kAmOb5PD`Nq|B3bt924z9?WX78@I|=g zIk^2h`##v77Rb2pU)a0^a|5)E02{lqKK%aysC@t(H)?EX{{N&Q88qhb96Y}Z9cuvX zZ`1MmOO!Q;)Ka09PHZ;(q4NoKI|{{I|2<_V7H!=EcGT5N;7fAxaN}2Nn%n9-uITx@n^K?>XSRvn&<<{{pq)LE#I{d!V&0 z8s5L>g6EMy=L3QI(fGzgq2=Hb{UxAr`TzeN=P}Fy^{+u=+l`vPH9%wF(6Mg~(3lR? z4UM4v1dekUWI$t4j`J8Cv^yCQ1~_CVbQ zxmS>J(gW|`yTIwtQh@;!pP(}?_JG(H3IBhA^nliPgXZHv{_tyHK-`509Ulgbd4clr zM6KV5apK>z!0j23|3PDg*v7Fy{)ELlsILy2vjg?Vq5cef(ahjrk;qU2ox20yUFgB^ z4_wDtIx>`4G%_@R)@Rfzgy?|o=J8+@0;e~NM1}_M-#fr*1GEkWt&w1LdBfKnu`V4`gl;>^|?`3&87AL2mG16o#zZ zX=JDY`LQNJRmUQM%hUV!EO46x9!K*SWW0aR2G@O{wa>Mho&uqo>@}8}|9^qP{iP$r z49qnk;ShVk=Tl9Tfc8P)=lp`w5cJHazZNarjnFWi2-(x-2wn?j1Ha#Q%^cA97wGIK z@83S)wkmWDK9faD2B>Ui_WrdI+}}bH2c6H!;{6LUpMxCN-v9p~))>OZ(;xo-0d+&; zj6{YF-oNLA&9hYa{~Mf6=P|@|Ix=hkr8Vs?23FA82(X(P89?VHGkO1>32xJZ!VFZu zg2q2O7Baxv=WG@&w)x(_r-9Q3sBHKCJquiBpr-f!59s0K!Ps92-j4$7pVUF_VFI<& zf5Ogh`8}@{)ZRpLYlHSYhWgnD8OmlqWGDx<+d%HFw6o9wiD}PgsE3Q$Tj+q)SS(;* zvS?%|vq)fL^Zq>p9{*6k7<3$DDDPOvPzEZqKxa@{wAjw|{tY=(3*w)d;5q{2A8?ug zjUmQ@#<+tjL1Q_PbwQzE|3lVw_q~Aol^N16h2=L`JiK&faOl)xVCdvxWT@rv5}C=x z2)bw2p_7Y|u~yR|V5Sx$BS=kx69Yr179%5QEX{Eq!vfHFJE)xQKE=qO-^pNM$-rRa zIG2ILl9PcMw7v?I=Rkdai({Dv77Mt9Ky4d{AEtrF={oi^SiGobaIl!iz-+Pf|KFNs zB@xiwW){f|%pMHC!D;g)s7>Rt6E&B5rKzGE0 z)_ur>!W^`g1=J@6wR1uHW-2`mbS&x^7(sXXg4UmVF#H1NoBGGFdFkE;kRI><|G&WF z0qPD=c?7O+7#LY+Wc}6wht&ZF28*Sc1{MumLf~?ovFG3q#s7k!Gli|IPcyufVqmP*@Dc&_S)3UDf2h@DxL~n>fn%m3L%9dTPjDE5&P}ksw+`G^1j$*n*q#BE zza9*b@pkb2k@FZhp!uEyH0};6$2}OngWF4;iVV|1ZBx*m5=#XJ?U{-U(?EBKgT{}n zC2X(SEB*gl&wRLI)3}Wv$NZcXRfZGosd8i(6eO6N^B~pKw;X?I2_JsPwpG36x zF&uE5%UA(wU(Nc@;0n4k+@hYrZKgegbM?s=hi2L{xPb0~0iP2vmodQlF#~fwXsz#K z_ANEFQX<~}|K>vFOh9WVKzH(i(hpQF5Gp4Dk^`+PM3OUw$T9o@$)V|!gvvd@l>74+ zDtDx&UP{E$;s3#!O!h4n$qbC3y;|1){{OFy^;}o8_(uRJ&w||H!SD@Sr&`AS{|`#1 zwO;I7KxqTCHU!TeVU_y*0S=(FQEMBx4zwo`v`5Y&+4iRQuZ7^TsG7SL>nxr#FoO2? zg3^-r|NlooX&98=tnV>^&vBjU$;bc_n|+dz(NclIW~L2;h4=3%;PtjI85w4P@Q_p@*WiQJXjuPe5CD}o-oM(w z?P!o+LHP}^+eQ`(!1p#XcrbQ?#=r_e>pVf_ zruDtw2B15KUN2@a0QF%#7`}qr@SwG%mJ0vxgZ3$c&S#pb_B+T@K>@VSOK77VgF2{v zI#d03q@@Cb&`gcrQ63CD;Ip$p{sOrXq<=={?`TT}hJu+|zhgjilrz{dWSWY@ev{JH=rh>@HH!odiTD5i36`4Rc~ut2x&P0Ad1P~88ZtQ1Uwi%gVPmv^ z6h9t}ZJ@c}0Ec=1B|vVO32`&)Ogje9JtH+>u{Z`@khu5%|2bejL=C9ld8d}cBLI|U zv{x{gI?iRd14=WN91QF;JsH?weyCsm8ng}*JoaXBEVIC3fzb!=-+kb5nwRmQaS8BP zLkcL2L1FQtow;bH76U`5<{>+fJg80r#eJhDGpL;ps-u{Y}-|L+DUoq^ggAb)xP|E~dRpIEf~{{TAox~2tOKC;)$QxdUQ`u``W zo#Mgp30#MO(oUy6gGHkobAhGi|DT|}@DtUT3$U#l1C=?Tybo)8bt*GRf&2j47lLT> z*{OQ}?go#)gUT0>JHh!2w3ZOOj`cTU-3PRc0htTZ4>H@L#m*CEK4|VA)Q;>p$-vOD z5_Fb&H+X&qyScv*{b3|?VP-+y+6Y?nCC_mI{)7hbY}r%Oqk80#jeQvcNe6s*}%Y954!*7_Z;xtC&+FO1_lr9PKE%` zI!Tb-Aish91nR4U_??=+4M6*7toQylfW|xcOm#@OLB6eke#LFoi^PN4Vi9`HFy-v5!-CBynB5C8uF^-*AB0nqdp*s++w@+DFq zTf3D(z+o=zesa6%-oIvo=PE(t1)#XJNMz{nV0Z`4-<^sKU7)j}Ky^DPpMdg&MT^~G z@82EZ`9I8Y0H!70zdXQwt&WEblRFMFOzPOjUc3vAwx&ULx!%7 zgAAS8tqh@{{Gs0lrg`++84iH<8-w)KJZIlhbBuk9MT@-*cunE&4saO_I>)4AA;VI&tqD&*n`fHWbt5N zd;l^Zbho8Ni@l5Y?{;we2UJH`YMwpNsmZ`wsKvktT5}6(dsyG&od7!H3Ysp#W3*7c z$=<))8$o#tB>%&a0d%(o!%I&FhL@QP0-&>hUU)Ka_%*O7zHkJOcb>6$$glvEHh!xA ze+XVTx_|+^?+853`fD$EY{L8hza>cS>-7HJ4o;I;+!ui4J_V@z!252Y?px;lyA8Z{ z;-wvf0?2)M+-3lE8{<#)|2Mt=|4#wsPw&64z-wE)|NjGrD=6Q9`Yh1!O#p?j!#wzW z3#&zo{d@1TY^G`gaECiil)W}e7kzmE{{ks#~fA#*| z3C$ya7a+pGfyetdq+RL#dlPsL7won_@!&SG_y513vx!0Tjm#D;4jSISTfydg|Nk2U zHlxKM*!%xK4#@aaJz^{l+OGuF1)zKe%{Psm%HVdN66pNSm&y#_G8VK>3ljdPEo{JL zFLT9u-e6OcV1dp#KI5chpU?Sh&!(fj}Z zPEcHc`iI`X+ac{A0{cdg^!g(7c7f9bsJ;Nz6}ajNsNdLNb&dyPEoeTd5Y*2F%>!BA z%X|P@`vsn(Y+wVg@$&u+2{+I^WT@vAI4tx2-2%@4kg~qk;iV^ogC)cNrr#$SG-h%! zfbyNg>{SempmxbiP6mgW9t=!Sni-^a_A3S!(Ajq{H5nXczhq$b{@o5Pqdgpcd0Uf>Q+#iw`gDh=ZBeE%o{-Sw@~$93S9R><&naR(Sv~joS$Lo#ryYc zaD7ZD+(2W6U_GF+p(TsKBAFRB<}wjBK4;Ou6amgl|NqSd?HfTh)BFEF*mgAV+DGkX z2GHIc1&})-{Yi&YaCiQi44#Vw)tME^{7Wn~nK#vBO6i3pv)Q4HTf@d9p<_WH^|1P8 z^+{F>sCkLd`lbUE2j0KCT0vza()gbW_`ZZW46rha-J-?etM~6F=$JEn+_nR4+_u5{ zmlL?ZXt98S3seVNBr?=_FgyqM|G@FHfPriFL54buMus|z1Qvstpt)5A28Nl63=N=h zAJF{0_wN>Py8}EH3OVO<3M4!nrM-VQfz5}sPg=qIU_s+op!2LC8gx!RC~ZT}%7=zSXDvoJ%x3_dCyW#hj$Yos8^L88$bI0kN=Jr{ zmv#&cNc$Liyni`@%NW#fcm^InvQ+rLAp9wt-Ry-7ZJ=@wv}Y0;4lEWej)gN8g2IM@ z4HOoZ3jYtyRAgxN{@nmslMf14XxMrGZf=CS_ZKA3|1a_W-2xtCf`&;7q%5sOtn*}s zlxr3X82?!`{QvL4SP9zi;Rvdq>=*t2XMK-(lYP_wf1vQSPx}AY-s%58d!_&XKx?3^ z_d02LFgyjf5v}JqF0iil)v=CpylZXgxDgb_ptI#bdn-U^K|;piEx>b0(DIN6G8bJb z0qVzi|26=RX@SOzYRaW69h(>wKx-&KWuy0R1Mrv@$WNg2k3r)<;ClCWJ-Ge{ox==D zTi(C*!Q)mSc1Q)AUESl|72dz~z+(m>nQWlFJfQppJ?p`V)%({3aK5fc=6z8wC#~oG z|Gy8oU;yoZfsdhp=9W)0craF&g2v53XZ3>WV#HWEq$~o37pT1fbz=;ndK;t;)LtT_ z&LV*!#rxMra5@Byt%BOOp#8j{wzZ`KgNXHB)(xP&%N9$WtSlPX873++6oA^q9t_{X z^#n)`d}hT`CtuJxdkg8Ik5L~OwIBVUK2Jv&479|nbq ziVP**zpPq8X$rLW7qsUWwC~%Zg|DOL?jsTC`iBzm{O&I+a6b-wenSHTgGI9F8Smfy z;C5xhLWUCXTHYGzikhXrL_(Ib*m?h+2yVlI#)G_nPXMQ7lr}Q-ybBM;GSFF{f!_aa zfakFwW!Fvyn*?S_$iDLr44^dT{qF#HjSTcmAdtL*_rC*Rb0PWr>;YQ^X30d&4-BAt zvq9(2+G<`>m}tkK@)9(k4qSEHP+1TBH8<=ZgBfpDRFT%Go=xFf`gRSXfsx za9HnUV5#5Z;ovxj@qqV#X>i%&{qGaFJo5e%39X|lplzCNaC~_GpAJsT-v8G^)cv~w z;s1^T_gB6DA8rJNxA*@Y;4u-%dMg7%iv(vU@BcMm|9Jo33hq;Y=ZhNPa?mzaJ-AE; z&%Yq#pmPL@;CUGD{|CVJvG?!I;5jDnT497*aDMjw?+R|uf#&fn5ONSd{?7xKcNPm6 zSdrwwZ5{9b-r)IF@Vz<+ec*iN{qGaF+y{@5!{w@>;llVZe|eh{^zgAvK zq|*burdYvY-v1XfUNC_6Cc^fMz~{p~7z;Z=?U|Ys&1>NOGV_!xKy3?)7N7q$`?bOA z#6jcI-oJ9d`3Kr=ht`e0vfjTs!1)q%x61633=ETBGO&Q!@1S!rv_~J0s9Xc{T(C+|;feL8;;`d`ljvw{Vb$R>2VX+kkYBbATd*!A+=M5L2{-tLt3W_gVaoAhV)Jq2Cipy3|w4-$_i-z zoWWu#gMq~{1_KYqyoo;)|1AWk-)3;S{R`S-W6`3p1KRdF0qUpND*gXwsp%gCs;eg| zGJwu6VVJRy;Si|KoNVG3#%#qvOg6WX4LP0 z;NURlzsZY*3>`J|9|Tw&WLO6(gMKuE-0T2uOTAdgFyTcb!w!ps4C`x(r7J-4-oG8d ze$?O0zyK=8K=+h`_P#mH`}YEzFG2ok@mmH7vl4K<25Pr~!q#!#{~HT7GcdepWB{$9 zW%vGF0v`WbXbigZOn?QH_w_pkSRLmve(6+XSPx3epgrl`2N~9b&xLZnTwztuz-Z0D zz))8qvfPusE00VnXxpYN1C!1aU zJaFCxojVFD6Bjg^GqAiA2k$RqwwT7iT&sET8fYyCXg=S9lYzU2nYjYAujL0LLxuPM zU#^{E416yY85(ACGRSsZV_>K__FQSkNd}HiF$RWE4tBeloD7^D-xwHYyky|&6l37X zoMnVbybonj1JApMpc|9{WqWRU0- zW8kjjxV~s6Cxc|iHU@6(R)+mA7#S+S`;j1eBq3^^gVabt*xx~HX%IV~)}W#&Isg1e-*a80apoS)5?{%q&eXePos=nBFrh6HITJ4G~|{<;bw!Qh`AN7SGoA85pe; z7#OUA{{IgPVza9Y@}35!T_#s}|NrS&Qy^UtrpabkKgq+vVeUVJrUC{QaJz9H19M$* z=e4>__ARdp7&z*Ry+kZOGjP{FuCDO@|D&`+a1kQ$jzI|c!eIoh3|@ool# znZ}Utt$kWuQP;8<6268EjMn!UB)oqYfcvRchM@5M&oSE=9DY|U6d4md7&8%b`|v$C znG1g?{%3^kNql{nkpsH_5L`Bb@~q=Lh6A9rmY{vIj`J9{yiR7|cu~#J0LiNiOFS5^ zfb%D4Z3rl@gZlU$3|GKybgIn2dGX| z8xE!ibid9^O$H0l_&jJF`Nd*ry#cPL{WHCP=Yz{X^f11MM~S z{{Isk&M0?}F)%Q6sxYuvYX1Kds>x;tTGQ$~mjOK1=fRkM7Tjj5m97BoYxn;32D~N( zRKGYjF~q#IV+?@0N#(^{h6+#|gUVKm1)%U{m|#)QFu{Z23bxF7kz~d@1 z5V0TNac)R`mmToao)Nr9*@H11ahEbPXb(7p4aiU6${I?5>TFmTdH)WE_DMg0%Lw$a zfNBAcXM*(ohK@sm&e8z+4V;cz{3k-qYxMpt4o*8zzZQVnV4(D2vDAM)WWA;Wc%BO? z{?B5m|0;`?eO+Kb{Z;_a5rWl&<|tZxb?T3OhSqC};QqMHqW^!vb}lt>wrJT8*~j!- z0o*qM^$9@ccrd0R_D4X+3_)$%n)%?i$Uji~!lK20JCd8h@e7)d1m&$CSv(s+<87d` z*^urM{cG`jub{=Ty>j5bdCS8v@862xwyF*IJUSlm+D>qPre!a)_iuS{Uja$(FLdt; zqeY9aj`wc`aGxG7e}I9_rs@Cxgkw?-pmb-^GIgi-Zw2s}8e9!14}#7C0*B2*e(&E3 z;C3vUJm|c7MvIn*a^Alc!2K*xo_eXtvjG%7wcv9&Q!&r~fyS%N0!SW7SPHshWAEY` zq`T+5e~W_8*@DLH8E72-wOG1$1|)9fAZ5h?uo-_rc_`r+I3F>A{0xd4@89y^c}#E| z!u_&)0#pt>-UN<+xZFd2s2n8zAz=XbBUBEYk3r!FiQB0=L1m%$Zx!(P0oc5jsNRaS z56Yl%Nl^Gg^+EdC@V-V$jm-h};)G+74xl}P@U#z2Ltr>a;64~=Z;xXW;~S7XD9k|Po1ifB{tY=J9hBxA<}scD%Y*y} zo_|o_^Zu;@&YPe;^Nvl7Yitz^LF-*v5;a*ED>d1VrD`%5Bx*7^gYL+4oX40_zskb_ zqy|~uaV|pwXzw6Y4TgN8CW8}5&S4%SXg$7w_b+R3x&+LAN_mlheuj|NkWocNxHaG3b07qs7v_?x1rS zA@$3nr=a=>G>&KiK2!fsDAXIrRUZ#q$6wi(>&!pnM7%xAguk2OC$g0@>sJ|F8hQW!WsBfef{zsvjo-!(}3*I673+=gU7IFEzU0aSk}n*M#>|NrKI;}29m9t(T~iF+Av z9{2wL4|FE;0T0Fm#2LrXF=}W%F!7}_gT+ft1`d4VXN2lUB(nrwYT_Rc!)F%w{yu2i z1$HkY%xp^B2d}^9DI?$6(AaR8AxD21WbFphcm}gYOWJkg#Z2egg{WFAxvXe|o6_wQ72o550noe8C^XGGmksiy`yvnKW{cx9&-wqqdJcmkXkQj6T)ltSf!lqJwhTG?oy?%K z>oQ<$$9W7D4wD!%z;(#dVB=1C2F8y63=A)BL&uK5dpCovy?>{G{cn-*{~u@$6*OK7 z+P?|1zji{Sf(K(PXq`M0$elAzg7((^kFiK#;PU=84Lk<}8W)4wp$!TwXy-Cn_`Kyi{hm zfUnH(U|=XgwIlek_wOX|-1bX*h6$j)3TRC{$P9}{hEh=52{ev}ZLL+OB10+2EYO-k z&^jJaz60e+ihuax0zqsGn|0h30w2UZqX8==lweo z9RDDBuv;1!!0UK%xdr47B>Q8%eJ;Du)Bx#4q~lEB;q^_l=K_%6P$hz{r?YMX8}vUafmY{UoU0^@2SylV`g@o$HV~I zdxS{Kj5V;d42lm>yjZk^xp*)zc4)UTvpUXWTH!c{@r!mFGn>P_{|{cqG8nwHW$<|E zg~+Rx3go8ckS*T7_f*Ej|DL|LM%o;V_TEpy4iq0=$lI2~7g!Pw(Gx;B~dgWeR9* zIVi7s|1JlQ^I%Uu3|wgG`3v0a0}NaiEuk|Z=Es7^1sZKZ=Q@Du!T(!8?tR?}iR;c7 zNSWMmhk>CpmcgOZmcg;s%fJG3e->z-2W}>K>?ZVz_wQJ+|G{c)Kw%$H0UC#yX#>{p zRO{&ty33v!#0S{}ssmu*VyVE)3JNbv1yJ1#-bb9%Xb&yxYmv+PZ?!LKL3a^-(*&Ij z0x}1benI}RXbI!N=5|ne@%|kHuK#ej%@MoXnAt#X^8WwN1ypByFoq)L1X&>G48GLl z0hf!g_8{0TEn%Q>NH!0~&`3~S3c1%i23-F``~6@&4)Yj}K-OLJoUm13U~Jycz|!!a zfus5f%ai)Ome)XMtJd%RC1QP7fWP`4%afWV9|G!^g2v++RqBs?2(U?DmH?ft2fBj~ zG}h<+Z$5Zzq52uCg2I0W0h?pY;Cu5x{qLIRuS6`4C4kn~GAATUGkE`-4Ouq;p4XiV z&Wkmv;IS+Tuphwfmhf8d-_hXmA7mG3ED~gw_rJ}FpmYwZ-=J#QELy@A*&hPUwM2va z6iDLdK=X{=zoWtaM-u;GeJ@IfFkyUS})IL>2a(C!4!ugbi%XY>G-Lyq$p1YT+~!tOeF@KOUV zeg!7(IFI2(rzV34sN8j&$FK*qHtY30o)e(8OAReN7xe5H7#t@t2sGM(;tzBOCPRQl z3j_H6B2c>()YhKR$#bEiMV-T9Y4{n77SP@CKH#GIG~Z!hv9x1goM^+q0vem~{w)a}yYl{}1x{a}aT$ju zW**SoAvm5P>G*^9?+8f#w?`cxcAU#109xY#9wYyC4LsHf85?5$@zS2am~b6vOn4u7 zjuYfR@Ba_L>#rbV!pu8BVxab=_y0%WcH8TJj2zZ`MPFDuFfi2bd0k;$&%oVj%fQeX z&mapaQ<)1u;|-uSdL9hB!FdeQpJtAzj?!CV_lQBv>N{VC-J$>gYHcowK+nbd3py9C zdnJQJ*GdMVu1*Hwu1p3I=s9_R!E>0`_Rg>hijcE1e9vzsuzP~#`@M3O=X`Zulru1Z z)&|xc-CW`QTL8R{qoxvE2JCoI$zTDp+i~9iJD~IKynpk9*9JkwPJra=RJuX>!1KWM z%_|rj=KbGL$I@H@+B56@TL4_w);BKziO;CFI9>6&f^DES41$=?v;cG#8$?`SCaA2bZ=S*6FpsGNG;RnIw`egv>it^)T-JF1E&=Cb zklr8l3>x4yfXWOSpgJ6sN3gYtf7CM=fcB(=`XG=zz;vQE=8}k|Jc9)&TtN1K%FRwM z22qO^1-^-%pz~T87+=OS7);b+Pyx|Dxfl#U^h7NN9nhICmR>mqAoG5DGFX7<-zP!) zTm-=B6EwFDN}HfQ%S&g_xijbfCu;uw2N^T`e?C$3|K3_HFA?pP42%wQ8CQVxTRJdg zPV{8Z0L693Nd_@UdyVmrb{l9P2UEd|eaL-~2z~G0Vc_x)RGxwM-FPrCerZ%@kg2|{ z_N2b%mdHeF1_6-VMr#H!SlR}Ml_osDOCaTUo=!~$*^Sl=BG&g97#GZE0FCc5RNqs3 z0?I2E_ZT>8?ih)9|9=+>mb=Hm1sWFuiGk$3|G%^Cv}a&~mKOzJH47Mc!E(Q5fya%& z;n4^>Tjc-$jn)h@8?71Sy#N16sHkR80IR>pz+p1vIhRB_Z5RY0@%{hE%QyysPA%|$FHrws%ZoY&4p1M>;vo23Rfd<4 zaXkTic@%V3ysbmKQKFZ?R#5o}s;6wd7{owqhk5@KEEO0UHrg`;fX)xvXwMJ?adS=r z$ba7d|2tSHG75mkSRmso-mtT5;b$y@#>HUs1fYBYt-ljNW8g0#a|Ylw>!9@v-hb=B z?QKxpIL>2$oJ-#lF&)&#@ctbH9-n`a2%iV$@nA><@8Nlo$N;`C-Ekg6fcM`9@R~^v z1_l?9IH-I9oj>Ej5DlIaftn3H(=6gJc>FmLavzQN?>g{2D@cvQy#F)2e?I`PDSfHP z&;fEQ>U^#sxJ-t$S-lsQ&?qXVAJj(A*WiF;md|B-B38I2Av_zM0^8IxO~q)p`G)0dC8Z zV;{KQZ;5#2!RUGPhvI)l(7JB$oDlTB1yH*IGzb3EkpX(%4hMKWTurrfr9%^ghBc`F z2s$qZ)Q5rInFOkH9GjTVc>fXr#{;Jv1G>AT z{y(UU`hNj>kIWL#Tnwn~Vv!ul;{7`S-2Q>O>o4fO3vm3k@S1r4W(L=fptCJN=U#x$ z)&;f6!S0B9CSYy(jMZA=AwNhjsJ#t3o74L@2PdfB1?}kswTB#<7<@o`+q{220GAKm z|Nnva4TAdW7A+BfJs7rt+q)otI?VeoA zhxczbcsmDl?_T}=&lO-fmctd`vhp_@cuW{%uH(G_3DA1E0CXM^$ZqdnKOpm;Rp7XT zuCRBysD1yH>UIY09^ zEW-4J7A(6SBIKLe#bP~Y16KVODLOT;T^xzqTf9@IBu0rv-? z=~@Jo4?uk|P6pLi14i5%?a9RSbt%Ukxx(CAsu>BxC4)gwB0QnJK zw;;_m!TP)qeNn9Nu+IdAJu|qjgOrmDG9C=<;IbEDuSP{p&Bde*y9bqC7pI2}&p4zy5*iU;X(E%#L#zdTb6f zFoge?u&6l3e#}yV;eX084#ryh9|j4>cUrx&`kyM;WJQF!BDy1=eT%|Nmc@TWl2={)608YyZyx3=$sRH*K zCwMThLBcnIfdN$4c>jI{&flQ3m+TWb80{YY{|oBB+AaG3*RJXRU%RCL|3Lj%P#(0l ze5P+L5oMoTZNp&o-B-uz+Tnhytq;SjrWmMO6(5>v6?AAZ$bL|n32HNY|7HZ&DbW02 z0!c$|6FeAr!EG<_oWCui4G${Q9h(@wc>jXb_w{MFE9zMfgXWeLKy5w`hJ)bp7m+rg zdutvr=z!GLJ=qP44<>MV{_77o{_BoyhOFyczyK+ufBglItAW=dg6>m-i~j+a|8*&| zD`0IaaGCt;4>*s4?p^}*vq9+uBK{j(pMcn)`Vcf0?fw5Rcx@F(4TS#(e18vQKM`pC z?w_ZS{Xtvm*`uOWNJPQ%XRNJQQj3T|WnpMDioXM@TY$9W71pm+eaHNF3@ z0M|VraZuQU@$D%d$yU*PfR!Dx@T9~){GRPRLZ-$%gfY)EMX zK=q>Eod+(*y#GS>I(z?)2DkOS|L+3VFW&zTf#cKr|5|YQ>;1b1+(tx8tN%cAc;3H0 zg3~B8j-hK1qM5vZeFeJ}Dh|49k-_`d7x4N_(0*?3{~Ms~*dvfJ*an7rNLpJ5b^|Pr zStNqaq+1ED|2q{K%E98`a~jz65;YlkLFYes|8@tL1kXQu6HaN7`QAF7@m0lp9~(;^!|MrJU-z4cR9GM2iM<7chERCF@Ny> z#RP7L!23onmn*z~{RE3a>}TMB_l-d3|AE^sKf(D1BLDA3{qNrupgx{;RPwghw;438 z@BRN_X$Kl>z2V?6j|sds6tf?*3+xwA`3Ejne!T{#MNnG^)R(b9>c@cAi$dB(U%~ki z+?N5BG0!72L3f;k`Z1uk6Qr&34O~`%`Y|B0VEq_Sp9UiT72J-uIl#aOk%#nSKz$mB z{1*1f*ZpaJfS zM{THrhtqBk28Vf!CqV5;ivtW#ES5$`!rG7?3_HPj1rbiKz;O+--;#lW+2R4i6Hvbi z)OSRL6QsNWt$zclvpBY)6ylbLVNiD>`|+Q}F%xHq{C-xbJopSWuwKx-EocoL+>f8Z za@hU&8SH=iNB{qV@{jd@6F$&5f%h-SdU8;D0qw5?$${Jkw)0qYDn!i}aJdPV1D#vd z67|pf*Bfv;2bCv|O@F3%|NprVGSn}1`d#ZP~Qo3Rske@zJt>kMBhJy*Y_AWKym5)|1S?h%{OouL)CmhsQD-GQjwtm zw3f)B=?{y|0tRMK{!Uo>|DQ#2bYI0%_G2ka8yFInGBEyF$WYKQAJliT2iNm2KzvXi zuz`sYRL*$+t^>D2z5oB-12V%RIr^&iZ#!^X22nOl0GF@c|9?M$^u5gyYaXFzn0qjq zD}wf))XY(?gtfOpYmlJrZSWox$0mj&(0wR-KzmO>pZCECA2dLf8x8%15H7&yS`r1^1$MGJ3;_pcA&wib8~3TppF#QW!8a9KA4yx#c#1jt?#Gf;B} zR29MRAM;=|V+75qgZAINXkiS1`a!|_|Np0;^y$#VFb5PSpn4IMwmcZk6u@Btst11k z1;-P}P2l!ji-9_*JOlNMy?;UWbAbBZumAJh0M#*|esTD{208Fq9rvUwtmj0(2hF!P z+A}af=8XQ&0IiJ#mD!;4Hb8ZX_ir0;o5lJ+gM|10|2G=#LGz&>7(jQ+y#CK105vxO zG*@nYFGd8(EFX|r4)YjfK>Zu2S>Uz^%q;Cr29|}k;Qi?mp_*(KjqwaDpgTXHV+sPG zwHBbW_(1^%zIz?IM&U;$&kbz*O*|M)w${v3t^|drV-v%S*Z&wjK<)$G`v*Fc!~6fg ziJ&#rj!g_TFKrpX^TVKd1(5r|>wSOi1fR12n#XZyf}N!nW9j|N2V8H0+AO~pGjdpZ z<$n0-%*fCf%fK-EF+A2X!Qe$0?Q`!PdurWXU#?8gi#wO$M+pAK4av`&nHZ`}saxwIhvgU(V0(a`V#Q=m28w%5;B;Cu%<)Ch#Zo&cS#0=@UrQj-r^uMVo-m*BD#)NZp#`2X_-BZEK< z2lFzJ8$f&zjcguBFX(PRP+t>fzX!uSaNPoFFR6jsHxTm}7?90FHwSbcfCr-ys6FTi zN>i|T7wA|Zcx=Y8iNOODuAn_kj`J97ynnugnBNGxr=G3s2dG?1WT^09*aYrBfY!W# z>JZR5`QE>sz~u+1p9z|i0JpJF+tNJVKYxJdq#gF|{QrMVrX)Q4(EaPdXb8I7QPKP78}MENsM(EeKL(F^#9%BR5 z!Qe9K*c!wc`oG?Q-3lFtWU^?<1D#>d?ENbc+(w0(hZNV0ETHxb=o}%?Sc~1G|Nrd{ z{r_*b=>LDarvLxJV=N0ma}F_S)|N5d))Fzxt-j|yu)3CKV6`>R!D>ogfK>wHf2*Ka zwff!cTPzY7%0PWv(B4u|9)iwCEP#qLgTz4j3RKTl)P#c017odkeO%%F+Z#IO4d3Ly9Y+RvczYd(X) zS5=%CWFf_klmnl?4UE1z+*5849woY&A?+0)_XzYD*rIXPHIjX zSHQ-a3)L9^!^Sp1w_PRcO`#+qa7TcBobb!hs(rP7P_L9MEHMNLbPNG-E-g$KiI za2!DH`ed5m!Kg0+Ps7l$Tv+<|{=Egf#s!qm@#S&2`kybsX#f4y^IQiQ7(nd-Yf%3ZHqTYV z06yOcl(xNpy@j+P_ks83SAy=ta+t?Z0x93Fg4@{MzmJ0RDfaP1#uMH@zku7npmqSL zT>(n_-oIXh#Xw;Ip4a;K8#H#v0LllTxb*(@8r;r?$o~iL$+S4YP++k%HXPRH0NtnL z!LSxm?ldw$=EHv71<%7;&v_VTv*`ankY7P_TA;iIYJ-5z3-kW<4BUUU1l_|1n%7FX z4H|P~1ocfIc0UKVMM3&8`-5x1Wh*ExLE6}N!F^0nUl6o@0l7a2veWz5b8y^(`+|r5 zBj&XrXHGLg?0W(3_k!XT)E@-(0b%_?i2QR{KK~2q4}$uDDDzsso`L7yLHfacy%vVA zpgs#k?=x^ayWt*MU+?kn3h!Ufz-b(79}+D89Gp(Q|Nj$#lpWfLGmJSH7$zh#7$DV& z;Os$(7^pr4jk$ut4VqUP!Q&JE|If_H)c>U4`R}d6JO&5I9ZdgQEfxNM({5(qcbLnd z0J>k;`~UyKicHX%Hviw%YW^!L)MVhY)C8aR3%!d+J0vGd|C6P{|L^);j6$HZY#Qo8 z_eTA+%YbB^H2wGbRs)Ip$Y8sM3<5vHEYBz(= z%hjnq$)EsQ%T)jJmq>l*574zES0d&`U2m=E{2Ll5`$p8QUw;*GX7^qJSPHUik&HsOQL2FP!^Y9?| zI5zz+=~RZ4CE)cC^Zwtc+5IB`luy9xl^}XnLi4zX^?wHD@c#@}lm9Y+_JuD1|0hrtK59`yA?hBDB6FUVgY|9SuaC#v1d zzyun<*KTIu1nr&D2D^b_3baqF0ovaKIE3Ge^^6+vweP@b8P$WY=i=l=@u zI4M&95mXL9>c;or{<-6%{~Zu>{{IKX3&<>oIsZ#Q?g8Bq0ir=`C>-W6i0IG%{{ysc z5oEu^y#Fgebt))~9p?Rafz*u*3lM9F)M4`*%ni`_G7m;|(A__UAotZQ)&`#~P_sw7 z!h>NFxXc5c_fS*IzNP-|hk*L~pG4~SgYV=P0o6%}KB{^RsOsT6ULF-9=+txS#Z~)z1={T1` z0n}aw#fJyOWJo!$$S?tt4%L2GANctSa^C-cUWAB$5&`Wc^8WvC{$KpM!h=y2 zF%AUXg9mqey>ta=UKGjg0-&)q(48!x{YTdS83erl|4W303&>B9xK#B3t=X)<2Pzx? z-+-qZxZhMZLiWl-@6!e4qWzb$x zm>*-n`=r3@`+k7OoPL1KgxuW(UP}~XeUM=SXg&H=yZ>Lnea*$ML1!9)^9`&_a+t#a z@_!4+y$*92u=^jZ?+>#7J3w-wPe0IY2RDu{~$gzkc}t2WTw7`~P3q zI!VR`XuE)bx!^H9!sh-ffX5HoeqIkoC0%g4qaIS9fYxq+>W_wG&^p_1pfM=OSn&UE z;IRi#{pird5CAJLz5o9J_X$C9;y8!FqJHlqk^29yM6CZausBX)5CQqmgP{lP{|R-F z{fQv|Bg%EfKcM^2L2}UY1lA5jD(4kJ<(#6u)Bpe0QKuQeW$q5`ikh3o6*YgXD_%yS zr>Ae=@*fn|(0RcaP+8{v{|9(|3&^dYwT+H*7+kCq8754r{{Q9mLxwhRo>~050+imp z|9=C|X=yhzFoVi5(7IDlz3DKIVa-cL21pv2!>~nv5BN+O&|X`Pi8c(Ny>A^L_rTH@ zXl&2>=X0=GkapQuThQ6G^?!efG}ME__^WPB3i}p_`+gk-o&Dv(&<$?a*DpQ+I^)g; zwB7>LcLAOM>%q_m?vsG>GiV+GWIt$aZUgup(k~AufcjUU_Vxe&6`-@mwC6D}I?nyC z0vZGI2Hg*>@c%35Twq9>TOkLYE}-WFBbR@mv|Mw~7}}rykCdLf!2NUNbO*Yd0+yy< zAN>CT6z_<1{SR^P3A7x9=8=is|Nkk1(v)KpgM>vg1LzFp0;3-|cnt%n zz2VTraHi9qfdO=mpMEEUK4|T=MFWFA$bJuoc5r_YT7PrY&wX4`v;Rc^D8GU3<$;*> zU())(|KHFx5)B}+`u(7?|9>ecAA-yVmCugz7*gv0{;u#~0H0gT2-?e|4Yu$97s&ho z1L!^`eNevgU}y)=r9kUZj{5nJD{Aik2mpTbs-Mg#Ak zkHO`~ccqBVMqY?IY9G=%BMl+-pzcmkf96|mkvz~ zJfOC@_y7MHwf0&f^_>S89Of_>)Kvch?{V>9=m4i7P`P-SGdbP9BuT9p?O>0u2KY{RebE5%heDEugs? z==zoe9*k0;GZjI}l@Wg5^TYo?U}Yj`%nf&W`0p;rzo7ON$WF&Ops~{bpTX`$ogWbK z{`mmhzIc(yQ0D#rKj>cf2_B46AbUX=(H?@X)diJ-p!^55yAf3OLhUdBwZ$zK|Njrl z-=J~_ln3GE-T?*%P+0>l`#@{48$1{#5#u7za^Hhdk{2Aeu>Llv?Fu@V;}*2d5sTjD zcncoa1BC}D?}N%3P&|Owqha=!OT2&HhpcHh$j}0AcRcwG8DsqaQx#gbYk z$ov0$@Z1B)k05_L%=v!;v`3{;k)fr&^8sj%^9pDV05m7y!O#Ytr-GORzIO`RZj}Iy zwLroXsoiR+^8df3!~ehaodFK8@SM=dumg109>^|Gx$ph|O{>L0h6ZpQ_<(^0R1Z!` zW3T|-u>cBVP`?Wl?jDR1KA{qXD`@*%Xm;2gVnWy+lP>}`F{oTC6F`M#SP$og@&sKqu5PwA9k;H1*krO^mAT= z$2>vtij+n`XO%Ai+s!EU1@2DJI-CFh&Vuvk90mhWT!PM{1?fekiMQZ2ZAfY22x$K` zD9%9n7w#rdUEZt&x-XHXezAfBC?A5xR>54;h1rk?ck|6iP=T`0-SJeEs zt^mgq(m5C2|G$CPg@MX>kQ+hg>(;E)u7J03P|GD9@1J+TZmw_r!C&T;@-;|NjLvhUYMcK?Q6-QdofUlw%Wvf%nhb;Q0+uy$5dB%=v!l03-$%=Ep(6Q#Q$?}@11PP56BcN^8`^&NU=#-3gOLcz8=yXCLo#R_ z`-N#um2^cz9Ro{!ENJ}Xg=%vh0|zKQgW7@K|6hpKKmHNWPzO3w_629H?IV%;y&euA zF;JX=&Ikgv6+rCzmEiGlm71DMBH;Tx{y)Dtp^iZXV$SokHOa3;K;uu4Fcn7l8Jd4V z{fmlu3<{w1rag~A9U2CW4s#i5!25I>z;jj=9t`#1HkeI<{-=awMj`M2&kHBigZqSn z-v6JcPN-)9ou44!{r`F7gn9-EP&wxP|GDpkdeFK>&{-PK9VgU-#*&^}djEfJI-#C{ z1FA-ILOla`eI=w^75ZS203IVm>>GmDRYHlNyb21Z8c_RVw|0g1|9_s)c6JD49^%3J5$iX`T;mh5cAjY_!5};L-D^M$c~yB$`v)+v@2?E zfyOugOaA3l4X)oo`zJu-FyOvf&4~c- z|1ZF81dv-Dn;3HHfBpyng%@b9-*Fzp9E({D%%HRd4Lct1|9>i>egK_G#_aw7$ySgb zsvm>$*OQeK>KHhxox$w6pnZvTM>bbXsAFKUsAJ&qV5kA_{R7>b*-*#8VO`C@Sigti zLjCR+0re&9Tk7|N^6!(>no@9nRso&2QMY&%$S*A3|DX8Q@0Aj%pSuEdx37rRga3a) zZEf)Q1|$EOy4J-Npz)5H%3mTL3^kB7bTzl2`S^+81aSWUj~H|0fwjl^LqY9}nwgMu zZ9!#;MN90>ipAn7p!u|#yT%pXzc?Xngc|UknGoxm|9?Q^y!G>bfZF3Bp!z)gnSd3z zEv0fAT(*JQ7OxfmpLp%~|HA9U|2IH=MjUr0t3cKu#=iCbr3S9+t@ko;G}Qk8gBTNj z95|&KT<1;zX9iH22puzprniYd4ua3H-|^!i!-1cS3@3gnGF4DB- zgZSg&LC{_Bp!p$CI`;nma3d()K|KC$`AE*pmBo#KA=7}XpXAB2F#xT z83*SD&1r(772a3!VB|RoE}KDphxy7Cps^b31_s84WKfy^FjBjjLET|4LjtJp39`Tb z|05BQy!Zcyw)OKR96;giIG4epp^ky4e(x<2@Ba@~>*q>1fZ`Q&rWmB0cqjno&)zMG;et@a)Z{t zfzo+}_y7CgvI|sBg8JeObqpfb5B`7i{(t`@Xs#U;mJV|nEE?)SZIb(2EgBdEz+*U& zHn}cTpNjTe20_r+t3?8Xp!fg#y%Xvfz;o@OJmta24VsVmf-K1;s7IU-vCR;{>4bV$hfXs4TDl_e;ca4nsh_^&=6m*!~ls z_B<$ku+;Cl5KzDWm5BHM`;7JXq(Jh2>-T25M!V4Fyj&g*U|g6D?nvu$WjHfkYfsFpz;sghpv+b&56Lu6B|&R*Z+SJ z5dL4m%=`bnT2P(`r9_F91UTQ6W>0L>AC)Yb3% zB?9W(c>n*m6{?@7zV4^i@3{=1J75=hFmn8Xr&D--@AE5C#P+xLF^%J!xH7&11K=Rq;*Ax10Ia*E$}dh zw)H(2*+FC6iuO$Z|65By>P%3d1l%sWZd_6G)4Jki1lYgOI`sEONcv;+0riJLXE=e% zDNw%m{{IX-h7Wb?4bT{#e&_%H4)Yi{Ak^Fi_xZqmv^wbu$2p8k8tOrL|F&m+yp%}Y z;ms8u429siDsa63u6u9mg6sj$6**r9m0{rZ7NB!89Ge)P)K}dIsIO+<0;w+DA3^h3;QhSdc4QHFKOMNvjzFrj7rzF@-5T$oXTW2Yp!yhmm)#VQxwjO- z?MiT%-4d;9TMSyq!%)+_3OwHkYIk`5|1}d7HV#eyK7jPr?FQ+)`Ld=)3fhjmc^A~q z1h;AH85C-&R*85p6e)tz5$OC3$Q;7|h+123P#Kp3%737KOnoi5z7GM9%gp;{02K$F zQTV`vkrlCj6WS(4?oXhNTcF%g3mP8+%@uq9{}~F(N1!Hbmt$2APRf1U=9$$;_}XumV4900`)C|)dG0?t63dobif=3tk;t^n1W5U~Pqo`dxFuFtKh{;3Db6X3Lq zG}q$T#317R^CY;f13GgWI-Y&NgOM3p^e`|sK+pUD_ccLt?~7sUmXYUKbHQahC@p}} z1gMM#m**Jk2L2(&=%Hg&9*j)j^DjZ^6I73Q|Nr(E+W(IMj~{~9MZ5*~BSCQks_z`< zFgQTwsIMIa*;TXuLjWlKfWioDZ}Tq^&^S7%?+=yOS`o}Z5|fXvh|uP$jzYe_Wpkj?0- zFax#S>dirU`x-B(?dC9-p$F6^@cw`GFKEr$Ye$AMP+0@g3+lsq|NoK;4Tm|P{t7rO zz-jOncpL|6mj;}2P`~Nj?e^$Slfzx5${}+(@0knSSe?+YfxU5+NY5QHZ zt)F#+!P1IBqgL~jNKK}cNKGaC7RR{^8|r6EfcmN%YVA*n)bH~E^`WQK?|UUuzZZ0N zCqqZA?J1Gk_*)|ND+54nzYfrPpt`5KD?n`#h#S6eg34epA9T(KLoRqu&<3S1b!9K8 zF9q@Mm5m_(Lc-+AQc#$H_Y(ZSG7~hW)lkPE>tE|ZZOSi!kouJ&22{6r|Gx#U-$7{<(%-zI zXt9rh5fpczHfc>7`xa0dg{b|k3#m&l|Aneo@cw`KV@>iWXt{s+DcCQdwRfO4Aj5w| z8<3fS0h|{yr9pR>g@Eb+NPj*~4s^z>rNjTvAU< zcdjzawW8_^Gf`}ud}55<3q zpnX(U*G@CkRD#dMVtyG0YKJp|{aov&BvRiJ;NUQa@e3%ef!4k{&SQMhX!-vED33bM zVY~yLC*Gx9@p|X~12wIXaluMA&|OX`xuA1BYQ9@nc>jj%|L?T?{{lP*13HrzvFGx{ zOIrp7P+0&vdlwYW;C6=V-v9qX z`v43}!fV;=l=m_+)X#n3;4qf~yjJI>1%n01|Ddz6>z1#ss9*8A0(3SHXpKJTtU{0( z_``z12c*XP|DRllpBQZF=ROFiue~J#y7QyDnn9s%>njn5rvC+?J2>nA{s^eQ`$+_p zrmF8TDAY%Rcc?=DR^utgBN-K?#|DV)!YJ=C8gU;>%-7gJFCl2!% zLS9!Q(v?L^${A3a^8WQ7T>rncX3&6!H@Lh8&r5*DI+JhXOf%rI7=|BrtR4RU507F| zC_Y*L-@1W8!FquJX#ZM>_Wb()4s#iN8YBN-DD-4t@@oK>!3yCgS?sJE7=l3Vs*k-~ z0h))^p8p@DR-w?7fyKIk;fDPJ21bV_1_8%u3@sqFAa#&_+3&fK`1s!fx;q>c$FOn) zbl)5(enIVVkXrol``-nm#{2)TUZ{B{=yB-K^xwey|9=^npS=Hr??Yks{{No?UT#Cj zpK4uj5kofxtZWn|0AKE?o{||a* z7Wh6}P};Zpp6XzAEw#aFYihaGl+@LYcK@G%+L$1{^=%#%we}AzDlRi9)Z8@^sW`@< zP?tKp!u!`>@Sf5a`~HLbNT9Q*K;>ukCr}^#2P3Gj3cC{s)GoDXNzDeC=l$z1xc}?@ z|G!PG{fmJ5&I^$I=y|!K(w;%##l8POK;^yueDIymjF$4C{fCo89Of}_fa)h54F*O_ zj{pBb>*XPJKSK)aE>!Pdf5Gi*@LZqeFOm8g9uD>YF9cNDFep_2Vo-3L`(MNR|Gy)( zmKN)3+AP-9sw!0Iw}SV;7eLJtsMS=esMTaBsnojIWbvGV(fj}Z37|eT#O;5;^HCNL z7#P82Ca7Q7@))|#<(F(tF=!6ve+wwyKw)IjlG+c_S62-RuRq|iUhn_^T)^jfB`~mi z|M~+yUjbAO!ott{{~yhoLXbHO;CqVeRJ%d(xC>;C_pd+T_^-3>uJHc<_s@&E|3AQa zP~~(*P4XlW4~8W09)D1rfXoBCbJ=UC`+n9!-1qMZlKZZC|NjpfA^;^-#s+={2GCi$ z&^$f?)Q*Ao_d)v>>ZM_8XB)l$|FEn{1-ldJjQ`Y6-oJi>$AVtkL&{d=dkhSqyjRnr zC;*Drik1sapt`)G#e504UDU$x5?>nwJXg%{*LJ{1xn0 z4~8$GvHw8O_%q0lH5Jko7A1EcrPx8Qa6(7sWNg(AZSP}{|W z;fsOxd;x~~m%l4Ob%dpY07IoEXpbBNd#D|QMX2VBfA#mgL_l)@)yEhVK>cw@`TrF( zUjb@oxq$m2pfmwqmm>n6n**H@1!{*o%wwlZ=p2KB)$TGA}Mf4&9x4MA~ay?}ww`~QE$`VkHWhDK!ufkG_?3D7xo$Z-WS15}P! zw4?<<+u@C`AA{Sf?B2hAfzOnCX%8>U!F8a;g8% z4(^+CFfa4||CPm}f#EoK?MMOxH%59`0nW=D-v7Tr)59mwn2#Z74FNbz%E9R&8=M|M zWhH10&^K$)z8FTU1q__tKVO5}Frc!_p^2dbG=~c+(>xeH@o3K#V5ndD8j&t+7!*P^ zB`oS+uAT-SPf5OAQT>BK0W^p0!5|FIhe+|BP(pmh>2 z?cwK%sDRQNwER*4w>iQ6px?Tn`rEOIK>(DtJQzNJ+Vh+UegEHp(w2GL(SUi)nWT6DxRIfv;~_&;$3ce5j)e@M^DzE_>Pd^1bp7x-4th0z9#>S)U{I*%I9%cV>nk`< zS}HJbgZ7t$#uq?)j4htWGt{aFiCB6uNYt_ii8ONje^K87x=(^Zz=`4i3rKkXFKF~+ zV5si`uS-pN@sfezB_{*NOHT%YAO9IRe#$cl{ETOiXw+n2nP|_T06LfIryclCJ@DB+ z4)Yik8tuVlHK@Jn0_rO|HZh#BRH*;&!2qczL1ASvpFsgP~77p_mKx|KI!n{}hmVNZLt{vOWO1d+;-?{iD%n&!Av`fRW+#dn*d3!1+Il@(yKTQYn>Zu9>28C*X@#4;B`#lYu(c>n(|@X`ieu6zKi zf!I~z{p%BW{}V_al=eY(fa+}gamTO*Y(`7QJkT8nU^c|OQ{KNmf#(#VX#`ZJsX*P% z;Qjv_XzsKU6uw|REg3(&|NnOZ*$qjX@UaYbiNW-<+y*_1G}FiX zKPY`MFzWAOV3=voPy>q7pY{wMKkXR;Aa^1ZH~h3`h=8&`{Iq9CfU+O_v}eeGvM2ns zXDDd2XHc1F&rku{_c+m>p~2Fg!2wkMfzGh_{R_IcEE;2ujK}-uMp*rD!GqxyV(kM5 z0|TfW_icjQ!ww0L%=;F}{|`Xxh>6}mpMcvpgvQXI^Azy9#j%OO;zj-cgP<^bslveU zG6gyY>4F%81f_qdo!`BGJ_e_MNPY53170sMGB8xMd}sodEugTgUkP5H%mX^F0MuTo z)DTYrjU85MGAPtCJLuJN1yxjff%;7UVS8)AMuF;Vs2kyJ?ia}n4xqdW>MKIrk#))Y z=VS2NU=SbVK8u#D7v4V~gU{K3xa}okjSOrqh2h2DABz7D!s;u~SwEoq0kqBxw0;BB z*07Gs`UkDUet`VaXv-i_KMy=Mzohvu15f?`kJqgKGZ<9A1of*J&b?p!NW$|6c!J5fY}a7!(}mFiO0B3<}dAQO71m9$2`7+6y(;j4MFn ze6uT8kl zz@WbaG$zQvF;RknL4PNh%~R>seQ0JR0|Tfm0rhP_Wilw8g63K*TC$bAe?EZBhb~|c z0JU{M>m@uGg240V77G~o!D$0LpA!gPOAjqGP~r~MZv*Ye@&36MT>gX12ldY^TC%|P znD?)@;QV2|fFTXkezQz@uSDuQZ#X#4 z`Crkf$WT+?`2xhwu{gkBV6l*)1Kb~Neq7(5T4JV|{=j6?E3&M0*Anhk1;DEE*ULED{+y zy#N2IwLZX*2Jr*qlZJx~6DHhe;AnJYm@+Y*fv4di!;A_483Y;`8RkrsXAo&rWLPlK zo zzfWqtEU(pfc{qUf5`xrNwB*=<(j91=Z=yYe2PiMqY8p?g?{om|u?COv)UrBPShVC6 zfx_7P*DLV;A8;7`|33$82DqJ&Gt2weEAaSFLp?N3T5@)J|GW!s!+`t=I+x=|Jp<@0 ziz5y989Wf_fen0i5i~s@rLmmzP&>hC(EI;?9Z)_7m}H34+e$^(D);0 z4-=^DuU^8SP~QnE1OLylRAi_Ij~zT@XaViX0`(t2Ve9?>*G7oh|G{R0#>p&Na(+SF z{1RMtK-RDRD*@RFDzhzGa)Utruux<)@L+g^7~2A^PsjwX&$9E=Rbn{ zW6_e^3)>68W~y|5*Zrm+aFhe#wxx4|CUAC ztK9)|3#<%-%-O8~*MFcsxd+2T3#fM(;b+q@Jh%#4x7eu6AOMOt$GMR4NsE@;8K6Fw z_pj&R@()z+g4SAiFg*Cue3*d;)UK$%r+CfMj=`W3G~YOfK?YQ>H6La$ssA4&3K~xX z)v2Iye5ju{g6;wVwL@U@Ti`MKmfYh|d%$z&4fh!|>f0VTfW}S0`Vtt}A?1GV8}DDw z!RI%E;??{A|B}h`88j>!7-}GC>RYPC0fq+fxapD46%*Otwl%Wf zEfp9zVEx6K3~BH@9mrgZ=LsB@p7JWSnig8MoE{dnnhalRH5p4l=cd+b1{hd+F)-F@ zN>_v`v)MT@{KtM~D#QKMg1rpvpuH2I`~&p|vqejutoN^H;Qh6ry{n*cC=Z7F9niBF z|5faKamc#){}0eyptVE-ht>DIGOGg&jP-L*fWia3#|AVP`8tk)p=%!l2V}kBf6JQW zRTUMnV8s7c?v;cre_XQL*pEA?ud^ zKR|7U`neyF{r%uY4P*~J#IApiFKrk&XVf!r{Iq9au>Q}$3EB$>x1WW90dz*ILlXn2 z{lxgvnIQ-?hFP;zNd&ZJp%Qdgqb36*=zcO#KSoEBfzeVEJpTX=XHfos$;{wU@k(B$ z=0uQ4Ek}S}U5A2$<5UKTMmGkQS}!M&`YsL7nid1cDGVa@tq!0yEIRcdHFFt65NZ@a z;v%4ayZ8V9b3l84KxTvd45Fd#1yh~M3^t(h*kK-n&r4+n4p939+81;Hl|Qh)5V$Yn z$-sc^&Pw$D5y%W!9|dd)biDzRT`{10%t7j)b_Ia!0`*ZqV|Adjj;;Um!|$1ReV>5| zpZ$~XgU>B$@L;$DZeL;84If{-6AEf0fYv*J&eV8m&maM{p9j>|0_A_m`KA0fEFBoc zKy~y)Pq5jLGtn6Cq=43XgUb`}`EUP@g6ctsrvDE>^$EC+1dkE^h4oilKz4xK4w}0L zl_@Yac>4FyGiCl=1+~*G?lQ20@>9q?=osrgBN2<1ymO#(4%A-s{&^K#hJntQ1g-f- zazE%yI!2KDA!XISR**TM{AfLBnBmqzv^asSCm=FTZe0M!31|=c z9MJyGzo4~rAooGy1T=pFj*~x`pmq)DY_FI03<_ZXg66YQZ-duUg2IS!ocwjf9Vhur zh&Z_nIm-ib_nQS$SfItppO1(*$(Ql|c^TZk0mTV8Y*Rq%X@7&q8bNLco#TmQ7IL_5 zf%^#-hfsgx^Ao5X#*B}fmeBYBm7M~xxg9)t19DCq!_9z(`wSMKJv^ZPXU$0s3sAY@ zIFCWcCh7lwi)4uh7RSJMD*OY@`&zW*n^_+K?LQ0y?-u~g!+8Jy4LZjJ6nASt_JZRG zw8oSOzkuS;`~UBSpgW}CeuC{=V7QS8^;05f>z>ux}OK@Wx- z6`(l|@cColwDs#MbgcRT$PBRiK;cb98qx=y<60{XnwvLiv}dqr*vG&C8oQ})^>C5`0dwG@Bc_=@WA#&FkA=iZ&s|?sa*+MKZ?9&6y#q} z+5xql9Of|~r$u=A240JVyjByuH-PDb_s@CY@xMl81_#huCs4b}`~M$b&=>=#O#qJP z`^KQPaSWif{-8dWH|T73@IHtCYryRyP~3srls~}pQ=q+;*8d@8TKGQ(i}3%TdC*@X z7A^T#s_!!>fc^UO0;Dfc4sK)1Afj;CZvUpSvqSbB^Bs zA$J~v{Ovf8!2lGVpgA&&mi%|#KQDmSF2l^6e3F3yR6cqC|M$o00RsbQJu67PMN0vP z_sx{|U%kE!Zpu4+h4PhJy?x^{;+c)Xz6?s83_KV5#>1e|_}>i(1VG7NGS% zm8J{|pt zkNzwMhPrL5L_lp7P`kuZ3UvM^#u^C~(3y7*^B5ZHfBgsm-Kz_l=c}H>pipml33SGd zNo}OXx|*#P>uTLJDnNHagW7_idR`k zxsjm+)ZVF|{YYeTB0~Y_?1PF91_e+avE+cZ2^km|k=CSmG}aWvX71pNNT-~lSrCfYFsfa(@V`u=~$ z`~UwONEkA-OipEBXn4p_(#XlcQr{B5P|IN@QtQsXWg;g7i^E)o6wtX~jf@Nh6))vg zYW91H)N%xg)W&=0)prDd&U5G$X(#F4r$$G&0%BEUK$?npEJShBOra&ONe#P&~g?u zj$qNi0KX^LgTVk?$D_A>;dKvmeXVv20~4q}?!j>JAZSd`9y+fJPA{PS?fW77+d=!N zYQ>#FQ>H>Hq`7tCb8)^<9rE>Zd%e(4We{P_+`g{sde919TtJKTuk%2f8!b(u+Z$k?a4D`i>uI zXt=|`@nR1H19aUJGq~?Ihd}@|cH{l)I(Yo6e(nke$2tFRSRMHPALJ+Pnc%af!Q)vL z2N?K4YXB@-iokPfAbIa!*TM6D+VdF=K=T*c^BL_xXZ35(XTRVukHJ8DIs?1ITm~Jm z+Yd0XgVy(3v=rR|`NR9yb#VXBdI5u@2Lpo-sLTh=WjoCK|3P~O1L%&fJr)fNyr8zV z<6MRY4+dWFJps_V#0G38c&%@-r1b&@L+@YL!DHj#yJIlspO}w$|C|oKbELVEVUMjH z1HYwaLPPzWPa^euJRBV7F+kS6wiHK!+-ALi!PfiNHE_BDjazsy@PfyoL3V@I^nlC& zuYU#Y0h;$n1hnqZgF$H`XkbczDg!^Lj0L-|r5H3XxS>&z;edW;DJV`LVF_{f1@B+i z!0TTjYD=_0bBG|nJI-ZzA#2I3V1JK+-}+ucL#^j0k(!quw0=4=bksa&D5-dUu?Z5! zi~(W)GgRywY8cZ03os1{p*@3vDgA!~14z97`e)FZOPOj- zc@=p}W(Ck4_Vt!QA}<{o8tSz?wVL-aFo5E~aUSCau$#c{EInhrfWgW8*H!TNF{r(S zkSnwD{&f{Rw%f3efdxrC)ce;}aN7ZT#}9bi-lCaRe(h1TU^ODup3m6={e_a9lALRGCrK>9} zT1viy-0c193fTW3anM*7s6Mo4DV2xHLC639hJ??FdJ+DAqEy)T43+dbH4OFtcUL6O zVO|D`FHoKC{r{gy!#xIuMmYu+P#&>#U|`g1gRBK|oWigGl>0fUi6OQ}25Uhv*9>jexh-v9sHsBilL9%HHRcmVR72B>bb*aw~i z5@?iT5CP3$*8SUE0ZKQZbG$))uKJG072q-12jF#-FFcvnu zF%A^Q|8pGX{m)2$-oQ}bX5morpFzQ4-v28gyBy~IKcn5nU<6vb2Qu4X?tgH(2X*Uo zh+8j%+lST*80@|O|IvYr{hmRbaR}YJ2rAb-7*2ouq4=*6UZ$5xSAgbcYPM@b`VBv= zD{5t&D{8I0D?s%!q+Dl|0JQ@^;e@qJ2l?;UCCK>K9B?_N0S?axpmqoY185AvqNVIT z#I2XW>tC%OFfeM*W8k-zV-Toj1-B7ldgLt*FbG(*lp8_SgX7=&0fQUpY!Ybw{6%{% zxZHaKD)&I`R!F(W0WOE2c>=ZEdjKl;E`j%iy;NkB0Qn0x{tIfGI5x3u@%}jp+;(nM zWO!p6#=vjsmC#VDxk&`P?`j@{1=vq5<+UJpSwCR#@cwlXa;L@r{~J6QIKX?ZKz4)5 zJ&+l-W?mu<2N^zSw}Hzui2oLpGFY^f?*p0P{p%ulZ4<=Y5>T180^~2pxr{8@vp{Dx zGu&~U!{DPm3w+Ky->g6&tgXsPglnh&1avVOqe>;3;f zkNiC*0Z@P6`koO(t>z~Y&^@uB_A{uh3z|E%Xk-N4O}4>4e0jRvZ03QDb&0!(weF)VHsjndR zK-Y>?fX+!e@}iMpg2h6H3Xr<$d-5tC4AS7ScTk(Hrt<@=Y?T0&zaTXp4AS7b*Zcp! z4zN8fl}kb4wklcg z|NnYG_ddYQYGn8U(W44>ABgS!|La{WdL6z0{|k71kfFf})LsJJ`NF^eTGPh>DpSE` zHZn3m>Jn3M`h}!OJqO$un**9BcbLa)1BpwjSSQ-@>d8{QE7^@{fb7kPRG%M1a%$0|o|g`iG}| z6>$7O!sp9gD7_U*uZ7Y}5#h!Z19p2$RjT*@zY>-<|NnvJV;$x)xoCsR!g&ll)(s5I zpfwZPa~Rk_Zntg#oiFw8iS`@@R)={EDeyP~`5*2MWpLP{#XX;Kj8KF7HDO$_y1o@v}b_o8O97q956!GtStcTrK$qmS;g%A>kPP!Vf_F! zXYlI`NWJ6S|97NO=9Z;{E?$jfEm(g9pPAl>Yxq=$_2_l?vcF+#k!pXSDwJ zYhX}-_Vd6LXs#4=&j)B-r!7N-CuqJUkt09>Huu}<$*7>;#lQiY2L`ndL34hfIpU5? zMn%}%FZ#KF7Rd~pAbUV&foQNrPy#epV$1aZzaQ@FZ zfWz9EVM?Pi!3*X+y&n<)S`uj>YA&d>+|9_)Y0sz#nhS84$7BI7pBFMT zz}94W|NmZ$_STRwNVMB8w!;0ochBbB%8fEMj zFft^4pL^8mAj6ER?+gk_TNx+USN{^Jp7Y{Sebwy>&>8A46&V^pW001f|NsAVWN2`h z#~=bKJ3!}Dfa(hm2F59`6&Wh(cW!{>l}HALMoR{cpNZ-HvEB>1M}mQ)Q;}i8OsoI@Iu#if&9wUe z9~M5KwN0S=<|cx|C=#5nD=ak`cz!B^&OZA$rB>6aqSn;&TBQcK4p{&i@2StYT~WXH zfkUnBg8ed|DOPjMT5c()NTfa2k6`y zPUEiXp(_A;S!C+XK|EZ)E6zs=o<|mwz=c6&WT>ddRTil_Nt3 zsLk+7kzodSOi+I! zO~xsp^Auz?8F=c1JoM@Wn?&m8y#Vczz94JIz*B4FCE~%rzyqq&>+i8|X~<+?sAFla zsI~U4s40{Z@nBG22x{kBS~Ku~_K|_c-Q@N%@YHQuCDKp|QCqijb%oW||6ic$!DB^W zwR0H~Aa?zq(6F0lVX4Tt zq2BY7$mCuBe$-F-z~C_VUx=j*17mfUcnT;SKw(*_DV|d65hMZ%H|seJOp{Oj`%yoK zeaobi|9*J?|EE${GaGbH5oq5ZllT8W1r~}-4jv495chisGJy9$gYL-mVAx}cJkAfQ zXF&U(JGmIRnp+rHI-W3aytDVz(iwvZXdE20 zW(2g(6Nz} zUpAe<=QQw1=H%G*h_(l;=R@I%xdmr4`7(jG(pm4Br30 zi$dJU^r6w7VFon+J+Mw>IALke5K+I|15%D6%Iy;q6&WtrGBkqftP_on3}Fft@^ z%spyx^Z)-!4hDsUrHqq%o-r_j#t%XJMk>8t90HB)gT{qwJ(-s|F)+Z|(;F;W3Ri&E z5P2}DgZp^a4Gav`ooY`&`@yQ`GAPu{_R#WRP}vJg;~;lBHZi4u&c@Q-!@vzXPaD)G z^2Q}s*Ox5%e3@PPWkwVF5dYFa>fS@|Q(FQ9$O zFFQ`_d9AuBf zy#GrO=KS*ko$&+O8sp431|?AY>L=*T^*9EJPEQ85nQ;sXot_NrGvgQ( zE#nz{>UTr)pge<5V?0C1Pez6l6CD{YfYKo(fBjvtP?LeB(UIWdx`vv zV-R>5&md5%)6Cl+_aP9e-Oy6U^h83?3pRYpkOJ_-~j3$IL>1bc`47}&=}9)@sp8Z&qPOt zBaMy>&@*oSHds0`Hh|pF=*X~Vq2_LD~ z|M31n;ENUp(6~v#OURu(;CrpT|NmiyrdtWn8qSxX`$Hgo0?@s^OxW+Lt^?2iK+2Ns zi1j@1HCEf+g4@Hed9FF&vIKm$2&kP48Y_ggi@pDUg4U}HHkPprYf$ z%K!?0M7Vt12%XObtzGyJ8WXc(~k6N3pfPn&@9$xmBwTMT6_E-3$l z&fxa`Sp%MfuzmmWq=CfY)*0ya0lcrZU%LXf-Wb}~3Ix?#P`5(U&`Z<>P+ATlyK;aMJgVz220F76J+9$l;|NkGb z0G;Omxzpf)2g7EJ^MBy+vroGMJ)eW)2PKdH0N)|z(8M4C^#coNT?WW*xO-90NEGq@ zSp}YVgt`NCM)C#^hRuk*U+}Qq3^@aLJ~WSm&OzJ@IurKYM@U{`uz4|$L7;v=c;A`@ zsBdoR^8W{@oUPyQ0qU=+6u)F(2i;*()AAz#Jg0A`pan|Hpz#0?hRqD1zBA~)6pI7~ zP#Y0(*BLXU%?1w(qS7j??ZTh|4GYknub_2mp!fvEDqv2_ zgR7OnwPYdv`$W-w-zF{2g}Cov4uXxCyZ~86IXE?}E=DUj)755@&k+mI(_( zEa@=?i~Aj*=`jH0p8AtN*Maj9(pm@5`CQ&VE5P&LAT^-0Sby>-C@q5XQuTj%mHLxE zL22=XMFInsw73y59smu04~C84a}nU-AJDw@buMV{1@!DNP#FPAgAK1i zid(3E)*11)of?g?O`!F6P7MDqyi{bo0ZPlTItMf_02wDQ0=IuG6d6Bw zFsy+FIRkiH8{}sXhSiPW_GQ!m|JHL(GeFBNMo=C>E+f4EKM#e)IXG{?&l!I46qL?D zWiV)r6r4XG<6MY#Hd0=9Y+_j8{j&(%{{fHVg7eqEoe;DCUxD_6x#~NAfX2U$XwPTh z2eq5!|1X?_Q~ zA6nEIcAq4)4tpjGI{X?$vm{5-N8BG?wT%kMRJger>L2WcaDb z&;#0kIuW$@95lBA3DX^&jtm{3bPVZ(GB{Xr{r_Lf5nusIFAnn<4C;3WPpjV>c&&c# zjR5_*;51ZGzc(NNv~Rb1DQFIN2WZ`|heZMdA874|<6OoL`FjjJmW~WPmU0XZwen6P z(Eg>wOGkzt(3tPfI0gssp4B)8kID6n;BzBEYeXS=^p=PRgD7~76ev&DuY4skc|Riq zh&@pev<{BJ!lDtj@9ob;Xk3BDp=&_pUVYaGP&`*Og2uNL85%%wG|?WSzgF{+NPXuH z(3oxrXdW4~R00Uiecg+&8sZ0RRx zj>nOqW1=U6hyFYUcFsp2947=g6|{Cw*-yFfYvg4Fo=TdIM8`o zu(Ss{s|4f*@BjanSST_wcrdJh%@Z;RKVuY~pkk>^b+Kgazwa5>qHNRWk-J~{$qsoH$m!a z<|`fD?=MkM8Ugvo`~Ra>s9RSwIx-e$cQK|r%w^b7-}M5t#%x0)BSTBA zMvzE-rvoUzEGYBBR8=NTVVn2V~rhK?O7p2W5lKvilESbI?*Y0piww zjNtMewQnoq{WAx=h8sGD@BrG^xnZHm#NffO6r=y=!LSr`E(B^=&4Gj!s9whmuOCkl z;q?$!{%=4EuLJd6;I()>#Vf$)HDQLE=Rk(rpOe_bEgQW44STpPIRLFB!TXMF9YRAx zGJn)1dWD99&M38YFg8x~GB&QslnAKxl&}a%{;;nmIluyRmUu|!L%Ui{DG{3le*T1H ze*T(d4~vk@Lw2CK?2ybBJCK@+WVQw9^TD8VkQ9;`*ea6wAAss@bomL*3>fD-|G**! zx=RpU?~7ziy^wl;G3fkba9ay>2NtOQu09MNlM)2wq3Xj7O5Xqfvx3@ApgUl|cl%{R z=8-}*Icz}wuSsU#;=!;OanAuW`0Pf8pUMmppgo~Kl^GNol^FykDl=$+%E*bz3B&2diXUu zGiVfgFfcnbF~oqwB*VThz;g^@p z3<~ut6hQrD(AkNM6PX!6XURVB{{O!ew5JF(-h`|dqz}mrj1BPfd=`S{zY3x4M;1_e zg6wJe54w*Mbas?Oqb-9@`2Q0;_5UANR6k}=0PPI}xeZjtc>n*KtB}mV7?ON|uO|6- z1t?E|!hb>?1H(jH27~&;4B&nW=*$EUhJ`Zl@Q1h07J%+UNQBxC-t!OMe|HCT2jIWE zpmgHc#NdK(!)+8dfY!u&|Nrw6mm7Z1V_-pY#{!5u7GU)MYg&~nLFv&_fk6nAk6>{D znpX>1$z)gGsR5eP0G-9hInkcM;6*)y5hy-97#3uJ=FUL(8hQW!j~K6lhHpqGlO4!h z(7qlNbLTNY%u+@%OQvR-b_HmiutfudzxV%t4^htTgqjKJqk_ytF|P@19y6-j=AUU) zX3(&8VECWt_5Xj(N{xV;rD6p&OBtuwsxmY{&q4#`7Z%VMR>e{#1@HfVL2JtpWhuJUwG`Od1hS!4U8P5puFYE@bHfv6`jc6(Bc9>K#=oxtQ+ZotEYrjBYhMJz{){wVjf$GZ+K@3TQ2*+$HF(~` z`~Q!Npm{w|zY`QE_46OV@)YYtI|hRnb>KX;z=L7V7h7A{BTD3uQHd>Hy{dE?l9)YF>?G^@hP+CAs2Ld6T>^t;38Mr|8n06}zKWNPf zD6BzcWTNJ=|FxPrX0@6gKcHnQs7zo*4f8o1$nF5uXCQZ2G=S>8U!eWzh&69ew~+7W z*>kkpz-O{4*eWnECTcP;R%$js0pD$`X<`O)BWTT?r2+$Z%o`LoAh*>lHLj>x3hvkF zLE_@)N^JSXgJIT1@VFFcdW)9Z6_$LLDPkdtpfwUtsMggsH}jNQJ`?) zKnj-$9t^Xt1n*lQ20F8;`Y3cC@&BKOpt1&@2ACmp2HGtQZ0K?0IF~^JRMu9sE&!eH zQt18vXDMi23giydd^-zqc0M$GL3=sD=AASK_j795oZ;u}InH4a(Q9E~a+t~>qTj** z+W&0>T0iN*z#sz3T z7=XqL9Of~c0G%mS@sdFSlwKX@GK7?@Z1@oJe1lNPQf517{{ysMLl_iB9t;dKK>M03 z8W_q!2d~1l6J5|G!T~l!Y@*y#N0I)e9d$;SJi`4UaQu7=yyMqK*9+C_mL4 z1Lwa$P~QqxE_(m}eiUKe48#~HRKIo$10%=`kbamR&^k2jR(Lte1qv%9GZus_-5?aw zvO@rro-3ZS9|NW7nrF@xAxl|=KxY7f{OA4uJ7_=184UNr=Hlz6D`0(EsJ)J$wlrv7 z3ACmW)Q*Fmfg}KG1A_1Dn9E>bsldPsa?eXeh7};Sus(bOWK7=3v5C>e`)3@u{{!k9 zfW}Q<{Ab{JDbFDBBaxxtMLmNCcwGkQtc!;X6)*lX82m_Nm@%P|VMa|$KmceTF{oWy z)8Y{D;~~R>pNb3{eVcHgW+(F07(b7pFXpY{4 zfdRZf2~=N!`b(g(Dh~z*$i4#5eM#VXtZ9ffWsD3AAuVinoyrWbb9>=u{M5I2IDpm~ zgU-%HDxbj4ut@&@zt@?85xUM-pi>2|U!)_2fuSZjAOK`PsO=6u8*bkJH=sSw-v9r@ z(jdf~mjC}Po&W#uRAFG8tHr?Bs{&pZ3>u^R0MZLq1SLT6UaP^r1++G^*4ay>)9e3# zNICQWO)ax?1-g3B8Apyy3?4NrnU{gx%gn&2zXCi)DFSmZ=zL5k1_r2`9T0Br@NjTI zxEVChh|wpubY)<)X!-viwDt?MUc1)?5+0yB(_$$Dqa|o>^-A!%Fa?m?K<>6!`v3n- zPw;ucSDYCBgZ)^`8MqEKzV7`W^E^}!hAFANwYx#%e)aobSAg#s2aikt1Mh*VpZiFp270%o!`%M|>i0izaG3Ld3uw#? zJVp#&ANCKtpAS->{hwp~AH0VVQBSinFlaAjXaM;Yl(#BYy*LE2ALMpW7&tL7RDk{M z0NTqB_IC})-(WQip!K`|FBGaX)Yp1y1c27FJ2WvERC=5|RO=pG0Xka%G{#lS9uQE= z=_KOBz@Sj+%9c>+#ijxpqxJs(e+nr4W^#hVZchz^`x}er{~JJaqz?1`_x$K&V6a&F z{|9Jn9ked9rV}2fHPGY(roiq~fV&TTk5{dW$GTc)&vhX4LHQD_5K7c90nhCU)T(HS z)Gr2~aVUXih6Tuvma6~%gTz5;4U{%P>%>6m)rkQ#_Q;@6%i^)FmJ4JD*!^$N?1YW~ zgKY(w1Im*ivz!9HpH z132$^Fid;{8h7{H3F?Okj7FoO3O)+GM``w4W; zjt9d;#J!-P`CiDmiaemRR$glIfW|_>d&)XqLiZleV{ou!0iDOez*FBI0NOun)9V2% zAO3#;qdVGfqO*Z$P65OhMvk0%Q!N7Ifd< zFYx+&o2LK&En1p>SU+Z91o_STXD4`m0y-Wc0y;YZbZ4OV|36?qg2vk*@ioB)Y%plO zEi(gyMe_d(pfM4JWCl)Lxg7&& z%+gT#|NojyNdb^wLGcWtp>6?FATvUh**;ln{=Z<6{C_`a?IXxuMNI}yg=7ZSN=^O; zAp0{l85lw1nKjAY7%<4ZU2 zJ}U6pj5S@#pnF(2EFBpNv|AZeeq@2~Jz;R1%cuemYjrh-ms|`Cof-@b(D+cPdFf+T zr~#Bsm^SO$Mf)S`c@>=we_%s*f`)Gyh)*&0w?B z?qJ{q)ibr3>?WXgy~7*^pPE$3OQ3edk1hrV(D=6Z|NlqyTfuugCs=a+pC8Hr)+gx* z8h_CIzp_@7-2|k@lJoz5n4H601`X&MZVk|U6euiV?N-qEp!d&UaNe-g{0|y0I8c+! zZ~;^|gT~G9#ZgU%awWca0-d*L$q0?342a(y=Q2c~#E}LAL#HPL=!^md$GHqCHBUm! z3Yx)j#a{=!e+Glse}KxHpBmse zo&qw{Vc!1@AhSSe(_!BKEuEeWjQU-mIQ+i?#0KqIgz{&A;|-!0wAUE4j-wgV6zMeBM{&)e8uLw)e|MNq=!0OTC>5Qf4|NRKL|2EJ#c!DqN zZJqxAw@F}ZPDtkX|58ihMoqHkC7WahMvLTj<{w!SH!6}_lF-W(P(B9r5g=ohpmWW; z-h%Ebgs-Wnl?Lr`hpyLQ+ySarJs6n5d+R}K0YGcJKx-CW)G{!6|MUc(5A#xyamP#4 zHHtjmKLf%0-$D1;LCV>#E70Nwybh(dfk6%A7E1*NgNcoxd;YpWcm6uU&uRds9v&JQ5Ohtw| zO9ck=nTibcmI@3OGZh&cEEO0mXDTu@S}HIk&QxS*vQ%J5nyJXpY^lJIJX4XO#ZrMG zWu_uStEB=%>P$t3HcJJDw3&(w?Uri)|AuO^*lBk%@H)&TUhfY&KV-jx11Nnu&Si+vQ)ghXp8x-Uz3b;mwN@W5fyQ+$6&WVftke?eNd5o9 zaS|vW{{qkLgYOaA#lQfb*LA&IQIq*_9k|Y(_x}h;3^bQk|MHgzXx$BXt&=tSTBiW; z`bSVZqgM0tBv3m5GzSjqOEoq!aMVs{RPbQvgw=V>h&5atpmmRlptb<`+_=5kpu3V7 zUMDj!fc6)A|NjhjU;Se69Uda!__huRs9*U2GzSa1Yi9w-Z5|9APik#HtOK=0W`gcw zwTGOe2U<@CIztei2H@?U4$%F0fuJ-6ws$dj>;QDH3>Rqq-0M09h8oa09a7E}wf3Mp zhJSfq}8sK1ig#*@K~0i+zj3Tn3k#EQtWnT5M2# z3MvB}=P(G^Iy5lUH-q-xF>rv!K45#?Kw}>-{xLArMq32buLAo`0kl>W6qgJc=yEA~-hJ(aG`y5dG2whul^XUJ7i|3~qK<#1=hIYpvivJdZ&aC^9 z$k6eUoq++g=K<7b0^L;#>N9}WyxBGV|8ECcqtEjHzqJAbgVmI#4OYd?0-dT144^Z7 zKxq!trmO$f%zHzRzWM^RPRb^nTGFUM%Fj_uf(5=1AaG}!{QkQ`DeK0a~)W$gk z)b9uH1?H(!1Kq{HW2?X-hlX@vBc8z{{?87 z4yw=3fc#_`!@yYI{zzn|&Ho#fF$@YG3=E*~%y68?3>qs0g(nXvd>!WfKLQF@ke*ui zMszW@qYEK1N zfcEgzx&?#IG2!~@2wq3B0+d$jR;&h<^&K_y6aqkNV7>qUDFmr~>Bvw}_k1_#ekU%F z9BAwYBo94n-xIVi$@~95kUxtZ=P}lR#vnm)=s1tz4k*qY=KbfeWMsHt@qj^~R^yQf z=$_S@t{(xG3=9ghHUHnRSjYgfp9x~#@4p~B!FMPoG9bC-cP>~Q;tl~&e;wo&P#+hX z&Lp%u8LAxTF|mNc$@~Am3sw&p7?JG-*$MXJLWUI}dqH6Wva`0tLkr~p`s@gc+O+73 zpNR|&ptDVp?E~5MGLfO7HZ>ZwH<1Mt4eIU1b|NnItw2pUnCTjeG&qR30Z~@eI0h`gl06IGb z?9ZQ!3>Bbw_Wu73a_>SW`xej|W6*e`_y4!x{wZkv+e=1<3Q$~w%F+5x2?mF`3?4Pf z9s#vpKQPKmn+Krs61=Vkv%EaW&{6ZkAfSGg1*jZS0QnabUm*8`{0mAu-v58j_5T0& zgvA2}g&EHn7+!$(vw_-24?$;a{om4Q%fM*uz`&8I$&gd43E7hk>hIL=^#bj!o&c3+ z((h!*aG3YE0h9)<9YEtWe@j66y#N2r0ha|!85lv~1BwllpARsR16sjbyi6sXkXUougdfyGjRAz-31 z=DGt=8woVt32UE$?z4ruyUkj{1Z^W*n^?b1s+z=@p%u1hNGalAjnv`BzV8r z>wlnf_cb_;f%?{Cd8`fe~aEDD8PL zH0*%e#|()Z(3%sFzd`K+sDB$@KLOeI3Vc5gXzUKjK3G4r0cu_Y+&t)*F=Tu|k^ySg zMDPFqz+?0H;`K!`_>N-OS~#$gp!fidVZhA6mS#Y8oW((g9iTZA(6}VJ9iTLUG~NbI zLj{=(%r#lk6`(uOKyA=kW$$aC_LQt9LrQ&T0Qh_pO9jRWwOZcSWHlKl)G7zzy_dq) zfq^m6E3m=h0AsGj0)`Y1hPtny^~cr+7;LN)_yj;}_dsicYB_^1)p`V8s%2;2QtJiE z`|MllyFOp5&$@lB{?6xX^7j~Q>hC=Wke|a~Q$Hslpw`{^nk5&5tECpGEuej^R#ObR z=iMT}(u=XMR?|tulHp%Lt(WsPO9sXXwVFX9wVKA)EIrvbT6?l@s^xONRvRx?Q2(EC zimc|p$@R|cTWU3}MC$*8^!=X$(pUdKNTmM1M}YVLe{U@v7nRGP#+$2zaOa0 zD3i>|KwN(k;%0T9JQY8TR`o*$#)r8CeLMHm>A0-09r>@ku084t0tibYWvo| z{1GtuF9VMULmfB`fbWEaw(V>c7-SPQ<6R)*Iujc_7-~B~;S3u8dl}0h^iq~V?Dby; zHc(osjR>xI9m~M=x|V^jzS(N_O@>hC#;XzyXLhR$u<)Y^DYs{ijL zBCE+@Q{VX@Kzl!uoW1v?`Y5Q}%O3&SyBNfw`Xp+tyeHLHgXJXZJud|4gVrI;V>nZP z7_^W0?_AiJlSMLvj6L}7qh^u%-4dX3`#}9o_AQfT83ZQRGVsXXW6Yf#%fK=DF9Qo` zeXV`<|F4s68AL!~WL?b~A^)GjMm~y9p#I)1k^29SKxMR}W#s?=;5Y}xu_q*5fWo`} z|0NMn7}ql&5~-E|?XN?`H7I?6`mvT?%_6m$>|1KG4y~%c2U^?5z*v9slSo2xU_(uv z=PSR+V#xCT|K9?1c9!-I1|HBF7Es^Ant_2qdj|t! zee#U}P@56r|34`H2i@CU&&j?8d_IAtm&l7ukXiq}KqHy40lIG&bQcJyzYH4x2epr3 zdH=;>28Q}&4h}Ef7&si}F?iHN_U6`r#uh;3zvDcHkeU<5pmrAn(%IqvEn1q_c>n*| z2r3&O;>}mQe@+7L`vRE(Y75sq2an&Xz|5+64m!W;{~q+Rq~@e?#fxL$F^vk)S-D8_ zRp4?3R9=D0QN$jWM(_XsbwOnqsO=3ZuR&uB9t_n1AUA{dJi+}BFZ-*&Wk0A4uYs-u z0G)&5{r@R=?*`}|S&%uPI>7t?Gw_*f&~?wCej)Vy`Kk+`c!8vq|A?^w=(-Qkc(SD? zpN9uS6=)ow5VVIBJa-P6*JN^-$53Lw=>K2)2TY9CdozWs4=^Ys|K|jqvGpG`wrkPS z?%@4P8$8Yfy6YLV1`SmI)F1y0z7xk{0q9&_UmfpXCg6EOn@9iug5)ipXUT%@et^h7 z3ir{48LNYJR7Kt zt-mK-0bU;mxvTv@$UPPV0J!293qn;68b=kS5<(BnemGn1_tk6 zTHt-2ps;joVg%jI^%v?^MvIpB{NBGzz-!z={s6VHA$9HZxuCf4{$&iVCqZ)H_T>W5 zoZUlys2q5o7n+;FFGX&46!Q#s15Ht*rJ=3>nc^HNiXP~|e zXz%6%keeWSO~7*%p!E}w{&0H1>=d(MD7ehSKGptd30PSAWQ z2h%bShH}tYNFivAIA{(Cw5AS}r)usPSAg#H2D#h&|Nm5I-nCe0&%ltY1)4j#_yN?< z2KgO)4(syQ6`=5g=8K)6Gc~+_)yaa&8_+qY9t;c$77G~IKy4_CdQh9{3HW|Xkh!3F zeNegw+2z4dj%EF4*clvc8we z0G@wreOzHt$IJk3Lp)$$u(s?7_x}Ia7L+DHV{)LnWuYB2Xnz@~Z2>xS@V~_Y=5vtq zaXX4E>KGq@^m_mQ%Lz_HmK}>x^)kK!?d^A*%TNPqFN5a2JQx@0AB}X|w{} zO$?et{r{w)3Vd()1`mc35#)3O+Pe)J6N1#&9hKfcyTNm@Q1>uF+@lFj2NnyMuOZy? zdn>8!=k4(RRSBN|u|LEhW_^$Ufvtj}!cRK}hJ~7la>ijEO8`ipO@bk~46$hG z_?nOmDnlNC$A=+)Wzhktu}ENGwP@-1-V_>jZ^#ALNlMD_oUNU&RB$iB<7lRX&7uEaL2^HyWqQ~=`v3JOduD(w)BmqOJu)L+dNNeJILVOk;w3}IOHPJ@ zA4fA2kkn^D)fYh3gYI;n@!}*y!;6;;9WOZ*?^?J1FC)kRQ-&Xo(wx)oMc$= z;w8h1mz)e6ejLqQfTVr}RQ(31dXU-!FJ3a7c*)6d;iV_TjUPud4={sNk)ekFBv^v zaxwj5~fD&4!2Bk7wB$AiXb+s7l8ErWX}!&(J!9ot^le1aWoqqRzE$mBS2y=IdV5Z_3!xcEIR|L{{Tqe zPxkBr5dGqL?g^0EA4jv{VfWJ`y8={t=9ze}`0oC&X zs^`a#quEI5HyfIMv!UrXd&i5Dj0ax4WIXYblkvh!PsSTRj%FjJ$Ltp%bAPgDe*l^L z(z-rqQzOU1Ch7lQd!_$>Et1(^SX(~i_x>dVZhzV@Vi2?5 z%a;MZPh$ZCBd8p=cl!U=I_ja^k6KXMLKA$(!HZh(JUk;v9q23t?_V0=HV0@f&Sug7 zzhL>Le;h&c#*p%{;~?a`gLfLLKDX8*Nl`D5$- zOAcHIgUtR>4q6w+AOJPr479e_uIc~37v-S29^tLvb1Q$zg7+PQ)PvR{K-C6=&N1>} zkOAK#0FrZ@$It;99|YIY{~>iW*gprD=Y#4%iOtDqH!>RcvQc>j_GtAn070tw?-)aB;UhiMU;Q23*`|4D?D5>7}LsCsjGe{h~jt%Vg0}L#Xdn-EsLgZAyVbf^Fzys;qbzBM6R0pkdX9Uez6=_70mqSAH@II2jVEv)S9>Z$ z6zJT^hHDHKwh9dVAax)!5;dJ1EEa(J{q3za$2>2E9A_}9IL4sl{YwSh|MmX=PXUx3 zL1EAC{-pvwC#Tbvfyw63|9=+8gqjM~83dqxi+>i!SU!XG zf%SYyf#^{MrymqO8sN1tJP~^sl%B+LHh-Bf;yfI_@Lfu;MI4j|zCK0#rUh$|f1`_!THkBFd(&eDD9iZh*o7 ztiMI!Q=t|E3utW-#2!V^STv*eFBMx*n)m+y2UPF;w>Z|-<^BIZxK9PS3#e-|WPBta zT;_t}5)?-kE!{HSza+q85NPpq!~6fQ1lTwSsIIVE^#8y2FD39AKzRJQTn67=;QdPp z?0>ta|9|bA{{OX8`v2FC34FH^gVolq_f}H`SgnG5b*v0|yQ~DdCF-ZYU~riG2V_12 z=xhf>zLtZe%>~SP;Cu@1f4n~m3KP(J{KZxb0rl>eD?oQe)-73G0rFG5KKqv1XVn$n zzw*F!2I%f2P8OW^maB5mNxyfuK1u=y|OU4R;w>K=+b6&ie%_f1v5XfY+=bq!0M0K4 zqM&l9;y8l>B)=$v=Smv>GJy2{2Zv`%w;d>Nfz)~bQUs@shP&WgUn2jKP?t8ae%`OT$aA;g@zmGJZI2($?A@C874F=WB}cZ{vSN< z)zV!8>C5E?g7kYZXoKqpQ2*3=A0vbHoE{~M1562^dJEM50`l}zW zW(Mmy9RU^xm}=0}HA2*}gYFlCmgPNe-oJ9dWt#^B>y$=Y28L2q0S0jS0A6p}J;(e1 zk3XP(VxuN+$Lm@K1^rG2dr&^AuI6#5uKwEwO1l;Z7%M?`f%?>-J~KFN{(mP38iTZD z`v2D!)c$!cuVKj{A8n~ApY`J*LxtTVaN7L;laZkTG@oy$^#8vdNbRHle{B!_|6g6r z%mC`|T7&Mb*xG%=Y97-AtMAVzS_O6Aw=(QLX(jNU-}3$Qb(ZHk!u5B7+8Rt3K>c!u zdH>Ep-LwztCU9Te?$H0g-v8g$+AaG37o0Dk_QUcwlR*X~Ui+jPCJr9|wOGKw3`&cTb=2;Xp!5VX3$!k! z;Ud-4+WOKzp!QAo?W1^PCn77?*+5F}R)a8kYZM8V)in0M(PA z{0hknGT=OKaey%d6!y)Q3=E)hp{{vxh4=qAj1c=71uPCQMu6lIa<89)<_1A)oE+yd zd}x$odb7}u=~brZ=GTn7#l1`vDnS0;RLRI?#3+10+r)z;%no0>(OUoK%9^eyj0nV_@+DVs9D^V{HY9hjMxpfwDC9)QPkY#?Jf;d9t_fbJ8k zp2MI3@#Cwd5cB?@XxPOd0xrKm?cD#*SJvc%;_UwhQ22o26I8}~Ft~v09*`bTnyqhp z3~CoKg3_AzFKO^NPQxt*8<3v5BbzH~AA{-~X>fl68uy?*+%*li7(i_#Mo?OVssXnr z8*VYEfc3U4hUo>j|3L8uQ6~Yuj|5~tI9_id;uRt<4Q@|0+(N`FR2fE z0{eCG>k5klOv#{h@BRP9SGz}$`WSS6wAJ?>O;Gs*Dq|exF-m~SF~@noOd#bL(_N4r zSlMcy^#7mt{})?9eMNhv|NrbB{r?BL7ZFtEg4Wc5=Bhwtrge2+n{|}0jBrq^Q+Qz3DUNSPQ zc=4P8bmwLzsJ-jh#O&bxQw5KY-J&D7cQaSiqEyNW0G!A$_m^Ye3_%pg0A&w|@8Q3h!U3;BvFk zj*$m+E_Z$H?Fw)j1*hSE4Ry)0D?n#+dH*y8x2-^NXK{e32^0sQ@m%oO@Z#4M-v6H) zg4ftBU|_J0>Pfb??9l{;Jt%A)<}nn2?vQbq_s_xm|Bor4^w=fb!6c;RW?cs8&d?Ty3l%NwODtL#*lJqXw;+W9PeU1K{p|CzuzXy%eRTymFV6wx zyZ;jqWyOEc+HD4K9%=^l%S6Eaaf<~^o#3zmm*3A=LHQZfh6JT;Q2(XT485LWaDkQ& z(7vJYNl^V^v4CkR*qjnjne%jSO)03a^Sp37xunUexeKXqSsgVvP=z~c(+9$|2s z+F}9IBd|HeU~@`A`ax|(sCyh5jWOI~(P+%T0SZ6R{?4Xi1_4k!dH;VF2t9jA2eiHp zl*d8w?ENbR>~C0jA;Rh}2XdVa>bHT;pah)_QFnQBg~Po67i<N8PxxWl+oV*|2Ncq28Y8M zaNan;!Usx67A-xuEb5pQy#GIW3-R-xHPG;8@L&)EmmeT;aK8iG4(oa7{r}H|hDL@Z z9t@G-`pWzNpB@WE(E9cm1^75Qbln$hZ4qc32RvqSFAH?v+<(ygw#5Mk1&gJ<(iSZp zMWA^T=zLzI_x~s0wmE379JD{G`5yyMP4e$cps{!lh8V;iDd>75&^iT6&C{TH|F0Iw zSr04@FkJFrh<5#<_^%MOh6=pS{a&xMb#+G(Xub>-rl7mve>yV!0IgH;{{I-9zd&Pp zmR?y8K>oFU^-sZJ9)rS*{Y+r@TD0^=LgF(CTo!vUFo!hkXZ)bu${_DJ7ur^D=`Dt; z0ndMUFfbcH;}|^OYGi@J1+LxgAA876lR91r4A4B^`|1Hn`l(c-`XYKuq z8(d$5=Bg}O9`eKbTvh_#nXIjhl&tq6PSOu}aurlm5_x}F~d>*W=)BpdLUcDNi`619+Hz;2lbYBdV4Z0ht z1Ij)OI=>#m?lS`269cI)7*rbL8Q(0lXM9zw8F=kwJR`K-6eLo=7j#b#;|YXY7!Sg5n7jXV#VvOF(vc|KbO?O+fy& zn)02=(reXWYY7Gih@1MJfx^owsPCJV;lnU10mem^@B5i8&-v;=-L?iamkKKDz-^FU z;^1)xP+D`G$F>7hUO>bJz;OjCgFtt?K*S^=V{8W)=EK4Y6hE*q^#1?Q5L70@_!b8k z7Qobb|9=P`y94!KKz$RuVYCYrH!L?mbLJpFT6&#kc&W(n&pO73E$63?MT>`=LQ$5$>t?!_uqyL(MA>Es!~N9g9Kh2UVc?yPz&( zb_MACbx{8cw2#bj9s@_6$K;A?&o-qOi3}6!p6v$R4a8Wf$@;+iR~$HPTP$Q)W6{9C z4Dy!;0}r?is;L6iV+<-FG4KDsK;!5CLE{1!#N;VNL*e90Gi2@B#+L znl$MOP#?nkm%vU?+6CDOY6FA%3s7`nn634lWEu~tZG{sm03ae(&-M_!M!DI9w^`JcJ zFpoh8WVZMJA72};gU1K|TeS3RgTfz_*1dm4gX7)%|6i86*2NWdDYGj;;p_cN2%INC z=79Dm2;I&wgxcCpc-%g>v^8#p2`wYnc5H;N3Hg!!N zIDN@L-INGQ7ZxpjejxXF|NrUo+K)j3)UT0=gSoy44mNcV~Yh0OTh6AZj0Uq z&jWzM8?>LM(G0Xs0kn^tLFe^$28owu3>wvYKPXk2F*9h-Wngib%b)-mU+FvI{WA-k zhQV%$0=0vG&488*8K5xf9!S`jSkbF!%n&2VTPh zYBPiGx%B?U3F%K90Pla;FnJ-v7EpSx-pipeA&~)mH;4BxZb({()cXt|yCC@il1{*F z0!Z5dw9ktXBF76}H(2|$x&mAuf%6p)cnrXjkpa99v6j`j!s3Ad1L*8f&|SF}2N)c{ z@dQ@OZ3xP;`YD3~xNHaaHQ2#rG9-V3>&6o8P6lDnIZL4RD4>0V_47e#?f(hy|NoaX zDl@RucS6?4fX*KRt>^V%2>1c_2WZ_K2h%dtc5gPQ-Fwu7A;9;C;=hR?zk%i{t?%_u zwf^6I1Kb{X@*A{Xg8{VH0^~RE|2M#67mzg12)e%%G#1Nd(b9ha)IRe56%KBTfX)f9 z^n$FJ1kD?R+OV+p5~ywVB8!0mG^TG0887{7RXicdDyYxM%CLWt_b&!;c@1m3g3_Cn zK>tQiJ>va~3mmrKGzv+-jNo>w^W_T5_urYke{q55e<1Ce><6HJn#BQz^B})io_o*l z{r?8IT?DG1!C~Rmt6{0xs|`vkp!frcgZAM-5{#0aGVClvF0(2e`XkOcK9;1$Z(*Lj4)tL;9(M)d^T7$*{1FyY|hK&UViGc3! zaG1l$0@~LC%Da&De5~Ly8Fa3SV-q;eH-N?fLFZF}T`kumN0#g4Ut6^q&Eh z!H_y36f$m_z`y`@qvmObmyQfKK<$fK_?>1fYrKDog8PMywhTPr{{I067I43G4w%nq zeSm=tV%MLQpfP}ky9^u+e;Gs?Wf=rO=@(=ls7wa!PXdiAg7TF2uTXG(2lI#b|34Q& zZ90c02FTjb|9@gZZnkKdAP>?HbuXlxN&xK<`XA7Imw~7HWSbIbUyybu14pF=_#SrX z{Qd+N@1LpQGy!!RZ}~|9PkQOPCXjv)=w5ATeW(Hw z^Zx(a7Gxf@t+mCXWx^(qnV>V@pyq(vS`Bv?7(nS5wD%9(MgrGM4&eDEs2wbz{Wu^q zJs6n4Z7^v0Ap&k|9sXS5!QcjtD{!0j+3pIMId!Jp6&?)k;Bjbh8^~pH1-K0aI;-aw zJ9up{G(5rUG$Hc^3>4VBYNE%^h1(pBcd7=dj zjNp0!Y&ILXeglp9RquhEI|r&8y#N2|g}U9Qk(q&^dZl4A6Ms{~h%*he7Lq|5mpNXn@+37A-#|LGGxYp`hXYiv?W&fx;Zr zMzLs_$l(3c73_9s-pjE%z`$VDz`$Sys?X*u0G)*mn=i=#&HcRC%fMjuoxuS#HV3Z9 ze*OX1kI-~K0c5sC%S1D9JL;z^IA24~srf6=XwCEnw0Fe&|L-f1_P|8Y-IfZV{u?On zy#N242=Y59JwxSHy#N1Y(BA^-qck06V0g*Qz!BEPVN=zv?qTW0z-Vd0z*y-e?@?*O zpis%d%up+9sa5wk5Of!f3vBIb-SX8H7RMO(fyR13>%qN$v4P8KP+3~nzPO_9*k*9M z!lH$75xA}QixoVN2cAz{z`y|VD@2?bJmv|~2Wqo}#=pSpz?&aec>iJsrxmCk@VX#~ z9#(MtgT{0~`Yc)=mRKz9XNJf@+BncKa|88NEEE|FJQ%!K;Pn@DYzR8uGjX9ZV$CCH zObx0x43ZB6AoD&6;4^?w&M#T0%pd_fFAl1w5OnreqcVdCXfH=ai@XZxjNw{kB@xh> znvI$aEE8237;2Rj^g#QLKxh8J-NXRd3+KV$=?Pi`4X!)?pJo8v`3Tw@Z?TY}%BBgZtj__5$j;4FTRi`61)K;QIapXzi{5 zRR12(Id0Ig6rM(91|HD;Fb#_tI6!%(X6eUkp!4=Xce2zZYk|&zTLM~#?ZM!IIMb9F z;vdj{6qsM2;a!O7mw%<8{fb!p0~uonuMe3x+54A2IA4I&;@I0L;{B5!oIhSFgYSL0 z16tqi!QcTZE82>duMYzx=@E9%vs9C=8L; z^@HxLu4xGpsYzB6@k84q3NjCJuB3Y{X#ISnGJ_20?(SMmg@9Vm;7PJv3_SHK9YAFc zv`(7D>HRYf92X$Bf#&u==N3Tn>m*OmIm3-A3>=`eP~WKmiKnFh|1FXyfzFXV(eQ+U z1(Zg#+reXj;Ct#o`%^4hCS3#PrvwIO?_ZF<6R3R&3KLM-;KAUoQ}fjF8t8mM&>o7K zmsTS6kF7*%m96xU_8O>w!Unv@VCm}$iCRii~fJL-kZ$;NjsBm zL1V?B@((g@%4h*F+ zdH?eP_Y=VOgX4VKcJE(4;ITDGm`}Uv{WAuf?;G|q2tdbJk=6=Kj`jZK1NJ|tegp0C z2AKt_Pc2#|mx0z;d;jtQ_YW-=G75m(GNAhD|8H>L*civ^5Jz-|N2N1Oq#hd^^1JF?sA z(q>m!v`pRyaho@|E(FcDd;k9jZqI|}A}m@a--Wo%8{F>&)pwxq0*P6)O#b5i%NsoI z@nSD@d?JB?-J)fRg7+_PaGin(zdw-rU;(2E$c>;gHN5|y0fz_FjekIGYf$}f=`|(w zrz67y5Z}^k>W80>3@;$;Y0^I(89?i2|5|!IEJ2JPPb&wF$AjA7mR=uNVeN5CulM|* zv1icvD~(zV9H4utK=bG?4l+Cdw^^6I2A_58{r?YmJk??Wqcg~DpuU{<|I^^`fV!>1 zVj-glc%B(lw?X#=S}b662dl3F&HtPRkE27?do(ICifDH-fWjNp{s6Cwfuyl1Igs%7 z0{5B0`>dM&|A)$XLFK@6@h>(rfcMRT+NBmP)24a<@&b>I!1CZrM@9=!n-xZZFpoI}8cyK#k>3A*fZM?q3mD_T z;ZzO^r&Ew|w8fxxD9k3%a01`3K(r|LuU<2ffqt zJGdOMSilHg=jHwXBzPVj5-0z*th8bPol5}PYYbk40#2LYKDG*YjS7qpIs*Yz=~yga z6a>2)JjQbpJRb-#i%AC*2jDcRIaSNjYwB^(yftXNAJhi~_5VO?g&^_@-j-fdPl4tG z?3n)l|Eb8Z;in_R4ut;IDVAPS?^-7?Fj#HvzVTC$;lNKvh7$<+sp~AgrW#tFW4vPd zergfyyaOwNslAP6pfr8M!C@}rmKO&Z7J$xj0Jq~IX%yVQwOGI?0rmrUeZ>iIxd`zC zV~oW@MhS452CYx~{|!7JXR&}$2CTjU6jvv}QWULPpRy1~e^v1IIhK4U#D((vS=q%Q+2pBW%42sGm_&B3%J$ zi+lh41y0AX{=3Bi2Jkv4(Ab{${}bS~De$d|E7Y7+uyjaMvp`npc!Qvq!KUm){5wLq}O2B?G=tyMb zf6>UW1ANx(Pb={J0%-l8Lla{Rs1F0lw~#)Sbu|NHbv0-#^Irlu?|}ATwM^xMssYb` zG*4$>0MFSm{r?Xd2LYuIa9<Hk+N!%T*Tk4$eC8iK|kEU&%z z2pfa25~<$=T95Sa3^d#rz;nO;iy$fzJuz}h-pmAcTesH@5G#>21z;Fe0PdY^W3%Jh#ZOeCn=Ub9N>3A79j6nVY ztqDPx^BEjhQ1uaw%Aoty3LGXXGRlDV*(2Qa89Y{3lLAgl2B7o$ELs>8ED{+ty#KER zxA9&oGHTTC^Z>1G6L_h}Xi&ey1JuTr0EG`|&fWXxCve&2{r}$@Pc;{Ed@%xwzwnYTnH%?5?V{{^k!KGy>99Etb;{}Z73 zh7po)K7!LfTE5|Tocosrly5*`4lW1&|2biy$aukn!CC{}#)kH7L1jN;O+u!F#Q}yL z9t>6+e<=Rj2wHCiYFAr*pZ3A}|Fl1#F%3|;25DPE#^1gF9|q46g2KgN9s{f&#$wSj zo!R@BBRDQ#cD!_C*n!%HV2$zq$p~)$B8}btw`iFz0~)LK{s}qP1vO7iSM>fF2yTOd z`}FX&^bh&He|`n0DX2Jj9sx8?3yLF9`RD!f3%KtDDa*iqJp%I+=xhk9pp<#u{||xN z-r)MwYkE4UeFkdRLHIL3Z9mYOg1?qtS+a;W;f(vxcHlotul=Al;Q~ne@EI?teg@5} z*UN*>Zus{DvUVerVWAd-S3T&S#kv1rYqP*}d*1)wgUA0Y7BDD-#y&t}Yu^74g4@H; zFb1!21C_xREz_;Q@%zgG-2R1`Z7spT*r>(e14)DbTRPqv_|o|AY6W{H=fX8(fxv#%jEOeg?N&7utc(T?Ngv-2v_KusQVq zKRC{gO@CzZ{M}Q~F zIzs~FhJT>)8)DvlSx~(Is<*v=*@5dnP}>evhlAFkfY*InGALL(Fff45-vGDm3};-m z5}2{l^8Kndt0^r8mgi=8)z3QtI(Iq5;vmBoaN8R07s%OP77G}9!08R#pW6>k576`m z+FSG=+^+|xgBeMwS1T;YHLW`Dr#~|VM9$Y4Z!W~qGTC~h~ z@BPyNT)%n${~NO4GXsNmI|JxU2o0F|i1v*wxZVJr4^n*(ToyVkG-hC`KMg)>kjZf_ z!;wlYd6ildFOixr0a{%r85BA_86;i`Gl0(;1D)Xp3P13A=L81!pP+LBe%XS@{~L-K zB)tD01dlsI$Coo+EM%AfYLkQ8g~iepknz>O;CddkM*3wULq$y{cuqP7W;VQh{bd7g z_krqDi&>!aWo}ngOk+@}Xc5q;jslhK`rz`aF8QJ!sIINMwHdU|Ps8c}0|RJ$qV{<; zi0=Vi%dG$%#{}I&S^=v6ynns}kGF&7LO^$Kg4&Rv`4G^Y?2ASQ@Oc`baW3zlAHefu zptCD16d40N7)&kD%X<$7Q%3Mz=CC_wXF<=bsFtp2H5xs z$gST0=Yz}pPDO@d(0Wu*ItATd4_fO7isM?%Um`OV8H&AsaYEYXb>J`y0PVYkt6!?% z4O8#^ixZrepkp%NF(goW2gRL5%giwEU)ErAK;vp23=A#S4;cQxxCiO0Le)ru)Y~Wh z|LgtB8r+Tsr#J8z)J!vwocAwlQ&1nvx>|t`G`<6><00wu6L>xr)TRKP8__7oz|!!K zfdN`(F(cHy1J`4qv$sHT016M3bJBkN0>{6FBEta>24lorF?0{U2ZQlU@cp&0`{P0P zK7#IC2c6HikfG*fEcpED8<6mQ2`>Mk=VM#}rAdng41pHl^9bjIlgA5Je@}gyC5hN@v!DZn~MTQ$7cO!*^gZGc0;59W1_Cw+aq~4-s<`nN=mf$uW zXv`ZFH&F52-oGrt?NIOk|F=NyUNu78Sq42n2QrQTI={e37JNo(t#n1rOy!D(WCji7 zb5gzk?~Me-@q)Vy;4uV?mYH`!^I4!dR?wJ+_b*FuT!Y3lz5nk9rxVcn28SjF7m%AE zX=xST z9jVUCZE*JVyaiPD`v1v3kIuV0D0j)oQD+j@6VU5mvob~)U6Cx zXj=*Jc3Hk(A!&JTg;}R9gMh^YhK8C~-wbLs11!LEr}G#CZ0#6Ss=F8z7W`!3veabx zV9UkM5UOcl1X{oS(~)5TY>mZFMur(b9x|)|-52Bi^AV(-$;dF{r6R+GmyQezAZd+} zVWJ|#0ZRo2QHui%5)&C2c7W!ILH&h^jtm1n^oQ z(484S-+twljN#_m6MjvKZ2y1>3(GW{*9n zuMb+kdkA#L#&+-+G{`J)J63a6qNUetVbC}dXlxl2P9Ql@I~UY`u+*G=z*=Iih1K`D z-d5M7d0r{c& zrM!xzS4%|ADGx1h{!P7IVbLY?(C^lD|#CWvBQ5 z{~eun3|xg;3&~vAFA#isN4dvLFJ4^ z%dFoZyS;yzfX914Z8PMxC$KgfxV;v|pa9;(GGz{nRq-5otDrfSR)%wetpw)eTE3st zZh3Cb{`xr=K=Z#L(Dn&z{+r2R-al}i014-(;C{Wu0!9tcdKFMv=ly>xxEzF}DV7?L z`z%`K7J|o5{{QE&0FB*&#)zQnIlccs2A9o{G5|EMz_38OlOY`x&fvZ;NNoZGGpO(0 zY0tnHs>x=g-^l=KOM=va=9pq24;`}Rk6-FfCXj{!U`4NAinEprxn|1tvSe_I7629TYg@((oT3r#Z_6-${JK<(Hc3mH~; z|GWbp=ZEG=(0U$FKSuy`zA&V3_5@t#f$CeEL;wGQ`(w}N9J4q!)eYWX0nJVQd;JEbHjDoM1GQT$md+A^nEeg3wix7ACQ#i0+Ft;khx+*x+JJ8gC`!S&WSg6Io1R4+QxDVc|4c%uwmlveo`zIt$q3Rf+>IA`V z1N&#nV~D!P;P?aW?E>xV^8Ww31(a7nY0#o&&Smdk`rvUB@BjZ&Kx6)pe4!6c|KRn$ zpgR8lw@}bp08pC)blzmceg+QE+6IStP>n|RS^wwD0HqmFdU-J)v>)!v zM0nZ+rPu%W!1Vw$%|Z3g6ZQW8>%)ut3=E(&2(r`r|EH(k|9@6M`c1H5G6u#5AqED} zT~n5t|M!P#f$!-MbDYZnI?Ly;rPqcdm71a}YPGyp)q>Bo1)T%U0@_;?!@$6Bfq{Y1 zgMoo5gn@xsfq{V;bobT-1_ovjKElAjFoA)AWex)a%Nhm-RtW|MQ1)Y;z`(!?m1Eao zU|_FcVBlzhsO8jQVBoarbY@@#)zy}o^Q!f`7&xMnKuw`dti; zj`J8jK);j z7+`L_?l_NO0Z2~2iy^>Lb77kI|NkDH$_$K1;V$Ah_rC>XTy2vL_Hbthogo^+z`&5g zz`#%dS}ODZ|9=S>W?*2Lg2e7XVlQA|U|0jUS}?LDVjgah&(B2gKIzV(_%oT)^l3|F4OD7efe0%u;iKt>e6Z zIZ*ZuP#*C9|5pUbY#&hm0Igv|5=+tVVsLSs_YY)_FH~=d}L&6(X3?|ROz)*q22IqAUpMim44%AIe-v9r$ zK-pd1|NmA%*)u@r+e6vQy#N1AfU>uN#@3+hqu&4jdO+D%z5oBU0kJ{hVX3*`5opaD zhz%06)Lh7~-^JkUIPb57Hi(|fprYT!U<8p{@ZNFWU+{dreiwtWrRIYF-v58EK;-9z znvV1SJV3+?_vnH)LhsBD)*7hnFn$6A8@>a)LCjS+~_#(4>XM|oZ$Wcp8=BkqoDG| zao!(L{0BqTpL3k|2O9qicZ1T0_y1q8_&*2DZ)%Qne?jAa8;0wTWXqxb*cJW#f{_y6DE z__x$tB=7zI7c~DbQt|%(3!48I8GHZ#1*@C5ZgK=q1#7lXT{rjUjA|DP86T@2n(Gm9MO{VD*l z^}86tEj1T4djJ0^0nM|pdRoG9?oSR#p52jyJU~s{}GshfuRG&htwS? zatlCmpn3yTXMors%)r2K1Vn={s0{#eqowAeMc)5^9)Pkpc>n*o1yjh~C8<-v56>%fH1U-v56>^Z#Ob@BcqT zpkc8Gntu5l=Y9vRdHQSVwX*_ySTJ1q|Nr|PWX!<8U<2bbfQB3y7($Tv2_QD8Y=gST z-249zX#6ks@c#b;oc}E~7l(QO{{fBv#i`!^e?a4Zagq1`A8SB*L21BJb8(~h|6kzr z3FY^D|Nm10lDE{H_saYKj|K>P{w(kRKS1K3Hb=Mj{~sBkbYiJF)yMn)j~IxWMN_^1 z{|JDv7wdZe|ADx>0@Nq~pQ|hf8V85m>3M{K1vJkGZVUhaCc3zufeEyy5;Qgf8moYe zi=G3Ic|q4&gZl)a^R*#s>K2~@^~t<{set=`pf#=_Jsu3QZx+l41spGUJ{i;o1D{EF z^mBzp%i<3pHQqn3f#(|`W4hdLLH$wCc(h~F|2+$p8B+9Dg63ELZ&>`8feSRY9%{#8 zS3mEEgTvhabLzqO7juLAm!SDK$EN=sowf{V`kml86`4+3h9r=F&|QR}{X60RS?oaT zEIVx((m`q*=KX&FZoh-q@caYst9O|9|BUzl{|=!0#GvX=z~>O4`*|u_Kz9_$Z2h75 z-w<@}gLTwthMK+F6`;9Fi-im=FQdTY*&UGa>`UNrX3+QoXp9}St`u|^3rG!Y>=@(^ z$0n87i3o(gA$t(;P_$=(vRkWNv{AY#wMl9dzFY)Eq8IyedKa zKmT1IeUiTiq4t`9?&O(i!@vNEKQ3^;43tJ3oBm5!)G)Ak|Nne+u?zzfXb-&i|2FXW z1k`L}(7J${dUo)=tKL7wAa1P&&zC^^DNCF|=OKXRPT=b=mP#B0^^Ls$&jyE8eadaf zzQdmv!2L$3*~y@>Akch__fJu9`yRAM2)sYDR8B74;stz{@)HB zcLS*f;65(cF7Wu`lHCwDTt=JMTyoO;r!Yhe;f9-NZUB#A zV{yYBh#N%U@$cBg7=h#l@E8x08{RkW@sx02Ww3~ z3*ci9puM^vaZuj1IKcGLB9UQ(_x}Z8H-O4SP?-kVtHU6$P?2F*eJA+-J|56sQ4a?3 zBjET1joCCXFo4Q(@BhCl8xWihEFf?EQZpxQqkEyW>3OiWhazdBv6` ztlmFQf!8QN@+^Z6sEh)+36$0?T9y=h|2z*a6Bf*3U;vea9t>>YvKLfeH8euXE9hl>!{llb!4WB69h(>%5bjte4{--S#GTckaA!;axdXID!25qAI9$N)0M%Wow=2AVo&(S2g53cQ zt7SIcKl#97FX|Z`Ud(6oc(I=`;KhB$2$22O_n8!|=gczk{{Kh!MLlD}i}{QhFZMGQ zytvN@ns1bRQP0@$Vm@QXi~WofUfgG#;r;&)>x+8E1uy0^u6VJZal?!Ij61yl|Ni)* zp7Fqo`HUxC>}S02;y&XI@BhE=S{z_H1Ih!S{ez%9>ivHXIGusgtiwEpD4p9Rk4OlMab_GZdG_D2avmA!;uYmk$ae(O($ju-#y#LPzy8%?5fYu9w<`1nUmKB1^ zGpp}&??cM8{{jo`;d6zc{l_g94Gc^mv%LSG0GI8M{J^jRv}PO9HU*yx$^cPw3Yo6EWWgW!q zFIT<)|F5x7WO(4gAb0^(ID_{$aYFXIfx;FPPZkFlE*#7SctN(uTHuG znqC&XMA_Fj6P!Omb+tnic>UFXiKl152w>g+2Wqpz>Q?Xn{~ki@WDu}O zW?+HTg8~O&=0etMtX$*$OB`H2g8T}aw}po>^qwkE{f%aBCz83KyQmsG7z9A)Ui}B% zO#wCclJ_rh@VY@<=7QGScrfsT?!XcRw+;TEW&qvo1WNayu(L>H0N6kFyj|e+IiU3R^8`4*f$!}_ z-KWXp{o@+A?6FW}_~607UjYvbW@vf?pR1J#&i~+WJiw5NNOyc6VfVUN&pFKiTH^%T zGY4_|ba4Iy)p-t04B+*rh_ogO?iXXOi(*vq{&5vt=Yhfl)W-4te+=9f1Es-=S_TD& zInepc7H~S;0&3TQ+cWcDI5^JxzX6;UL2C{hAa%I+|D%v|UFtw}#Q!Uxb({K~!Hy2| z{-0Q|585_JVBoN5S^38LAA^ARFH!LR2e4lg7&sttyNcQSmnb-Vp?ya1T0dz11+BsO zXVD_O)%)i`aGHgRt905i@LOvB{~xN!2D1l~}Ma@y;3ebH| zHUF$DVD^FfZlE)tAo~zkS$Y3d0ngz<%ap$sOZ!Yg`<=ai9tTYr({@4UMrx?OcnFpFD1hv^MTK2Pg|2zhcOK@1i=QUS_f#kh^ z9tG$5hP%)>0JT$FR;57Xj)VK}XmW*6IdC7(LXiP_=MxXc`Y%fb1~v}{9>`fCur-T2 zwJU0F8CTT&wyvm|r(6Nb-=I0knTm`Gp#C@{?J{bB(rzOQgG9p<1_4Wl|KA#pFmN<1 z0o@i0V>1MQ0eg+=(v7CVcURdtq{{|`du4?&qMz-&*gV%HXvKi1=G|7!rR+!DTsUoh>9@@Ws(laQ*_78})9N;p?tJ zc66Xw+(WgU&Dqoz2W*(XyHWqV_1b4+TQ6W10%yvMMeRT{-2JF;B#dx z9xyO~%=pO&zH^!5ry?V04VlzWMTQTcH1yMvVS}XugTPNlh69!ip!)(=oBmW}cwwo) zAOTv_53=(oBf|nq21WtUK7gN!3=e)PGMxCS$gl&n-p-PN!Q!VPLxZIP13PF9GAJ$n zWMt^DWME(ht+%pNVBqooc?6vPLGH8wpPj_0V9~PL2V}PQ&qLsH0xAc(SBcT0WpxZh z?g*rx4~Z}6+K1JdP&sfL5~>d-2hDGX!Q)s^InbG$ATui=`VNE3aWuIms2n)&H}7QN z0PU#)@1@%7c?lGMptu9C_W+$U)$||fF2X42c+FvO{s*PW@Z}6f)yo)^AnQq@8lYx_ z*D%=}kOQwdNI2HO07;vxXF}y6@&5oS|GWVdZy+^H7A>oLplZN*r{NxCO%PQ78mJt& z9&fnE0Nw))l{*TNI|MHO8tySzfc*_Fw^m<(%0bFBRDIC=atPdxZ@34o3nBV$L-m34 zcf&pCUKohnGpHOmPSNz;h01~3F%9>iZ8?a(k5D;qJ=Sm!`7Hf4EKoV{7(&B6=$>e> zzBS??xr$=}8s0w-!Tb-Z1EA|e)~F!l4}#mT4fl}OxvYYwmxD(^eb$D1&^z_OX2Z($ zgWz>s4fhyW8toWV>N~+_+(6dZfz_=s1li&J^B_3>8}2diG}?joY+3X!cb?)a(O?6{M}pis&!E$8%UM!E5)E{{IL0ujaaOg*6L^4>r9L;Csm8CV+aal|*ceYzi#{_iu0G}_~cZ-_eZcxZZ? z0qFj>|1h^(EM3zDazFU)i~rxgHr$7t;SY9et#k#{E#UGGE(f~*XYp&89Ju^zz~@fT zy3U{b!0Xr>?lZ{XbSFd|xLw|G7jh;#XdDC@SK##DXwTpQokuv5-e!vKm&r(e(QLR6 zIS(D|ml~K~_JPYkxE#nY&5xme*$1xs@%jZkX0;De{@rKr!RZ&Uy1n4?zu^v&U%-Cc z3$Fh``xhGO7#uvn>y^McjIn_WlD|M_JAvAypuP@hY!1BF=zrS-?R^Yv^>@MJy*!}4 zk_Q8W4tV^wS!GnS64A>?H2F3>Hnt#we zs-U$>9t=#5;PK0(|NpJ4PcwkpdZ2s*Ztu0Moeo-`_A(kgR#^e6U%h{Eg4^8oN(^Gw zmf&;XkoGODJ@lfIfx-LdZg5zE%bb7L!1Wq*|0JmG{~yvvSbGIBj=%xl3jy*MxUXxC z+}CBS@cwZE9Bz;{_}VYtKR1BKUO?-~Kz#%77{$+{;5-HD^MKYCI?REr8HCugj@A4B z{~7hMmn%SbZ9w-A{C)kGLDK5lhd`^X9}=vlKOz;>+rn) zXM@KVA>qoP^Ljpm0O;JrS3emTz+*E%cYx<4K;!)mO$-jN|AWSo{%-;6Ujo_}oDCk! z1nGC2_x}i3yajacL^gP=2r9nD`~UwFAoJ=T?*{chz~N^t$Dr`y9)ko(&5uNe0?>K? z;Bms1#}yEDJHhQg&^q21%?uKteMB`aMk3xnw}IDfg4Th)*vB9N${!Y)3<@tb86+TQ z9p!?@bijMAl(1=_Rq-vKg~!hq=8@-Q&`Jovxh=fnRMzZm~F{8Iei z@yqf5gkOpOXZ&jXzu?!x|0{kS{J-JX!~Z*eGyXsDTk-#i-;Vz;{7(FT<9Fl#2fr8o ze*vpEK=lP^jn~VA{|jC|{9o~k@qfcB#s3|z9RE*vmH28;;?=?b8(uy9 zzvDII{{ycT|DSm6`2WJ|#Q!&5H~xPBT08f8;r|z)wR5iz{{Qg$;r|~XGeK;y+{6Dr zKyn~4P`YOY5e*Cs28Kq)CZ=ZQ7M6}q&MvNQ1<9H5$r-81+40Fasfk7LX+^22RjCXN zOd$18jLZft27wAQFmNn?2xfCSHG^r6<D=7UALU&Gr(91uAX)be1FwL=i1C-tg zr6F?*9LrBa`DdZ@B`AFxLN82((97pR=|xZ)axXT=@;)ek3Yg{+g?NEuxgVI%vD_C* z2SI7jdMJ>8!l3+ED4h(Yv!Qe`gkB6<_8iKGgbT;AZBYJJ2t6IDkJj|Eee|^t-9O8YLF`{P5lYX3($M%_wgk#w1Erzy zu&fr!Z->&*a9^ek;V%ZQg=JvipclQ&9AfV>S19cdq3LFSB*eaDX%KoTG#@Vg4&g6j zhtlE@dg(zZ4GsUr(ELU(dg(cc{q(XA-JYelAokCD0ijo@LTODXtqY|Mp|mNKhL&F| zY@vKd2)!I~CN0PEzYzZ7yQuUEXgRb38V@U=<;Ds@h`JSGP+A&FD}c)9;+*`F_{5x? z{A31(l#=+wl9I&ajQFDb{1UJ#1_qA9O;8qu;yO_PW^kQ=lpkQuzz~cOYZ>_=G!yi) z3KkIvpFFxZ1=Mh1q=g51pb!qU{z)cD-u^!SX_M9{K7ba5y@B^9m`q#cCO z^cPp=B{LK!78GP;7NzQ><|QWOr0S-W=H^!FCgHP)ONtVcQ?0ld6oRc3R1FNxaw-&p;4IZ-1qN+{3e}tnE{5Qe#N=#+|r6{xY^ zV0#oYa}(236%tDnK;8uT6XGJMEXaz~6deUnh+8SBR+TCwRhFa{D`*%f*eaCfW#{FW z=P48vrGnIH!W`^aTwIz9at*|Ckm0HYFiBS*Hw92SPAyW%%LjRGJT^HNZgG)SplvXzOcB{cN}gEXPWF(d)$D5Ry7K%!hh1C(q)39CXAEsMa+GcsWa z&dzko&o5C>Emi=#Br`7^ocKXXG81!PMUX;He!4Yi44A)qiFt#tiz&8TrMjd5{7Qs0^rRNi0gv$OPs8(xOz|veaZlXcTd z^O8X&d14MI50s=b=x5~Trt0UUrspS?q!#Iy=NDz`gB%VfbfK=-HPW-tEi=_i&n(d| z%Fiv`5TBY`P*SOp0d;(CYHoZ{YILP25?xCk#wElw>eOHF~L^0cD-T!p;+lvD-PVlD(Jukl~GcTPB5-2G4SQ?rzXgT`_1%(ELXkn2zG&8l*Dkw@Vi!T8c zrbSqlm|KBV=-OqZ6zPHb_E;5JSScb@fmq;S00z|p1&z!+1=V6rP*zU_Wq2J>)lrt2 zUs{|~3HBX9H3ew-8O4i6rWTN(OiW3E2C#-|u>+)B(o}%vfW)+t)FOqn%)G>$%;Ho< zY++??U}9CIYX`}Vwzi;9&dkq)3SjZGxq&H2eNJkg0+Q++SRsPqNOJ>o246_|1xW+N zpvDI{ml_)7RIGefTi7vQd1R*3lfu4 z6*BV_JX{?EVCe>7dJs6RfkGV=XI2WTIiPwzB)=pvM*%KUiY*{aj18=E@{_aUGg5O> z;*%=lb5k|cAO`E&fwabhlQ&2SwzO?*Vq~SLp^=!AnVzSht6-?9pr!!kU{`Evm028L zl%JAVlBkiBpPUHFn^;v^7+R&_O@zi4MplYYC5RLVE>}<@!`RZ$DlfI7MAr_#Dod+0 z1v^_%YE{ryFk}Fk0gez2P}-`{0mWWUg^q%fYO#_gv_%GLcVJp*Vq#9DCrwN&DG7QL zQ!}gF)Lf9OA@LOtPR$w+j;4Y(xJj3vrlFOQQiLs#O-#+f2G~GTKZbsYNxF8RWL}i2 z3rY~2wgndZObsnCq7)og44?)$LunoZG&`uP7OO*=3W<5C zIhBxvnVO=Y0m>elTv(MU#G6dO>oE<`DVXI@!iPG$;{7Av?Pbit~r5 z{=N#u1v!}|;4Uwykb*U8K;2((R~}z2Z)jjbA#x87vRoK!Hvk*jtd_1J81@%DSnF>7IPz-M7 z!o@&!D5^+ueo88;NJeU60azrzSQnb!7<~Mly%k)8g8V^aAjJv}pc1XPB(Wsb3RK5| zhey!6av&Fhx`qbuR9TdoTv}9|S(d5*l4A(X15u#tRtjdNrXY)_f--cTZhm=sBe6(9OH-pnQ$bfDJ{~-dl9?BupO#jfT9TipfT2wX zWP&EBBGu3UjX{B`QjHQ#O$9AY0|iA}1(+aK3k@`N?UD;h!HP9OHo{#~3>uxXQixVH zu&9Vt@bGjoP$*6<0gY@JR6vHOxETBc9DS@5f>KLLi}FCh3hL>BWKAl#Ai6_}GE-AP zdI~{9hYDHwNecOS3Z;38Wr>+Npg}(cWG&#V00}5V17ik|Q$Qn4@mcvv8lc(?lq*$p zVC_SwLRfJP<62l{|Ao{wR3c7Z%B%hQD3eTccP@g(8F(nb{6oJNHLAtCI5F<{>MX8A;so)R=s{;qO zA}p2yOH+#~3HSzNGZvTS@yP|H8k(S@4AlAn@gM<~lA2tUnwy#j>f9z}mK1}B z#PpL3N{f;6qN%xs6<91kJFya?5#&tp7=ufQLV#zGEu*T z@8Ds7aH(o$Xb3JSGP&WSlWpmd&@rvOUgpmCzq;^O?GV(=Iw*c`{497F;vh7BWR=7Ci>f(HIG^U@W$ z7#xd>Q;SN#-9Jdz-OVM$O2M_LC?7OFsQ?aRP!ExdAuXjOJ}EUlGcO+0me5E`DbZ0# z$ zr6kEpAr<25VrUtkmQn&5%d<3x$R@+v@wwn0fdZm>fv7YxFomRADA(8+S~-NI7MCc% z#_eEH0dD6e7Nvu-8N7s3C;?S;R-itSo}PkgfsR5FbSefW4l6i8Ngy=^QdA}-g6hre z)I88233z4)lwf>4gMA%CoIMm2!8t_Lz$B*vl;*+hBV9X%g3KaY(1a3NvlTR7rk8AG z32m-IxrT-oRwel$D{O2P42{enO|XK*9Egu$s!YwTKumCK!IkKi86&Zc7(gm?bBoh; z6G2siZeD3FLI~8qgz!MI1)ux@YXL_ks!&mBUP)$dDr9aAl!w6zVGT-#;>z5l{2blf z!~zs&8ks>G-5}L^$yP>Y=2oeBB@E$?L4KZo?p6w+dBvp#1^Gpwc`}fi_>|O~_yX`S zxSoP1s8mQT2KNI%4LEQ{EG{lhE!I&;$p_89fX3{=obcJlfWfIc_O%#rN_k( zQk0pVo(dXZRY)u;$%CeCkddGXP%~32XcrbLVqyU855V~r;IIMJS^6+BBj^A&ynrkQ znPp&N1uBW+L7iwwc%#Z2np+t#cm@T6T7l`A#U&6&fs!C-_|T+6A-@3Hcn5U^6jTc| zL0w9SN(IlLK!xJ`(xT*41<*J|PGSKlWE2$gQp>FrR6zrf6$<$|DKIwFnyAkw1t7-g9-v;X!jOH z)Y#O}3Y4bd^Em|;;4~henGz3bv}k}NHKD_iC^`+zK(T-se#T}7M41RG(clI`8zInv z7jTIR4cY>**K&)~trQ$VOJpF;PuRp7DAR)FTr!K36N|t@NU0SiMTwxvo5bAIlGLJN zE`$kw`3i_07pSHO4bhimq=E(LA4lKk;4W93z9SSlC8`QO{@wsk{}L&37J|IK!<-JB8Daw(5eB>HwX0*p@{`1 zXlVu(jLwWjHqOx0&;W;@z$slJKP^omBfq2|r!+ksRG%w=RyA?q&;o6O<>aI&famZ) z)eOi0e0oAMb5rw6OR#AGCqkI}O)YU)>YSJdDr_=A)fuS8l9C8&oG0dh2johKaB5m< z9;zNtHHk}~b5Jn2<^nlc5tpI>aJ&|mCWHD?3Xpj)=b&I{nFsZenK=#*A$q*vHXEqV z3mHl&ElLHav=s1y98kfED{+BVsz7>xi7Bu}AfT}mkRGH^H8MBE<%Y}(P~?>sD1aJj z0X`85Df#7j#U(|liMa}(RtCr<9JYh{6bfOUE>@s?qTu2h24RFm23V=4DEPXm7ArUf zsTM1^Mu6s7u^R$fKL^fGshBwm$pa?l(3}eiQxgj#hUn7bR8U_f7KhKE!_!Hn#R_?) zxk;%-#kjrVR9dV6%IBae#|ShHs8F1o2p(SncS*22y*LNd?SVE^u`BV*R{)i2pi&B7 z)+o+NPAtG{P;pLjNe*5WPDPn1>8X(11?m##r={sAz{a!k^AzxSM1fet5xquG=cWW~ zO`eVdcx5^$6=jy-vj#K-22uqY{mRMA%huD=Q^1w6Qo$1_(8XC$#kkbM3KnGZkrFXT zHy498L?ksamq8&vFQ*bmqJfq%h2SwJkWSDFnv&9DTy`TBgkU`&{}G|hCo>N;H&mX7 z%UrO6(gM(`p9)n_Pb#G(1DD!hXi`g9tI&lDWTvL3 z8X8%cAiEGQ2DLuDATx=fI5)AVL>E-BfEIM-mga%t5VV{E(F$dNR^`ZMrDhf<>Zar- zGNj}tVu%-47MG;v>VkY*!~jxQRFce4oT3YwltWewRacN&lv$9GT9lZ>keOFdiV~_R z`N`RtdFi^K(lIkXkHOf&jG-VkuOzcHmmx8yAS00h+-4|9X2{Jf05x88K|M3@7!gBS zW>IQ+W>G3bBDhM`O)4#BC@xN9C@oIXEzL;I1T*qsj8qt-0>*#_Q)zJ$Lt181QK~Lz zL^UrphoLw(i6Ju&G^&!6n3uwknOl&_04mOk8Ilw8z_x(bvVtuHIUonT*cQ>$FHS5; z&B+0+n1xyaO)9#ndC5hU;N`0f;Gx2j#LPTUy98MR)MbQuGBYoo!QS59o*}^5(+Nbl zFsK$gs8;BxRzMgG1<9GI6%YYX8@nJm6BGeynd!RVRVlil`W>VQq9i#7lz_o=QAMd` znZ=-VkeR|zmYSE6Uj$m41#vHk1u_j(4e912CZ*oR-xbo=E19FaJhn|S&r8X4OK%E@DeF5P;gr*IDVY(Yd!Snv$81#4pRwOio4OgVGd3W>HEa185?z zG&i+KH?xSLC=HZWU`10>PHAdMett;?LsC(GVhT9rr{<-W=vo*U=@}X(G9Yo1zhV0bJr2NF96i`-X$jvV;PGtbMky48o(i3x2K_wmoxP&PH z8IZ4=2%#$=3_~*$Qv==H{FKyO217GbB(@n6+Z>4vQV&^Q4%GnXfONn)AT4l?g{c9o z)HO7-L~uavV#rNSWGG0^P0mbY$SVcqcu)ZfqCv~m%M&XZic@nlbxVp8^NI@+i$FC+ zL2@QTS!POVK0`66smoB3nv+_Pk)Kz|P?4UBawWKgIuVo<0s zVNj^BV5l%OW2i7TVlXyJVlXpF0ws4{P-fHx&vWKfD8N=ZfQsf+1<;Hrq>cwS=X8@Q zb>X9v@UjBlAw=YLaPh61T!K`DK!kEqQ$WHwsgMOLpsb<`8rRcB5lPO^%S%lz$uEMG zWN@26@u8cNTAYlq2`rSGnw){@6~`RV++n3cYDH#o32amxR91p)1r3dxnlpgbN-mhm1pHg66Vyz&#hxm;`YeV0|5hd{B!TBYbwx60o+k20vDY`Y65o)GK&>T3y9Q! zt#4FXpr8Tjv13i!AR9n)47ig7a)AP$j024X<>x8D7AwGpWbmoQ7>(fqHymJP6}r(G z`6Vz@1Drh-Kqf8O$~xy4RDv1+;IdKyv>&7(KPNLU72MN;sYwJ)u|PXJV1*_5 zMM!3VmQ6vXP{DJTkcnX(sH^geFdURqTATs0GdVFiBNfu>fZBvG2{fGsF$nAuPw@69 zkRWL88zKR*0K8KHB8^z(18M_Aag+5F2Jk4!L=Z0VN)7t-7jR59JG~N$9+qYXplLJI#9?k?$$+}#0=5blls7@86>LQf+_UBuW}w-loD_)0 z0O%GR&<-{SjD@mrT^6uiM+gxUODm0n{9*-dg*;6K8(Yxg3(&fFR0mp^8-VsQDcUL+ zRHQ)xgBEFkivcM#Q!A2F!JT;pP;LX2+`&OX2B3{2pp}|A6$-&YL52t}7lQ{#9=f|V zr$Pb5HH34y7<_^h6cEZ4oI`?;xLgd*ZjM0+X)Xq5m~x8>1%(J#(2`MbHRc`=q-tOU znm~p+16=^EoP>J=H0fw!!4MMU= z8p{B!?S$qKungERb8M=h#Su)Eg|QVRg%lN(fXkowl+3bt3oQ#!E=)=_Gl?(B2QBB) zC`r<_OU+9`bBcwD6<8zK4YsxlXl}5yM0P?>Y97RN1uX>&r0~!xDkwoS*T~Qu7T}7gYfV)Kq1-jq?Q&8_IIXPDs zlp$ebJc-4{`N^4yC7ETJC6&5GscET2sd>q%x&`@}c_ok)WEth)!3UU*jB-%lyfh~j zCV*lDLs)=|m4a_#4rtGGYKlUBkwQsPX&z|cI7J~Wzy;JwNX{=x0Y|(-3Us4yT4o6s zLr@4|&AHH05WE6j!Jxw20yJMzlnORdRnMdt(nl>TNYTxy(9O(C1C6T`rRtXzq<{j( z!qTb?Hc<){vNQk*#ph&#mS!=8dHQ)mTmc>32e;3_%l#pf(LNEN#V`3qDO?a`aJ~Za zY6@^5_~a+1q^4lhNDzCC3?WO8GV^uOTx0~RNudgj%pf))T0Nlc-k`8l@bPqk7R?Z~ zphfs#s}X9Ui76Gf^#asi1ZxAUgRWXF$%pKE4GVAqnF%Va4J<0aO+>IVc#{}pGpKzB zRfuXiY-0du7#Or{Ei*Y4RHVS07Z~EuOoT3OX2js(6cl2m5E1O`?+cv+S4~k!f%Z>9 z4k#{2O$M#oEKkf%EiC{okp*QPE~v&}R9Q&37TibxWh9XIVC!7Kt17YD2GK;=E;L7i z1{y$`0(_x;}<6hIS55EsEZWT0UNR3GK1febaMfSC%~m#7fn z3py46)QUGW%K@#thL{o@;2akvpfuaW<@Q`I;;K5E?1DHF|bRpXX8h8b1E{3Uv3}k>yN6_9})cB_6!uC+X_rt;0M?u^HUTY6ZP{p8;g8Vdv0FcW-k&JLF zBDX_V!$a18<`$=ex9ykYE4T#*a51nM^^u0ALJ@cqNoorCbP|}KRZ|plGE=}y{XxYo_GmFNLAVpXD-W_{ zDpdipFhn6EsR(Qv4ik*9hk%I@EMgG}O#!-U1=Q}V1XmTHE-+GZ#ugeTrm#%m@9Yf8 zOQ60>YH{YA)-jM|BP(ae9CumJ-8tC)_RPB&GO2HYWC7_isur#9p?)-rE z+=I?ZfG-ITN<|(71veTY`cWlPQxsB4Q$g#`0$?X9fvYJ!=-vW|%Rus=S^;!=31|}o zY~4BXLiQpQ3&Gh86x_Lqd8KKI$t9(r`7}@$C6yt-$1w!d89|az0L?2Z`1^4|CE*9K zs1_^0&Ub;xx%mhAT7ge}iciZg0&UR%uj!2kl|!IreTBYig@S6SLT)h^1GwhPOoohi z<&_mB=7P=^F<|fu3v%>DS=*9dl$%(h02Wu|Vo(O3=Y;62fwjVPK`K^NP%8yIIRYvK z!3q>W{TeQqvf#|BRM6@w)f5G9C%C9{QGP)INJmM&f}yVyynX~50O|@En8FM|G#}ud z1+Xf};Z$%F5z0VqT!xf_yA-RA)8D=+A6^3x`5U;f=^K`F3p9w(x^hA46=(1WG*=FtQ7E?k(mcNsVp_Q zM8NUJ7_(C_haB5)+E>Sa1ecbf6W_&@cfla|M?y zpeTUa5u6P^cr8@uN-C_&UbB`nh}h zxyHMB2H{s5;N*#<2)t<%G$91CRlzSH6x=ZY)soO%GGH6I82msRMBShVOM&}&3ZMW2 zC11#JA5@8>bBL$Ep8-N#M*$*ah!Dc#K41}UX=6d+Bj6wrZush}D) zu{b9+wE$`$=x8eiPZ!Y65gi4vNidF^CwQ0=>~6?N4Kxb!3QD2T5UrY1s-v0`tH9tH z07@5#Aqw!38M&#&#h@eeK)cRBsWvGwIXe}!T@j>O0qn-qvedj1@Dg4493yx{8(h}v zDI_O@##});8Qkaq9nuIoW6aPBoP@!(p{=cg0eC@xV@V0<@F-9!D9Kj<_nN?Mbp@z1 zxWJB7a8E5!@P#_e4YJ)Av_hB*iy6>kBC(iarQiuKHIj2vz|mw>0U6#ZF38U-PKDTp ztS&FLBn>>iV1QkvdwvPDt5uW=F#~EWv`+x_yrHR)6=)xu9k@n@)M8L6BNJmQXc+6- zf$Im*S(s=_Ob|*yk%UEsDMAG}6tO5VLnwg;5?E1ytB(TY;7J8ghp!m4XA#s&fOd63 zWfN#HPSwCDf&@Bu|z@K!?bAiE~G_{~U7EGkJ#O)SyPg^VX}B#@zCz3Iv0bRk7KY$ zJhXNMA7-imDm?Pj6q3NrY4G|T9ncV>CYoY!iGo`#xClwhNi5C)%~hLOSQ#*6Bo;Hk z#SOGHk2$%KC2OU8MZwbJ~5rLPU3OW@Isc8XeW`e^G zw51wJ2DDKF)I&${zKMxBB%rMnz+MKq5N@ABh`%$Wc!pFV3aXiKC*V*G>ytniO%u?8 z)P(}ghC*G9#b|gFNDrR_KxIu*X1WytTdPuw^1)LXgcL$snIL1qMHm+KkXBrAX%alp zK#Jg|gH||!jwb*G97?!@CfcFiRV{`z+F`jHtQp)`c6D|Jrz&)XAP40n7Nw_xhS3!4 z6jZBHU|GNlI`#=F4Zzs|)J1}|oZ(>yZ@7SGO5jchTbh{ywo{`t546G~MH7}hAUg;k z+h!p#lmgkkq*{!0YN?Jw5@`1@teFq$Dxmn=$lMHOAf#l1=6+CZ4KWom5LQ~03U{qv zJ~(fHQns~1Dfmne(3!VT>p`16Ak7kRNdz_oTvCBqx?tx(wrE3x5ws34w*a)ex&(Y0 zBzQBhLL#Vc0JY&ERS`5dK45kK&h6bL$E2jp1j zDafGJM5>^kITzMqm!UW{uQmZVJ5b2yUdodEoUGpk6HKxJl5V&EQrpY_Tn(4GI}&0X6>+Mi-?f zmqB*8LaYMu@mK|F^TmU*56p5+NO}Pos0(r{IBkO%kP|{cZC}u&ZhSoWc-(kUrU#v4 z4&#F>P6h@BR9P4wCJWNRz`(%qOdZVPc%~1fji5B-xOI+aR!~0l-2G?HP`*2u=5lNU z(;S~qLTTvz0-rBK`8U8cLftelpW`$1eu>YUz|jv_ z2CmBiU>4V9(Dh{?{sS-{MsQt*p2L5+0W8FI8NWPO5tQI#U|`^5U}WH9U}E57U}oTB zU}4~6U}fNAU}NB8U}xZC;9%fm;AG%q;9}ro;AY@s;9=ln;AP+gLw*K61_1^>20;cs z1|bGM24Mz11`!5622ln+1~CRc25|;H1_=f}21y211{nrc1`7sO21^E31}g?u25X25 z7;i8zFy3KcUl2_f)N|be`GJ9f3v%rW1J`Yc&0M#k;&*K$z>Vdg;HeH)q%ZbQ?_ZOHwjTsJ|wK=wl2a}#n60oP3f zumsmlsC_q~_JOZX1gVFbcN5}HuA5MMZo$+;%m*7n1i^I+YCq&U3=ADyx1jF11#us` z0(5zq&~U#84W9>4ci)4C`#oql-h+nI9jN*{(0IFtmOmfB%z?Oz>poQfT?h>k zWnkcX05$&s)ZBZJbis8W8m^G+!N7GN5`J9wp!8j+`|d;OJCO7UGZ#j4L5d+5mx1dp z)ZDvJbM8U;cTnS<>kh;nFpXUIA^zif0M&OFBF}XfA`Vjrqq*)v+{1Mj)m&WiTz4Vi z2$SawnE_^UhOEddD2-1^EsHP6F94lZo*EAtKm(m}09L@j0FwvxPe5`Y#ZV~*2CnDO zcz6y;S6t60faSQJL&NPkG~Az~#tT>x62bKhs{SdeJ7G$=p5X|GXV}%l^ucJZrx5qS z`Ol!~>nX(jFmYmOu4j;RMXY+TI&gLZvlti{Aot90J%fhVGgSA%RH4grJ%hwMTz(!j z+~z^j4NM$HbIpaOqqz`$Tyr7!aBkUjD)PHXwGF-1A>5A(O zRQxr>e6H6}cfNx1-$29pH6+|1x)CJTD^zi=SJ3c&1v4K?zk-;H&*9SfIcPGX5VM10(3to}!ZE_%zTqgn00xmz4ODeDH-iX~hNcpf+cG zacT)@2XiiHx*oi^0;C&?Ip-vNU|;~*$pW$rD$2mXIVbl61ITm+7LX*8c+Cd}1|bFp z26Xiu9~c-wR}i6#&-}o^Ad5x)>JJPI$_xw)JRr{_nZN%71NaIdMl|^1~7Aw!y_IXAP`&O;-I{MBn~)Ev-d9hE5RK}~#Yu>o-qGRe785zOUW32Dc3 zuC##iouD-2K0eNsiBNtal&*u)kb0eSCFFiLE=$P$YMd*(LGB0p59}IAl=At?p<48J~o`oi${3rI1jEe$Hq zK|KRD1_lOR@#`%NVo}@&MD9#(kPP|bAoe(cL9|qhL4@rKgG3;>YXeIDpd<>)f6N)> z`rvLD=s+OI8B7e|86wbRGw2i{@OUg}I1xHpo0^xNnU@MZb_V2=)D#8CzIo8RA*AmH zHNdH~xKaT$i2_v(pMfq0E#8Igcm^w0$jdL+Q-IuMPz2t>R}5Zvl9Q9d1#^#TF=(TF zC1h}0Aw4-W1+)mRLZKizDIRnu5`+iZ@dsuh=_6T7W*+491kgw)Xb?KTv_uDoji3W< zG3`V)033ouY6oo|g%18hSFM8l37TuEfcqyX6@Fh7C>%=^Y!yJOH4p(64!UFuI_8F^ z0@Hl(KpS|Hr~-8JP?)2Srwap8qA)Ww2kosWKoK)C2Av-dix|kDnQBfBXoW#y3TPC? zpd!t{z#t7i_sE5;-PF|33Y47V(;+u)z}WEx=BUa{iBo2YLzxANX=cX6DFa=OlAny} zHdNEhae2WK#Zq%zUa({UO>TlV5kfBC0?&iO*2RD(;S?1W;V}-D1WhVH7cPL(T(oMj zf{Tl4g`R3fEMzpMxLg;q+@K`C0JNu?AtE@$KLED+8I(gHt8+oyx&pmXIx$H01c27pzE_`4{CmHZK5jK@;d?@wCkJQpou+Rwzn>;iu6i=jUNpgtSpH#K{(XH5@2L zz^;H4N#J}7o@xN4=m1Zrcwfih5Z53in~)WPiawGQLamDr@sAI2LNXK_UM2aUMHA4n z2T9U5zbrK*Kg7ujG-D1r1yCWx%{K^C^g@k;#W$+!L;PK!YY#wK63IMdAAl+#kPkqE zil8NIAf9L7AP2jQwFFi z1g+-)ol_0VWXSe|hb}>pUR;t|Pyjyo5Vw)WIE}=x-2|snWZOYQ+#t(+{2g85K|$c_ z?}8(sU`j(mA_H9GO>wG%>~sdNQAEjA7%nu$=|T*pX2dHs$Eg&XzagG6LGlc8jKlVH zr06JM6j8|PAgwS(qHKocaZq3f1p5ZZJBI}MAlV-bUU5rwf(!O>409!v-oW9Bq>?}~ zLQ;u46``AnCpHm2!WW=O9*2ad0`33}N(BcHhC0x-qex*1T3G-(qztSWRFs28vB8B8 zXg^yX%4q=bOb0G}AjKGHNlIC2Q6-*Y6gg2LM=hi%DN0R8at>mGz9hw7)*w3xR=VM;QGzS;lJ&u*74&2)a5DqC z&;!X#kd>eUN&!;xf`bQ18gv0{X#r^c8tB;kOwg5jB?{n@Ej2|CwCDzGY)ZaDqCyF* zaZwDu8v(g`!{%^MHUWoayr-WRl8uP41T97f2P9~76*#GZqEaDRH6<2FJ+j#ln?WH7 zy=qdw7}i`t(gE@^)F;sJ0M!6_;G^%=lRr=ryT`Qq!9CrrtO9ihKg0}OZ4gt@6gAG8k z1RAyQXhUhwDS!@IOHWNf4hzs_0!fL<+3@sWr2z6eG(te_TkuLjbMQ5ipm8O*kOf=_ z9v|R&O|W{n9LO+mIKpm_07VqI;jW0}Y-subHRV9^kUNG!Tg{LzxXLKk2Q}hI*s{mbWqFMpD^GHFpLKD6^7pwx*0p$W~LM|V`gF28-zk7s&ufL0{ zp#pe$Gstu>7qr?L>GmV=-WZT1nklfl0@IWbXIBL$#~}PpOb1;k10H5bPE7`_p|iBg zC{5C}%P38X2j4tvP+?)f;1l3%r2rI3T6K^7P( zLLGrn53!SE4L$+R@eoZxF7b}e&hf#XQLb?BAdH7DGR-V11l88r7}i57ZP2m%pnXOP z{sB%HN?$z&C3Vf%LZO}jY~mMZXyoNu$TpxpGYRd ztqgGt!Y~zd{4}H-S3s9W4GB;Hg900}#T;u$f^rKUC6FKkg%{X`3P_;_PM@GK0tFj* z$UqUakR5uJ4rn|owYV5Q0)|Zr+-$4>XX=~+P^Pvpf(}uG%?2Hy4Lbh|vKdbYHVj>s znFtv>)lmp=c8YgQNht#Lf-5k*2ks<-7fKbCmJ}3Y$b%M1LZu5zz^Mt@DaIC{yTm~! z;eeMilo}gpROIO>C@DjIrVF~`2Xv9Ft*wF)XiyO91rrO%cq$<;`1*SKgKnmQ4DNv& zA(o(P$a8h`3z8s7%q2A~u{5Vd0TkbefIxDjr4eHA7Gk}n5qKOE#<2unWfJNLIwb)V ziLg6)5_3SAH=|rXryyCkG_eSD?~jS0IRiwcYaVE^d5S_}G3aJ9&~j?sl8mDK()0|N z-Eci12ju4!=jWsrL&E?rWo%@XoS%m-YHErhVusaP&dBxzvJ)w#q+Zq!~ z6hMb=fjj|mG9ulB58KQEt?hlr?*oCAMxfCkP{Wgp0n`U6UPP*yUoh_zAx zUA&{<47nc+x_u@f*b^ZS4L?Ym17r^99s-cbphNoLO*dU#g`E82V$do{@R0yuyMtYQ zgJ2as=p-XFn<1?enDb!91_XP0IK?{$DQG|n5YYW0ns`hBHCPat64@gP8jiNAphd?h z{sF1aP0!6MLF_EU^gg5=6a+pMF*OBJLV;ZmkpO$$GY@*@UXxBzTWNM%7PifE{-0&L4E)Bx}(XI^3s zXh$Ka1QiE)3A95Hbf++~IUsRJJVDYfXgeGv?h8tb zKsUf6LRklNyHaXy0r=oUa5Vup+fxD504RcP`-2L*6hWHNAS*x_q(lK!kOu^Ng5{AC zXm9|u9|7K{4r;-AI631>cnA|=13-E>b%8cJgU(|tPAyRc7iI;;pu18`jld_)VVM>( z2W2lS1<+DZP<;ZPAx|qV(9nckYnGpj z*Byb*wFli>hGHh7w1AYBD8&P$xC0dukfZb!qCsczXXd5bs-}Qi6rf8+ZNXzXP`km= z66_NWI{^i${}bTk2#ONb6wpWw*qfjl0Iyomh`l$O1_cF#L68O4&~h3g;p-UetqNTf z4wV2OLjYQEo>>CxvT-peD1e0(Jaa+Y91}}GlgOZnLr7mICnv?%iHiZE1bpTIXdD5w zr3IAtKs(qJK|_A2MWC)NBp$%0W$1#{GAJkn`-I~+8l(WMn4rPMIpuI;LB}P43ZDEt z1;?V)M5GB%6nBG^fwr^d=P7`X>VS=uL2ro0aC?4ovMxluE=WBCI8s12$b*K`Agy03 z&{44AsMBYlz8*Z!ftm!6J}_9ff~si+=vWHS>3-I7wBL*@K#e$11O~gavG>Us89i|0MZAy z?{#z2As3H=s@05g{oZ#PSub+gK15E zoSSPUC{n7$gUeS z2~dkZFF7-{ST_%=d{Js~W(sH^6^A_dc4ctIf@W|*adC1HP6=Jmrg^NgxtTb$fg~W> z;8ARDYH9_ppi@)gK|YL6Doq2OCkbOC!pPjz44DI7FarrNb5n574#okmLxFOT&_jH7VmX@L1AqJ8GUt(F5nUacP z64(;ZD7pfuI`(l@C`-&KO$8mtUuFM<{=pn$Ma2#1yv`FW|(t#{yz4K~sRa>fLhO}NZ}6&c{mxbjjmK?kELfDRcf z(m{+DgSvcR^AOGjjZY~A_{Mv>__%^sY`DflkJf{hK?JPMOD#8q*-cm}ykrA~MrmGg zY6(2fiXmkp*j88yfi<7u?hf${Qb?^R$OO$%LPj+~>&*&5bBWNV3D|q^R$>agGA+q1 z0^QlI0J$X;Yzw?a1zJc38ixdxlpuA`EpnKOic)n!;RRC%T26*y9;oA0qyXBE4myvd zBp+NnCZ&RwV}P%*SA-gw4nC?FJTMJ*FKE!MNTIl-G&x&GAq{%9G==f*8Iiz2Wr;_SuRmlsA5`3cS_^KD!6CsuuC4)A3a|?)5UCgHFoYSP zNC#yS_W%P7IZ(n$MU@Qjbq_EA6%?Shgh2)T=t^*0Bby3NO;Ejh3ZOezGxJI_^U@K8 z0K_P;{R*Jqhc*5%j7m%and9%_7!R5Q0ZoD6b}1HB0lx9bqPQH7u8g3=;Gq*7;Ogw@ z=o26A=r#rO;XmOO62*N1$Q`eBKAt?T}I?EipMW z2Q=)0sANE8VR3#=Dd=<$1=SSLd941&anf#egTOzzU!a1QjOW!xZ%)BO>4kLRA1Z08~zb#zH`yC(w#31<+JgXs|+VaXQ38 zzkFz)5jMD^qmWo!T$&5g2--3Zn!o}Lc7n|Y)yklgc_61Kf_G@bdV1iU%}`IkmE|WV zgUesU5HnN-=-vmADutkwO4v$qP!#|=4-H~dK&V0i*ltKGRRObQ4OZupSdyrqp$e{f zG(lZ6FiQa<0JSV27<^R+_*Qvr&h^dA106%;m!Auwd=o*liVA*3;MJg(2i# zLul6%>Sru1dPvyfYx0A--QaQ?JmQp}44UdNGBt*21kGP278NB{LarGGcPYVV5oDC> zLlv8uz!ih${S^o(H#dbVFH1=wq}sv^p*p#kkZMayxN1=oIb`LNFEp&x=2{cIx>R5u4KSD9M8UUY%3o z51M=MsRoxsuq_!dt=M&f^Qvlvf^&XRs)A~TLO_6Ta1iYLOQ^#^YQTj9q5K9?2svU4 zntLHNDmeQ>m{1cztsd~ne~?KL(7;bl4!9XqtdNqK0xnu$?Nbd<11<%0GLI%wjxx1? zrc7x69e*A%wX}ewWAG9e0*T%XrWg?i;1XBC-`P1He0dJ6@P_&ZG%X5>8}R%9^b9Z^ zh2rG=f>iKar9w(leiDRLoLUHGKy@PPfHV_f`$fRIL5-3Ms8V?K0Co$g5JxHfi&6`6 zDv`p+%n%wrSO$$jN8^Ids{|c|1T`Jz1@NUnFz*rP2NW%2djb-!P+x#^0N7k&YF6AK z12Ggky$Ay1b8|b`3E>DIQzONfVWA( zatc;eAkPq1Vaw3aZ*bbMN3o=ZZn= zxuExIf=q-Pk41UptN<$jH3dM&?xC9xSwM*^ zw<$oj13)YW9e)HmHWR}SPTIUl;b3&RMgGn|84b$4%uaBdfUt$=+K6{5x=w^sGs^YTiZem81)w3q zWGgdsOOzT2-YNz)GeC(SQk*!31UVUi6+-wfXnb&XMv`}Q4Gut7@965JpnxPF>>TW5 zz~Joa7vdNi1S(&^MHjf5gl1oG5euyf%b4f0!BMolvfG=wS zPuD_S0@~REaR@lqIfJfbg-mfMfM&unMBI0Pk1@&Ht+;KBtR-uE5N&JK*0)H#R3m_1#l(?-HZXA6R1!~2Bjd?6a|pE;PEje zrJzj^rO6rKZn}aZXh%Deq;p1M9>{o5?F>6W7u*d3?Ky!&1nBHvQ}Boi)P-OHQ>zS+ zBX#Ydg2f2$C@3H<;DpM8LI!FpI1ClQK7f=9pqnAU^N8T043yM7T|liV@alNfYz5lL z?&jzVO~jxb`p|*DM0hGjBsj1|kf4R`(FX?sWE~CEU67Hd{PNTy-8|^H6o_Mv!m|MJ z{31Z>eP9*6Uj%q<6zC*>u()$RcBRL4fgJ^dysw^nUhc3gZfEfzj5(i(pt$^+%sI-f(BXpBKY{(LvJ|G4w zD1fA)Zh#xCpb#ACtKb|0oA6LAg;@!gNrc|P4w^^;P5Kg{0(8uLBB%}kA4rX1rYGFC z6g1mB6$sgeMFpB|a5JHy0`;J3se-d7=-Lm+eg>=|1Xc<@zyMTmf_fTA0p$pm#TrsD zDLjtHsRYgSNTCbSf;F&UQUom|J-8r7hk!zgV0b~)Vh=EA=sO2FDR|};l$I!fPkhB1 z?C5IH6DiavS5S&dRe&sp$7&F&3Up(jS<5*ezUZ+SzJm)?8Ig=w?I@7sn6< zaBXh@y6pn$Xn5BHG9V8ddxr!k*r_l>K`IrTJi$X=P|XSox^|!mcJSFOpc@YJixdLP zwYgwgu*<`x!6teH2O}E^77KEBMix_00ExyM8iMEVKzr}tlmAeMfaDdNQQQU=3h;0$ zMm7m7=<6AbVmw&T-PIRap>s}ZB51jjf~UWWBUr-4*O39VhMyt8!%11yz@)-T!L2C2 zDm70bz*Si_ML|QgSV31o71ZbqaP|aUm|T{boC>~g4t!WQ^0G-#vIMm!GxHRZGxGC` zQ{$6B)5=IDgFCBMApaJX6mucl36=57ht8j3lY}k404up6;y zaf51sT=I!*7)-_mdJ8NzIi$E{g%X$8=Npv=5&ao5kR81`Q;krZ!l_fbS$kNo_D0tf>tqNiem+6cU|6Fryo81eWNA z$>9rPPNT#fdtQs zXmtndekXX{k&5hccrF2%8{pxDmQ*468a&SE9Bcp@!$EihA_p2XO;x~L25a|qY6@>AzJ!~5JFfAUd|NY>Wn?aAqSj*i&gN7MNs6Ig6_QqT~)280KSLH z7BtWc>iuLS8H28#F)}v-A1I@mX{7+tuK?EoHUf11Y>9#@O3NuZu^)tcfKhprPOtOmh)20Xm!pJiiHQyI?AWcp5Yo4qDiQS{5POgz!yiaVlt2 zQDRk_U!(^dbkd$1=;OrRSX{8YE806>a=MG+21jN{Kp7S6Hc#+UeNfr~ISe8PN)8auA(A0< zZ8NCJf*1t>&+e(FK&Kx9oSXwyQ$Pb-pi8X~S>MFO!VFXn8Aq$8SgEGOS}8ShAt==6&yXCAQ{uu&(X=p6-}ilsDA|V5u`N;DlNgO z3Z9E$hJsEx3I-MKkW+ObwXH(5Np>uniGKN@#0npThcvU`rUW>9IynY`mvN!i0O%^9 z%lvc{(lRSR?kg>TRhe*=piu?`kdu%u%~b$z)&^Hos18#AsWv29wUc9zs~?(bOpk)h zRDg70K%2!N$AqBy*v~Z_Vi=MuQA|?s3<~yh#%C8;g)d$eKEa+KdCT=1z%$$q;!KcRRl>w2z6#AIMpF%V*_&}y9xE05#_ZD z_%c6T@DAFH#A5Ju_Rx@qtQsvZ%Fjy&U7e<&3OXnrq0_%CwFtbK5TslowXhU)XE?Yt z2F>+=HVhV9p?VpfNWjCm;QWG8z#5uC#$ci4ts&?*ab3HTq@4Jok`m;C)X)sP4-*!N zhGv#l1rUV=sW~NOC`!#y%``VgC@n@c)EvB&9B!z&IZS0{8LC1H@V;BPLJLEf!lI-^ zaPkBXA%M=Q$w>u|7v!fTLI#a>(i!l^tmSGV})h#Xo#Tml9qNGHqX^5DGmgI;b3+Q-7u$wcevILFD zfVZQmrYL~#X;wfQJ_Sc;aayu&a!C>RE?-My2CzOvZ3V0LxF8bX32bPKSRu6tW;%G9 z8mu!I++I#iL6)>)P*6?rb^^sTl4Yib;K)W6F@g-;rzK{m>K2tGGk`Yn$OO;AK`;LW6>u7=rJzGo3ZVB?revn2r4|)K zHX(v8>P>;1c7<$4erXA4Dvw-4(A}4r3R+7Exs2WlVh_}4P?7?jRS()~1+o!zWCz%8 zh^oBO+@#bZ(27jxURAJKh+J-QI=B^{Us?hhl2HKdhk;&k0pddx5fvAS6`8rExzO9g zb5irtOEMHvE0R-FQ$VfvjBL;A8q1*7S!JME7|?7Fc(VW^jtxyrt%}MLa}?AR z3@S_vz!6A{YhmXr7Nr&!#Dk(2w2B0jK#0;D;OnX28|U)_@aB#@ z^%4bW3F?HFM?rZYw>TXVYH-D=dEjKB08QTDg+f?#LUduCf(E{a8`9I zSl|V^swujuTJYPPB=oZylibRlX9__!3XaY3ntrK!cBW4+Sy zK_-9>V*~3oso;cMk{l1#2GS4VgIGDKc?csA#Xh)W;Oy%HS}uuk88}!Hv5gmOJDOI| zibvdfT_Zvu*Dv5!;^`L>1iD|s8%YWLd>YWb@4C8Npu1q<%@j^hhr|lO1%(xY%aw}C z=giD2DMFHFz~%{1Asg-(;u_@Z7=-K&gkM3!#2K0C8TvW-r2<+~bW@WQ90m3hbyRt76^Kn-G0`L77I7vV*4 zNdbx%wDQ0&KTp>HJd2F71_5j;LN{bu8%HREOLy=cCSX_QfvyP$7l0_MsKMnX)LGyS zl~CV66oLG$0Ln-4;Qi~isww)gW-?mg>Xw<7uK>Ez9el?;xVVSp5YR|G*x4}CAsw;2 ze8^6ul6(bF?Fk}4MK!3tz**da!U^OUsB>Wr25YLzM}vWm)Buf_ z<)nf()+6~0T->91#5q3~bU`2}KS4cEkdauN3bhlo9Vrzy5eYh;Jrlf?0hGHS&VWTR z)Lzi+COC+pwn7?k;P601BcfD8tx#ae2kQ1zNXUWDB`QtKf%_G7Fc_%Wg9tb9)EUSJ zppZ~a0rhu5iog|~DrhCD2E=Q&s-Uaw!LET!n1l4dOA+vB5m*x8ROA!~xh_uuxx|6Z zK7f`2Kts$wEe#Ypuw(-Y5Tgpn241jJKm=4N!WwwCz*Z50`ZAy%54gqx9c5doporLo z2zD@B33$COC}v8F!HpVlTtKaZOe#PRZAnbZF9P-Q6+ml_QOp3H0*91>AT##GsU=WT zpb-r_`~}4v(1-@C?lCkpHnW0NDIgc6f~p}fBOX2gUQ+`)HMk_TNY@T5gHV#63=Ze` zl+0p01wZsO1ekfKwV$DZu_Z(=BA{WtS5P$w%6p&&64YZM`S}XqBU%)|vkRc|8WxFA z6|f8lNlf5zCh&?iRBu~CPZS0%&_}JrjLgh%x(56 z$)HOQ6u|r96}iCo3g|+rH)S-tEDfz->!`sdfwtCz_twL<6hJptDI21Nnvo@B&4(n@XRYNO-sv6&II+N6LE{0`D1!(VSj2-i1;(eU zrWB~AFeInuq3{&~KvT*#s>R@)5!oJ9Xfb49Zh_TN<*7yBNXtdHH5Z&Vion-sn3`BA z78Ip`207w0^Gb_T83KY_Kr7WjL(!n!Zs4*g6SQ0lS|2NDfMQ=kHANFNP7P8F9cc%h zivpVKEiTOk^`k&7Kkz(m1sA%RrFo!J;1s~7!VE#gEcDEKPw?(ukU}nol+48Ry!_&l z%w))*GdPS3iXek-1w|>kIf+TBISei#!B&v#^N@~PC`rvNuu@HNRwyaTEC5fyWt8iu zloW%eN)61d3{Z7pss4vEa5#a$*6v zDDw*lwNgka0$pFLP@Iupnv()Pr5DtXPb~r6bC{f(Qd*R%kda!H%EbU`$%6tZqg+3) zpj0o}%Fxot3M2?lfO!R_kYRrCq%|lBLKK-;8X|LytV)U!!Nd9xX)^;utCZ9-@JZgF znIUIS=yFW3L;V6mVO;P^Q3C@jP>rf*07|-`YtR)+^7Rxv(-bQ6OF<{Er6!jsBr3QE zgo5S4O~;~C9nd^tF=$OeBFIlkIjOmNkV(kAf>N;C(+f%&`~pHj`4HdI4ycmM;yh4o z3)!Is+5H5X4g~L0@(T#%0vQFmt0lJpvho$=9Mxj*(Ptq4fadgI5d`8xmPEt55uo|n z)XXwaD;pd=FzKvR@KFoUS!5jrQ1uYt3OYP5H4kbfETf`pfutR7_OCf;)O>vx@kcp{$&~frfsS2f_L*PIGngZ%Z=NIIH z%I|{GqJsS5)M7nwe1Xy$B$kwxFY<<5TleKt?!* zfF?9S*Lx~}i~u*p6f{8fqqh^}&=sha#sOhA`61*vu-gpfo-Oa)=Pf zk?BSGr3J7JbRdC(j7q38OLal>N}z4I*+_}N%-jSapP82pN)gcFI|anH0$oK0>Q+LB z-U2+F6d;Q&A@0!4COSF5nogR6NC(!po*1L#8<)O!D~Pnz+^l) z9&;G-@(aMXIWRMwjnNp!(qo84^prv4FU}OTNz#~s^RhCxJ`9r7(Xh^Lh9#oAg+A0`ex&qP+21N*{ zgacKz-~+TlAsFTy9~SHq9|Bra5%1{Y62yQa0@@kO5P+cuMFgw{!{-n?K?xYcPOw_= z8IlGj6|o8m3a|;uo2qj1lVP1cvRq>U?Fb>e#=^|10#w97(}$t4iKUeRC>}#R zKqtDyyZV6!tPSFWT|+QL4Z)&laRlwlXI6m@JIsTIl|pV}USfJGxaI?$&(4Jz-r(4* zP{>J5OaZlZU{$|o82FkguqDXZ1*yTAoSz3;6PuF?IiTD%P{GN^8{8bkp$och(lrpQ z2q`p-A!`8OVPR&B7C7e6>xnQ7hWi?Jnka?}kHox`98dy>H;jrEqCv@5PY*k(Z2>FB5?s!p`We(7&rH!#C;E5P^DgAY+I=3;OT zj1TcO1RII)rG){w{#Q^_&;VVTW`F`heH85M6f_JpH9?vKAkJ|PjEAs%ky46ao2NS{(_sjN zIEO@p#5=pWgCZ%!F$he#1YxEUL?;zKaun?3ic&@ym}991u;}v)3qjRqVM>&Ju7RLc zznMj#o(y<7392cU=0uqi7Jy+2Mr1kWfHO8Ij};`QgAelrl_a34{4|BIfMNv=P$OJ5 z1;mClVPP5F(8P>bSAa}L@qwW!(cyru7j)?iv=Xn-wJR%#&&*4KjNB_|fikBdC~GR{ zE0~!;=98e#H8nPXtRsW+K?8+WW#BF-T*Sn{Dzy+Pw;CFlm=NVf*FXi(QIViP1l^U8 ziX{z$`V|V`2mvo;$wa%x3Q^LSo0!3?It`3=ih{lZs=v%l%<(DLQm{Y?217#&Q>zMH zyIkcwH*CLKLzX2h|7Qaddds#8MY*477oOXo>`< zLM|dNEr2w0L91aLgSZ&{oI~S5XD@?Fp7;ny(CJw@piLU!)QZrK$Y8~(C8Y%l$l6en zm#HE6cnpvuKusA_LsP2?@FGK~h^aYROq-e;TBR21+Lari7R^W{J0gY*O^pq$DvEXO zQVWwx(;x{1;Ybh*)bhwI2H)ods;0OY6r2M=B~N^SQ@p#YANWKwaOV&r;~VTA><2ou z5VS56x-J~WKL%!oprwMK&V*{Ql|o8tK~ZXQB53awxVKc2SOVRF2vPyx-UDv7L)LGj zh@4~#KSrmStc!%Y7@{6BoCdNZwHVxRg!l8{8>2v;M^=o{JA)P(9Qr8aE$_u0iw2=fjmRhJ~NO)sC6Kl6d-#yL4%>7 zu@-RVfu}#n=1@@HN>vCBa*p?O0Zs0rs)6*Xz|ANeyKO->A}TMaO3+qY96QjU-iA67 zR@1_!$l;DdlSkT93$hU6E$CK!M8v{`@s%pziaa%07c#mU04@bkM^&MlQ-Vtple0mE z0{EB?kO*J4bFf%~gyFl}`kRr|4z!Wmu4C9)aL7L{U zBG1yq!U}YSFrh6T&};%ZQVg_h1G?W4l==y7*MKTABeYioR0taz8XJKUGe{4(ArH>N zprtY3U7Db}3A`X3v?2%UC^B|wfJ}!b=u`#J$Tq$$8X(0;mx3UwWN?lF$s!6IP(7qT zXwNT53ut;%0dvDIND3OrDd3gb0j`j_8`Tt0{wY?#Vkf-oj6C`WJ@Tg*xu7tzFoMj# zLsEm0g^>w-a|V152`CbbER2wojgbYYM~AtG1ftX!)l6f!nFXoECE)Z5?)D^>C1&P; zCc(j{On?ubfTV4(Ea>Ek;?#6d(?qwpASbh=7?ucd?Y97*Oj@9yR$Kt8x=p})8`6s5 z0;WdbeJBVKLj!YjtK{62-OQa~%oZEV4dQ}WX^K(?n97l3B_^+0pjnhb8i0agl*klTwr{R1Fttn%`~$F+mo zdx~5jH44h0m_q4MygbO65+(TxZovV%PGEOgDPTxA zf+Zjhh9phU!Z^gvD8vex`;;1+iJULyAaIarJco{2r>k3-nnwTM!L8^Fonue?+ z0p)hk-2vcGgE#_|A^a5r978;i+y~v#3R*Cmn+fW)fez?P0bP|1QHW}ESSJb60L#rR&P^;y&HyDwaE<}@E5HhaQi~yb z4#2l`fMNwc(WV2*M4(Q01%zz~W`kB|l%zryD}pqDqY-6wIcV8)VhLz{s3zD`@t`08 zjqEchD5x44fVQ(#KqWkbgTNAQ!2$8UP7#Lj9?l^?s3LA?B1RZ$jN(z$1iQEf!;SDj z<#-~j^KkL>1I=DOLLnJ+vRn>$VyPT7cM4h|P@a*R2Z}V%C`%q>r3yGE zASD7?`Yg^UEddo`dJ68DpqqOYN(;b?wn3Q%o{K;?WWbj1z%x2zX`TWoErYjzfZYY_ z+k*BmW#)k;!TUf!1+GH5fxaQQuWeDG4;iii>j`moRVV?SuK}v4D^SnmMJrPc&5aEZ zbplFQ8Je5ml(I0ev{Hnwc?At(X&9E~DA?F27#e9R=qeaOMgb9_Y-nL> z8=99{qTrm7nw$;V=!+~9RGJ40K!uRhBGAoHC7>HVOOO?~n8+ zV+U&aPbTR zWogg`F6iYW;8-XEug(W6_5tnKfVd7)jX^fcXM&C~0V_b{8c?)C5?881G{|UZNfL_` zHlRhCI?$FAIGwx5+@$f5io86(DG*YD6fai3r;%0^Rlp z3O~^Kk;$No#L}%45G_0%q$VC{>=Ar>D6BC6G8MGv5qx0;D5=7hBS5QhNHq#cBp|i< zMFpT6Ghtd370M0Z`Anf4RHHyf5Rk$J-U3L;Pb~(mSc5bb;O;L@*CWCdM5hT}2f!SG zWEU1ynR$>P0j-Y(tF%%8c?1@0IQt)ZLCO!T=@Ys^o{(Lb%1~m|$k^Q23bYL)J|i_JB|fP#J~vfE4HT7W zsU^u7@gON^KN}Q4pq8IPaz<%hHYg^+l|yAoYOz8Rcviv|G{vEil%JLcWr3PiU?$X$ z=n)3C1F{ziTA-k{8I4Sgj0igq#YcvqffkY)j7Fw-TYx#4DUd@|5UvNOpiI!^N{&9@ z%f`Wj`XNP?phj9rKKP_Eg~Vb7(1o}PKAtXMX;5~BhauPm@X_Lkz8+YzLctjvyx_4d zT|0%MWN=++Q~_Ey3Ch406$&MwIg%1kt^vgdG;DqH^Fgf*1yG6X790S!5;QoFR$Kr* zc%rz#2$FgIz=IH==37ZdX0bwUVsb_%Xy?7BpJxc-T6CyEpe}M^N?B@ANoH{>xSU{rqd|ojXd57?w8Lu@wD|`% zsvtR2H>tEZFJBkjEY-~{$YFqJ4siBVa4Lls46wy?sVRC2Fb4*Jj`31($uH02f@*=u zpgA3CAE=}P-+qz_a%C|W_*fp$DLuuRDXEaKhn5zgF;+-frihW`O~C7&5v?C16B8q= zqEyJj1@Jy&jk5gA6!7L^2DC)yAK>T%N^#(Y-eB*eWDX+}OY~l;DP%|y$vRVG6Jo6c zCs|N20B&u9@0A9Zj-Ubrbl!1%PG(9xD6NAgEGt0A`h(7BLpVtnbX7`z4rpPfi8*-4 z4Yc4H`3y6+-~eZTKPv_2oP5yAd8qng1?YV%piBjhR{bJyxemPV zKrMt)P;mj#0(LjpCQ!|eFdbHH9cTAu-Gc!G|NP*5mNEiT3s&B#rT2g$(Hf*hfs020m2OQ}E=O)M?R$Orc? zAoEHfwJ>);>`?&Mr;cHco<5)@#E`}U*#GeME;LFIIRz0$h7(z9~QY=ap6ms&@<3T&>K;Z#eiVpKN za_EDTGN|1FKA;xluw+o;2DP?e$`N+KT?SDD8k>Rn7I%2yQwwqlr~v}*P=gN;DJ)He zj$Weq6K;1#ZZhcRgES&S1&>lkP@YjJh9p6-+3;o3Fn^;cfdn%we_$;%OifG~T*89m z{e!`jTR8IZXlca-x)9qyMK9QI(3%e-3O-yDbWJjJ6P7OM=rKf~Li37hib7FwQ8K9N z1+|^?L9Al1D)8`qF{n%dmq5_?10CrP%a)+H#VC9rmOH3I_Wyw=WT2&*Zbn&gCfu!v zG?1QJ0x!ObD~k&fixP7cijq-^GT0RqP@@#!>OiS5zZg{O>4FXsVL;qj4pmyL4|S0t z+-g{(5vl?-xB@EEAnFt#a}?n4#Gx?Q-$&miEEu_F108v#muzKfXbzfKK`-S)0{pE& z7iVH^>4I82sR|+fF0hs{7Xvo+kmLfs5;Pv97&?H$1=^FS5E9@II@}SuKp4{ZM3E@~ zoo3um z=LV<);^7qnIMSdCLqIhEXa*d^ctbPNf&_FrA1FvbZENfy0^a2i;Ogh%>E{j)6;SMe z5)|kZl03+cNbrCcH2wIyfKnEY^aGmg1L+5qx}X6`Py&LU+Xh}gVg<^cAO#=`K<>hy z(2R_Tj8t?#V1%8CnIQvm5(H%su>J592+m{B$OR2HLKakmI=6}NJ}Q=UYGRJu!i44p z6AME~o<*1kPCt;m1?~HRm%c#`x<$=NCPv0^w}RXWPSUXUI=GPwb}OR5gl@TmnhWj{ zfzvvu5Cb<-F@wVxo2yNbr?sJ8F*3o@BL$@@P+kY`B|>$)k%=)l4}by}PohK0h2UM% zh=77-Nc4b5Q-w7+Q@G&a1}kPj&VU6SBmsj(pjj;y($0jpl665z6MPS03aFc&3QfWl z;MIpn+CkzepxGZR3BuUeh?oGtNU@2@ zwAvscrURY=hLqu;rY5xM2|6vZD8C5Y>P`ifT6tyQN;EYQHk1o72^<(OlgdGtC4f%* zPfQ2xdIzlrh0Ju|Fb%TzAM7#(uyIxjpq4h=I&e}&N_t>7fEHAknp=T-Okh4}whdGf z!%RS=YDg4=6+wIqP2VVC4weR)X=#M5q6PQPKn+lkqrh$i4Fe=5gO3OTjRS%@RN%#d zU~hnCL_zIbB-Lr)0LBzxX=or$-AySj(F7lfn3k5N32M8blnY>I=p|bj8(CVVKu&Un6#;N5Vo2v`z{%q=G;*O~obP@(bRc0}Yfar017_qXCpsON&w=eHu_?fe(qop#juy z&;!eX%pk0%q^L9xyc!>6h(Z_U63`9=L+EfYic3>V5Uo#;O+>jCt0oK=gO>loJBXl4 z7}6uI(19KI4=SY+Aty;-SLfpE2sye8CE}6%WMqmGxyUjGM&N@S5IGWFG=omJ!j>D6 zbQ>F?v=NbIObj3i8`MaEi7P+~6CF?=Juw%05h-jq7`g&F1zeng@+MqYQEEXB$8Bq=qqL?JO5w5>cRH6=Y2 zawajj*$7eY0axV+R|Q&22`N`Fl*3xtpfUns0kn4tswa_*#*$1CTEHuHAWlH2gER`T zDhe(wDpPQD_68qF3~rrS!xl4u%8VfWATDSCK(a9CgdGLQVa4FpM4$)+_moSEacK+& zZ_$E#8PvOhnHdNgRRY=L795~ntN=0$mKvaj!c;j;Kms^0V7(e$mtR(QGrS{ zORU2QkU&Bli-&AEN*)3&bA}YOAj3=ztTOZB({eJ?GfLvYZYTyHljR&5-~wxQAcYS| zGqjinZPdz4u7vm>qTD$@B^6Z`Etnw6Af87u6*Pbb*&v?+4JTw%K_hplvRF+GEl2^a z&HxS1gO8q5NG$^mZA62X%_@M$WGg^BjluqcP5>uC&&kWpECJ2yW~NmtM2A!sq@pW_ z4K(HDmw=A*fQ%GGgN_kLGZ#ILA_o_WW>75;UO)lv3`2s&+27aKGXyr^1DaQXUAzZs z@}#DK1|=XW@mT}PWSJ!}Q@9u)IzXg?v%hbEk86l4OcI|J$WaM365v{a z_U(fW1}&ff%_1ov+fWRODaf{e3}bw-8dIDOI-C~VAcr1V0WP^fo&L1X85`^x67Lz{ z6Cdp9f+zXFwZOI+f+{Bkcr-#15L^++T&QzH9D|5T_{gcUxFoTt1e;qSX1cig5EBB3 ztdx?PlUkArO2);YBc?R<6hc5V#hJwl`Pqq;I-t?$lFU5N{FR;_G&z9E8Vyi$UlWq( zK}=9b%MQG=0wfDs4FKB7u3Dj~ha8>|H$nzzpp9sJxe?(?NFNepG-O%5o`ObEvI3~M zM6v*>7zUs32}+B(pfn1J0c1T;pCBwKNGvJ_hXSOKg(XFW%-qEERAikn?|`BgoGfe= zK-mY96d^@CarGN0KR~hrs6sNbFu`yWyw8EuensRyE{0%NzhM6$&}ceR!v;3)4J!Xp zm4G}8Is^|opBfzC><22;@{8~)L+V9A>{EdB%o1TI-$2HZN{hj#kQ+sCfrfFwYm-4P zPyn^LbMsR&(=tkmnH& zhqwpS+ylD_RJMYSt}n?4m3SamDT6NVD2B&Wa#3m`c%C{BlvY9M23Gj#LQiZ|MJR@< zfgJBr%*6m2Hv*ND@gTcE#~~NzgM!q+0#w0c^Q@_{A>3w!o8f^CNmaPK2FVa0uR&a< z09msHzI6(>jgUKX;N1jp=;|d~nS(B5fu>e0>&YNCfR>V_r4}jTPeCb2DF_}-;F16w zPY|O(r@N&kmgbbCrZALb6d}SCwrCTcB(16& zld}szo8uVVJR^KvL5G+^!Zrmo&=c?L?Bf_59Pi@k=&k@>%MB@1g22OGTntX3?#Mcd zOOrtDl*GIg@G`p!1r5*!V$jeY=oB`4O{fNs%=8QeAJ933@NNR=q;n1MW)Fmgn&A8j zD$l{=Qa-LORtn%H#zm=#ISRp!o(iDWAEY={hz5;vfty6JdI;qpMX&)}(69}xRf$jm zUbs?_SOjXOLV9xw;G_;3A%pK`<6_83O#$z60y`prpmMk10I*7s{g7fcMNa_~79aua z4#AQqK;aP-901;o;^XQP4?6GNRRPrIwNeL8Y;eD|k}L+0|LW$JrKCB%moxNi9xJ%}W7=7E~=K2q@szfnm6-pR*6lbXYh+ z`wgJb@ytufOa>)$h3MqcB4}e3vQq()sF33qQ~>&d4VT1bRJ6Ix;k9>=35NL$qukYkZbL#W|Ks1rO;QBwot{f)X% zQF8-J&?p@^p24*wXlFGvmqC&$vQ>D1UJy744`wH72t#(xR>jbpR52%!{DnmAgA$X=7Af^h_m=%IUQWQgLZd- zBMO{9L7|Qks)#^`tA->3SRCO{4Uz_>W>CKsREj`?1y*z+5;M##ghQjGvH%=bCKaGS zA}4HMcEQ{Ra=LGbZ*V-JA`Y6|K*w*lmPkPdul6Kc4#Pf)z4pL0k&xQfIb zP%y`Xl*Rix`@6WtgBBJOVFQYe5b&Ncw2}qg`CuIZ{^3FKAwiDLcyk!k7oZ>l>jG>#-XcAG3buQl2XvscKLbWPC4WXdn-f%QH~3t zx8|r;K+cHC0TpIe3aYxs2F08OiAA}fjp7C-72uoOAXgoM77)W+2ugb(9}r<3x@VmI z{aoTPeS~y)Jj@cXPG5hQ_<*2ba1#l1+EsjTs1rQJB6^ldso?oiqyjf=z27k4}Otf(!#eMgl>LYjP^VDFUVmy*XW40J<(9 zzo-(b13cXXX@0}B1f@bJSwX9^EJ`atfdQ)XP|O9bfPh*Jx+)9gzvNV?nXn!dXz;KA zw7nnP1OXjcRti}c0ka9i0K}~#;1LUu-qhk^JuU`N2*vxl`hr^7@bmg1Z7PJ1FdPE* z94PKV^@@KmC<0+tgWR7|nU|QGnG6e%lvHRE0rd-^ey~yidjPZ=x2Ock8=%!5DJeyu zYZs72Q9=mnIb>52-UCkqWag#oLpNBF<6UHvp&^gQ!=8Dd3yd?XKoh-b#qd-B9=ZaZ zevQ(l2VF3eS_B?(wSX>pfed4nf~G4$M)(&f1SICAf={DK0IBN<$M{M|w455blSfTqtNK?WM-1w{*J{Xu4N322xGoDuU9 zb0EE6$WVqN7t{>McmXI)LEHoy%!RofRHehzVeuvC2ncAhf~kT8D%d1Ypr+>Jr-K$W zfN~tT_<^ZI*b3T34^onsUk+aL0P+d4y?)@yUeF;WX`n4G;C{PBg#!5843Iian2{l{ zHDh39p!pyJiwaGU#~|Z}kRU^N1MEmpn1S4gbygT;Jj`^T{B+1!J1_^NWELkU7J+X> z#%nStkYLly$OgjNNGQw4KrJ6o4-7hM3mNS~NywlO)dj^7Xn@K9nv@X@1e6pAa#uWf zT{)x$j=Go**(6hQ3utmcgb%nPO@$=|@IWkNq6{+Q1q&ERjA!O4fTqMiaSoA&&bGmm z8AKTQkL3N%2SRJ&~ z05^(3hC_-2WVP^Y4?YMb5qu9eSSz?jKy6^A7UY-1WqOcg7nWTt?$DS!{qKvJq&tYD=8Qx8p^pvoFKJiu-ND@5c9NZAD| zR$zG)$zX6$C+2_(ib_zWg>)7UxNL!(KA{UX8>|*zjDS^Pix7~h(D(o)F0eXSdVp4s zpyCqJMuJ!d3VVP*>I*tm&)FN=cn23cutI^00WO`Iq5!(8S^-@OXGrS7G@}Qh zTV_Ep#4OMp5p3NTLOH55sOl^&hOVW783}4$gRT%xQGgqU&<{GvK*6Onw?GfHj@A}D zPN$<#T$%*qT2$zO?pXyjxIwKBh!;UeTjeGefbW@vB?X8KZXYVb+=K2#a7ck_A!roC z9p~u+jvR2pgq*dRnFnqnz>NYq9OO`NnVbn(@&itKDR4sqauQ3@@{4jIfe4>WfO;3K zF&eb`0#x-uMh9Zy4h07e#Cf1=R6*xbdAgv5t{Xy8acOcgsPPPP5oEy^7Ly7<*DfXI zAlVO7ABU0D!C~ z)CaA01x1xE$VLWVm*5a91?a3B_(BW?UnlZD2+>0qs@sk8jB}<6Dz=t<;+y@9%qCK z@VW>t2G=}LLSlfdl1*iB_V5e{@prLO2+1$V&&f}(ge_hL*DY3D2n7n@BUkhDK*eRT z4njS2%@fQV`2GuMP=FE!EJMRBLj)MONP}-M2kpT}vJ!DP4ye>l&IOH58h}p6@eJ_w z1fArcmjbIcKvUEuX?c)^M-@7twFz)`QEDM*8V9@(2%-~VKh%|}Fmn*~Il4-iOCfu0 zpqT`^h`x{fv^bAXZu#8GsKFh7EB;MGY-X zp@w1&6X-FdP~XDrM<|5_3c5PbAU$OA$;dI3p0nVUvk&07Gz@;?UodJ%)!3=JWo<5*?n#AG~-K5-PeGpxorkh++lmjZTAxCqA z1hGgOTY$m_G#;3fnN$R6iGYtoE6LASD9y_RRo}2%)^hU8L0A5Os>6(Ouq{{&G&O)2 z2tBLE!`a7MUo{0hN35Wr1-bYw7IaoINJb$gH3ziBRy8HBSi!{;!UYxC#as|m6tqCQ z@zeA3Q$UqsL1Hmz$0OwSGT0J493C?_hnV1(uK?B#x_P}cH7~gm=9`q#+$7K?rR7ko zAZIUw)qq;FTEIa)hx)V`k>A0xV>#|2(b>f0J^k5!8b9vC_gW=0_=B3P}>Jl zf`Dy++W3ba-o+-J@&0xgD4%S;Cky`*B8RSdq-33TRlY7xX6C7HRPK-2*p?F9-z za4zVFzx&0~xFaDICKy^HP%X^B`#mUD7ub6v#M(7$U8ZT2Z3l=>l4(o0$wg zIIJWe)Tl~=C1R628SWIfpJ0$E?7E&RHnty zz5n2aw~!$dE70CzXb(OmwG7PSVkpke1n=!*@N@#-CkblP=z|E|v?B0b?nWk7kQ3o; zZ56M&T7AJoAsDgzfW3YjTT$zaeF1S0i-#;Su|eINsEuu2@P2DG#k z++GF^f2XIWC`5a@fXeO)RnT&5h^JDD@*#r?dHHz?#i?bfMX3q_2-7mk!43x#pnZ#= zLvu{Pd--+kK#c^5!)Bav^*M9n@TfRL0PD zh61Q%30gL(nxYBQ09zLg@+)X<69_A4fM#pK!46j!oS#;r06UBv7L}kX5#nL+spX)d z-_imdurlyschF(f3VHeEFw4M(6s3Zqk$@2pMWE6bNjr3veQFB$>Ufj{19CRZ7I3Q} z5j=!}X$z`kPHJK?!V|C^6sT&zU4T?@Zv<2vK>P~}Hh))NQ1HXsx*&JJBY=w`6x{y; z4ZtIHJwS^}%TtiHtYJ}wp$09$m z0(5i(7FOV6Ai!~jq#l%JAwxiEr8x>937GPgMa3c4KwJZ%iScLtQZLC1lC4w=ZzOUsAy8Nh&*8B8&-GC^n-Rw&H^ zr5PbKl!9=;B0Er8LnW*9*^Bth#r@%CX z0Et7~#rfenLe*uh%g$AjI`WK^o1BEvz9MIE0sD1#I+sNe} z7NfyJNZ~_Nxd#e=uto;XkC6}tm;{MK-T5&NEP|gvvKPf1T)L3elW0ClIZuT7ML8k6iB~RG_jz=^rA(`4L)gKe_-Bz)B+2!=yPM!&um8ka}3U z?M6}n5(kAhD1XgF6Nl!nkIT@+6~KJXkDI|XegZih2(~xC$A!TTk%9D&6(C(8c+Ubf zPzycs9Yr;~PX=2DfTR#M5m^j65LOp78IV&^R*(W}{hAqo59I-kb7GSM-wS(>q zRABIl2m>9C0=gX%w37?e%>y^d!vb8u8>qQpDuQ$JOBA4&fGcDqrYOK109K|Dty&z5 zT`kB+q*+I(g^;01kS_3$9{9d+BpcvHp{XmzrUrBuaAHZK0%ZOjv{X>Fm`H^%e}lGY zLR|*!c&kEY>LF(4=P5u{!W{h#r6Du-v zbxbYI3>gZNGgEal@=FSGO4AuKjgmpf`Gf6A%PdOGt4hU^TA?za)NEvCm77>xl3GMS znWa@yX)%5^#zs~tsbvhHw4v*43Z+dLN>6NIo$%gnGpgTfu=86=ul( zH-~C6!|!NwWScCZdMpU&LAJ-xh`|k-PTV|$T>YY4AxRNd7P$xbhr0%W*7T=V6hLn2 z1kFOEg0E2EVnERYSwN|p0yz)F)5sY%hy*%C6O=4qB^;VQ*ytj%4%HL_nqUre3vvy1 z4Y5){)(o8!28~alI1r{M80slv^n@4X=cPkNSHXV9bQWm1JToty0W^*bqEW1b-DRm- ztN^-D0~`wAl0{cR15~)^fJ+z9E_vk8hlFHWW(8;*505_Vy3xIfeCc-yXg3CA5)#Fo zFg*dTL7<5z*uC)h)PO1m@X2y$(TQdh?8bP|or~aGW$`PAT^*0lW>P!^OCNZB1XD!F zOE7g%KNUl+Tm=o*;_wtq1LPV$q=8og>S4(Sc_s}{tih~t0nLsosHWr=gOVvIc|)@T z2oF#Q_6bo4bMbUha0&BtQ3wVTE}kxEDs^!K zG?l6b#wiL=!lXh$71Y{;6KHBZVeV4U052o}%>fpJb^+uofcHV8DTkB=V3n}>Atax{ z+KGs!D6~ca-QfWax(*Bo<4*EojYv=KJuRda#w^y zrfLO4L0&e6Py*`6QK}Xo>`Kd!Qkny-~^5Wuw`%_$OCW= z$o+7RpQkf4q4=ief+k@UAeV1~+5?WkAx^%|R-jEa`9%t_43!JICo(x1v}O-HbDfl% z%m6#j3^Yj!TKo#r30b8Fnu!6;4yA(UsfuB#tuznOOoHA&3~vO1?tg<$+$5ENVOeHT zNoit^La1X<2+SCWOmJyIYLTZuR3_NRKg3GGDKSOC#Wf7PFtSnsJjaun2U-0II#Lp$ z2-KkjpF)hO2vHy<7MFmQ`+%A}#o(@nr4@+HkeisBl%JHJURn%cS}8z!W?&(Ol+5C6 z@ELjFL*VlkI4k{p=r=#HN z=kM$4%Y~^Fwv7}?HR$4oOfCjrkgpkvN|M1bADEh3ia83x`PC9E$obU^N<+pGIlpE? z`PE<=MsR+GjLUF-odXu){JIWG?}yTtp!9S7#GK5;;?!b>oXn)OloI{4l#=-3a!8Sc zMa;+wvizLE22z4UZjslAZ27Zeu*u7Ze~1n!1sWd&jg^ANZ5h#5k~g`qS|P8^L75*I-db395 zBw#;iyd9?2gn(L@I%Jxi2t77LsDYUYDxP3$g0zpP6ZiyMD+TZZQ_v`GxMu)(Jf#$} z5=N1W0ZCC&CU{LvNj`LCwVs{(ikVdF#iUPQC3vxL`HE7VaIJG3+Bnfn6NfNlnr4MRPfVy6w2AP=| zxG4eRqKI3XB1JJQ4nPf8aP+}UK-OYnXpYq=6BF#>re-+AEex=lV_|54h^z7c#`Dr~p018|+L(*nzfFLQ^p4;zQ8dHiRU^EKe7Rj2>u=4@`iD`^+jdk&}@h zs1XHJiB1Ug+Dq(DJ6#a96mrRhb9d8Ik2pw+J4*rUS2$P(Fq@TM$$ zF| z#7J~4#7tt`3q1@7bjlEDqyf_XL{3J~2+Pk)%SxMI$8~Kv^|5XZ>SHbcL3$0 z1VtLCM{0y#$UsFc7~I@~A-!QpCl@^a2&xQ9z*kp;CJ)iF9ayKafjLAcyZ}YIxdM`W zK#L%`Fcc-GfKm@cMMi333TRjg>;%w3!XPQoR2Nh_u^4ml z2FIdQh06R=cwGZ7C{iGa)}D*Ovsj@xKR2}`17uoiPI0P2DYzm;7>r1Y_SpPpXk-F$ zHYBw{T&a*+k(`>E0=gu<0%8@o=MMECs>-~QBG6t-m=5^Bhe8tQYCzB;QBatJZ_@)C zqL5#fT9gLbK?FJ{r9wdq)F1$rpWuKA0PUd$MK~xf!0N%n1r=DGZf*c^I#RSChd6jY zHq0!T+uq{Ev*XtY9O9ZMoLuw?KL@o)_S->3lfNFM0kJQUo{2PFoN{vK>-Th69x{^)Vva1yToMhXi;KLQDRCZg_VN;aJ#oz*(lm}h4nUbOaasYVP95f7v-*yF% z_3&UtL>8#MVql199H7b=TH=y1F~KEcX2^grBp#drt-uE-K+}RIXh#|-ZopEIbPwL2 z4L$@28faX|W~8T<#Dhug@J)-K2-gC1_tJD3=B;7q5R(r4C)dP4C>j7a56BcOF}T1 zFV4WgXu!b0#0gO^qRPO)Xve_7d=knxWME*w0Ks7OHVh1Y$`B0ZdoeKhsX#E8KM7^| zB$vnx1`bfS5o{U*1DD8B1_2~KC-+%Kc!-1bZ(?Kt2P{Mbm&jg54ix?gMg>r}93suY zC32ln5rzMZQ3-|rkx>KGO@yoe!)O8F`*=D9_y@UKfg6WTrI|S?wyK%11E%y8!V+^b zQxu94^U_m6xh2}bS~W9P57d-}=;G8+E!I)ZgfyceLeBX`sgUzFKn6k96@j*TXXZf; z%Yd4epQZpY4cv5sXbs5#m+s)hDM;2FP?VpPn3MxLy9P2wTAT`Qf`D(y15cL)JGsV3 zc!EyGcMkFN_lpnq3D-li9dv9^a87wJM4MY?1?b`?TLq|aP+~4rMgzPz4ScJLLSjKC z==K(PD7vJkflglo^=OJB zwWnmJrKJ`XL)LPDl*7CS(*Sl5vdNG+Zt&TR`9+XhU|{<|^tc#`bIRjEUW+eEO^+{2 zO$J>N0rv(*SZ1eIDu6btL&DJ~9CFrFkgI!qn5%P$e^7jgzjM5wqpvHn13dGPPLwMy z&#bD-NmVE+%>fp!gtH_uyzyVue}^O4mq{4Vqd3*L#Wz9^krO zAvG^WAqjGwm;z)`6X@O@(1pEVbqZ;vIXMa%pxgm!gl47|qeMJH9qd351<;Wes+r)) z8&FFN)YU5opMe5*EVLF;uu_1WB?2>vw2=rt2nXEIfIEaUGq1R$NC9#N37QlrCKO;&hGyWiMc^8PQqw^v z1{Q&`b}8td3`DktuYyF5#*hrq%ymvqemN+TVY4&E3W-Ijh{IZt9UYvUp9{J_7}}4r zRX|vPqfk*zu~r4$umX1@XsKFGDro;O)PJBu8S$4(6`)}PYfw|sr~@kk*m>|6pfyF3dxDZskZSTtK%I5Ko`ARDY%0A zaY3#jwtk^LJ|N>Va|=MnJ0<0$BA3F*v4(0;kZXXCqq8g2B;Ul6)LA5e;^ zgjP=Ab0!LM5|dLE{QUg`K!<9VWFR{Lho+Q#1^*zV5*1X65~t14&jnLofCad=^$7Cy z4`P6Ed|h4PoB&@>XCw}S?cwQS0N3H^Vu-{xL1LSN*v|ezuJI8eL5>zEJWCJ{RM~q3 z2L!ppP4fwW*y0-;6z>}hwmifm$OUYGF-QxX2ktw9GL3$5QfhofW5;`}1eonH{`rNyADxWFcX>K=vwLk33!21i2%=a3)puAGzoOLS{Peucs#I{MK(->WSRqjX z?8p29Pg8x1+)-MU)Wj5p{4|AdN6!!i1BFaTW(FPX4L->qVyZ$$ zVor%3gQG%0X-Q&9W?8BNsNMq|HwZo%0d$HOB!Cq(KvTte`FXkqpk7k3LU{)0C=dfk zdWS8t(*&)ffDSUCP@pv@;87&7=>Pvn*y2bv(<|2dgS$@-A+0Z}QX z1)w!jh71Ov9gJYZ!0UlP>j|P57#KjJ(-{~TwlXj=Zew6zxXQr5@P&baQHX(o(U5_G(Vu~VF%Pw-)pv%zwpD~Sqw(aOMY4a$e<{|)8C^rP`X%Wy#9WCvOk0&+iS%?gMHtz`kx zpfye)8nosIM2A7lvjfFDhz|`j;v^I!=fy*AW zP6|YOLdE@{bQYA(htgG08pf}O@>`&EKa_^?r$G6jbz30wq2X;0<3q#E9&4}ApmZDfhMM)ia^IHmXsFcq$;QuSSi5DOOQ%5_0a`I znYoEYm9Y%b#i_~pc`0Bv{0LINdEs3#u5B z^K()d0uqbBlb{|hjv?T63gEB{hJ>?jFr?$7$A#u3Ljyw#tCW)XvVs(_`LH{LKzvlk zgZ777fu!R>+c`0ffn1semh%ko3GfYO08x%Xj=sU5^A+7AA7QcK2$TkX4bE~8nbgGe005tGaQ&8kU!IoH5ln6S~2$Voz zsnW{A+yLSjBp(E)7G);pfYw$O6&EFgCMZoRKx3q!OT!_%ML;fxSdHdxO9KmtaT(>{ z6RaUeWf$b+r-L>S_y#M41;Dd_b0TPF4jjD@2`*TIPE0BWU5S!k1U{@Qz}G1lGI*z2 zs^Fjis>h+FieJ70n5B>eT0@kXrvOr_1D)7UNd;de1#xh0eoARhsxByng7TrKBRJva zrsnE`OOc$^#IjV~;^h1S^oTGqHNu(wLi}A66ci8#A7jhY$i)aKzk~EZ#<~@e3J{P^ zkPIklzv>+D|ei5oER`8n&AO=B7Cs0b!Er0+!~gDlotXOhJX60;nEv1noL009~){=27@S20gO{hLA6*zwN#-5Jo{CwiDm_8*Z`cOz!N?2 zLnq#(98)HFf=!}$}7!{ zhx%H<##X@ubReP*tj5huE`ab0l65OU9PrM@0B2p;-ZWkC%_X1)wr&8VLj-m(PR~Ir zR)vi6%oGLCq>*z#C}>YyCg@Tq1?PZJP|q1$0l`*lfzIU(4RQ@;@beGR_4Er4arE(V zbzung3k?RRE~pQaGeIfO)5#a+c93h~Tnk+g7j)NFfU~C~Xl);8Gz(u6@(*%_NPC3G z2L$;$$9uYf(h!&l%E3^+t21Z;NQDA8ZNc>*R`h{m6cW4&1|WNpooi)iWM&1CECz+W z1p~rW=t&ndeZp-6B|cmU6h#p@DWauNRQFgISe5A7fm#mnnRzAg;06@v{7YTCg3KaV z+5rc(73iKyP_dw20Ogxo6{V)5sxddVDnS*oFh=EDS}=IHc)CG~HpsXfs8yAlSON+x zh!mvsfvnYmuJ3_NhAVPGHA7T@*H3`2&MnSO%z+GCfNMB(qacF#3`_>!PY6|)QlWrs zE$Escu*Wk}GSfgEMMFy~uzJu4q=G6qeDl*ZAVWq9ATPv2qzg)lG(qh(185My^cxu> z>DMQq-$o%R)zB=yBtJg6pi~27gsvULc<||rn&@U5TVeYs*_;#wWz|eX7+NW)mcjyAwHQeSIL%cSq;fHU8f2h>n8ci%)D$o;tuzljFqxPG z<`!op7Nw>@-31xP)JtZ7)bH@3oeNz691LLF;VQwWNQ3Hnm)_3403gZ2Zw5bLT)i=*cTizu&NF;6a`M?iU@zH z7U+Pca1#|&Gr`fRS`03gV2(mHD6yyr;(zQWA={Y<$!y@74^1`5rQntYXyzU4NNA{m z_zDUPpiYDp(yd^LDJifq@T5}EGK$nf@M+=-iQtnU91#P3sTG;UC7_h&2;G7S^Etfk zg_sSF%*@Yy~;`f^EnF?G=Tk0BEfQF%Gi>bp8|q|K|Kg?#|vakT5&-!vIZ+dOUPXeMfv$9AZ-fDpmu6- zKya{ra6r5#Z0!lSxd0y91vf82Mu9Fw04oMDJi=k?Wx(eR2cvSqEAm}jR8#ao-F%RG zxJHz62{h*c5>8}9Vkf{KvE5Mlq za)&F#zgSeFxHL2mzC=R-W|V3QWCt-Q{Xnlrh8TvVAhQ@WY!MLbso;~Dm#w4V9^v5x zEchUovlDO8Y%ch1m%IQy!VL+vIU=bP{D;Psohj-13A30&-#kZB&PY=U%7jvqR zBelV;GPn{?e+7_t!3vaBQxyEY@kl|gKLK?CN{dp9aVi8|F9mOV;8YcwR|?wIk_w3g z1%&{R8$kPn6hI*f*_C8cp%4vi%g2J;scZ{A)g0<=1%&`}&>>`?jb#c73hogg4>*N- zy2QIylt30VRX}d_a*qHVI-pNmKG)E<-?OTD3OGv=7G*m0gZD&Qmg_ftU-AZQr00SNED5J z`3j!?-kvVd7AT~!MK%U1n_rq&0?HKNt`^*HuqA$q3cjFqu_YOac?yQ0{0A~oQBe_e zv_0r(dVd9PPZxv-z?Oo96d-MR&@DHac{rWmmk%1s0xvZLt$&4^&&2>b79Dy+0H|ZE z;G9^L0xmxbauV}E2YkTJDFOAW^FU{(FeE1Hg8SgQpz0x~k|8m(NH-U>`-1^A5uabA z3%bOXA*r-jH!&r#pd=MZASJOhJp)A~wW1&qY%Ek4>|7MxqD=781~@;pq9iphCAEkl zIWZ?av8YlvsVFlgJ(VFdFD)}KGbu4IMK?J=FAuU%H5s%=1!5w|F-S70B^jwjd8s8x zLNEghGLjgIa}$wdK%GtSFtu)SVnJeZW(jCXX;BJ8QD#1pD#*|xl0a#35)v;Zu{cFH z3FZ%ml%m9PSdc*3V6TCL7AgQ9b+y(I%C}lxRD9$a=Ed!;LWYB62286RA z{LFk^xDZ2jY9;t&AF%UbgIAy-@6w!9h8$zaU>1xIpG43Fk3%Cl2pph@lmZzU*M-!3 zV58Bsf+m*>7$8B6h{oK+0$oJBf|pb<N(LCyf(Jd%@I#E@5-n+Q>wT$&FJ(EI{j$X(p|#mSjDIf(zcm+o|BrZUAFX=*SU#LiNvMy*j zI+T|WPPgzpR+N~W4Jvp+8y)kD7>Y8BlgmNt){txf&0Hjwl;nZK73Aj90^Q=uV$isD zadL4cvdY9_WFANonvTj+i@>K{W+dr?PopVLEdq@Z>%u(>I-ChC0?O$O#rbI^y2X%# zh@f!`vJRSKpq7__0vuFCFqD8cIOUaqvQnxpD4<{h;DBKO6&AUmD>PFj_$gpA6~vL7RA>u4I^}pC@ee7ZyX#o_-1-Q^AdT z#P&!~dmA*y!NuSf6bhO@3XTj0Q6atzVZo8XD3+TUTQKD2r=;fSf}$Sc4qp%-vL^+4 zDlRy2pa#F0sUbsIYF22Vo7SQE@)8`Z1@WjM`q?m z5O*NbD>wy#n#j{Ge znz$iE+{hJ8+$h)xq~6F4P23PH?(Aa1VC3v#3L?xvggMA;O9m&<#G03rzl)ASkfWyy zcxfHt>@yD+22*nvbB5r8oXiphBxT?>kCBss6N4XQjgzOoKcpdKYUBoYnPXmZMt%`k zTtQdC)5#Zli?@Z534^JTn-R>VIMo?~)tM4hXJo`+YG&w2Se=OvgQ<~;3t@#uJ`AR2 z2Jo=N?Lx3ZLuc$Jx&&KTm>Vz{8@d`W7@D~|DLA`$`uc+S79hfq!Pp2{&=MqQ#9(HE zEa=E!tAxiPpU<|&wj zDrh(w>L@rG=_oiF>nJ#yXfhZ%8CilQjW8s26dX-;6dcW9c%TDfcxyw z$v-YI52bSrmWH(TK?5s_Sd@UwiwCd&1x*{kH}qmrnO0O9pP7PH6?kPisBa7EYeRdj zAiJ#;f*m~}W?F&A8(_wQguw+j=Es>e2DGZ=iN^(Z3ZgFZ!F$1Vg2OW(Y<6)@5?B+MQi;BPk#c&q5Z3t>#!)Cvb26;h~k=wJmPCM+_*GfNQduqZ(if~f)p1R}~Zt5V?{&^#JMJ4`J?1Z)|o zv}7pBNy(>y}^(Ln9xkyb)G;Be=W?c6k$!ehV{Q z6GKO==9@5B7+IL<8W~}gHZp=po8XW(VeoJY3W2RB%gxNo)O85~wdM>eR13g!9N@fb zU;!E!1*qiVKG`NPF|i#{U;wRK1c`x`$+7c&yS|U_y;ebA zhQ@-sn~v6gFLJ-dU62o1QwdTribq3WGz3ONU^E0qLtr!nMnhmU1V%%E&LNOykeLcP zo*rZ^=-^*4&Hw)c0|+xfP9Fk^jpES|7!85Z5Eu=C(GVC7fzc2c4S~@R7!85Z5Eu=C z(GVC7fuS1$pyOcRuIJjY0nFyw0J^W9fq`oS=qzHe5SZXffS#KIrNM$o1V`rz5YGT~ zdl86%@0NCuJh7OgvjC*j@BoO!z(@!9V#uKg;Ly*&z|px2Ss~2%P%-l7>o_{6fy{uL z2WNmpkq;&Y^NA-oI>G0dz{YDBP{W0&@BmF(f-JnZ_5<&(wFaQOl^7Vfk~lzONHp{u zlOz}ojsGMtE!WZjR?fhc1UdKwK?i^(xRPLW0+bJAkLx(ZVO+-^K-ELiG1qaZdya$V zX~9w>moN}uWN>y3P5fT(eVhbR#1z~L1cqwFn2^vU{E5D$eQED^RqaiQ~hHeO;bP-q>V0(mzu7^fl zJ{kg}AwYHrfEGKzHM4;3eTVZ#8KWUE8UiCM1i*`;V18y{Ab-sv%#2ZbGz3ONVCaSb z@&p451LU5`q3fGbmyd?PXb4ae0+1E<5EED!*ddHjax?@+Ltvza0KAF7GI~zSNKFHy z{vHhhPzZq5C4n#l!vX7J2+Rhn1DUWvfRQ285wZ>n z#7DwhkZaoEB3zeHcO1ebxGq8W+0BA%yy61UAA}eg0)iXhJHix&85x3oU}aZvNqzxj z^B&9)MjZwQ?j0~5l;($(a3J;YeUD&C;SL6d!w~ym`v@5r_!$HsD>6Xpjlk+)gt`C& zV;f{283TM?7Dc@YOeu&4spWTqwZ34}IQ$F>1>iXxkol0!Zy?1C3=DED4UC4mP!0oZ z8W=^rA+iT%Olx5M`Vgj`8_IyI&r5`CX@rV1Ffi~hKyp7qm=WUNw8Y|);+)jff_RwJ z90$RNi$NS%Ohba3Ljdgl^31&KoK%oB6wjE}U_I*;l!HXEK>SOpdl(oL1;FtQwp~#O z%my2)D2QN#1P%x?GWa_~(%%6gFdHPya6lN$hQ$C#jB5^b{~w4xAOMyJn-7u%?H9a? zJ$*u@8Mq!nSX>XG`$-=`0-5U(WZx;*BS;uQR537cJ%XfbFke}iiNVtuqCi;$i7kZ0 z7DQqTFoM)8f;B@3uE!92Ib$Wk0$eX3`(8O?HKBYk#lZCf;t#GDQ2)Mwq+8BdGq3`# z7m!fljP-`{Am^tj17~bDn8Eb|;xDcjknG6y0um0Kv5>8l zTrVK{IAfb2>Yu~h*#_l<+y_Z`V1WT4D7Al}^+Wd3k{@&f?S4w_N0|yEBN!;PUxW-h zk+p0==8UrG9s-oc|EPY-qHHw$M#GPi5E$t6!@$6`9O8a3tt7z6;1 zPJf293qf*l+#tll5FA>i0Giou5JX}NAlOjFTwkExgYqF1BLjngAR~iwXoC`1fQf-Y zKor3j5J6%KBeBJh*g{Bb0R$Ut9s>i{SL|tz>noPo?TtN+FMh*rBCJqL07gJDx zfkB9afkBvqfkB3YfdQ00Kt5(*PyqFH!0H(o6hM6-*8+$?7#O&|VKHA4)E{>R1q4LD zB&e_M+5nCbNfAZ{AFvz)gCwX=4;6>`<2$6^0_DOfu9Y{yYy|xR%74MYAS%Gf;Oh!W zAEJT?HYgo@hn$-ORtzI9fcja`aRrzdjcLUR@KFOKn?QYV7={RQt%Br31Pw`#T&rL- z#6MiCp!830s6sTuNsyTk4%cc(xGC38;iRn zM8NvN=1Yiy*DwDpK|>L=Q{=l5dlU9$B>2qh%^J&bqIs&h5>9~ z1#B$mi+V;z21W)`##Ic^rMQA%2`It&z8|`SXB8wbf(DeJav+NHg(q0Q5#uUY=LM2r zK#~j$44f~XgXJw5R)GguKtTtU0#lqX+QIUs3~>8}z!Fe`^ZjI){jh~VFn54eaDH3_ zrWqJk!4?MaKn1`Q=ZoE7^UWAm!6phJ2Yi8LLGIfOk!OU<^FgJ+6z7W|u)Gli+<%;4 z2`It&+@6t9fRVwHaTOOcBm`gsU0@ZQ&)p&N46C@n0t~1VmYmP)!SYs&t9V!;`eFV6 zE9ZRP4v}YA1@l+juc-gg|Kol`Fjy4>1E)MBL2`*gyvZdBv5rd=;$1FLNVISXUjggj z5{9M+QAnSUV=;^mJ>N=19;^-~j!tul%7Ep$L?P<9M3td@9Vp!nr8h$9ZxC8c6-viK z>8ViqAe8ry%cDv_jbK!RjNfukhX^pLmw*{?z6K<`5PV3!M(`o= z1?Ou*>PrNF395OTka`X-uhoMpuZ3owHk$p~knn`-*UdrIuX_ZQuLnt2aP@kSav8zj zgQ{L1Qn$e6^&#mN&NqlbRc`<(?-25k@)6EAgp3)%`9_d22sqyu95)Pbz9}Sq!TDw# zsP>tm`Ogf^eddsK57%$*f~w#C2`b+eEk4{J^&DKk+Zt5$ZfN$ogVGlR!u{@O@#79k zpGfi^ko*fb-wQ20d7-(-8!i02=b*aB=Lag^7cKqyp~aUUT6*_~v|HfrfkX$wKYbGXz4QxE&j71Q#Nq-W~14kjh6p&ApIA(`W&?Uk%yLF z^HNa#mj`KQ!S(0eL6y%(%P;v;(B#p|hkP{q3((@b0Ij?#gtRB&_7|f0w`c~ceMM;I zm!Rd3614Csh18F5^Gng8S=S{AZiqM z`EfB?_$@(;?;En4`lL({(=t-fE67Tz1s()$K9{Tm?T zCGhmH5iS31L`x4F(bCfFWhr{#}n2zZ=o~`vNU~ zUqbr3aR0qRi|FE_(c)vy~kKdrFe~aedcWCM5Jz9P65iP#Ipqcj-&3|9f+7I8* z!tWbedHW5m{Qr(t9(_k^zyCn1&wiqn4?ofJ^DngY@Ea{X{zg;(2d(`0it9@PBH#Df~X zO#G2^vxuKnqQej(EKZcW}YaT{bFe0Cx+VoVUk4ij}&V8&m@IrzBHP=3|e}S zMJ>OWWKq*IlPqd}W0FO4k34Gm!2~f5-acSbK(kK~Exwgd^B zrB_un_o<6sP!+C23mY-qM4_On*W%zP|FV{E!6UiNgK6% zX3{|mA04#(rh}$m7cKqiq2+Hq)cz)u9%}i>q>q-L^wHGoqvb~f)cS?V0JS`0GC=dc z0a|`DM6=HjwY|V(h!%fFXz9-wwLD}pMvFgF)b=8iDO!FtMf1NITKY9ZOMm8Q^5$sq zX^s{j7O3N6OcrSQ)dIEtXR<)kZ;4u8FOD~Vw@e;r`PBoh{PRHbp9flg^hC=qo@nm%MD33; zd7;Ih7h3xALyIpz)b==&A6okNM+?6IwE8a)&HP~0@dKt1NC62CzYsM0!_d@+qowx< zwDLU~&3`ed?K7rWwEPx}R-VP8#aA3!dPN&gWQs?tj}y@Hdm@^964Bx(5iLHG(8~8@ z)b==23Yz~@(e$UG z0?j{_sN>a4m1ymkDzx&v3N5^=(ZZ`5t$eFNOE0x(`s>i@(>k>9L>n(-szb{U^=Rq2 z9<@Kh)PUyS2DJRsidO!#p_$i)7QXFh3w-+tF^`fPhKD7F!53T;{M{EC0K%hCL|0*${C&HR;U@x2NyzpX}7zZ$JPU5i#fu0tz7*P+R;M@t_Y(8}|TXz6Ja z>i7xMX0-U+f|g#kq49U1m4`df{Idg1{Z6#--iemK_oBIXFIxKCi{}5mX#U@amj3sn zm464&+`~NOl{5?P`uO6Y* z_m9!?`(rfopP-dbPtepqK}*k1(CQns@hzs8Xz~9Vt-g4JmY(0D+4mN$z5O1oef|M0 zy?#UspO0wy{S#XFe?m(yU(w?8D_Z&d6RrLC6Rm#xg;t;aMzilXT6^UWnt%VG$^S*m z&wtVU`wy+W`-hgl{-d@xm>E#}hs=zq^&vA8YJOv8Ms5Evv!K>@%q*zxXJ$bSe`Xfc z{LIXXTK+M!qqb+5xlsF?%v`AL0cLJA`?*o$mzf7OeKPZ)$@8N5j~BH)$jpzXUjQ}# zGYg}s7eOuWnMG046SF9qe??KtBW5ww^ua8KS{^ZrqozM*aWwm(>zZKY8M6dx`el|y zt*@Eo(c()9&ArNK?omO_Z_KJ__G_Tl&&;~0>7UscHGeakqWQ-Z%{&{l^k9SLemk`E zil#petvpCaEq|CZP|IuPEY$jm zIUBY7XU;(#Uu4clZC^3xqlJGFYWd4tftLPiQ0p(|8Z`ITqP9<%>(SC{1Dbyu(d1iD z%X?Qffipk(cqi!5)c9jzfg~tceaga$+J9oJg`oV6h^RQIwdpt(l@HT|+EqNYCkk%4aRx7MSkTrxv*@Ab2NpxL^kj^h z|5!}W)SIH#$1LV(>CFOlyq3ih&3qfw`kTcTwLW37L(}hz=Kny{{xwS=YWs^N0yTZI zM4+XINYwg(B??VG8nr%WiA62HSQ60OmxwxE%#w&^eiCYXhb0-cJG8Xz8I5EqkpO|)bg686)pd@ zqq(mGEx*i0i=R2D{S}rusQoXNxoG9VT-5P?mU*c4Ez5kg^fDhUJQtw3X8~IIv=A-4 z7NMp0C20O#idJ4ML+#J7EJLd=mZQ061zLJsfu?>Xn*FQL%wL73el_a&2+JC@@@EZd z{mQZyE&SJ^#rHZi``4qTugz%r9c{dkWh+|wx)m*bY)5m?4z&7hCz|{&wDJ;dJsHbx z)cy*~9<=nj2ep60vKK8q>_bbR`_b~l5lDdyudh#{rO%US`cI*S|0%Tc=rmgSa|W&a zy^L1gTt=&Z(b}IZSJ2YKH8lILp~+uI3(uQq_3JIP`r#H@{e2s?{mya+t-W&>t-M1U zKV*4`=D#Os?t6+>em+Huucv6`#dEa${{pT2e1+!USE%hfme*+c`88U2zd;Mnw`leC zTh#F$mbYl(_ZF>v^cl6i&hiV?N6nwC45zQ0q%pZPfk( zs}5@WlvNkaeR`62_CHvS(9*LBYWdGB$?lJZAMqZI7|~ zpruzIwDjzUmcIi~%RkltwDKkZEx!e!#aAe5ea;$+rav4l{v*)Re7wDDHfWYqRCYbsiJrJ|+3G}QWtH669SVa-HspRs15 zrYF`cH2-Iz<;QHa^qGwoetBr+K_Oarq3wrbMce4IUnL6So@T9 z0a|)qfEJ$%(9+*R)cnr62rWG_n@-cA=H;r_ti`G-~Z=%&7x6s1t4r+gd^)6a|xrdhi z@1v#PhiL7UhiLABo*xR&pD)qU^DDIa;x%f2g7pnrc)de&{|B`46nfqi+`i9f>HRBO z{re5I|H}FuExdoCx#u^Ud;Xw>??1Hk@gFrkvoWCNFE%FB^uflAnt$1tQQgnRg2rb> z%|C2xsOg!F9o4^V9H{*_HcnLkv7zl3VMALVz{Z2-ULMr=XX8bUPc}X@_wb{Z=WGI~ z;m0O~nm*WsQS$?v2%7yOX!7Ey^#Pj%YW>0{iCVv~NulN!HYwEf#3qfJ-`LRhld#F4 z<`*^@H22G(mPc%|X!gmXxnB;oJYhT1-0Ge@oO*ep=XBQ{Ia_5+&@ntNVc*nZT&u*Cu)Cy%?q`?z~+T!9@=^dHXqdX2b&LS zeZ}UF+TLIbMr}W^g`nlBAwtj&v4b8p`H2cubuVBkTOK*9o z^)Xu>TK+FWE1!zd!n+tPeV3xvziee_=?85+I$H&5ea41%ego@VwDO}8Ej+5w(rXo( z{Z**_6}D=$^pCcFf~^KEztp1EKWu2{J+RfGwujgn(89k7Exk3Pg?BS*|B9^@H9fG- zMT_4yH2d1n@>e@rcz2+cXPv0#vvs0{M>m@Ly3xYB2d%#7Lo=@r%|8=R>vOh=Xz?)# zt$dz>R(?-G%MVl0!gnf~`(~iFciCp3_7~Y^qWNzoYJZCj?feC{S!m%m8%_Ug)cz;i z95nUw(9+|4)bzY@_#4l_z~MKH2Ga<;lCTL{@#O@KlY-fhrMX&dmlOW)(em2?H1iIi<>!NF<;Ov^`tcB2d3Fdb{U1UL@55;IBij5G8`^qyw&Q5+ zqvL4tbsWwAC(zoTC(!cCNi_GOtsh~7-d_RhpRk=mGY@S&8QUqe^6C^?`ag|2zruC~ zt$le0ExgX6)nDh(^6MqE_RnRs`uGN#dvBw)KkuNmU(x!PYVAALm2&!5op^Cz_Q`WdbLgf`#C_8Bezen!i`U(w2|Z)pDgj+Wkjpqcj@ zE&cvRtFQi`rLVte=KV#NNAv$b)c9gYTc5_xfLb21v!do#b~e=TVrNGUPj+_H`kI{s zHUF@qoyWk=fm)uibE4Ll>|Chj13Ncr`e)}y&429tsPzLoKWchq7eGxf>;h=&1yS=0 zyAW!6V;4q^FLp81@{e5-HT|+nquDQm<{xF$@`zmp&3skV@|Il{Eqpc5+^30Jp0jJB z<{x$~)c!fUHkx{EH2>(JnXiZDUVYU1mE8cfeZX#jmYxjI(vKl(eq%R6Q*VUY{$)2t z%}?wWX!cp6<{x$|wD`3`bH6oe{mgEST3)eRqqbkzZP4Pw2DN|AZiCt%VYfjGe;d^H zFuN^U{;@^NZ+58dDRz6*_5iyBYI)D@h+3bpJEFPA8O?qd)cS+n1D{sQl z;uCE=gFON*ydu%kMXL3hH zLvw!`YI~nO9WDK2pq1}gXzt5K3s1E1CiYx3|K+0gN7?hy(qjQy{ab)0Ux-#-6r#x& zp_P9{X!)%et$Zs(OONGfxx1-fRooMAjFIs%}qV{Lm`_S@lKU(?Ok5>LnKr62%qS-eIE&WbH zGjB3l{XGROy-Y)E|4l~=&*^CKJsU0k&P9ulxoGjb7%l&-M$^9f5zw@v{ysy>CWKPg~H!Ydc!`xC5_#g;ccbNpJ!t7+4_bKcMT@U} zX#Uxc)_&QKIv&P;04@CRbWe*(3C$9@tm zJWivfN3{8F_S0zQokkr$V?T}N|I=vY?P;{|Mcbdoeg>`md3yU!I_q-%rrWlP9R-SM1Nw?0=3{UOq=l-*3^<>sz$+ z^cJoE@(!&$e}`87yhn@g_h|Lad$juSJzD&HKr634prtS9y=1WQH}=nH<;fSc`1pb* z{}nBLd_^nIzN3yWvHw7G&kwZn<|mqeq4y!d-S-Ezy~-hs8h;$ZsP!+0EUJ4s8IX8eSas zsOf{l9kssX2t{cnqN4Q z(fpH%T7Gb3p~gQ)4x0aRQO$$!=tsiRA*7UHU{HjfN6r8hfZu<$0TQl?OCjL_b0OD8 zQ2PvYh%My0C$0^k`T}&fGf0eqfomhE{Rg@#2PO|v54vL+B*wtNwGEVC+!!GD^)N7S zZ3W4@!i;C&+6L0E#Q?jnoNF7XyaU}81T}vLsQfQufL&(AwF6ZDha>dw0C@yt2GqWt zASuvYNl^X{ka-|6C?9;@66ne&sQEiVdO>w8)crd_>V*;Z?FP9w42ci&e<;Ge2SMsV zop7lBgCO_WGB7Yeu6^P<2+FUZJ{6>%=Q;>-FGvqeJ;;B?2=l?$CV|o%OdgcKE0N?u z?g7>5Q1>4MwO`AT+ynBD9U{EJ^JS(;`a$jo-O>&<{{X1{2D;Q8avc}f0g!t^ZFuOt zQwKo(DNvmc_0IuNe5xb-cL0=ML7NO<=7HP`x)Tb<2iaGLq#opcdxU%UgWL-$v!LO# z9~3sAyQiT110er_QYp+lkb2OK<1ju*Jt$0J>OtWTy2A?U{{0}n9FqMYwXzHh3^4zK z!XGq-3G*K)t$;R_K+W3^8h-=10V=;A6kdsl@Z1jyFDWEGD7?fG=I;lE7w8H!n0cV^ z0$s@ldgYu7p>=#4We*&Z*RL4Nm#|e;n zh}%Iv<2nHfKak&{`QZe}KcG4W8lK?&>!7fM@=t>FLkmUFWp8Idd{ChVl|KtI734;! zd(MEuD<9$iGa&Qx5Pa}@Sto>h&w=945y8Iz;`@UP1!JxYpzt(8k_Uw+=*l~&{Z~Nd zgX$0%9~2(R@bty`4B~cfCXl-s7`Pch`av{EABYC2XJFuF0{H<%gTfDNH44G?8RRYo z2CmPb@B`5h^I(d&eu2^z0|VCwh`C%JK;Zx~ALM=z4dKJp|Am;x`QkNLh?@zbkDCdU zK0xZBd`77Im_g};fq|PDD$k7SPF(KeW`gJ=+kGEEX$fR6)IH45@MDI#3*tYpCkBAv z{Ll%um74{WhZq>RS)lHNotq9l-wLb<3&G6-2~R9iC_>!ObKbemLgJn4EF>LpGeY7K zMKS372u6sxoUrrHSRmL3JG{+(6|dh{hj&^miYq?ErEYG`tDK zFS`3+;Yf%kJAOZc+9n|PLDI#bi{CGSV6SttLh>m$D>UCi&rJbK5O6b7FK`k7pAOiz~kst#Ds13`&zy)oWGcbVaXg5KaIf!;TsNQ8q z5{L9pAnubAfY1ym7RMJS6&EuUr6%R)m&9l0#TOLirx&Fb7c=A+B<92?6(!~+XT+Bz zCgr3u#HWIkCKr^(7pErY=cObTRmK;WBo>u0fW&eWE8+_>ixBQ+$p8NjvfzWu6*3M7 zYiDsQL;6Xub}_dStlWh7lYt=!Y7D4u2QgvlML`@S3~HM&FmS6t(hnqD7#J8QLi&je z44}3>NI6VDsBHw|gK_@<|Gz;DP+)@S{Qv)df@lT?0qDRoghvAs>JI36=ZGuVA>v#q zko*Z5-!0IC6QKTI6bKW7Ml zjMKo(VF-YUL-H$39G;kwa5rPKN0F414dBO9jqQwKEcH$A?9)vpqRtJvHT$@bQm}aApKpadInCXW~ewc zoS^RKSpEzu4(k_#-NV4K{1sFj#a;%E4sNu=cISDF`8lD`>KSRYqeL4^mVm_C- zC5XeoQGgn59Lpi~Ge-d|y+hP`k6FCYX<5~#ulThURS&TrVa{!+IAq)xF1|1oDh^H8aC7EC#UbO2aP`X}_datJKL?QhljsjSH0rRgP)Evk-CrmxZa$kse zA((>aM~>x?a*Cr6R)oOJfvlt8D1_8w2y;MV2Mi1xh0p{K4+qeg0Z1I0u;JpMz6(ek z)aM4-4KqI*#9`nlgrsYP`NdFi)cno?-Dk>Ch?f4BK@OPUC`3*F9Lqst4j_Bc(?4je z2PBT3{y}|ykT`n!2aRQb#L?3Ka)>)P3enR4vhz^)qo#k3Wzck0h?f4BK?bxr3L)tN z9uCW(`3QP{C_;Q2)O@t`zica194-A%hq)6i{lmr4(mz}rE&apA(b7L$94-CB#nI9~ zTpTU^!^P3kKU^F&{d2&@(b7L$94-CB#No9&G#$dl(bE62eUR`hLQDT}^=RoIE{>M| z;o@lNA1;oT{^83 zakTUg7e`C~aB;Ns4;M#E|8Q}%^bZ$DOaE|jwDb=bM^FEe(C|l3|7lQhwDi9e+Ab|d zOaDv1L)D|D|7DQ=6h|>y`d}30nGJ3N3$1(9=J(Jz0XD z{$b+i=^rMJp8jFt=;Qw4!KT1!kyy^ntPss=1v(HIIf_%=b1jl{3~egc?O#M0;xyKkI&4Y z>e2G!Gb^Y#T7G;6jrS{P`SF=ER6Ux1pSeTDQS&30V;fW)H5@oTL&p=q^Kl?0&~X0@ zEw8RX@&~*f{`oRU5d+5+wEXxPVlKxONVQVC}!hA^l!|dhw3{AIJ(emTxr%-bs@eEVXbs3U>IIg1RFRsgwe8O=RB9BlH zNjDrDN&G#VLOusvgx}obvCX;;7{Yr#y80;To!cITb*2-V6*J*HF_x*L4V=;~HxE z=eiEbR~*++(?8dB2%qB`Bpt!S;TFssNH`(HVd_!SC)X`Vy63otnm)N8!x9V}*U-}E zZAd!fxDNI5`(!z;qozZyTM+kgTt}@J zxNbw@j{|z&0o?rCFnb~LaPb>3b0G3?@!QbwxsDo-T(@EFM2$zT+t7Hqj+Sn3L(}1P z2#qiwqMrl0P8A^zDW^EDqowDYknrWWj+UNpLc);)nl9kx+=S$3j_au9E!Ry*cyU0} z7eYNGTsW?yrMH`qaN&TaFNAuS`%%kVF6gWKK&XfKhvPbGdCPSZ7H*LA0#|LL<~e!|euYe&@OcQO9uu5+0c9 z(bCB+sDE#u`Rg7u{oFwF*F8x3;JAU7PanYSMa!r6py3Zqzi{{5gSe0523kJ72MteX zI)bae19i_$wD7zGP5;pJ1y_F$;yw;&`htr;fVv-gZwNvh8vf992N%B&b>~gga+vEb zOdKuzA3*&JO^DyC7XJ63`T8bAA6)%?Nc!NoiIz_x#W@29H2osfL({`e)OH%z zJ(xHop5f~6LgVWuT0XrG6NjXCxcWPg^ucixE#E<^Uj~kwX!#4eE}R3J58&oN&(G$# ziI%_a!Tbxc2d@4OG#}lB#3w==7H$w4E`A@Pj^id;x`M6?=YVt%5as_}h<=V+XzA)M z)SO$8@PnIw7veq+=sJ6ZIMkic@&F+YQ;(KT?!weV(h)*EG(F!!O%I$Qkn)k^7HWFn z41vT4$1MmAH|IGto!^3(hY*LP0}kju0E9RszBz6|+=UQ_riWW-@%0>krXFGsT>Vq1ziy+38`m>vxp5mc+_;`X z!v|VV!p(UG(a&)ktsHv>4WHYP^ny?iwf7EM`hlsx14-AI>e1Q{&!Fk#4w`@GLBs71 zgoc|l50Wl9?x3Zsxe)hpK+mm*tDg%qAFcd>o`=P82jXvpdPq9pxPumM(DS1>?m)s1 zp&nB1aNL2=aPfH%|8v}dgcCv>=6BrB(0I9n7GG~5_Ho>S zga=&xTbMXnI(!RF&(QJ=p&shayJ+$I3TiL3oP(=>1x;^v(cTqJxNzKslz(vX*UHjWTIra+XFNi!`{TrA#S~`3Mv5x~H^IeUL(>DaenW^u z{K)~WpAq6v|K3A&Kj$1s{^Yoa>K@KHptZgX3>?sQ1k4=HIna5Q`>5%ba}FfjIqpN! z3qt)&aKv-mM@?^>b5=veQPUOY9B4oEK59DQoC6&IO^2K-L2H>o=AgM}C3IZ@bUzrv9MIZv zka|e`AjBaH4LBa4xql^S?L0_5B%TrKq2o~xQ0ryRmC$*#2at3GQ_p1yoyU2A+K%E} z*$obV&YNiV-iG*>^Cqe}oVOt54kudsit{FZ9jLBgFA+Mj@nf7lB(2hII(aWwaTfE=L3iPqlW`~c~=bKZjFON9B5 zaURZFsO3552S~c&L~B=Yet@heG=cHzjx5w4-02#yBlu)N6?-O1_sVMXzu?24S%%y5gz_%^%p$7q17*(A3=Ls7#KM3 zqUEE9kn)T3E?T~L0C5K=v^@@YCp5ot-i4%hgg7K#Iq!j!BO;uk{Z`IY?X(!_9}~YiPd~E`A?UuXCc8+xH>y!FeA?I=PRQ&SB}~J|uqN z=EKs-14w)##G(1|0a|+g2$@&qe1KN(e2fD}4Ce#1@*J)ntvrFNM=v*^<-S4J0N6_$j2$4sKL&NhSTE2S(O+OFO!t)Wt9h?u*!t)`--JH;K z?%?Lb%C|>o@ea$^kI>u?D_0+(xf50nKSFcQM@aZ`K0*u6N04?7=Oc)_;O==0jur;a z$7u2U5n6veMr&_;gtRv}AEU?nGO$6MkJ00OGgKVnF1Wq0^85=Vyy4J?A&ndYlWokeBltBt0V3 zL&NPGq&`82L)uH6-%!JuixH9^IKQEW8y6#FVH)Q*)bQbAgsj8l{D$gZF2<>l@cafz zUkH1bL&Z_cJuXIweon};33z$V#dsL3o{JqK4>t#T&O8@8YPfL;FNLZ{Ew8wQA@fjN z>}d81L*j*t9a3*2%s&k=hXXbJa|uJ*EnFO^`IJi-l3}2U>iIK-PzFaiF%JxkMoI-CP`~`GQLXGJnm*ffkPt}5lBAb;y_L3Tq2Nl)La~B;SW8>pNj)6{6(PQ&w(2LoZOK023#Cy;V%M>7Y?-W z7lE`hxj50nUj$+w7bjZyi$LRr6D|BjAnVDwIMKpii)gTKNxFFNph;*w4=|^x$qq$!VavlJeG+MrfnJvA2E@`xMXbREKB@HPj;Ogz5=}H%F<8(bBCcWUo1wG-`RyWeW>8wDfEXS#QZDjar^_*+SM&a!I45b6ZIN zh)Wu+9J7U-d&MP#w+^QOkKQ=sgBp(rEd@7BbPnC5>9nbJ;=$dbp$^=@%Yu zaQCB?leW%o?-5X?(;yH162>b zuNxr_^{)(CdIoKY2kl>$K}*kepuNxx3|um3>Ddml?vzUgEj`;o)}3<6prvO!$od&B z8Ay7ByT=Z)e~}A%?;t`PvM+#31}(qaK@JGyl0j{saM?lguMArHw}b3k;gUg5|B!YL z7xX?6guRgQ7A_gI^lt}Qr@Bz(DK z(9*v>w7!r*OaJzskn|&imj3M_?F23vwDfPE1yzrh{_R0~(LwQxmj3Olpz6`mKU_Up z`nRu#sz*!z_K@}lmke6^x9^9lN2_1p>e14_J!Ibsmke6^w}-T2xggzRM0suxEl*_8 z%5%7SwDfNeEoWrW(!V{VeaIyXi640U+C$qpvS{hw9ui($(0k|+>LDFpE?KnnZx3yU zK=08+sE6iXS+w*IZ7y=jqNRW6{x>dJwDj))2^cO}wDj*h7ZU!mXyv~nG#|;LrGL0M zTKb2Jqm}<~akTUg7e`C~aB;Ns4;M#E|8Q}%^bZ$DOaE|jwDj)`S)b1(if+`gew<2ekC>{0kaiXzAYtdaeWL2oJCd z$htBv7tom-3=CY*^O4~0cLALp0uo0{|1OYqaa?j}>E8vi{*6lxE&aPd`fFTrXzAYt za-Ia299sGB0!cSqa%kz_r4j6EF6g|; z@-PXlT!QkslFW{>f%pTV9+GajQqa;Nl+Tp{ z@gH10TpW__5aJL%R|>>DOmRrMLx@B8Tq%(7z!XO-A5tKEt`tamM5u>}qovOj2%jqj z;%|g{m^fOzr$G2zDQNKy7l*_r!W;;nD+Mjyq31MnrJ%(Z)EQi}(834OY-He?g%%E% zAnAr{7R0@9doMxbcNWw@SU!dFxn`l|JDB(!h1vA(A*CfM@xrSq3)T3mVO>V z^UEBx`sg7<9T%i|0WT-Hp!b4s%|%OZkD&Q+E?Rnf1PK?exoF|`2pSG^A^8UGug5TZ zQOgI;SjhfdF6cSHaP`o8Gr6GaFJR)Fv5RfZt;^hS--E+-_*n?2-4UPb=xoG9d3s|_J#v^Ae z5PjbGTkW(i7KQwDROREIgqeho!fdU~3t;pzB;<=5WSB_Fr?&MN1DaAmPXb z**1wt4=@#Y zdJYK}F6g=*m^f!FWZgd3JV?0$6X$vk33o2YFet+PP(IgkH21^B(bDa52%l>?ntR~l zX!b(S@#I>LmajiT)75fFIKkcd5t^=+qt$~Sq4B#M;t#lb=sm7nE708k8S2gzkaPrB z59M>MKyxQt9Fk7q>OVunc?Be%;o{J7f36j1>EtUU|8uQ`&~Wu%A?9+eMDs6n+?;DA zn!mn7%afI8d`~??>*pE;T;d8Bm_ybcM&0jyE@xB_(Ur;{RYP5U@ z7l-JBo4*>u=UR=H&f(%{>1Q>B&jme)9bpbk91?zT@n6vRT@9fT;?QztHEQ|K1?6+C zMoWiqakTPzHH6Ovy*C_gK3p6vzJ5c@W8hkY zmfo(z%z@Bw^P%hGxz<3;gNbv#fQ}16&&h|2zlV6H9h&=}gU;?`VBmtD`wut&Ib^>W*E%%!KZl0TIyCn`hx%(BYJ73ZLlO|z zI<)u_h3p69T8EZCMIq-$ajir3FPA8EzF-|%{E9;S$+ZqGeuW|D=5wt>D^G+W>bTaS zh8veCV~ap3i6{be!8IXPU=dpHs5A@jLh>(R|Ot-Dt@UW-l>{W7xYncQQ!WXJ zKe^VUrhhJpwNUfX(!T_BUSmC4`j>>xQ>;fz|B{e(EL&jq zj2e(|=h}c8j|las@yMtF&DR@H;}M}AVjj$$jGB;i&$R(H9uewM7C4 z5b9Cmkx>&;9&v3zjYouf)Ocjng3dE;fat?CA5z}H#2K|<{)NOdOdMf8YB|QJ4GVwN zaty8>l8xcz7^5~MUb!}+mSYI@sOgPS7jk|)*GANG451#9KVa@;)PIzY$_T+>oa$h8qi`riaDjuGkK44OVS;Yk0RAn6hAeluwNZo-lNH=(6}b7+0N2@qQc2}k6OQ!12`&A5LEOi+2@(&O{zXgwUJ!L$n;`DORF9Va zy&>t0YZH$259uBt(!ci{aE9R8j3fO+?>mRt%jg3!muoY`-!O4_{BA}||Gtp)%C#Bd zE==`k>E91p9&U!jGp2foc`$KCKS(@rZN`!QH>0J0e~3D+%{bEkX0-GV)y}mUl8#{Z zBK(V%{sSTAa&5+u{x_qg{~*YHCS03wr2oxm=|329peom99O-{EBz?i$$ruJHzqmHz zNdKGB(tkK4p13wc!WCu?!oO(gKO90Kh2_aHRh&Xz4!=k`B1G zK*AMf4m>=!pr!vfsDHQMNdH?P{)3srm;|}+h-(WZUBko?=0g)ObUd69I&Z|a1(HrN z)uW~V3`n}?+5(|5)uW~V3|RO;{Eev|E&XRg)BhG6>3<7a`p<;8gKG3<7a`p<^AgKGg9<)8Y6-WBtikANKKzDh7 z?g_$?{g5yahGTXCfSt!U}L z2o^p#(*IVp^j`w;Ki5_q=^t`@Fe3ezK=ao&9O-`>B)nna##jm+C)|c3{cl4{|Il;L zxVGU)|J%^ge<^f)U>lC~557+eDZQ1#+>ayugYV-)QeO^pKaTXj4K4kb!_3E#{AwaN?p)h&r2lOY z`(gGn)>K6UjwAhVM@#?hF!w;h71O_H>AwROo;cF~cC_^033ES=^uHaFeqr`9cEQpEj`R=n z7OXwo4Q(Ipz>)sJ_Z1@LmmWxbaP7d6{=xSbBB}3%qyw%UIMP4({zGK-koe%*fg}CH z?>~g*-#%#m+JPhe??6lcebD^114sJbftLRJA^D$c2PB=s!Wo|aq4#~m#2Ndc>1PMT z-!O56dPsVKi8D@sxPxm4j`Y6+65a^)(D9`mIMV+PwDdn2TK@0Ak^Xl;!W(Y>WQaPh z9k7G~31@`+(bE4EX!~jhj`Y6+E&We{_>*e~j`Y6+E&Wf0q#LdsIMV+PwDdm}+8^A3 zBmG0J6+yIrra|oE+KD6m?}WrZJbb1@;)81^j`Y71t^A(>QOC6t;t!ZP@bKJ;R{qa` zjz{gpk^aH=c_QVPnb3VY?@HPDr}LbPrnkp9M1?NBZB1R{qa|mTx<8 zr2n00>38#32&G<<7{Yt--#pr??g-gvmxn>YbPXK!^}a1KU(^q3+>FM*clyKtocU1;fl3A8@lg(Lm%LQDV9 z`-{1D;Yk0xAnt{QGviX|euP~((*G{B^uH9^f7yj2{qI6c|H~lhfNK|y^uG%&{V#*o zr@L^Z|6OS5e>pV2?81@$ccG>K<&bpGwF^SS!U2&!(bE44NPKhcf}}eP^^j#li1fb_ zlK!}ML;Q`Y9xeT^gr^uH1k z?p(WZr2pNJ@PM1Y3R++9#*zMaqow~<(De_yaio9nebPwv%PMI3up8oUn7#1$+Kra} zS3~E&cH>C@yV27BT4?#O8%O%z4GBM(y^QN%?#Ge-ccZ2M_0aMB-8j40lDj`Y79E&XqRxgSUR-;I|3H$dFSwHrtJheQt|{X^FQaP7g7 z{`a7z|BcZ4Vh@h=zXvV-Z-mx&dm#SC2%kM@=^r|e$h8MY`rm_={x?JG>peKq{~omT z51l{Y+Jhtg??FrdTcPFE9vta^4_f)Z4LTmX2S@tfgO>icL(&J=9vta^4_f-)0SkW| z>3rLMFg}Es%e5Cr`rnI|{vSfy zZ+mg1|GjAGA9{`z*IpdyA9Af7BK3<(u`hN-u7p{Fc z(*HiR^#2^9j%y!|^uG@+{l9?r2lwGf|NGF=|9WWoybnkE--nj|H$v0%J{;+PA6oi< z0WF{R;Yk1c(9-`)h<#l9aHRizXzBkIBtE$I;Yk1c(9-`aNO*DW!;${?p{4&<(DGy- zB%Q+2Ej<12Lred!q2m?%An}Z;9xeSt&)4PJha>&(Lrec}A@Rz!4@dgnhnD`|LF=P^ zIMP4lI4VT?e-9lm+K(gs?}vmp%wLQjA^zdok0br>M@#=-py9tClCELqz{7JtTKfMA zO`rR5r2qX8^I+yMeuem-Yd<8MVB!e#(bE4nX#U-gBmM7(q(_)JjNc&sEjP|NUs`|2uU3%zhl{e?MCK{{bPY9oDKaTXjACg|+;rR;^E?oO@r2qYB>HjyhzTS@`{qKjwKivG^F!$g{ z{}5?J`u_t7U#Foeo`u_`Y2iE}{>Hh#)`u_(V-#&mN z{U1O}|NkNBkLv)A^nU=7zF_WTVt|I{0UYW70BZVYVt@n~*8v>q{{X~(xcQ9G@u&lk zc!r51!Ur||GeNEkW8gXfNvD|VA@KtfXJUeM;J6OpNdE^=(?1h4#6MgIaHRhOsOg`H z1zJ8Fz>)qBK*9s=9u^3n>i~}Qe*iW8GqFO)iw@vO{|8XhKNA}yzPS$INdE^=(?1g% zwEj8(Np~=J!owf3od%x%nb;xW#dQ!z`ag)8{+T$S;{ykAr2m7c>7NOD9v|019O?fc zYWip5g!VTN;z<7oA>je@7ZVpG-E$p;&@gd?f6>xE7qt95h$H>HGp<88(*Gf}^e+V+ z|2c#s{U1V0|IqUvxenn-|A)}hzckEzh`TV|kCy(S=frUx!jb+Dp{0N5IbvLgaHRi3 zXz5=Tl8(6!;VAzPp{0LWNc!M91ks1-ezf!tJ(r5>5RUYJ2rd1~L;Ej>aHRi3kn{z! zmkAnuT!(O^|3hf$UjgEOu0uG|{~?I~;N~kr;*aYPj`V*Bk{;pel_2Si>ky9ge+Vu8 zD?{5Shj65S$T4t;@?QlK?p%j)r2oTc>0cG1j_WYQT`+gT^VeZ$07BPSFsVY@1BY>> z|HEkMUlrniuERLe|6xe@!R%#HgN~mZ#*zLHqosc}X!(2?NBTdEmj2bC{n^7f(*I#d z{3F~09nU|EBmEynOaJN+cW@ns!~@J6M0ld5e+_7Pdl*OhKa7_CHDUh6k^T>(rGHIm z`|~i4^nVyF{cAzOm+LT&^nVyF{cAz{n}>0v|HF{@hlK-^HgtUBFpl(p7%lzlK+*@- zVI1inGChe%|2ok2`b|08JWUkB>`BRJCk5w!HL3$1^T;7I>R(9*viw0(XA zNBTbk@gK~cOnQ)Xz;y&i`ac4RAB1{n|N00d-ND2W{zXgw`q1{?5gh6N2wM8rhq(tw z`agn}{`H~l)gw64{}HtGZvY8Lt|Jh8Fx`)q{tY1R;5vdM{U1R~{|3Hi2?`Zt8mM;yVC{*R!ge?y3Vt|K_o|4~re2ZW*RA0vqS zxQ^mT|3}f%zcC~}xQ^mT|3}f%zcIA@JPL_7jQBc=mi|p4e6FK7(*IGk^lu7@SFWQt z(*IGk^lu7H|3`78|D$N>-wfJ*IEo|vA4N<5X3+ZgC?wrs`WG$zo5Re-yB+A9fgDw%p7=rKZ=(AEg<2}breVXKZ=(AEg<2}breVXKMF}- zFngISAm(x%#gYDxLeeinJPge%Nmg!|FbzY}zR=NOLke+(`C zyFmQUbqq)PKZch6T_EX|>llvoe+(`CyTRN8NvD|ZhnNQwXYzoqPd9mkRW zkE5l3PiT5LjwAg;&lyFS4+$5p<2cg)aY+2b)q6q9&*M1KKlD6NgnCH%!gU-+`iGvk z3Rmw3aR=9N9O)l=9x6gTbiK-P9O)l=PAWn@wEc4&NBTdGmj3;r`S&=E^nV;J{Rcqu zGuLq(=^uLjE8IPSu<*f={*R-j|6oYCa2>~y{*Oc43pYOml0LYOL*f}G4lf^$L+po% zGljsyA4mE>4k_>9>ce2}!IA!9&V-ep;gIm+iJKY>>M$3oIQ*9i!XX+9*qz{Hti zq2=KTNVvkp5$-`N|KlL;;5vaL{hvT9|6%)`PvA)ZCm`_yvzI9zlD@f4;7I=`Ao6ha z3DEZZ2^{JF1f+b0t51Z*7moCQ0xkU~Ld&-ku!IF^S0KU%E&V4#%i9w;(*Fsx^q&L? z7p@aH(*Fsx^q&k}uW|yCPGSCnyXPdR?E}IPcQU0w!k6nLj`V*Lk{)5^Fr`A>e-cOf zKZ%z9(;(r_brMJVKZ%z9Gob1DB#!id5-t5_Li_J0A?Xh0PK1Ba(tj3oyyzs3^nVg9 z{g*=PyOTK5|4Fp;UkaW7J&7azpF~UlWzhIN3869F4~ZX`I8zxU9dMn*k^WDjrT=n> zKet?heG*6dKZ%z9Vf!~v;z<7|(b9hf#6Mgoaisr~Xz9NadLGD0 zh`%x2kCy%`q4P&4aio99b)ksypDO5h%PAb`{}fvKuY#5*r*NeIQ)ubG8k!$Z;Yk0d z(9(Z3w10XENBTd7mi}uX{^UA^BmJL3OaHYn_e0VJMtGh=OaFC{aN#4xhRj`V*Dl3rl$WU7Oe?25VxK2Ub1v3Yp{!gK$ z|9Y5vaHRiJXz9NJ;y$iZ5Pg{Dqow}_2%qZ|j`V*DE&aDb`(LMUr2kWB>Awx;Ur4&Z za1Z2q4@CNJgQNql(~x+^RF9Va+ac+X>okt^e;Q&x%p9h6h<~_F<4FIf(b9hhbUy1e zj`V*TVn5vcPU!gdX&mYQG+O%agoHcSX^6jJ=D^d#X|(j;1wH@aG>-It8ZG^IL-<^$ zaiss#Xz9NP+8;cPBmJL-q%W8|nR=l8yVE$*|7o=J-vdbpT&HoQ|I=vczZY7cp2m^> zPot&(UP!v+I*lX!pN6D&xcmE{<71~G@ce?N5o z_cX-c80sO_8zTKrfUb8sgCqT)K}-J=pz(DENBTd5mi{L}(i7Ji9O?fITKb<1aR=8K z9O?fITKb<1ZEu{xk^ax1rT-}q`?${FNdIRb?uCUL(-dfb_6&~ne+H7?;p(SB$3xEG zNdITh(*HE*{Ky#`>HiE``kxN5kLwJM^nV5|{ZEIa1FkbT(*GH>^gjb;K92N%1}**1 zgv1lq864>!y8ay=KG1tLxX$26|7XzB|7=M9;W~pO{hvWg|FdEKh0rj2;rRt}O(r7! z&w->@uCtJIhp8Sd{m+4HjQR z`d1(m(VZQm%72(*HTM^uGxb-(2T#r2lhh>3=h{ygi2_{hvci|68E-(K$#w!@?P! zU(TVW|7|e!IMV+)wDi9N+Fw40BmJL4OaIVwD7enyNdM;`;Q@0e(+-$>aHRipXz70^ zv^+V7BmJL)q%XMnJ0beH&f!S^=g`tWbiWhVIUMQ#93;KN&4=z6;yQ;T{hvci|Iqz8 zT<374|8r>Re=o#7u5&oj|2eeuzYp5}Ifo2(*FTydN_|G z{hvom|IqcpT<3A5|MO_+{~)yee;!BrKaZCFq3fBr&f`e`=h4zXbUg~!c^v8gJX-oc z0!hbQ=W(R}^JwY+C@ef7`e5M<&yVNP(*IFt|KdE3^nV_beqrV?LFWs(&f`e`=h4#t zG3fe)^ElG~d9?HooiE`!k0bq`honcidrm^@>+?9$|9Q0Z4;{bYI*%j$pGQmor=a6G z=W(R}^JwY+G%P%Eq<@%mVB`PL_A%E59O?f8TKYc&t*Hh{KU2HiUQJpTfY^nU>@{Xd3;JJ$sq z>Hh*+`hN@y9~|lb0xZEn$J?Jk(iztU9O?f8TKazia}SR6e*rE1KY@fV*99Eu{~}uX z{{%Xob`jz(jPSgOmi}S;6EEUO{}<8H|4T^v;JSz-{a-{&|F0qGlItSG-7MH%gvL~lmj2&D%;mZWu?JHHjMvKDaL8NdFhn(*IZJ_{K#X>Hi`meqioo`U#0Au8TO* z|0T5a{}W;#*Cib3{}LoT;O75=jyGPyk^V2CrT^a${alxDr2k8h@PnKG8LKCIbs0zczl@sxnOPwI=ei6DSC~2Q^m7?C{WG&d z`@feV?!r`$n*N#DA@Ry}8AtlRjGF$LxuEN5FXKr6mr>I{GZ!SDxGv*J|CdqIKQlKp z{4Yb|8Pol!>7SV!T0URKk^V2ErhjH0h<>iika)l}A2t0m^T5o9gcGKEwDivlaW~gx z9O?fuYWdI13mH)7x{M?JUxvg#%wA@GnEN5&3KK`92ekAr0B!$Y#*zLnqosdgn0s)f ze@Jk^$A6ebAm(yi!IA#2prwCNNP6YEf+PK3K}-Ll(DZx-NBX}4F%K3F%%af#+7%q> z{|Z|A7lXKu>k5wae+4c5i$VKqS8$~ND`@Fo99sWg!IA#2prwCtX!u`&q$8NW;PHC} z68|u9X4rjdS8$~ND`@Fo0^%R8D>%~s6}0p(3rPoDS8$~ND`@Fo9un?cS8$~ND`@Fo z2@-!?S8$~ND`@Fo85UnS(*G5-^sfSO2iFxyI)#NBB0SO3zbY*JA^yfte-*X;!>j=v z-@b|?{a=N+7iJE#F0}n~6-WBNikAM3A?cFqDvtDj6%u}M^G%`Y?J6W5VB&E9UPVj) zrcnQ0h1i3s9+F;Q;>HjKP`uBu{3)fW~>HjKP`uBpQC$6gyf5XB75uRx2-y7mSuB(uAhp8Sd{rf=s zzgKaj|ErMjfSJP_07(a2S8=5Os}T1h)I;3CbrnbYzlxUr17Yrg#2d^UxPPyqrT-v^ zf4HvUNdMQ+(tj`{eREyIk^Zki;avoD6NBT*Hz6 zuR;6=SDyk&A6(aPr2lJZ=|2_bejMrl8d~~KgZ3A$;Yk12(b9i9wEuM-NBX~xmi{v! z_HkXuk^Zkk{0H}M79>4!U5EGsCJqnJ>uBje8uBje zA38sH9bylrdm!$Gi8JRz(gD|X9O?f$TKX@7sN=ehBmG}TOaB$n`u94H^nV>K{ntR^ ziR(I!^nV>K{ntR#!*v|#|2kUwuZ7Ow~$V^9-2oK}-M8 zb+=qMaHRhmXz3riPL%5gj`V*6E&W5+?Qz|}k^XO>rT;U~^5+IDAwuQ_5a|t)eqsJ% zhORf_x`8A8-#|n4u$e-kbJUx23n zn>f<{O|#mj0prYOb3&(*I4g^nV4q z9`7cO^nVi)Kk)Q<6=@KG!WA>Hij5`hN$BKdxIi(*JF=^#1`mzjGT$`oE2q{y#v+ zCvW3O|F_Z7|3~O}&TSm&|2A6s{{jgwuG^4wff2vA(bE49=z6Eyka)mUkCy&_LiBUp z#*zMSL&6Vc4)ZVQ`hnXx(*JF=^#2Q5{@=!t{%=Fl7u@{c(Du@89O?fyYWinkfVm$> z`oE2u{#h7c;g2Kz-$qOSEs*fyx{V|K-$qUUEX>gI^EQt3e;X2?F#oc!Kq@@0+c?ty zZAf~Dt7nDypX)Y`^nV*Q{j+eu(gTk44{9O?fKYWio9fR>+kaHRh` zsOg_Y3KG6tcW|WtJE-ZOMF!#yt~)r={~bvD!@`Fddj0~}9USTZ4kSL|>W@Rq&pSBM z{~fgSe;k_M@8C%PchJ)R2}pc%-NBLm@1UjslhF9RgCqUlfyl$$&msfyKi3@`>HiK| z`j>&G|2sI+{~bvDAk2rkA4mGX14%Ck_0aj~J2=w+9f)~w^|Fxo=DLF;{og@L|8mgw z{2d(W{|;LEmxH*2>kf|ee;2j~izEHtg_s9duLw!^Tz4TfOdR2U)b!7y2#Ig5yExK6bUhl( z92RAWySeV-NdI>s;Rjc*3Q2!lcX6cuyQt}(MGfMAuDdwW|6R27uK^vOybB2@n7s)9 zLhOf$vuHrl2iIL3>HjVyJmBgzq2qyfaissdXz5=Q+P=CANp~=F5bi-s|5`Bj<4FH^ z(bB&*bo}Zrj`V*Q;y;+ZERgOd1J_*~>Hi*D`qzc--@k_={og}N|9a5&(mfpM{~lWU zH-y%A_aNyA=1zF{+=IkFOq|6Sl0LZZ;Yk1Y(9*vN%sn{L|2?$yZwei+zK0|I-$O0` zS zBmLh)OaFE-_v1+a_t4V6FEst%!;${)p{4&o==$(`IMV+;wDcbcNyl9GaHRixXz4!! zTEE|e=!1nbJiXmVOaBoNcXQo`gcGKEwDcbd9WT0%BmLip#1G6ImMEC{IMV-pwDcbh z33smhIMV-pwDcbfQO9*3NBX~ymi`l<@p~Uf`oE8s{u80+QQXIo{_mru|3p~$;7I@X z(b9hsbUy1oj`V*YE&V4$(gD|f9O?f)TKZ3cqyw(|IMV-pwDg|}?e9SEnSsS4BK@GH z|5QkPbKQr;Gp2g9^q&R`PaNt0K3e+Eg@q@?-COBp1+ay`J2{vV*F|1#)!%L7QdhM5Bo{|6BBVB#$0 zkZ|F8fFu1sKuiC%(E8#5j`aTkE&Vq_%eMzO(*Far^xp(g$Mpb5`hS3y{#&5qArEk* z{|9L4zZKg4e1IeUKR`?W?XdX8k^Uc`rT-2{d~iL0ltZv^Mub0F`kxI+_goJkG^TpA z^gjo>9_#^*^#1^sKq2!2EOQ|0xE?^_8Pj~U^gkEcUwD8c{Xax2|K~!_^LdCP{XaxY z|MMX6#PtwI`hN&14`A+OnGdax9^y#<4mejv!^9EciI)CXz}$l){XaxY|0`kPk0bp*LQDUvpyBffNBVyRk%zgHWfjytk8q^_ zM`-DPHFST?BS^f#%z^v&5hVS>#97ur`(KYB;RF*$s7FixYarpp1-TpI!L!9KP2uJz<2rd1uhxmu<5svi#2rd0@hQt%sBOK}f z5nB3(?WcZ(BmF-@OaEITe6B}0%Kt}b>3=Jnx5sGdA9mm6V;t%KFHjfW`iI`@#`PFS z`hSd;{`W)MOOJ7+|Ho+Q{|IEjg6lDk^#2$w{hx%^@6dTRSU4c!3oZRa&t>C!j3fO& zhNO3xIV`83<Hje#JtEXY)Nwt=k^Uc}rT^2={?}t1>Hje#{ld*Z108>Oj3fO& zMoa&fq5Y}HIMP34xE3+~58YqE1>KhkvlkwoPtejoZ2tWTj`aToE&X4C))!B3r2i*q z>Hiuu{Gt0kG2Mff{;$Ez$C3V@pr!xo(ER=cNBVz)mj0pZ8@Qg}NdHgJ(*G^!_|g*` z=^wg373MFNTaXChdV(YUKS4|Xx1sB2p5Q3|pP;3G===xQ6CCOP30nGxj$d;T{XaoV|4(4?izEF%K}-Knq5bzKIMV-9wDSKc zB>izch19DU{(Xv;{+~kJ&Gi&V`hSX+{+~nJ|4(tGf2jR1ds$vU`|r?o0WfiR_&-HU z|F59w`6-U{{}e6#zk<%sKE;v#pQ5Gz*ARDeJ;jm!pQ5Gz*O2te^%O_?e~MQAzk%lW zr#RC8Q;2!6aA0{09S?tsBmF-`OaE^n?%;ZgBmF-`OaE`7`S&S~^#2qs{lA6IuR-s* zg}Dlq{+VXBAZKbSbncWC%O!_oeKhL--nL;d>p5aLU&(PBUUuggI8IJV-3@!cthold#XE@UTGqm*oAKJcshNJv{hMN9a86e@# z^$b#u!u*8@f7JBP$^h+OJj0RxpP{CIRz`?^u4j;N!Z80i#D6exRwjskuID(?|8vyz z&&mvq-{&~e|8vyz&&muv$8_?T+eZ&|L3UbpOqC_Up&W={-2|! ze^yp#_&Hj%u`e$W>w*Q~wNdM6FWiWeL*`e+K=Qz^;bJXdOrk^Y}U(l0_ibbRAEj`R;R20H%FDh+l23mobH1zP%ttv`8z zBmKWXOaC&E@{a2Tj`IHnB)!AkF9RKqeSstWzd%d>vJgHObR8nh9C-eEftLPdq3y{R zIMV+MwDd0rZJ)frk^Wym(hJO9RypW+=?fg`{{(*Fyz^sfMOKaTYO z0xkV3K++S}3mobH1zP%7gsI1o{$HS_ejjSV{{mt^JbaWP z>bPFO5-wz301>}v>0brr9vtcaB_uz=%~yl)xn4rt1rvvx{}L_zt3%7HmpIb@OSJT_ z0dWV{OC0I{C0hE|f}}sLmpIb@OGtW$xsz23TED-LkfUI#kA{}M;~e~FgHj5K`Zs{+=XwdT2h)7C^lu0WcdnN>(*H}e^lt=7uUs!7{>C&PE&ZE7$A4bp zNdGS(=E2NiHHC#gB;CQp;o$ zNdK?U(!V7ny>h+6k^WzyrGHOIxNyCK!~@J<2>(LNgNZXAgSJmz;Yk0lP}4s%^d1_n zS2)uDE7bCz`6MhnaisrOsOg^>dd~#cD;(+n6(Y zk^Wz!rhnE@nEP?0|JSJLpEVqk4!B<9NdM6BB$zu{BcSb{*ErJuYqazq35h?h*ErJu zYqazq2@4+_>Hjra`j3W`BV4a>r2p5D^b2=?3?#g`UPJs16Gy}sTKbQLr5_yW|210r zkAsdUzs8aNA;|?k{?8f@Z4bP`k^bL6!Vl(7)&yvO;SG-T{{}7n!_E_U11X1K=D_{? z1}*(3L(&1)8yxBX4O;q7h3Myko`Z;KK3e)ug@hN^8%Vrisz*!zX%K&My}^{QCw+`hSC#{_`N|lIsn`-!OX- z;RA_Jm^f=8Bwo4RK>Ps{hpT^!R{obj!i(!I#2!rbknn?vvz9{3!?%!h0TV}<4+#&L zIBPj1p19uPNdIpk=@+3M67F2kb2?$-2=md>exAzY?OK>n$XlFwI9x z|JBg($+tMt|68>5-v%9jfR4Lknva(LVfW*_#gYEsqNRVRGOo9faK$tq5}z<})(+_W z%Uc}j|1Dbjp9?8>xZXnI0cH*&{L#|?Tu69vy~UCK-=d}exsY_v^%g>7nva(L=RwB@ z-r`9A(DPYg=CIC#gfG`y9O?fZTKb;{$v<50aHRitXz71GB)xLI!;${qLDD1KJ@X+E z#`O+I`hN#853YUzG=IH=!~;wm9{%qj=@%x>x&T_l{V#^5=XW^L|2wqw zzXTGmT<>tC|95EVe<>v0aJ|Ek{@pdi#Fx8`_|1}VEx!yzK8B;x4 z`dUYI$oo1ydj?{TF6_h{*VGc^3)L&6ni4#K}^>3=gMe7WA^NdNC4 zo%32e9A8@4q4`}KCG<1CC1CI3n0WJMQ?fFu2XfVdYH4ymNQq;u$86 z2p_cc54}Hz>jRGT{{b!iL+>@=`hX+-e?UwB7ohW-A8@4q4`}HhdcHi@2S~cZbU#}9 zhn{23^#PKOFx8`_f9Sd7Tpw_h{~yrO{}pI@{(vL>e?UwBSD@nqA8@4q4`}KCDs=wk z1CI3n0hXX4^8&2UbMd%7;7I=;A>}bF99XYI&Hsoa{eMJD|IqWNxIW@Y{~yuP{|#vT ze#DXfKcc1oo6z$1BaZa{5iR}SgpOZ*#F73#qNRW6c_myQaisr`XzBkBbiLL`9O?ff zTKc~WZI6A#k^VoTrT=@-_RmKg>Hi~I`iJgw{{4uS{vSf;gFfO&{~yuP z|3g@O;Yj}<(b7M3ev9iPj`aT#E&W61QMf+hNdF(v(*G;yc+^K6>Hi~I`hN`xcdm~( z(*Gy4^#2B$A3xzp|IqsoVByRPZSQh@!jb+zp{4&1(Ek1>9O)l=e*)b6PmuJ@^$AD% zhswj%e};q?*C!n5{}WpJ{|X&{{)8j_e?m+D-yreI^$AD%|AdzQzeCHDPmp+kxf7l~ zKcS`npAdCipKzrAPiX1?H!Qwzl>eX5(*GZ5`S1xx`u~KM{{KPZkLweT^#2Jh{r`uy zH$Fka3Ddu*>7R`O+CKb*BmIAZ#3#%gHYRBO@(D-!|AdeK0l+Te>P5N`uvO|{eMPH|7=_kcW`}%=)*K0HT|=} z?icusBmI9yP5*2>(Dd*bNBaMan*P~%pymH(NIYP=2Q~e(@j}bn&p6WmXVmo1#s>*s zuFp8q|7W!H&ksqjT%U2Ie`t9Ib0?bsH2;3ak^VnJ%!8{Jg2WToXB_DtGTaXz|7R11 zgd^7%9O?fHTKX4(hW{5F>HiB_`WJzjk0bqmK}-MQkaWQH1xNb-f|mXzpyOj-An6Vk z4)FB+1rk3naW+Xv`s4b7qx}DZmj0!n?XfSAaD|zJFdr@bOF`?qFF4Zw7l{2ZbJ(OI z{^9xp@i$ByVLn>=mxj*oe1U{3rh2sWF9U6leZi6bzo4am8Hhi*zTimzU(nLO479)Y z1xNaao@WMgCz~uRJaMG|FOc#Tp&sH-t}i&!{};6MF9%&O@dZcv|B6=r%R$S}uQ<~G zSG4pm4~^fiIMV-DwDhk4iEpm2IMV-DwDhkCGapC#{|ZSj@bFQB*1unIq<`prQwa6Y z`1*@%s%e{kuZz_is4T|2MSq-xU%c zT;Fh{|8J1+fZ5CD23JBBa}eHj-g`uBm32Y$zq{=cK8e}9NNuI~_gVE%&p z_d8np4~B#<*LO&`VyZ_={~?fc!}T3U`u~oW{zIYdpYJ%*|941wgxSj$2F)+uaist6 zXz4#3l5V)Z<4FJC(b9h+Bwo3`L;L}=7ZE;a=^u7~#CII&|2taxPlJUgj`aT>E&XRe z+`;u7;tx#sK+J=Qv*keIgX=qv^#2_#{pUdI)9*OS|Ljxy=!Tbe}-ydk{zY>xTxPCzNVX8+<|5cFi;`)Ij{r^Bq|5dQ? z$C3Vjpr!vRNC%PY2SgvHd(hH+pApXWQA7UO%oUH~DzFa?W zr2iji>Aw~_{`Lcw&>`~z@bLeMR{qyQ`%^!0r2n62>Awy-U-lD6`u~ZR{u?0afa@oY z^#2nQpK$*+LF?0>IMP4#{ARfNW{CT^e&R^~Khe^EGt9p@(*IAi^xq1tFQE6z!t6za zCnSDg;;eHa>4^(Et_c%Is7FixZLsjfk^X<8rT;c)`|u}@^#2nr{kKEQlb<-!|4)c} zVeVw>fSAkm6G!_0iI)C5Vc~-#{r^Nu|DBNZ&Gi#U`iI`f3wKX9EPipM|DR~-zZ+sM z*H0Yj{})>N?}6y&`h_F?|AN>LcTXSGzrS##|6ge7zYm(;e&I;}ztGbE1V}h?{lby{ zf1#EC6QSkRFC6Lr7h3wC1S!Y4e&I;}ztGbE6zKTLFNi)^IKb2MFVytUHU*N-xPC$M zJ*IlJ^gk7%j_VhW^#2Pj{ZEC)?=MI?#WWu+{m+2-lj|46U6|_8(*F!d`sVtDBmMt^ z$ivKGn+ZuDT)!ak1`|hw4_f-430+V43*rw<^^p7l6K9(R9nb%TBmMt^q+f)3NVstQ z!jb-eqox1ZQ1}1Fk^Z6gSHsPp4RHt8Zyf3WH(L6i19i`D9O?fzTKb;{33smFIMV-b zwDdn8VjtIU9O?fzTKb<4ZNL47qzjn8;PLevE&VTqg%6JO{~Im+FNF4|enZkVruk^; ze-R|za6#|=##E1%{ue{@<8Mf~VyZ_=|4Sh0mFqW-^#2z%(CX9!#8V z8N@!W-w=Pm#1Y|%mi|{j_*}nnr2pS&>30|{|_YoVfM1EfrJ;=9~|lb43<_6|8xDpk^cWc!UJY6+a_pz_XkJ%{{yifp&pXHx&Git z|9>FzaP^xZ;mZZRmmVgL2p_cczXh6p{@_Uee<0}*W)9m{X#eyNj`aTr5}ye5kaWZK z2S@tic!QvN3`u_uQFWmg?u<*x`{{Nt*{~gfzxIZ}3{~xsUzY~%!xuEA{!0d&G z=U<5ZFmbk>(EV$FaisshkobYC-vu@QFNB7PBg{uj|GOaJ#q}3Q`u~fT{&z#-o9i!* z^8YVd`riX>U;V|A{{Nz-|Gg0Ras9=S{{Nz-|GkiO%=H&X`u~fT{`bMuLukzKK}-Mp zpzCe^Lh?PPdPsP{#M$;k?Bn{2BmMtHOaJ?!{foai(*Iwy^uHh4p8Sg={r`o;C)_;; zApYd~izEI2MN9t&AnBFsFOKy87cKoCg!W(l;z<90A?Cr|a}YWn@)weiVdC)g`427q zAA_+`;t^NBaMVmi`Yz+`;t^NBaMVmi}Sq z2mZs6{{IC)Jq#HKU^@!U@BeV5|9@!d|2TB~=O2#r{|}NL;r=}iEf4=e(gjQ$5&mfD z|2Q=L|HF~~|DmP-6VUnhe>l?rKeY6J0@@z?ha>&}LrecBVd()!`u~TP{$cmm{KJv{ z|DmP-Q;_K3`iCR^|3gdvr(phtq&v*;L`(m$`!4@M(jA6+==nx4akf*Cc;)&JNp~=D zczpdwOaG@J;l=eINBaK{DPLjcu$_jU5B48N`u~rX{?9&nV;omz@GlO8PL-I zeaLzVZU*e>pPKULr+;n+wDb?%SHR5xiDy_iBjO7!{eOhyFKz}L>7Nmn0if*x z=(=!jMjYv%5iR|HgtWK08F8e4Mzr(~T@TI8h$H&koEvKBaZaXh*ti8hRok_ zGvY}9jA-c}y6%&k5qtU1&4`x%KSSEj+>AKVKOcXLB>*NdHWz>7N~1zH>9-NdHWz>7N~1K5{eRNdHWz>7Shy(jMk!!jb-&P}4s< z8#F&MLE;$}FYxk*2{rw*vqSvP&4eTUGohw`c6P{kI5!iH^v{Hv{@FPo;l<5_BmFa> zrhj%0$oLgE6OQ!Hgqr@@IUxN_ZYCV*p9wYnvvWemW4W1dq<<#V^v})(>0fX&;Yj~X zsO3L9HzXXnnQ)|k==q(ncwy&<#5Xq+j`Yurn*Q1OA>&Kj%sA3NGiv&0=ZCn1n;A#? zXNJT-+&u!&`iL1v`e%m3Cqg~UJvh=oGg|r=gto_+aio7{NO-`_7lOnSH#3g(&y1G- zg`wpkGmiAnjF$ezApKu%W=Ooj?1kqSX0-G#35h3eW*q6C87=)w!@?g&`e#N<|1!|@ z#*8EVGoz({Wk`RGn;A#?XGTl^DzNZ@ge#_h(bB&vWITbJ8Atku?ni-{!>$S~ADAKj zhKVD>6Se$j*MPW#n;8=Y+{vyDO>ZnX(mxAY`qzPm4-1a;&w`fz^`Pm21xNa4 zK}-MokZ|E!Q2B0S4{V#rGFzx`OeLPBmG17SHa9-H-@(NSa76&7PRzl0SiwY z>7Ny?{I`U}D>o}7-NEdIhd(P?`nQ6X&#aJm##E1%{;iE9X>AKcJ$pkekR{EL?UZJ^~9D+s`e_KfWakJt` z|Ey@~-xk`QWW|yGSs~#KvzOftlAgF(A?|{SBisYYA24xtdr11`X2p^ISt0Up^$yVS z99A6ZpA9YjJ3=Z1ZZ;h0pAF((xcQFI_+rD6{@Ebm2UqV5@h3MMj`YulR{py{)N!*x z(hlq3tm?9OXY7TKac`wujkpq<=QF^zQ}@e>NQH zpA9YjyF=oMn+=k#VeUlu7gD~$#MwO{>sPtiaHM}WwDj)`Sue-UhNJvvLrec2(E5T6 zNBU<&OaC5_^vBJHBmJ|XrGHO|f4JEo=>q02gn!Y}zb8aLHye)h&jzs{W)8a-EPX=4 z6($ZhpB*jzdqLZ8>^RatJ6ihphRh#vv*Sqr(EcCHUUnbIdK+$bNVqr-jwAiEqosd;Xn3;YNdN3;>E9n(-?8IJ|Lkb# z-yb?&#Ev8VvqRDgEZo=wpyL(nIMP2mTKW%wq#JH_9O<7OE&T_=%*T=b+0oK}5Hvrs z<4FJPkn{_8e-O01V#ksG*&*=*R}b9}!p#ox2TUB1e$di?C?r0(*>R+QSTcvM|7Q<{ zmJb{-3COr8+k+f<-n2tq2n1af3ZXNn{adBNdFvY=|2LR zA31QOe-5^>HwTXN&w-ZyBVqo7N5F{YOFLivvgc=RiyU z(U9_sn*&Gs=RiyUkmfK0HwTXN&w-Zyqapt1=D?BuIndI7G&H|+;7I=*Xz4!&7M?iL zKL=X+kA?XcNBZYLOaHOZ_BjWR^v?+~4<28!Q1^4CG`h}}cf`&iz+z6OB!oO(gKN(s+aNj=k6MF6lOdKBmTxjV(7m_}>xghb3sU9u;=R@mjE*$Bf3oZQ@ zK7v`sYSV|Eg$LE8^JIMP24B>v&j%W zhldX@TKZoLN#ESOkZ{6O50Qt7v#*2b=jMg@8zzo0A1(cFhSqnyIMP2aBtBv0uy29p zN8S!-#6aq0g!yRce>=2)&5I-b^P;8y9T4|%^WsSVylClvC&V4xyg1T7FIxKF1s#9m zg~S`oUkLZ3rT^U!Z*ucO(gmh^wDi9l+Fs(tk^Xtn(*GW4eZh+({qsTWhuO=%2Vx&L zACC0T2T5OW^?M=l!Oe#w{qv!v|9z13#Lb5z{qv!v|NW43&&>y+VfMnqlMgNZ?}x+_ zHy@7l4?Uj`W)AxSX#0T=NBZZ3xEHSeAhdqu!;${^An6OP{t&dh<-?Kw`Own;A!z-@ z2T6A@a}fT8gf~o_{SY+$^WjMUd}!(aFeKc$`EaCvKD6|I7?RGo`5@s6vlrnWwDf-z zl0LZkaHM}ewDf-*;va549O<7Ak{)69vY&vso0|{fE|@sNJ!t9wBs9P9;Yk1dXzBkn zw7%xYk^cE1{)5@e4n5DDn;%E|=SNHbr=kAkhr|QS9Ju@W(bE5E$o@@kejMqaA1(c# zhQt#$KaTVdT@MAbm;E$!Jb@oa`sYVW|ED4G!Of2&{qv)x|1;433qOwZ&ySY=&p_92 z@Z(7T{E+a2yZ;O|Lf536olx5 zg#$c22twiqCeD5n+TIhyk^TiC=>?%465rf{IMTl$TKc~UosSU2k^TkI(m(Y4e{Mk> z>0b~n{ojJPgIf?s`WHk?|Ffe?heLe+!asxCJ5M3JV8BctXMhCeD5v5{}%0 zIMTl$TKc~YEpG*Jq<=xQ^nV9hJ_zDS|AJ`g{|+?$3qt$>b0@<6XzBkhBz8_rhg$wyurlb;Uk2W{_jKE&q9!Nhp8Sd{ojX#JGT&y^e=>#{_jKQUxXmxifKMt z`hNg%AGZ)BU1O?8OaBj`Hh&F9direNdH1;>Hh&VJqtnfVVVz#f0#Hs zY=4{(j`S~tmi`~Y{EH*~3!$a|N6`L}5F{R8_9EgJE&V@%#0NKYT{)(DwDkW3+TRhv zk^Y6y(*G0a{y`xe>0byf{Xc_*BexKa^e>E-{+~nm+`>50zc5<*e-3S*2;)fq!jSNW zg#-IrXnQ~yNBS2=OaIV&1i6KAq<>*Zcq7b*_>)^0NBS2=OaJen<1NBC(!VfT`iI^d z$1RMb{1-+`|ImBUxP@_~e_^!r54~56TNn~=Fn__*n=o4Xe-BCD+|YCDG1WulVdCuX zq2-$}j`S~#mi|9L`-8$b(!VfT`iI^l#Vw4Z{1-+`|IqtmxP@_~e_^!r{~6lf5yp}J zh0)Ug7if7U3`rNTaDay=q`8I||NjCtUj#?`7ePz^&~wtcMR25l5w!IG724kv!IAz& z(9-{RNV&!>f+PKlpr!vG(D)L;k^V){(m(XPOKuSy>0bmb{X@@rmUj!}v|ADRt5W$iDMNrc}hcLAKgx;%w8NaCMp97lCxJ7WJe-YI5&mjv-4>;1l z2x|K0kb|TfZV?>mUj#M%bI3vX+#)#AzX)pj=TL?CpIZb+`WHb>{~T)2@=XLs`WJ>=rrTNFq77lp(>EM7R=q3uagNI3x$N5mIe`VWMbhoTUBFx8`_{~(BdZc!ZRUlc9< zheO=WEs7)ki$c;n%wCQNNIY?i;z<9ZXz4!|lJ2=hAvDY!gn!Y}e;h15<4FIIVH|k* z&k+wTf5dR4e=)T59}g`b#Bij4F|_ob07+-uVmQ*j7+U&Ig5*zbF&yb%3@!a9L(`iW zBwR7VM+`0fXF~fgVi0#>sz*!zSrC76i{VKBVrc0<2bw;`aHM}RwDg|~^DiVFVYo*e zHC|w$%Po!?FN#Z{{t}0{7iJFZI1X-cm`+FnP=Z*?z%7m%FI*cS;m9qH8ZU}VA>qX> zjvD@48zKJZ7Do+dt_=`>a*LyeC)Y-ZI&N`@KA1bXHbD5?;t+js@okX&$t{jr4sdOS zsfXlOgnF3y5Pb-7h`YJPQS&d?4oEn1i=*aKt{o8nbBm+qN3I=^aO4(8&39ZoApr_s z76ct%<=O$YR{~-W+&w!X{^6E@n1>LDx?cifKSCU44upn_?}mnh1VkS~91@P)5@_Ln z5Tc)30-_JD{vgCYZV8A!gg7KzxFsO&MTkS(%`Jfz{s$rce{xGg`~ep~0I`o- z5)vK=afti4B_ZL55Qq4OTM}YFLLB0MZb^uH5#o^W;+BN?42k8A&2yvJ@A@T@u zh<OG4~Nh(p}XEeUZiT>JpUecX}|{~^R-=0L&&Ar3PKE&LBa!i!r9 zE&TVx#L>e403_VGr64rIe26-3DTqFVIK*6TDTw`W@%<2Ya7#hlix7vnn_CLvKZH2M zpWITA@I#10!i8H365a@LNH}s!p@si`NVs!LL1=_}h&pa5h(3fk#9VGEh&>2#h&#BY zAnrnlL)^_R1@Q-5{3t{nw-m(RaPbpR^Q9r-gb;_CBMk{xgg7L;xTVp;{{+N7ZfUge zKLNEDdS4mboRcu~A?Crw&%neXG+g{F#C_b-5P!qP&p`acEe-JpLLBBENVvkqq4zR# zOQVJVIY|28mPQNz3ovoC@V@}zb4x?~2RHu$L_fDQ#D2K=6$qbO8sc7rI7B};WV;!H}pIjZW+{ioEv&B47Utwd~rk1m*JK{t;e~c=aO*C zpvEIN^!yQS8Av@3cR%!ANp2amc!b^`$t?q^{}JjT@yZRoFAgpaJ^!6s1}%P}_d0XS zptg&+p!YX(%b>%b>OYq34Wn z%Ru58=6-JI`6=8oXzhP^_(ReQTs=Je(c1seb1S%IAn5|G9(q0nw+veQA9^kZw+w1K zp9>x@Xz2|eFR1N&F6jN8+_GSA!_y%*^c)#(S=4mM1&c3P)O5%Ni!WK!bO?_xS@d)W z2^Vfzv~&oIFIm*~JUqT+A^8#(KAaz*;~TQ5>606JE(W(OYWn1cp5MVOi<&;UnIYlM zEelDfF!Q;g=XY?+Lh><8oby8`IKa4NQNy2`1rjdYvZ&$D4Lvu3TNX9^xuNGHaLa*> zLxevI)ID-&;RZdgfm;sEztD5mxaCm&%XJpwA8t8R|8kv$sNK$$9xZ-h=|>(dzF^@aj~ZX_@R3K2FGTo2 z!W(WcJbcj0Lx?(VdDQsg{OAS_U~YM|@(_9s3%5KZAHdCrhYwnL2+K$EsQDBTKB(~y z4<7}zc!7n30&2X#!$AQxUf|)NfEF*Xa8N+ackpzgfEq8HAIl)&pnx`R06kxZTLHCx zgy$m#w0sH+2k1Sbh;W01Bew!-{35~u5CM zAJlvY4_rYL*1{6XR;^Q+?6H~ZQB@7J|LKMb#vp@|6LWIni&As)lM_qOoM~nTa%Ng$aY=kpYH?~wd_iJKaz=b{ zNn#PYjh3LmK~jmu-DZ|1pg2c2EfvFADIi;ub5axYN(&raYkZM zYD#=@K~XWPyDbrFic$-5GC{$OMV$#G0p%qoC!**#1&Nm^WR!v8DmAe6~iQuZe)35BQzDspfrH2A|9TckyRRkN)-hch2nzDB9y=| zGyr8Hs6+;;77GId1s8>aqWt7|aFn43q#?*u1s4UdWNu1v31%=F8bS<7E+~ypF3G`V zj-@fkCYYj(;-dJ(qEu9O8YY8X15;C65DzZDKXk=~`wsRJ7qpH!NbmRb~FT#%TI<}iyCu-y>1C+FwI7vzJ>Wz?F} z(8$sRl*jcD>M(=RG7-%vu-&K;VVMHT=xA;PS&6DF5nPm_DND@*)o3V{iJ?(q3aE6~ zOUo}xPK`(LI;x3DMxZFt0~PN@u)sl60Zv7F@sOa!t|r9{YzjE=ai~ZJy9eUdczAGu z;tbWgRB%&74<(+^R3w7a43Oa#M3b((#EYDe(nG`30#(C7G!xHI|{V zp%K{MsJ;Vf$jeVbS8J364(|B)q{QUxk|OlvZES1`wl+S#peQr11eYq)G_WZ+%zzXR zdhwtJNOE?3az=K1T4E+j-C}5LmJCk(IjLqQ@g@23$pxjT{x^e!cuuOZ5mtF~LvV~h z+irQKIcVman}D4Nu3Z!JQsTkYBxWUNXq=V`R+yWZnFn$Oq`ipZ786r&O9$j3cw-J! zYGc%>h9+j{R)yrO?M`Vkn$63az+YD z8{W_)5mIpFWEPjir=;e@rxoR+bP)_qlEAHBy}Z=&_@dNww069qNs=WvfdwjZZ5|MJ?h@ zQcb}&r(_l#LA@9_~L>bv}zFA zRMZ1yRfrc+w3`~5f`cCv0x6}r1@VbFIr+(`4ly+{0VgE58Vui<8XG~*)a25l z;>XJx;{{|2s1b`r0VL)@ z3P9r}mz+DtbfdMiqsWQGG6EzWkkyWfnoo5HwjxdmUV0LG3S2Eh*K+ zu?LA~kYY$&qZ(*#2+mMom4&6LMU@~Iff`^XrD$F^hjcq0d%p7n!L~nnYTNr{1 zEr|Q^se|M+kh@^P4H}}#!4l{e;K2fvKnJxd&|56#mN2XHQoz1Qs>BlbmSzYK7p20o z9GYK~(!j|L-LK%bR32t)$UGU+`o-`xZViyq5tK#{VU!2zFcqa1$Aemw8JTF=BsmEj zu%G|~X-kHfoswFC8llM$r-PIgrRL_BrD6$#6iCw*q$VY^7#xqFK|)CSKnsdgV{l@H zj<;f#JLaj7Iusm|8EB1B^HfNBEdVt_L8E8j)-*<%Nrgl(*a)mDEDRyt53mZ5Qe#2D1t^PzDCi{? z7pE4LVD?BX%uOL7l%IhX7Z&CaLqXA1T$!7ckJ{C+ut)+Y#rXK*#IjUSb%qj?7M75# znU<4SQj(e%pHhMulNO-!gz4KSe##4gf{wSX=w~@J%P;x4V_e=H_@RlR7m{+?dagJH_^ZV+~NX7 zd1i7kX5p1+2pJ{-g*He*0mQ>7$vM#w(oX^z0uB^-XrKmsq7kHa1a$==U9Ze!)CwTc z2t2Q(mzi7;U!0nk5}%r%iE0(J!wXVSP?TB_pO%k(0?IJa7}}gqE{M<01dUXo4MHUv zLy|l^sT38)Lt;EBu^6>$kZ1xapFn|7P@IV)wi8Vt#W=Eo1sO^4n8ukxs_Oy^aB=_* zkfApu5=||@^%X)1*lDO?0ct>k29e;#6l9=QEQw~2*hNG>W`LSON^o$cjVs6itYN9$Yp)7cJ#jLLvZJ z0aj})Aq@;eYWB?f+L{@@2`)HVC z0GS7ZDFF}sqq-#tGyz(opogLa%`r)a2H;8szZz3;y9q@Nx^qBf9Mmpw_!pq2&?LiD zaLC2SgG?z;%*l>VNi9POmn5TPur&}R;93wvi7|M6gC3HSQ4L33g<+VKXaNpZkZF)= z1HFt(N`lNnfmDFQ6eGZrAOklb1;xpUdGYzE^XP`j29O>ANCDV{RCFVf4I#w}NCmXN zmV{QYBpVrndww7#U|TR0KpPcs1?V10PKHbhffPVn_@F$B5?skCkm3uZ2HpU`Fenu= zNCHxX)K0)q1{#Y3RUgTj@t_oqDGwPr1Q}CYk`iBBo>^4|YU&gf#^<6X$`qtr25tr9 zrGk<_sF#A#0#8YUl$#)PL299X1*t>LQYmSWX=0EQD6yd$ zkZK62H9$(R=Ezi}cm>BidVWkbL~#OW%?a+5pK1shd;wVpHVsmOrpKpc=Ad^}QjJW& z?Jkg7P$1w_YHR>5Hb6>2evB{91@{F|L&F48aKIIT8b^smsqs0Pd7w!;&`=|)22)4{ z2iE{{MM?>-X~PDIg=3Q+=1cc8eeq#gNhmn`(G5iexmn6AzkL!sZx621e4616z!R zwoW1yI>Uu<4al3Q-Gfxn+y|siftm>F_26|w3S`m=VJb)mPCura!ODM_`ML2KSlp48 zjHxaSQ(c-Nq$WVJ9g-BmsSG8m(?GQpq;P>+4H?`(Rb&dOdBE)vaLNL$Zp%o5tn>lR zXXK-LpUDU0xYUi!I6S)0k|E6#XS}lSX~cM zj>AEgM&Qa7yA_x&vP=f&M!53S)C_2|1DsvZYQ(feq|qo)Tp=k3FFZj_3rUcf5v+!z zH44&_&>d1#6rY)wm70v2ztWHg&Oj~z^~Q2@GxOsi3sO)WkOCPwfI9%3voexE$uPb= zGcP3{b>cED1u`8CSD%|$5MPiQ4>lj0`qV_!_yn7emSEG&Q9~G_CZ`0YA!%e_fEHFD zWx1%+Sw;rX#xdM|P(@h$Ze(DHG~NyhsNCXA^q!)Tff0CRE+YAsB&Wt_XQD36Ffsu3 z@nM68AfrImg7aJfieHTkj3H$^*nRM9j5#!7WB{$&;0i&GLv5WK8JHlY2#{eQHD)Li z_C^M#=BN<>jj)v5L@e=ZWB^)YhwKpy<)D%QWw6-Dzzi~Q1a>OO^N_g<Sbh@2=Q4wXzHXOu_Oa?DUFd~62y>_#O&1gyhPNs0!D_(kU}#rwLBiw zi9mHM1zIbD zn$|#xO#!Yo-Y78zb)}Y(kr8D0Hl+m8$4e|hSte^_WDM!Hrj&r2>!76=ph!S<1a!6n zNexCM7@0y6J!BqSzBY_&CMy8NKS#W^o;8Fuw(1PfURD#`}oQhV}7@0vjl3;fg z6{E(Dkr|}#2M#&Z#nnbeW{~k}utw18!OD0n!`enh&_#MMWzZFxXg)HBj2(eeA9e+h zZ3&>*1$D8otAP%0f)WX0DQIPUaS3RW6g4s|Av0X)O7n_K(2_|N%R2M=Q`M`Vv z3h7d`CXz8|$Q9i_V&68ld&1RF3AIj zC6=sgYz8mTL8$;#A*7*$QabO4N=eo4?KbzJs`g% zrzVx6=1b#5$c!M|BvgB#`zOGLK$Jjsrl7_;crRLsf*w4sK*$y#FEUi%#zCZqSUnbg8a-p)aua$x&r~E9-IJDQp@5|G@>}w#1PU{1uF-wX~Lt_ z2;!2mf)q%Jnw?sSK9pc&Vgwl~g)1sbO-36oF*1P;A;Hw3ItbL^3sKMmNoM9}lqP|9 z+My~jL)cLO+G>QliO0yq00rX!ziCjEFcqna21%#b&X6cAq#8aYKl@ZR^J+#SV9K<;ELcgkf@M9B0RTv>7sXya6Ba%N&qe0gGaD(VU@Ba=kPViUM}Y-&=C!Ch3i z8pxt8ROf-FDoYgf;A+6m0}p1Qse|;m;p#vU0NNIUswxdq_`_9!@)D>k2wHIs8sI@u z4c?rIVmD~3ZG37@emZzj0;*zAor9tnylerq>N!3qA7zf#$kf;j)#G3z!Jdi-H5EX+ ziBJtUfy{Bh++7UbQwmMYxU@iuSFBo44TmnagRI<1Eds46D~``kPR7hirqI|xDvuN)KM1GH0V5EQGQZtJj^f@8_l5YFmMdS!_q`iDwYv6GtlfDc;_2L z5*)#(I}?n|3?aofcwIJlQ4Q22?1~|U6*%O;`;zj?iV{(F02!GXLHgEUHIOupMUgRN zju9*aE`6}4YBLkaS{;Zwj7T>#g}5gJigNPP^$HS;O7u{6`Wl(Tw&Hk^h0fwn1gz(ptegvZYFs6J|1lq zh>1u_r+D zBuGL9>q$w)VQ^9kxaSF0l$@IqpMtj3z{ngl9*OA-&^k+0C#FDp`CyZZbBjS^N2z(B ziAhvtsRrO#WUw-L+ZVKP6YT&6BlA>9`Uk5l09Acx4MKC!^6nA^y`*H&ejL=vE+cc$ ziULrA$SVOYgi1EP-e;$T#REFeoW!9^oP5p*vxsxs)P z5Xipd{M=mB4TeS*pcY(+f*wdZu>iD&8FMzkA`yJt2eKOU>}Qb#8Daz(1Ic%wMeeA3 zwu~&2A>(#n$6^LdGNg42+A9X$%m7LQsQoSrP{IeVfd{2^@R0z}U6rWA%@!$;C88iZ zAgWM8%ty8HVmU=&{zU!i59AxOrQm}Q8J{1mQ-2{8uvxr6=Gy*0$G2DZYio+W{_P{ zMJ37c$%)Assqv5{^=OJ919AvO>8KOBMwaG~G>D=Cl$ujPDGAjubI5!_T25kdMm(gp z&df_gIseDV(gHFifUF4I1VJ^*64DPrRt0HIf$BU|rHPPf1aM$L)T6a!Et4Q!3?vnp zrX)e!j-&>QtCBISN-aWLkZfd`3~6pcoC50afOflrm(-&sokSyJ@G?}0LQuJ1gf>r{ zXauQhU@CGz$J(HHKG7I_N{Jp!MS3Rsz6+y7==K|!65Q>~L{P6AG@k^HKS*%nZM-Ie zW|&}YrQ+1QV$gzbv_ngb5}~_Qq4J=NgzAMv6U5vvxDEuZE=N_81PM}ba&ra0R4Wo0wUG*;YtQh0JL~)PP3FP~Dpb zS+4+*2E{CDgEk4Yr?W&s4K(jJQrpfpl6S(x5Hjpwbp}?ngfA&R?UX6i8(N zQJIgjDa9xWwDc3S2tOmUpd>#f9yY}b*$)_Bl9r2F<0gSpA(DDfLpL$GB(p3Pw4()W zJ)%)kDrBh?xW5ozl3$RIS*j+17L00jbH!Pp`yOmkin~jAS#^Oq8t&M#-R= zO(aDn`SGah>y473E2=>;1M)DamIj@aR1goTO^ZtN@-p*KM_7_UMHP~%kU9yZ8`e5T zEgqANA*D9V4sbS#FG+$lfzZ^NK-M$C)aK@=U^v+nvM>jx1iqgF;$)Qkn`{c%<_+D? zTUt~E+E)e(RaB*rGvf4M#)8&R#AEfo8DzBuOd-@e`6*ca0~+H;3M+8<<|bm4?a81S zM@J1wiG(QyrA`n#z6d>2Bqu?_37kVgF$q@+TG)WP=FBJ= zw8t08t&r9TI6Z^XDr%@gTdg2#LFN{Nj;boDEJ!uMT*i`&mYKj|Rh*NER+lD2w>rX% zgbaRys^&`6jgv;npzaW?8YxNzn+Iy^fCj!$T$uu0<_t3uG*DiaT7)BwrkF#<>0zo9 zA*WnmO;srtkjX`uT8x4#1zH@z6eK4W6oA{XAVI{0i?N#Fr4RIQ+8 z)!<~1gn43>QK}`R8Jkm(91qeCUDJ(fLK0*UGd>=q3RIt=N<$lp5NU9Qh$^3g6v7}A zuqlB|hk<0lL$dM3sYRJZg{bC$*6Noi=z$caWEMk@s7x)2&nzlLEk@G}AWa`|oPv~N zxH-)bk}yG%n9fOquCfQoVrn&l)U_ZB4qgrND7wd;*)bSQ_+TP(vl$i zXG#-`N+4Umz#)e7h&!XSB*?HVSOaGGB}0+}SQb*vmQ;XNETInOq$ML60v<8OswxFC zT?IA_>@3t!f;MQt($In$ZJV)CS}LU74pswlEokrvGD(VR7HG3;iGm(j9q8OX@R@X| zO41;U&B02bmP)`(1FHd9jjF^DvU3k?8puKn{}~$?LD~yoC16vq zs4<3|Min0qR+W;Ev9rV2zyz{L8>|4@YQ&}rDdNyFr?G(vBtwCXz%qw!Y+wQzTmvhB zp*3KQ z4N{<6F^V(6n<}uxbQ+|#0a*$=7X)M+N{AU6KvwmF6v0a{R29aMg%BVWkY-|9G0H|m zV?z_jSQ|(Mq$mJc6Aum)lvTFIhS23NAeG?dA|QpRwn5ViNChO6;?s%?us1}nieAZTm~S}PL*bu)%FW(JTBCfE#2E6kv$)qaK&IO&Z zgGD8#x6L4P)SxB<)IlhrZ)Oge9)`-{7$7w^vw)ua1$7z3PgvZQ2pI^383(K9p~KtY zQ7u&aLA^lGycX18XdR1NeKKTQ0L%i+r~-{HgO)>7V60#2cNiy|K?XoTLqCum@`))JN+2CEd`irr=?2Ln)Wz|}$)MxmKrw+&31r*?W)V2o zqC3VMGX9EJ4QTx{l2usEu|S-90rEFk4Z4#pAPof+yU^8u4qHUG3quWLQ6k73$ngTH zC7>e)KrNvBQj|F*<7CiG2h=>mY9Vbx;>?At8igbk(B{Up)VyT0wo`H<^voD=dP{|G z`31GC6LZiGCN@q^gfzz>Mk1-sP0d9Q0qBqjhSJP@bd|}FIX4WI$!Vx<-Q;A*+#QC( zlw6dHCybL*Ad8UE6{6;pRLFuQh$2vFhPs#5I2pQc7+C?@reWh0P<92y9XR+fHnXBw zm|}?Rdg3LRkng_aw1MW1CO3>b5w1`astu@C`gt{BYI0dv14n+~DPy;U^ zE=Y~X+}2^7VglJM3UMSTS%b^d%>0x@$Z82xhnhk*wn9}W78HSIZ8Gz+k|C!n>e}NTa-{5MT0xOiksRR^}I1ZOEPJta81Xc+OQ;@l!SU~j^ z=oou=pn;Tu48>Gt0XcjD;`tm%yBl+qCk1pMHrzCjGVG>VA{Q0l@CHQ{S_q~hhhTC> zett3dJR?-+Ll0wyxC`@44C7Q|OYoX*hyqai9z1S?Vo0hfWN;3uCIdXZh-2_06|`>= z?!$uQOi=j`uF4@T2$VhT#;In|+7BEFP}QK;E6PDx#;Kq)PSFhoDMPEjQbE(_aCM;g z1dnWBc5G6iCr3bi1aT$EK(u_73L4>t8wlD64N?>j$_gMuQD^UrQ&S;F0zga!sRk|7 ztAd;igQhmk05Z4?Q494sxSmAydYS>WN=6PLusSrqr-4qdg*z4VloaDM&>$&Xfol*b zcY+l%BE(7Zj$ESGT_^fnoYSCEvVO(hwpK{sPS6oOJdC?G+H z!(*N|VVnlqdjxkbSRwY4FO1WYpsfwCQ=!K(fl4Z551AMkKqhw~mV;__%;6Rj0|UsS zWr!k>SFmqXH!(1V^m`!+p*0MSqccnlK!-hcP0YtRSjt37ex(5z!+LUmbXE?0x|}ptT8c6M6Ugku_%D{ZIX)1 z6AR)|D;^U==q}oVj3i^w@pAAY0mZ3?$8KM$pX_U^_vzIw;)H+XyB`iICwVxGGS{W2#DmcK<;E1&UwnW`Qnz zgEd>rk7tCdSZ# zMX(vr3Jvq*I1^(NXvGII2C57k0ch#i7!H( z6VP&U&;TE3=?Zw6Y-uvu5j7^JhLA;DU?)MXf`of~Q8H*_RT`G#flN#dA!~WTx^UH* zrWVj9J;;5af(uKPX$rbH0hY$V$pYt@QzoX+rC4A~K{XAy#)J&^p_CS;iIAg4!3v>8 zF<32TL&3x}3EEKyITETCQEa0c3tcS&HWrkfU4xKYK!zxjo+f6XJ;^Yif!YGF)*R|A zfr%OD5CFJ3%zizj;cJL8c4lH`2<;PtTn%yxU}glFgn&C5p%SfFH#3H; zg+*71)@e5}gPz8NMIE}`rjYHkSX83hZ3>xlKv#)2vS4Cn2HD>TiS&4^r!JY8fwm99 zLKKvyuq!h+fS3ig6LZAH#M}VdNCSs4;;=W2Caei~tQTe>mgbE)^e`>3O;86FfbQYR zFH1$8g)=b+-B1fN3Yr~3IUg-#&CQYHDm5b>M?=#bx(EeqGsqkqoevWW=!y=oLQu&B z9_B?Ki#4$TjcUW3hn%QO645SWF|mNI+yI+Ms4;2*oAd^SHEcmVc*PxNiDdzrGy*kB zk=2$JpzPc>v4HN&gAVj&B%$UX%Opq%QJj_xnsr0nXlr7b3|Ywyk}XTj$pr1!iU(bp zi8jn;VwnutMh;r1lvWN|!-f`9me3(CkXcEkX`pss3S>JYYH?wi0@=g~QU_{FfFcW} z^s!8ZtU3ZINUcas1})IfP0WKDhB60aVhJ6!2dM?6Hxtz6i)9+5^Z-eNmN%lU`7=p0 zfHY-6@)+(&1f87#nnX`aj>p)VVUlPFS+5Gx3a*z?{E!Ge_y8oEUx0cwhe@IdWZ?ry zGC3z7buocSB6PAU4Ri_?Xr~OO!$7McNEI2Te4C4njb^5zZtL+CE4sfowem@1Q`N z7B)$Qp5&SYy=NmHhbl<76_i(#N`-Z#hcNc9nk1$|8c=8o zQ4LFjbj6cEhijuAie-`n-75x)KGZduCgANEAqsjRDYS(lCP~nP<3RTf7=cR!_$D(f z69FbkpaW|_rJzMTXg?Zcg?~zFQfWHIb^wzk(3VJKwfX7s<%uP!MY)MZC|ev%k}ROZ z&M;H+(=nD}nr7FO2MHHGJg&Y zBWMj=jM*DVN`}sCK`c+rOV7-MTy2TkBS-?BXoavCY9RWGS(7AKzZzm3s8?573>tkx z-K1%f1nVY4)M1S`=#6nuFF-om5Cc(yBpGy>4Z>v*b>;bJ@s$j{{0M3qbZI)OL6(qe z2C4+qk5CSinsDzrq+D<}mW?GL^l z1l+!eFG@r?8QCNiI`WLH5@a7}%_2(jN`+n$oRpH52U^$-)qti3GNcQV!|0rX+L9;} zktV6onjEAY)b2wYV@XYc3=V;$LG1<{lUpXKp!K>X3VI-QSjO5?Qy^=Tpwg*WrzlKP zQy>GfAXT8_wF>eJO2PZQ!RM!=-7#U3W(=7D1F6O`aFS*W+2;Y01{s!=SOhI^P=YHB zw5%8EaF8<4P%$Kyl5P9g4?vr3bd|B8fdL8%mI1vSQLP^ zNk!Ic7d-5Z)RNW&yP9;6Ty_(`Aza-abxvp>5(aH86tg9|EZaW#}%mfNZ@3DFY==@Td>?^nR3y0#gIf2@2ra7IXkr9_rO;riO`-P73-~ zXj4Pzao>5UTck}5lOPGXAOmzDA?o3HriMw7t`kVIq$0j58GN)H>SAV7L)hL8kO>v> zDapx+C?&rsVv?*962&NCZ3x}g0rGQBBDgh7Fc~uX0CEJhAr9KpRDod)^mciW zI@q#I910<=IgmoAuTWhC-P#0_2fGM#4IyNx6J?~v)G!q?pa4<`F1SGB9tG%U#hDs` zP9p)e_&@=a3i2mtV-|{)ptIy5(^jBZK$~4QH8Oy7aKZLKLpUDXy+SWgO^u+LA4Msw zkA-Tb5hQ1!s05$-fT|4IYlSK+DN4*l-`j0!WDFT>MQF-WAYmU5UXlZv>O*PrnHr@+dS`Hp z%8F518>U8Skm3np0ICJX$h$(}rsSrfxx*MbtBP!UM7~1vGM%UlK7ldv>E_*qGv%y zl1V)FWdf!qu%(tDH6VwAvJ$wTg>|8usR{H_2(Xz2_?HQont;xv0vA+CCZM6`cu-8C zw$n{bk{~@(uz?^4fTn2CJpw&(2Sp9)tcs}#V&w$HE{utKQxkZ>pJWmbYGi@Nf2vX; z^IE9EnhF^d23rVHiM=^yY6?2X4CX-`%_ma>NRtg>7V0IZrlznpOQ7HfSp;udK^$ez_(6L~+ zT2NX>HO&&TzYMGbl*qBDK=K$!1zHL*1?_l%`3s{JjnOeQHHF?10k#pGZNPm6jKMoo z(-cUD6RZ%_F#*q;LYf4qet_;d1}lWR0IU{sj@8r@bU-`Iwa77wIu&YaW&mkefz1T_ z8s}uNDQq_lSS_eJ0u{^X3pGs5j3JXIU{z38VxQeLHG?*m!Ae0BNGKC;}Z+hSt_IGl#EUFo7*)0=XR}WX+%#O@U3pIR$8H1})~$m7%qa&7iXh zU}Ye0fzmdXCa)RvCK9kZBwJCN<7P?ld0LZrPzwumzci%TW{&C!*s3~ECI;;eM!zb_ z)C_cbBP>yXQzNLDMd_ECnj1oT9AHP`SY}{qZUWt!0I~|y>%&}TU}}zB4nTc}*)TCT zhqM~N)*-7xD|^k&A@w~(T~TTQo~s5;%`K6F4B1e$h%$$*g9Ld4a|p!LJPFbR2U`lx z!Wrd|kT}NScd{s#bE|2_>e|ez#}^dHL5KvAm^Te?SoCpqD`}!T7Z^#z&lDH zr6^9Zgszy#$t*4bpT<{`n2FjLwFI5A0vf^tsX&`mGPQ(WPy^PEDVYSm+Xjauq`U@8 z7UUPiqdF@UGD87ss9@aaY-*Vb+2R-v+9(a)WR;wolAM!>dXIpqWh$g&586Xnj<(y^ z)G`fHS%M^sFeM>{5=au-peicDk|h%jAS(nR4oNA>2W=To&d){Lie#DyT?`CS2X6JD z%_*8DLeHB5SqVEM9Cd?6PqT1?m~iRTu=iSC21u?kH7_K$2wnVnw$jLX8}?H?t5aI0Xmu< zn$OZwOOi9dNA-hy2+0|xc_b}1&1^I}1AiIB6&K!tH}ChE0;rYR=1oG{p>&QD6$d2OXeQ1u4+|+#q9N2BJqwiUs62XpkCkLlEQ> z&>B;8vn(K|f`ioIIStA*#S${m3sMJ~uFcO$g$#7zJj}^7#S$`T2|n#89&%h&0qUMj z)09NW9$KiepxlUFucaUz(*UY&K*u^1r6%VjW}+PXWSRn9O9wIv+;)sF104m1HV~Tv zy}ARW3dJ9&sVEJyJ|0;WMn@nOx-t~12<-MU)YO)02w9_utRy2BRI# zQCyP>IurR{NXsM}? zQ<0Gk1J?j3Mx{ZI0zp;?Hkbw=5La=!dXQFjV)1X5@D5|j7nhNR1fRur31+UWprCDqXR!q~N zr=@~agRKT>0jWlgJu?FXL>mC406h_y85lvDz#wBFr(J`V4Pp&uGXqeo1{!)0wM8ko zR6@r35vGDYgW+d00~4$YL2f|xhbd&cHNrs5^kQaU206z7p{TqFhx7w}I}Xsy5ZZizJ1-?Q2f7L(9)|`*eGk`!k;e?p5#7<^(xS5XMATKQW`-7! z?lQC$m>F6^`pj@8>G>ttybQV`1{xP&lhCUWGegjUc+jK>RslXB7&Um4 zAnQNjc45hD;5&1n#(+E=4>Bt?GbaahH3F(>$&evA@Cqqt=tCC#fySFr+V*CK(7sw` z9_ZN1__UnN^bD-t1YPM_qM(QCOg3xy`}M$Otk) z2a0QC+fj!m%#5Jdt|Kb}9Z{26g1vwRT>=T3BZc@J)N%zku(1|5MrM!^aqyZL&~b># ziFqlIEdiOiiRq{*#K;1z#)WzgOAtUOK|wwP2Nv9XENVg1l+e_S>_u?98*NC=%m~zO zg61)>QSoV+MY-jPMW`+{1~qW7mHjw58C2^+A}mWL25&Q&zc0Cx}1ZS z{Y}guhoOP20(&ecHKiClkeQi>8eb-$^)S%10tzFLy;#H31bWjW%s5!JgIzK7{0Wf# z1*OFqpsP$0K`R{5#!AdgpljElSHtF{reGX(T<0j+7k2uA1$=}=oihJl8YQR6HPx>2(z zAJhnn2Pp#A8}XPs?#)b%AtTnHZ~-|FDXbL@RAFQw-IS)Kf3^E$38oeMlHHB2r zkX!^(h}#X&4Rj!*VUbx3HXl80n1T+jg$8D3UJ59@^NZr4mxZAOf*EMY1F8~MG=P&F zs8B^!2|d*gWIH&w!Ifbzr_Icg3_yb^(B;M;pFwAVK)D&E^JHdbf#`gK6oN7ts^!oz zS!js_Nfw}FiFWj>nHjYDh6E>gj2CyYWR?n<%Y`Tgokjtg^9DH&)$&y6SVeIGXp<&r z{{pB#kD|uh2+^j8tmpNrthgvSJ~cT5<<25A za|_6k%5aOpyDa02i%`Zg%*>GnMPa_c3?ECxXdw8?uEgYQ9AT3PIS?JJ3X~-?QWH}k za|5U`1KoZBO1Fg7LiSsM)PlnttO26~XPyML>moCua61D8NFh=tYTs=xKS%4~ZXr&KV0Y2vsRT=1jWn@o4au}YpWC6XU1RRpk zMk?5X%)EHeRj{bWgKo3{-;j`)18R1pKZAXQM8mK0^CmZhT2jF=@FLMG}!15;pynJJ+55=KNP z8bJoQK?Z_`#K3C7jzleZ5{)5aEns<2@L&(gM9}T_Sp1GUZf%xm2H7tMvNbKUpg10E zEH-P+AlFHQ6oS=&A`vCMBtoZ1z_OsJ*8IG9(BK+o*_jAk8w!oX+?3*y_>#n=oKzfM zfgU;yvKm7RsuPkC-CMA!P~~VN9f`?^J_I<1k*0=`T#ssW3UogPB!r;;14Swp|3Oa~ z067?JK1em_QY>V>sHTHXo`P1CV24A310#%+3=u06K!*;1E}eq<5!(e#W=Wv6^H6hP z>M;$4Udjh@E_hctwtI)ol8{;lU{%mAKw)WWG0J?JSrYV=JGgnc=2py-Oc8V9U^79h zATXNrNzipFaPz>+EijdtL1GB54C+8g9|dWtKWb^1WR3_@up6*;c9TFSv_Z2ISQVsY zh~C;tvV<&Ngu4N*46{X;WC_`n0auITPH3~FM94|oaD|vLm{@iKzEFn2;+6W11LL|qh7i8vx`pKyK^URV`A-&F2s0vW2hU%15$ow}<0ouM3vm{XV z0WE+7-ExI?tb|z-^q`KU+~oM;%zTVONO?wVe*L?NuV>G3XqZ% z$}uEn$p(;V5M&MDHWA872D4<)mSE6**-(cSl$IbFiJD524I#r(FeA~<)i6tjHuGWf zAUA@75zR&;$bBq{pp}Ff(EGyBm85}}Uci)KF$A>HCPYCGq#`-Lpb}J@C1#);^I-NnZ@xSKY{iZgRXf%Ngm1OX5bkmkUH@B zi}9IBs6|pT^tc<4ip=8pGSEdrhVhUU*{Gv=$F&04Lr`6k(`6F*cu^RQWRGGwg^ND;_47{}n4B_~7Lj4&18EQIP5=&=?c6~$@spn9tuWqpBJGUz(* z5=de#PK(bkD9OyttOA{+k(g2pS#*dR5h+HH31%cCi%?TY3iQG)s0wf*L2*?IauNdB ziF!tlSqf-`6`Jfpu0}tm$1DYOv;=5mwICOKc}RRQ^d@ptYoJSRz||3?nNfndT;41t z1=89F^)+DTfQH0SPyR4V0hQ7v3VJBYu=ZwCQX$7kqS}iYIVqrHXh8J`$QM`_CZwc6 zF46^?l$?=RT$~9ye`Agw+eF&>M?E z$};ncQ;R^$SBlV<1e>KAK^D(|ZG|XBE1*(MA=ZIafC3k5`y~~$I1(0};0`jzj4kYB z1h7G%u0O~y$e=04UTw3~L`bU%i(>4)O@fpPVD(`8v6u;6bp%!evK-WuKuK+ z7K}jT%TrK`{50s@zu@(wIFuMcR^xzDRCx;S$~Vmj()<7i4#-95o0iSeK%>bpe}hy& zjv@eCi|TvO84Sn@F~T{`7_tx*Y#Agsf-fw`JRIIE%{UEQ4S|({Jdu>24+_sx)Egen z(o7+{5a8<4%0Vkm(u-1yLDLo><53-H23cYWRS%NKY}Tbg_qBo*VQ(9zSwOu4Z9!uC zH3@RROD0r7Y6V&bO9O2|1qByW0cfVKC>7*QR0o6ZYe7>6DI!wx%Ted+(?H7wkd#8E zDluna)1b$E=&}5XpkgW?lv0vVMt{u>%pq%gVG5GLHxiZ>#22781I-OU z2XugHI;cs>(CREFADf>*rwxJ%254M^4)}o%mLf;CxdG^y8BkX&vnVyMDitGTnj1jp z!$D;WhOfQA#9ug-F(bb zddv+iA-y4(SHa^jmB%b0&5b~t&_OdB5ECH5h+a6F8$l0zhMI$! zIE_Fj4MY0!=*Ksj8(A8Fdye4sS}5H?b0bU0>bQc$oZQrs5^QCP5%l8sjKrkGywoDB zN|GS!1VE8dT#}!cilt~W0v+83S`-Dz_@I4Cs3DmQ8D&jREGo(@&dGY810MHGEXhpDK`m%O zce#S5?x6;yR+NB_7l2-#9iLo~gVHlGH#UTv%mP)8Ufr4-8(D%^0>I=!4RahR!Pp40 zH3?ZMmSkmY3~4Dqm8B*Y?HMldFF=+b^XecH>y|frK6Q2#~KA@x>W9SZ^B!nW2POG^w^hg0D zMIdW2va~U1IU49X#>CvD{CMmOl+BHycWLK>6=kF*7L|Zjje?7ERHr3F=A$7Bv9`v{ zjiEPgL)3s;Qn=zCdLS=EA;f9e7e<>KgGT@0z5sRdK-Cqh)1VubAf{m!DaO#XA5i(6 z#FDi9qFgMA2)ecyDPS?|GJ)=WFHFrXjVF{_Obj8X)`JyeGy;~4dcKjli817!2;2&wmrCJL0O_{jQD6ivaMM5yos87vZ15N}>cyw#CMJ-k zA4pMtS{k?xEkPM0F*h-V&H<&AK#ssJNklo=$lL_FNF^R*2xO%LXl+hB#5|PPHZg;) z2ZWggQi!U;98#r%4FfN~D=tCrdYhX-SF(UC1Wm=GngH4j1*+>)O3X~KhCTFV39uC) z2jnH@rpBW+kxW1%ZlD@C1zYFe+{6;P)DXI^4m3nnR9uGYkVNRtF_33VbHQtpFx5c% zKp>wKmnMN+0}Z!$kgIY~$A-*Jk}SbpI;IPvaG9m@?0az_qC90XwL*PM5Ku0R% zm0)!|=!!6?&0vF|X)LJ{)F3JVon2Up+7vN0M=B&hE6$O0U<+%|!bfBaAjJk~dd~BoO9ym$EHsOQR#2p)P2`)KLPy_0K>^wg1KImukduhI+t}RH5^`obNL?Oi z?OaiQL241|X@TaZpgoWw3VKirQ&Qto^HQ(|E$Ey&xX%kP7UPEMQTgM>tAl^fjh8}|i4(+6z{N(K7 z_}t9m{Gyc9BGk3v=4Q}Ma$uzeiOJaz<*3F%Z*BmqDZ&%WW+sru2w;W91v!~$snZO4 zU?h?}){4dqv_T)VK^^2jh&l1aB}Jvlr~^!9pi`frfdxtt*y=Si(AsyX8qf+3tZK{= zMI@+Efl*hO!S*(Ts-{%%vBanW1Z~5EoSTxG1By6Q`6N?#O$c%*tnvg|gkEcc7aKzz zjHDLTyc9@R1!^B=iZx4tu5d{yi3jc41KqBOI_hSYhA7ZM(T-xixdC*8J;=W$MVS3P za|6giAjp0ajJB&ebT$|w4XQ6N`V8ivr9>ca=77g5!OPQ7-2fWUhA03JdxQ73WTv3? zD$SvNyEM>}XSDW*xiRGQD2OXCCUwls%^;IM5P8h*k2&;=FNl0`E@TuVV{G!x& zKmPzUNel46Re=TQ)XdcQ^whlgSv?4EfKUP8=}HJwIn1TH321p#v4KVlao^8 zD>4h>!Mh#fi_z0+Vu~TygT+u~pnxw8m2MARxae)hHO78qi*CBrEgs zi*hk8H#bi*hAh9R$SiOH-)s<)pA1nCrO}zVkFx@;ee?q(HPt^fSCkRRGgfclZZO3kpyjs zBP&bINzFyO2g5uGbSyNQomhq>lAv>pFyp|rQE6sg3F>*F=1HJSevpgNl{{6 zG5C4}EWN2@V@S)TBD25^bWZ@btdk77y${J3DXE|{vg5J(!xS~gCKiBp@}P!^Ib^sU z<~&e}FF`9GlA#A#!PLMuFryj-y73ChSujPYIW;*6a{4_eMB@wc3zG9o^GZ+;T{H(D zQw2J<5LC+MfG#yDE&;9SMDIE$gVu z-oUPcngohX42MAuF+o>`VH#ur3Rzh}ViDTW{^rTakiiOMWy$$@C7>Z;P!|}r&`C~) zEFZ+FIzF``xfEmTzj-ofe>9r^VYWbKgi&J=v{((7^85nS8II%>$dXuWZb~Z6MXjWg zp|?RGD+Vt`KyUISgN`3Yb3$ewq?eePpNBfXoeb@uBb$n(80Ca{^JHlG16CaF=ou1> z>UU6E3}&&1zrVL9nl$uYALQg#l!&4x1$6BM%m`>gN-9c3t!`5cFbzu1EyzqlH_Q+- z%9Dyv_ePkf7-A;f%$)r6Of);8oi4D~p$<#TDJ?>+jZ#2Yh@v?^F(n0M&!2e;XpKEg zk)NwOY5*7`B?;dkR5|Eb z#TS?4qcvkwK*uw|T<#R)=;?^+K66N?18h>Tv!kC2nlzHvpcW++CFUh(U|!Z@o&s8_ z0V)kkijq-JP%%#douC4h%0LT$OURH_aY<1!TJ`}SfdK3yF_gA@SrZqM_Iybo{|P_ zx|I~Apsq|dPf3G}0cRGcWTvAo12a#7Hd-=^!Pf+$dOr;^w~<+lIXaqZ09mM%SzLi> zXsQ8Z^=V0dPJTJs&}*uJ1-Lm?l3!X-fFTEorNol_Oca-Z7oUPwJC&d=Uo}sKo`qOk zQiLI81Q}8SOO>LmdNofqfgHA0l!$ubgn6n7q=7+aEh$SXMb`(J z5iCwE!H@zSG7ReL7nGKumb$5_kX@YxrKp#&nWsXRW~5<}fvh$JnU#UoSx8NT4*q54 zq~@WH`lUjrsIdAu%>dHq$}Eo0Nlh$>uS`WVI1O5DrRRdyvc;noN@<44;BH@THb@dB zsMCxg$NPcy2|@;PFh?xYOdu&3p$63m=n0shA`jFSM3pp!ET#bsmlhOfW+Y)T-W0Ou z1f-+_+=Ip##7~2s>RMcoS(FHMW&v8MmIgW>1vGO4+0~Gei5mN9pi@ymQ4G3o3Svzf z=&rAfOw>kB8gy$F$Tgs$JyUnK>!(iKs0c3nS1#0L)!rC8*AZ zE)Rnq%7N)GV-rZ547AM+i)G!+u>a3vsy`ab--VkLX#KH{J zy+V;UMYSglyp9)1KgxYp7G{v^o{{8Hj#>xFn<$`|kD4*eAV=*Y=|{OP0i-_}MZXbR z>_8SZBlH`g6xbGKkh|8AK#e4io_@fS^homP;Rjwbj3kd9e&8dakmS+B54@!dNgh4?z#F`g4nK+RF+pq+wna}5np!^7MV*-3^5sHw@^&>Y2N)U;%7 zXo(_=nvy`v$ z>|S6F-kgwMfEpJmreKeNRaoFq0d^=<1!!^rv_Cl>)1X99h`Fz#z*ra|6y+3yub{-D$ONGXWEJRy zMeL@5GZ@^_rpAV-**FDs&QFm-K}M1>rY)c&3ZQa0otp@bC9r;+t_AG|f|>(zC~kG& z#06O-ic(I1@2o&hxfZ5qsUI{(fULj_txcMemfKCG_QUG<@K}SHNT`FUd0=fsRNCCV~DITI*xVE?S*L+3A0#`BQS0WE zv{W<`EYXS|NJ9wP8Zkl5>Zt|>sJbl-P@^%`zz~$&5cZ=N7O4itXeOXl8L6NZh(!u% zMaht24JALM8h}Fx$#`>A|EC&&%OWHNmgqi6MRA~s0a_%af)1xbibfLyBh&y&HAM5G zC3+Ybf^!4h4JHO?L7WO{mmw=ab0p}pLliflC8bnI+YMoYp#f@AN;R}V^`@a2x)qiv z3XDzA@>?qCTmpDg%NRAUr5b|MA?Was87vJ!3P} z>afKHX!xs00aYEuVl?x>ZEA!%EHMF^C_*+0YeYaxdxSwC4`2y3XqgUImsd~O;aslyT;(6Sy?9hUG&H3T<5QPn{lh!Sq8hTt5Av|}1; z?57%nqZLIN*1VHy1ddlUh1eVjx{s2fI3lc>4Rrd%DC2 zdq%k;TLV&Op@5+dO^F3)P|4RZB0kj9FT~6wJ_KDJWQ31ra0uA85QwFiHd!Pq1Sy2O z#fSR`1&72tI|jRg-4pNT=!|BdCCI{Xw|G}SXU71rB6I~N3PB2v!M^c9!6xxOj-h_e z9`R10ZdjFq90zi|vxjGZk1Oh0r$hsDOG||y1(1ALfJ=NxWPmHmavYEXkh9%9BV1kL z!9K%bPa??85M{wW;qjinj_wfup*cMf8O8szGR+r%W08$qrM4hV`5a&-^J7GOyrYmpV9c)-vS+$2iQ&nrts9a~H^ z1RZEsq>z#bx+5yJC_Xno4|NY^qG6(WvOdyq7=+FR-z%KN`~2sGQg2&m;x?hVe?WLMMR>BsSzkLuv}%7Xkuz?hCI}p zin{D1(G=8$aZv!RCCbl3sh|?gKvF3RkUjj#Xp1XAvK9((SZe&w35^! zEDkqJ134+Fw73LxQw_R>8i^59?x_3VrDON)|I(Y1qvz9cC=qY5>;KoxI_0_fH-(7I>PHg(V{ z6f`xapg;hr0iTP9MS&SeK}J$h3Fx}4cq|Ic;R--U&Y?Tb0xS!@Z#NBXXKbRGaT+MD zK!Y#-0ggWLLC*1xPJaGDz96=%lfOS|m1724L7AdZoLEqhky(@qxgr4dWXwb}(4E>T z3ZS(*Mc@mevAEd85M(Pv38sHcAfauP9G_HLj7_&ONH@6tMvn;-aMA-yfv=kd&ENDSTNssS3EB>i8WkXWgCqT% z;{#lS+)zT<5_CWocEzab5)D9sg6zmp$DojSPd`u8gkT988%R+AouwNOaw+De-iel= z3umB8lCjq&mZ00ZQxpn{Gf`8sCFsI9RObc+d&Y-&`nvjuqB{g!_8_|$)Pe~@U6q|^ z3EIkCFqhRsF~&jRDw%TbVp)_DrosI zs=q;=aYxIAmdWPmu>?|vo>?tHqYc_5nGZ29Yvg?kW><% zl$e~2-Y~LE0T)S0B{)+oXt)K{C7wpk@gYHue!*_8C`#4gqDsAlE?DtO{yhVw#JYrc%He1abgjK~W0&f&7Vg}$6`^OlAMgXLpaegCCNYmT_x;v?UIW4q6$nM$(TAIhkwW8 z(2#^*qMa8HmEhQ#`jthmzf-MADho#Yy2)g$Yq6}237v!V$1ryD| zbuZXo`FZFQRf&n9S$%|dNG6U)yT?5-5j2Q_p$hdv_{2oe>PrkosLNdw6U{M7tDq3) z_z-{8+BwlY5mY;ajz$Bu7BEiJOiVOSLJw<@IT+P^qIoh%9mxA2!=V1da8wF<0qz$T zbT7R9OPMFK=67K_tB79%GHh)T>BMxuEd$g`MAF$ReeK@;1MAch<;hr>S> zM%eAfD2)<9r^lu!z-IuVCj)?QvdKj6^(2DMCV|)v*8p(M_ z3dNvHOLOy6z&F35x(Rf!Rf51rh5UemXAizHewP~LS8gRsPo>QnBYUd`=5?WE+{szkA);+cBFh=edAq&KnVn`1W7bN_bE)Ni>srL zk3U*4CxR<;P((pp2u-4>egN%sL=BSwM?Y7ecr2xSBDf;XF90PzJ!5mU;nqaZ{UFdG zC(x~ykiHOT)d$K%dtxH!fL2JpK~;t_VGdFTP5_`=5x{3IfUlAP`3AJfA7VI~Pr$JT z8ZUwzlLQ^0LQ@28@*^pNTt1ARi4s%6^$(Kesi;GOiJ-w{h%Z3p1K2=pg#_sA;uHn2 zG~{fCl6>$@m7r0<6l}f#jZ0(IfYm!mka`m2PPp-)Fv6}FJkSAlO98mVFD?L`K%9%Z z>oPGBG;faG3D^S*G$0NM3h+IP*m4T!>^q1O(B+9(Re-yo;1zn<9d7|j4q$mKwOx`0 zdIQ8I)HeXL!Uo+dfSTID>M%>Wq(r!Npp1)}h(Ko>U@--=vPl9D34tO6ezhM~zk^d7 zNEz6F5G5EDK4=937F&H?f|5F+&ryCIS-u;9Kr+crY2!fyn@kD#Gei)W8QVn?SYMGr-p~9=$u8 zn2b@SLDdDL95R%c2)g_ii-9h_j-X-~TvKCcfw$1WhkQf)gXTQQ4G*Z6VSy8 z;KS^5@=^ECCMJS5)~0~h!5}MwY{ZW*NkZ+fCZ;BVrZB+!`ZFQtgn*`Sz?U6D4$(pD ze1bMIxhNp3hg6x^6@%;5c=Qd>iHV@4crFUXB`Kg(3fh-|66Q&u*(k7derXA2^C=0m zD;zAHnTJgllKL`>ic9p2jZv3MCMFq}fcy)dV}gy^f=X|+zG@O^DIRF!X8a4xLpRG5dt*~^K(+; z({f6SQI4KXOag7INKr^B&CRU@w;w^uz=p*qm8PYo7Ga(>nwSKcXM;}ifzHm)&%r#A zEHTLd+%ZNd1J&ASP6T&(5h}nIqbUJb;;8NeO<7DKuyUJ)k9$=xGCsDhrTqnDbzbcWh}5 zv?0bt0d#T|R5e zO7ILATG9dSvPyv%n~{QYU_)XO=;&0?FiCL<_-?M8Y%>Q0@*bR@NG6q+ANr@@o{zz&O#152|!ih=7;9?~=u`($& z9(2Mm$}w7rNygxM36vkPdL5i7Ky?Bx7)q0g?ru*o|g6xTpY0f`;~s%2MMq z%F$Fn%L`DAo)eG7{h$qcE()OY6(Q$4r=lNdo|t3;u3EshB<7{3#%IEpsi5UA6L1xi zn34rrS^{pYfEUDIwH92AfXxKkh;j2qViM>a8t}RwSgI|8999}%npawk)?-crZEQnP z3`!6wCGa$k8Y-Y&ZYZijxfx9fIN`*D0wpmgGacnRx5Ok9aGHsa&&3v^;N%jIB|U(a zKY&WSqEu|!z=JNzl9tPD~iy#jPHkxIn1_VR~K>=d=HvAhA4p-896!7438G(plM+j zg_5Go^z_ss@SXLjz6Q+)LyN8q^yZ?F|C zv5P`tG5F?T%x(i{M%YCGe4GMWh=7v~D29qFbCXa{nM+JE2M=k-gAWM-)lO)7Q$Zuy zX*r1{C8>Gwpc{+wQ_$)Pb8y==9(Dm{N(ox=Y+(Qjbm(zBn6ltuLvXqWxe#*SW_(Ez z+JJcyWJ(vT4&0E6FUikFy@en#2{M@rRs&kq3K=QKynik+2{MrjR#=i+Tmn8?0M*|X z;6wmX0WM5H(T%1AoD9H9KrLWw?g6I*unKTL5nC_H0$kX{$AeXYTEL(|Ff@z6r3|P+ z1Xcv3gJ4wxE>6Hoic0gqYh}^r;FBy3KnW78 z24n=p^=SDIG_?x#B*-=3vjM;f0zAc%iS9B>aE%5w667+1%E8?t(AsBk!4FvgjT#)5 zNEKXaNqhxH`^pkgv4K)O76ss5QGo@x(2dVb!8olVF$pr03axPBa}$fv+J&G~O;Z%W zhxcQXwSd}aYwPlMY&uq2FI88}sy<`Gs1 zPE*j{2q?I*S_)28pjggKF2+)^Sb~!jD2ze!Snl^qOadJ~;GzIB0-OZE>%u|7fR?C0 z^Pw&Zpnh5jsK}4cOh#Q|l>|DVz(pZ5xgfqcH7_MT74@9Y#3a!AQ;2*)QECC`a_IP? zvhvKlZ1jdN=oABp!t6}Y5`NS>0uz%!t5jVS;Ax|%Fdh=gNoY4gBqo8@twP#)1)u{S z@=CBpFzAXZRO3JgJzy~mTv8Q4PU9%a2d7NbWDhzU0c;W|wo39L&O%cHPE80y(C&Ut zOae^KWIDvqT07o&V0&qhaGz$g0=Nfh9KPd^^*+y1? zws|WFblGZ(0B0FxloqDU%|Q7OY0jCRaP+|rYxL5%hP@J5Y2fB$IHTi??@Ica^ifI72SOFOT?Fl8JXL`_9e25WX zD=_83&1H}YV0jELfNs`>=!dqXL752Em7rDS5GC*`7}FSVp#ri7siMYI1#TpRRDn`2 zrZl*L43aJ`Nr^8m&#bD-Nd>nH&^Hz(K^BFBl!EKwyi`z1&rD9mQlqCps-fge@SG3S zm!LK=S}6=VjU47pv~$rDlR%fYK_o%p13n@ET|2ln19B1ej0d`K3St5{tzcxk6maVW zq@Qpi2kpK@G7D0!rN^gb=9HkfRa4+82ozBGRHnj9A8^ho&IPxpQIi5_fjM&SDoO=i z{uvLt|2!TtE{CQb+)@U43T!6G2`MGuyFXKlN-*Z#pli;PGr{4DZ4?=_<{aX2uz8@6 zM6(c4G^M43*JYs>vY?A@AYK3k2DqfgPy#EEQXvijCst4qke8ea9!)|k5L5qbl^RiM=uS88u1}zstQU*#+ zxw)D7@sK4ND7GgXfD<#^c2EKVt5401FVD0v#}lHIh&hAcksC?S{HmBN=kK0NmSz?PfL0bkoe3(Y zKp_K4SfF5p9GQ=%95o$+d1JVH{Ak$cgVBL>Nk zot~Unkcn{zYGN{EaS}W%Kve;n*HDX9uwy~h3ie7q8M0alZXQ@Uj(R)U5Vc4JnTlGm zCWF>0A$c7f4LD5$CsKqGP}d!Gf-D)bVhQdzP)LH*qmSk$LzXL{r~?;$7~{Ulpp{EV z4g}93ftOIC1tK_+g3QP(EdUR5Vb=4>hTwWWB_BLFUjm*ViZ3vS^vF=xmn4IhGPx+E zfzGYN5^A88OmJDyTnnmWAS;>DQcAF|bV>#-WlB+q2hB1ez)VE$7M4 zM@uS@B}$;%9&!ufq1RKR_C1mzE0jQ&9F&wKCTGMKVHyJNoj~kBa~pVc3?c*SA)%!# z&?+St1*o)9VhY+yrDV`bC9pg=LnNXdo0Dt=?tY|{#DkjZpoI#cfJb!zXt5I51eg-c zfCnv30xN+mn1OX5(83Y4HVLc>G$;?c=o|g6_rzq-3MH@-m^Ap}3eauuXl?>`XTi=c zDn^SB(DEd(8K69YrVZSI1#8O#FU!C-ew=I!p5=k5g1H3EByb4=N@_Ud!Bae-7*9#T z6&&D!F*GHhyV}wBL?;`=5(lV%2D2|7bYUNwqrgc8oPSVMg2E3iMM73FVJa;(GeK7g z9+1aWiEX8JvN5e01xqPnGEOJ6I3B8pAI?Ef)Bx55iCc)Ak z%tEwafF(GXG!_%UX${#eDXD3gi|LY0z{4iU>OiRx%{p)rLsx^vPIzI3KAW5jS{nte zI+D>Y(M(JR-O&mT6f9EUu4YO}d}>7jX!$HC-ccO~S{nt{3{in52}>`aXw56lO+p*q zNd}#l57wOrF1u5Ui{nB5N6TZNl~GVtpaq9mmB0!mkWHXs9)0a*vMG2REu{pUez4{| z$bu*wi8ekT%aW61$Py_~EHmbgfWVEhd{H zn&I#P&D4tIc*wLSTK#7VPCKBrtOejf7tH0#$)?~!2{K_1Di=Y=6rn~VWcd_${EQnpcPR_s=#;hfmX(&ISJeygS$C7 z2eg?dH90deC%!x}I~8paQ!;3k6q2D>m4MsOa1$X5m(VN)x1`}pz)k~?KA|ZCH=p3j zK*5d~`JjbUNG<{ue4suDc!hi}>J4^@$)L4VNQxoL5W#y}L6i4rwu46t;I@MlfEG&S zgVxrgPH-kePTPPh1se$V4{XX5ZNLJw_{s&IB0*=nftr7*AkX2_0WQE`HlXN0b2Yg3 zgDhr&T_XlMrwC*=s!GTLElic*KtWRqZf0Rqindrb8MI!@MFCSKXk9^kacT*AdIGK8 zLJkQ~(THX@IDx{hc}Y%9hRz12r^p-ToW-hy^^@hStSPjK%UqzubKv1G`p8!$Uz zSIb~7c25Q^<3h3$ViwwfhXuHiUr>~vl#2D1n#5!aa0v$v_jqUt2I^#k59~t=3~)(T zlnNQ$0w3*%wxm88vV04?!~t|QCVsWxf)5-NppqdTe7Xvnjo_jWtOSyxv8e&4Ij{t1 zI4cE58V0T5a#4UN!;ELp>a7%o7)P>r~ko8&+?P>W%xu|z=CMH{g z8}AT#@QgO9M<9!{Aj=Ojax)<-$k3F4D@jNLA|9-!A~_Y@U_eucNI?k2XiC5(Tv2kli&OfSZf+@K4y3UV{!Q&Qo!qZtcM zGhkzrb5r6|^7GJ2YUrXYkRfm*;z5fF(aZs-9I!dXxy7L6$*Fmuh9;USaI*@m3f^P| zZ5Tv9A}$%SHVdq<092Wwx8@+n2qqyEu|T^tK!;MsCncw#l}3r+vL+?5 zBo#CO30^mpi{?sj8B>xAl7p#3Qvq(E7o_H3>B%L66Aff8E*_*LCm*e{ge=4=$j{FK z^+C`~2A3pYIdB5cPr{slfvm#rG z#(>iWlA3%_+C~rRBybxXWEtrGP_zRvk|FD_K(dJipoO_uM%p2(u#l8sMI zlD!};5H!bv+t*;fUQCAhXcy04I*(1G6`xUn$N(A1$^LJVsb`mJY-ck zni_CoL8wVbTP~FhT6*Q8fT94Da>2y~no-~x4al*;kZKqG7J#fvnAfr~?(|Md(wjkd;|51v#mhHi63-n1b|7(0Xjta7h8zKQI+| zT8E(HI$fYgIYR;&e}faULJJ&N#i@D4`9Fbib$6+{}^G{iF923dcFq6&1kJ2sWjm7ox{m}wcb)(SMB36aN= zkReO0AktX0gOd$J7Mo^pdj%p5(u}q}H8~Yr-azER+A$P>QwBr<$bk6dw8UKS3Uah9 zTFIaVRW8s_hi&o#-^hs?{Hfs93&cRo*i8jjQ4m?sUSrTq6}Cepl0j>xV7BF>?w?48 zES3U|l7Wukgw2UUwkgJ!q~)U3o}kNzK;0I|(LVX_1 z0Xi}q<68Q}Wau)fqD-Vy#jz;^7d|joLQO>7ft3teAcb&RNq#)q3i0GLa4iNi1XSV1 z7nh_K#6#-FqS8E!gLji5>!V;=AQzs4!U@)%MJxLtE2Ln`!5JpLBni@pL01ayRKb*j zjxxk>F1SwxQvu(w0dX#BI)SW)f^HtgcSd`18n|?V846lo5RcvC;4%uP4(gNq6zpCB z_rhRm!Qq;lh*@Z-fvY{3GN`RseFHAFUSYN{t|Pd=dI_G0Bj{PT;Hv ziaxkX(7Zp|f~yqBiYJgkAf=E-1@;r~Qy>eTU`mTqOX5pF7nhh|uIxyGEOvq`t;|b~ zFV0Css~b~5*BF8tYmn>(8Eynsw3T_uC^4Rbw9=_46&&QCb{lBe2~8ci$b(r68jCJV zEy9r|Q$UNJ5Vk}2B!Mz+PJTM-v~`LBxGaR3i%~YEfEGLfR0acQ9w}$S_G7oh+0gg7=V)`xK@O%x&e))gVbVKFqDF{ z3<{(ilsrJnu`d`(0j-E~Q2-65!4zUPU{fH6DuEQi$_g|ugIo6ydGxh;DX{fUNtn%# z6hm-Pm|u{D<q&a0w)x(QD7&bhA-$!I;auQ5*U3$ zYYJ!u5>yGup`h^_$n+wbN#Gg}Y!B$@bnxM1Xez*U9asgl%mW7$crX!7CAe4ts{|_n z*^8zET*-k|fNaC&vlP&lRIm!L8Q7G7tF`!eu%eWF%qN;0&~y=3g)ij6v$CZp!%V}95kecO$oT^1Xf~!%M|cr8&nCX z90x76MRO=P<$#oc+qj?+l7fsR$Y>Gj@OBF5d?kppK~)SSL?H@MmkOppRxN?d1hp2x z`z=6?F!a?;DWKz)AO^zKpg9g)0D%mGoh1QMh^7XdjzDVQ1r(YBa3us%0BPZ+6{GH( zOo1#*0x5uGcaR;Pww#L0)DFcsnwtC&B$bkQz{&q*j!q7Ud=8fT|-H^7Q zMhj>SQwsQ!9nc&PsG!3*Wj+P8f(g`^0!>J#Mrc zAD;qQ!UQs-0MuOppHhP!zmP>t;H(GjFM-x=fjb!S`N?Rp3|YPeHZVUs73?f5SB|7W z)-QpSfqV#=4g&G8Rv7E6xN}A*iup1|Ee1%Yk!CL1vN> zs5uP|eKe)uAqB8fkP1+7g{A;Joex$34!3xyVQ8wr&1$eJkTIalj-~+ISb{6S(q=FN zS9xF+I7i}AAWM_Lim=!LE`-36*vtnvropmULKECBN>0ryNh~djPbahrzWUsP2cVMGbS%>LpM& z58^3^Lop2jEnq@dg~d&vHB1O)uqqomhzuTALbDuP1w!2g-E0LqaRW3YjZHbYq=G5O zj3CfDCKrXg3d}VfDdynXFRuc2vQbf9I_7%a6wuW`U;`l2hw;fpl?5gF*c5`RJ%n)< zCPvs)L7GiXUVi72c_A21977g#7tFie58(P3MwLD65F3m!+x zFGZb+NCB-ng2fhSuUA@XUNYKJp%l=%BbXY*c1O@k&cvKdv_l|LKu1VnQJkBai{VOe z2!#tWL>IM2jfM@H!}=fW~Fxv25Q=0WCs;nFR_z zw7rBWkYz{^H$mjlw@apg79zonz}U}+>LSpZB%De?V_9fT8^|Ihgzf0tFjF8WNTDcz z7KUgRL(&^KC_vr-l@jq7eubnsup&?i09FK};rVte9xVFrvfYv*~6oSGD zWGX1|Q9~Vc^c1oxkdatafg5L#Fv@|n-mughpi`(|W`R`UFbh)Bf#Vq*%%BKD3pvm+ zR4|j0GxGC`!3VgYxg06=VcF!L0$Se$GXvB_#N6GV0$Jh&@fIlRAq5GxldMu8E1sZA zlQThuG`K#2R8FYJQm25{Kf$erCYSNF^O84#9n2EUjYD zq9`nuqL+uDl~FKdpv|8kE5YX#fQ&?+m4RF(1aTrrF=)LM_8s#npcPXva|An zo(8R*!ln$}*PsPdFm+f?dPo7CUAeb1bwj!gXFi3iSLduv+9~ zfSwGYr(i+U5jYzrB?;VTfcOU#g5beX)L?-u$wDZ>3^>S=EQAUy#SUmy7A!oHvB`rw zo=L^!i3RcK)edL@7Wn*=cu?5@%2nt|8ngxrRRwyWK-OP@VijZtIQw820;x_x$7H3Y zLnfmzOo1dLVj6Iubyz711sO@kpmV@LmVyg4w4eo#)Poh_DvKd2u)s<{=?D~b_^Mpc zVOTJ0300zyn~=dqL(?AO6a*}d8_3!$uyRm1f+{|+m*UZ8!;&G*IH=F#LF&*?RZM{_ z&;pwU%HyB~7wD}U$oed>5|GD1#-K+BXlWMIvoIy-X$Q183#tTUQ31y387V1{N)zN< zkRkY55};*TP{Sbg8OG|?6wm@KsFDI~RVQRY7T8xssi2eLL3IP#NGs^9ESMRfTX#U! z5^A~uostDr0m=@bQ$FJpi&58)q<~J#f+_;1cO0r9RVB##5IT-}>=t&W>ObcuRwBW^Z$X5zztrpY}s48%H`0RSIbF7E~G3;UK%v9fU|u z;7CEc86yR>bSp&xynX__=(02!{bcGC$OhL0Agz9ohd^dRdf)KT1W0S# z5N)goa?lmT=%ONMj~x_b=&2sEq6>>c^a2~QpbK3g##libqUJ<$Y)Wn-hQ){kiK-C8 zVn}BI&HEUG8Ia?vAQ2sp{nVQj(2aG_oB~QkxKtquIV__)sgPw`kbpp(sD;_EPK7Mm z0xQJQvPy+4)B;OG9a8|hKP0~_6>a(`6|`6j>TIM8juxP)kd<0s^FXNyM*}z&awrv8 z8K{`R)elMqt8%GH6M6ZekwPDAak3RLB}FkWx_kGC^&Hq(YWw zfn-68>(KW_q(atbfuupH1kDZLni3?3xqLs>5L{Y;B*C>TnojU)K9FR70oru~sh~Aj zF5sX}&dEocT>f+~A&>E~1g`^Vj`Fru;mGtP7m#Lry zSYS2ay90130#|OJ44G5{$`d#?>7_yzV}YGj5}yG&3K(^9K`LbRRTAjXr5s##f$OrQ z63`At&_!#gp#@ocl~e*cl>(#!O%|LApt3Okg0D40QwQ$bp{YYt0&XNFm0-?Tr-BZD z0tXrTvZGYUnNQ%jM4Q4+HG)(;7V)6{KA@Zd-SdNWyg$_loG3sitQ&z^IiTg^DXB@N z>6mNBQ$dG8rGO5S2N_&Yl%F17o>-Dvl$%(DmKs2(LZK?mMQ?1SLKa>@?M=%}%ZHRI zs6hi+cm-7in+1jKnnF_wPB>7dpkf+_GRUYWBygaWX)$KoJr%SJ3+{!~y!6bxRM7Ha zv@xSp&=M>pWuP++LCalG=ZR9GYq21fg8E&h#aM=JQlaayAj&`sDbOcpQbA`&!L5Vz zfg#4Bg#|c8LBj%~tUMn*l8hmPP7vFm>zUDv0T($?V?e{LXwt~(43ejzDGf~>ated2 ze!#8{vJea6AnbFGsm9=Spin1amT-^*q9Aq@6s3T&E$D=LRQG_EVu2QuWP-c|-RlP0 zb%Bkr;`2F^U-@gpqD##2FSu2K|IN{ZuCQbGMP z&{^s6DQI^_r-IgAfzB~12GvEN`FqS-6146LMG174Jug26?Np&u&>eXx;1&&d;T5RX z#Zsw4mR-SiOzVN7r37?rl^*IOcPeP@RSJ0bBc`K3%d8+afh+;Z$Cse)olXUY${~Q6|zE*WuO&t zXcj^$xsNI64XayF;g`j!~ZL}j5wDt-j3#$Kd zO@gI@R$W1qVHxL21ueFM%cf$V*hqyevjVvqbf8f|enBaC+b;O1ZS+(4Q$dTaASPlN z!$<`!wt~olj7mx@f|e*~!36Gd!7Ky~%0i+hITx)d4_a;oF%B{slANClUNC`b9AwcI z%s9~QV33g|MQB$wq(T;8!PLS1S(ciYl3xUBUZEKa9t#I42MsKwWr7xOre#*3_ZdJ( zNI~3~k_Wl59nBbU^BH6ecw`K-cmQ3$2QdJw088NlS%d{PqBt)e+%-Y716;*{6yO{d zOa&bd1+fOC29)A3Mg>zrckMycV5DC(3&FJ=$U;y*5M0)SS6HE`0@ro%@gQ~J^Z;6k z1sd}~Kkz>lvIq;L4l+7`wGcJ~H@*>yFou0o&2S_v^o=~JphZ{^kAgB6BynLJ3ZDvE zgauIray_*0OinCFOv=p3EJ15xgO*~YD8T&+N`l~2jT$77LL;Xoa}O9frE zhh#BK721GeDror?7G>x|1)!x^Xf6YlaA*#L7hN!ifz+V83!cu96=66F+?GQ2BgiNW zSAkdlfmDIgB6#Qp%W!8ZXc-o$@&ujxlZSShQz~TfRdEU0{`FMIBC9+MVQ>N}$N-)1 zhIZ;$Drg-QXuzT}zN8|)Dj9rm7kXa;w2%s-rl=x5B{?|}tw6Vcw7N4Yv9;botEWJ1 zqmuZXL~!#Nb$L!IX!#VxaA-puw7sPQ(++Sq4de&dYCjz6z{L(o9n?Rl(G6Wml~D*SI8C=t%8U$K8!N(wi zElVu}Eo)Cs1*^nT>_ApffeL)^n#fetxx!S)f+?^x=z8_|%wp6-!BQa$roak71t$8H ze5sb;wh_3s237>h(#Zt{sM{w~A(!qURDq1D$Sguv1ukUb!OL$zEoQXl8f1kO+?KLp zv^E1|breE7y6NDW3*iQkOLNmO+yG8K2vz7ar>UToPc8~zS3o*@8Rb~Ix}Y^rD5^3G zGO;NG&;ElA0|iN5eo1CpWqbkp9j2+E1y4}pKzkanT!5MiTI~c?0x~MK5X;B~c*E4~XfPxK_jltbB>?`V0 zp$nTp$_cHJONFj(0;vT#63ZNWDs*8JND0Vx&|E8qccE2Rk_k8igOs4noTNgRGJ#A1 zS%f*qo(f&T1X2NNwt>cls!}0SR;UpSUBd)Zh^u`EUBU!b2A_69GYQ;?E&wY*yVEfh zx@ZY3hnQNyHiQE@1PW9)CYi)zo6b*#E>;4WgljrK6}m_Xqy{|H0c!N2xfPP6Kq^4d zfM*FpD(EggsDnUCL3s(yENGRMWCEIJz>XXk8LCD3B5r`m|;$XmJu$ z8Q8zLr*u=Hi|fv#Hu83&3h98+76wM&_KSc)|0 zq9u?4MW9ov(3_6QkkSeyk2GP2<_JXELQ;dC%i*h)Okk^(KmmYWIzn#h1A86hAy7ib z)^bh;*K}ZINLHe?=-~^MOu%<_f^N!%v;)o2+z)LjC7Hy7wxVL(GLs5lmSh510Rk#Q zQI~h5!dE1Lj$1DST~G%~tEl$CS0sT$0CZs#`liEF_=+U35_koHW)5Uz8!1k}6%BfT z!`CI5fYvnNy}vCLzCsDrUi8?3uTC<-c7azad}Wdec+4t3qZ|_6hL&g^KqM+`)5-9~ zNvMuNi(SwHCGgBD*n8lW9vIW5p!G?x4i+e}pg9Aah;lNEAu~TEiJ55aTF8Y~o^?^o*LA&fgX*@YMB{?Ut7;Pp2vh)a~rW}2T zXewm65lF5GQx2RsKyuKgR#6eQ3w~N{0@(*Ud>L&INop#%{R~n8?xn<|w?`ohj39QTW#;5yS^+L!KnB42L!jY))DVX( zFaoK8oSKel2)NP$DJTH#-~^BMqZt8C4hVPP3KDSb1u_V_Sr$}A6+^-pJr2QX1f&#H z7=VVl(QE`K6OcT_(crlPNR~k>q9E&vKq@mbq49}*k`J=F2&53SGy%MM8%t>gSy%+| zD(oyRY|7wi2|7oGW#SUFpvXl5WFhwS0Xh!KMFCXXYj4mx3;hDNTz9_eV>T(FPnq%YPth!G{!KdKf%22J$ezLrhXZ=Qlx&LAt3m zIVUp}?Wou^&?+E^LQw68egkV7WbF?m0zr*Slq8%6TKWUgjC~$24YJ|~rOVGrg$!WfKA|TKvIYozkPYa%+4#)70<`UrX^?y5poW5SFnUFm23ZdTQUR($ zKy$Z6smVEsnW!^-X^^9uK+3?)viLI4c}{4H^&v2e%6Bv5Z{Q;|5uz;NfbJIV~KZolL>O3 zFlg}|uFwVd^Fc;IlosK*bs!D0_6VU6><=uy1swnd2@{BcV09n|pn3sx4ivI7Y$*h? z=m=qDc@YjzfR-IWQYOSsjPsMzKueC0RX_@M%#a1GIYL&4&4ci!6vQ%cS&hYm@b-9d zWpP1bQDQD+fF7+2lLlFL1o9+Y9k{=P?WFWH$Z=30#o*LYoLT}g8GCgMIui;K#$eUy z1XRPD>|oX4F&dDw(c%qJ#=*RW-u6m^tV#m866BNO%HnviE71&sCp@rqAeC5DffgsZ zD8NGoR5C$36yS~<`q^!1pjApp>OprO;#Uu^OW}54W+%u>C6IrLON+|l6VXK9?0WR6&>4AsK-!S3wpk zfeZopG#+GCYGzIj=+JmHv%r-mc>NJH3?XahK;yG$Ei1@^rOZ6gGMxCdoXqqL>>dOs zv6NIo%D`z16iCRH7v$%lADNW~S+oRF3BOz>BR4rdH!&|U9lhBES-J#D)}Xud(#qq@ zQj3Z+^HJxy(jW_$AnilYViVA6&eS4MTMRXDAd8rg-3LyPs7nIUAnTYwVGT~?5O>9c z&lg8C4m?VZY#jD14O!C!G7woUdesV9(1ff4bRJ12j)V2nAje5T{0!<9M+ zzza}7$JQk$=A}SZ$!F#!rlTba$m%ALTfv@(rXg&eN3Cn&rejkI?;{}l4qODIk87nt zmOg>(2OAWhmRXcrj(%)u8ffhkq{K%y5tKF1VhEflL8d_u*8xw=78irY;!!6c(;#c0 zkd%V!Ku~3az0L<6It5!=3Cgjc`-W0db22e@hNMB3Lm`jZiuD?-a!QquVd5+kc;!+Mt~Hd831nPWfsR5 zCuYXy@ke^qKmLDN&qcV%*Q}aMOE1FjO%{ zAq`m_1sMcp?PVB*;pu`1t&S_=3c|ROsp(9Qh8i>Tqs;Ic=up@aS_@G187Ya zBy3HkTdMr@3#Mq;g23ds#N}J$Yj1rTxaRnIoNItM4P?-U`NenVJkLGG{*#|cd zuTpTD11SYZ1K4QHZW!oNy%YtoWKk+;^(N*Pp)?C{MGH118@%TYtQ=hYp~nC`wSkpD z5+}GBgXRr*R|BjL(uxIb-2$t{;snT2Ex2bugC=r1z2(B$jUCT0)ic!r~}+-3oV9NAQf1vbkN!_h;<+(SZo8QE0E8@$F>%wCPOBrKzRYp zbKnjx*iDeK3#gn z$PzJ-DsZ46P01p;9L-?x?0Y;UXrNvL#UvK5K^Ba`O$R9kT_%LA70qmL3lF3L>}W_p zV1_MZ;TT96XlFg4yM59?i^(8y3R8~7NO&g$yq6m5ovLZc@Inx*2wXQ7L2gh)^9Q^L z1S`Zn=>b_+2J#75A!w-qXetcNG;nDMR|HPMwxf2iCUY?nkh<1T$8fe8C z#9@ggC3#rdZlE=1E()p1@#zJb`JnDK+8(wv&~aD@1)y>Z%^BdCeIx_Wq`@f+v=tNM z#Dp}^^0E|#q}=5A;>>)^6BW`@!08DlkA9D48f1AHOgb?m3A|1ZDG8w-sF4Oa{0dn; zxMhR3VgPbGAxu?4X$g{nXlW9%5)Gyl{j7*I$PzS|G{}9R&_lBhv=+@pArZ8OE(3bM z61ocTL@c=F?Nb2?lIUaeNu*{uV>%0lR1eFQ7GP z$R^#vIQu?>`vz(%4e11~TFDT8;$GxNch-Jqor$l+HYg~e&$(ZP)59JEC= zki)M)NolyzahJ*a}jv-0xFL= z^9osn29*YlbfR^NLF>>`AQ!fS+VsWHyOh!F0M}pOavt0k0Zp`nawVE7aOV)&6wq)M z+8Ly2kYlJ&RAFyUfmWkIT?V%lBSw-8AZyXUZUZ?BRNo*wE6D(~8V!0SeR4)(ad9T- z*qFSMqI{G>C&>V^E)8rDD1G7BVxD9GU7l7{3SB~k&GktJkOQgGib~@%^NLf8KA=HLwzpC$Pj2xWNuq05$`&gPvpn zS*`|FQ;=9xoEl$@y1Y8c0CEZySVegX_SwB81IR&CAbC))sw5s`WoD8AXl)wkDj-lI zC{IBt$&(B~tI|>wz^g1F24JcHx51&BaaE*A2A~CL(5MHw27S|Rk^yM_8Il6XhI_D` zsL30&2n|UcX6S;}pg|Qtavk`_Wz3V&lMF!1(4ZgvxV1JFV=BxPyk zptT(7MXAN0*#wZ`XbuDyP~dohOs8Q~v`Ger;5rSg25YM>$pEw@4bk+&;!8*xf;J6P zE6{V2A$XM#tmz1vEh|a|c@WL5;3a9usvyNcN`5)Y)OeBsWMLXiCDdc+Wnz*6Xkl84 zLQX|lK?-O-AvY1U-#H0A>4KJ~!Bj!I5TIRr&kshng0S)m3o5gea6`DkervNR2% zBDDgvP8>AFlZG+~pJV`9ljZ_-8Ek+GWGlEIjCLDTk^yLa8ca2)M+sI5I_o60s033n zcvLG9R1W2X(nbRSAahShSs6V>z_lZ) zo}|)ZBn>Eaev$#?tSnRwkPD@d^q@4nlMEooW~D(L4nEEgHR(dn%)+_TG|2$6Xbt2e zNH4Jnb>DN60c5orNC7DOgL=kT!w|Y!4dxV3{N?1AfSZnx+yb6~M0Fi>^%_(U$O@40 z=oh6Y8GshAr6|C?2{Rjf&)F6PX!IU%k^y898+g?d zN{=nc0JK~!MWG-uCpWdE1Z%+oIZ!JjF)1-GwFtWk@X{er3>25-=cQsReIN_eU~|iv zs2c{73?Qr1(i4k{GK=%`uo?hPI!TE|MX5QdmDue7FN*~A6tP4BWLa8baS5oO46gIA zG@3vQ(^3>bOZGtRuEdheq#U$T6mpIh)R@$Y63|Y1=taQs$ptwm-H0Ru(4sVO&k}4Y z+AhK*1IY1NP{Y7(!WH$9Q?!s(VoOD!wPC$GbA-2J3+G>XhwlkRc>N#Qhq#SEiD!`;E_;>nvB%Mq7u;JO7N~OG_$~i zp%8UA+EbA8v>-}Atsz{|4LMK?q7LFL?5l;73?M7aASyvUG0esgXmweN0z?It8Vqul z7F0SXu_P_OC>Kkrfh;IP3QsH+ffH6?YHn#f!HfY}MFv)j*{Xyr8v{#XaWH7bSc*bg zN{O)%Xb379^*o*=12ga_RT`+G&qz(q1`oEP-p80^06H(r1!P8iep(v1#wtM>QAjd? zE*48Ei3e|4DoI2+DJRJQbYPZ?LOjA6&`K1jX{gBpv}6oo7uY0_Iy42~`U`9ncu`q# z31*)av{VdY2xw**O+UCZh$le6qnl|dC1xhr0}R}f0^1LATwY>sYCL))1+*3nVn0^b zfgA9kumI&U&?rw)aT%H;AzPF{;aQpsIu$$~LkVc%7u1f@B#=v>!5I&7Q4Z?ay-5b3 zHDFNHnMpaIy=Bm-#I71Vwh3}!F^bu!js&d%!)7L$D#)A+bnP6-Iy8Ck@FvJEP-sA# z>yC8uUUPva$=TF1;u*DZaP>(_8RF2Wg3-IRu{MK&>Ots83N@D(K`B zEX^JZcyde2%*!m!fSsm_wskeh0JM+`5|T-&>6v+0{0~~X1yKPCLCo+0t=fXfgW?M_ z9zd(MQ03#3Q*&~P(3&l5>QDm#v|bCM3gR&|S#Wy^cU=Qnp#_eEq@4WZ?Be*` z%;Nl_l++^BRnkcYko8(%l?92(*$~xemVu}Az)FhnMLhJhEl@@&F38D5Ps^6z`VVXj zL>hbbV~MB+p~{L&ib|8w`lXOFw?I~b(g@b74zdypqy*HFz^(+IdO(d2%qj%35DR1k zXn$1^>KTGb29RY~AnBCU98jV_4L8WjE08qEjj#$2WD7P-WO~KTGofHq67ew_iXz3J84cJ9E4TGc&h}#ezz^NS4G6E}4%P&e!jW9f_dL(P(#vBpEEwn7NITX zNHPE&e&wQ&o0^+kPzhOQn3{~TPCUr~w2}#~q$EEcQvrB4PHHmf3WNL-EC~^^W~nGO zF}bib6Lo!Yk^yLi5@u}~}&`DP)Dv`nm&1&#~U_pLSYP_F+0Gb>)i4<6X zPG?MwPfyK@PcA40-QALwS%IG2L2Hm)KsQ8yjRL6!-(QbKC1eRwMP`9}YKcc;PKht- z(bY)?ptVOS3Kf|Jfu)(r+0LNOHLANHYmXo%gyf?o7|>!P7lq=a)cA_bf_U&=z4&5` zgb7(|1XBeH?&8#B^!-Lj2B6hOV5bD+7o{2nV^sp~S;0)o%P-2sxCuMS0JP=^Y>o@~ zko%DQWXM7(v}pj)L01U3gF5MG9tSs6Dl!Ygpf~n}N3zxd}xMY85sc`kcChM&gk)2 zod&L|V3wwof*OjTxhAaX3v^f(!ceFZBTyDXjrdfQL+#Fk@h9&~hYX-4ZAu z;|uZ&lJiURN>Gp0OEQ40T>>k~0o`IzTmo9Qh|wVitzdFd04vMP%K=>~lZ1AjY?1+J z1rxd&^rR13#DuB_6oVL!0=IyWZ3C&oFbkZlkX02V7NH&Xo@4-8#Dr>Na(-S3Xy_Hx zbww*zKnt4iD2`99NG`?Li=JcvIcy8rB``a%b)X^3p0KLUFF;wNo@4-80)^c{Nu{|3 zs7V5JDpv|h9D(QSG1@JV6S&&-2#;xhB|(58byE22>CM^cM&0C|!DXi*eYZMdUn zNHB`)3?XZwz_xn$`+Iw$$r>6cK=s1XS5YFG67b+8*Z_nQ)aug^wEhXznB?4o%p?q> zz@;3TQK*wrhLH77$Z9fk^3yZXEyPHJi8-Z3sCA4XXb}{us}fUEP)q`;LUL<&7Bzy%ao3L4I!v#sKbOY+g0 zpN61SO;9&G1vz>;qB#v*LV?W*c6Ri0L6rrqWP<92+LBb1n3tS^c`rwjA!uQfi$ZZp zQ8Mar9Z80uoAe+u8E9b+S;GX9@xX!q(MuEz~Nq!kFp#$$q=+$2rQF=y397o z5VANZvp6L)9c=-WA!JohW^qALCfb57L&#E~%wo)8N<+xHpUmP4Y$k&9Wl4TcemU9z zs3By9Pf31hK>>yoIKmQ3@-tC`9<+eRMIo^SZCR!vXvGfLvzRjA$SN)=D#y3ZZ=2`Ep)+o475QFGKPXVtZfKcje<~uY5-(G z3Mi9;+HPoa;44f(W0wWRnHfn~%!VvU0ja0}cV{t1B@ICbCb=jS7i1PCLS0yZUQ~gW zq<~I51$Ce@QZmsZ8?+(?wEQP8B_3i2=tvZdp)y0rfk_~jfaE|suRv~r^deDP9EOmi zlM0d{oBKe@(XK#EG6XGBaZ!LQwarLDuM;4vQwkE36XP@UQc^3>LJd-3f@Hx4pvi)h zK|yjRcD>-SZ&1fJz9caPEfYf4o`AJtGZ>r_JX}28z-!S!NAaNR2bZ`A6^TVfiIwr0 zC8?;xZib*0CoT%;>M+I#3?VB{!0M7SGILVm6VaO`kOe0Q6{tZ0T4DmOQ}T-{L1$p0 z4KNvkmX|=bGGXy9WL-&SKG?H46_{%x4IxJv!Bk*5MJCD66uhD&Gaqz1V|)S1dD%&Z zpfihH6f*O%It@I~09w`x>Ry3H^wGQqo=O8PeSj>a1gQk2M>JL7A{;vAk3$JKLBxY3 zu>}IS?!_euP7uX8$%)`F!kjxZ1RXX6S`P$O0Wt^EE1(r3NQz*`@nB2&p!Fh9r699F znGvQO)#IS0BT$7<--FJB!3-eK5|R|yK`7uG48Ua&WZWHf8Kfa(DGA8VWYAz8Xcax` zfnG_5khLUmC5a{IB@tvX30wihMvP%&L&!>!+{EMzP&XAM4;_O>^Ch?n$tX@O0-bMP z3>m=1EKMLM*u=-Df_9(gR^mLmG|3R85>!xvH-tbId4ZQBp;`;M2n^Fa$dF7@XK({5@Qf1b5d=wwpxeTb%mfD&SaC@PXy6RZWJpGfhdKaM z7eQ7&$CnhPqAoQsgdBhacLjLL3N(BWk7X^Op?Ru-0+K5r)8-}l*=RFZhM>c6kko;e zk7GI8G|3ROdICvZNosLPd|GK9T6+hyd;&=oWC;XlPB68osI&leOu`VfbOK2+$nWTv zm?Rm3R!kr%0*w}8Q3RfBfQJmkv!GQHIjI&A2wFgarUg8$gEbf8;i9_UOiG+(0@*q~rUE?UtC znn3GK&|HF~9DME>n)#^B3Uu?qMK_ub)aC_9M{<5%T4p+A5lDP_KI(?zBtytj6%_BH z=*URSNyDZMvk*tomQ;y)5JQq7upd~U$N+Atc z@G^WfBf;BV;5LJU3!5_3QXAsg_>5e%p*YBSLU7ZdyR}MF(RM}|f>y^Mxel`82Xpa) zA!wZphB~lc(0qZKmLcYW{DP(o-U5LPhhQ@ao>(DDuowa!g@F69C>7j>1r0AHp|A5W z1g)Y$az7}KfeP`A(xiBJlLyU-m}wGJYJqfsDj;lSBjl_hxPyvw%0cU5LASl38I4*# zLz6n_;waE^F>K8c&`O*X_;yR^#tKwJK}yj2RjKG>r!Y0J!==F&7@;jVGK3zQ1KsBb zQ;KRCXk`Ur^B7k5fR+LvZw14u2sBHbqJY>9hE)-0QWdf{5V|1@yDD(WgV^+iO_7m- z8K@tFwC@Y6D$t}$3T%@Lb`{{n3E5PFRRLr?K0Y26e4s;WQD@GKK%=%P3h^$HevZDL z&M4svmIFm*N@ZSRZe}tlNuWiO5oB~PJ|3n7J+i?Hf)wK8L6?z%RADj160%DoKE5O$ ziyg^HW(F1tC`O=JlAHt@Edi-0uFQ=GwFAKYQ)It@lo)~yfhj>X!w7WxgMmVl0_Y-> zOynKfP#GtM_~Im#O9sFa7EmqaMWEFK$UzH|HiVgox_cNb1=E>Q1Uir!$*mw+BLf8| zuv0+mjnU+cL561L#e+u(^o-5SkuOXJX*M=gNK(iJ4cx$$Am8W(Rsym;sU#jevz}C% zre|zsimJxYz!<6qbz;ECz|c4iB$J(51Uf$!Z79vOl2GQKK=MW)3qY$3ixP9wiqThGfmMJ^0F6c?4~-ZZ7@8S@B*4p; zQ$hO(isQkjA!HV#EHMKqGzP^0LLunrY~;B!kP;J+Gcqz$48TWHp~RA*nF+`uuw+Ii z%6?0bPE(N1^ql;p#GLr7{3OU_N!Y9~!=@0;CUcM)NJkHw5f&in`1pb%&>0;0dC94I z#+C-iYXLwGvH&F+kVE5(OAA2vBV&Yzg^@y%LS|lkVp4uliJq~AA@YzR*a#DaB=GJt z^qxLg5)>NX(Wt!A-1x*Il#^bKK*vRZ6r`4wVDW)DI5~hd!wVVEE@-r<1)YhV1UU&5 z)HTLt5IE<6BvXruWMpj9?W3SdJ(2S=o$6(fd52H@~Rypd)!W|?J(hHZzQe=bFSSmox03RR&I$#g=upN*iz*!D#5Lgj< z)EgRs)`vii0r>)UH5qjD4!K7SGR^|*F6h{Hd{Jp0sPTv#pN2-Dvviykauf4P(-M2np%ag#;$qGpd5NRyImk25;AhO`4tY|Js1eu+Y3%*4F zr6@EsGDrfYXz*t5q{QTGw5rw62y~HL66CBK)KN*0qmn`9g4@hk!Z8IT2@d4Mvc$|B z(3zQN&PoNj8mt0~_B6O;K|acI03$;qLvXnQ3hE+^+-+!N2(Bq0vY;XZv?LkTX3(0I zBn60y%slklDM1z(gNj5@p9eewnuIc@4weUb4z$4;G{uVPdP8sqfysj>P|#cePKS`r z4HoU-Yz~P}uo^VY;8X{Z#!L)`7Ko$**)NEu+Y%JAU}M48@`1LBfrr?z1tmCP6;~FQ zq~>B=(gF$xaLPh5D=Q!QJO_}9B#>>n#p#&ku%R(%salc(q<4l93dW!_yFjuf`33P{ zH7Nct1|8LvqyXxu#h0YzBKOvf42=!IX#muW07XzqenEatemdy*0hAMPKnlT40l30S zl+i=5JSe7N@>m=Rt|>s>_ssl^Qq=mw(AWel3py|`sk9h$&{jNnZK$4!p(XNu86!hu z(8PU`0_X@o%xEwMP1PqUF!t||m=e?)1m8XB9JgOV#u9yAYy8dN6WDg`|D1-1bc zXlN?HDGsM3$oP_q_@exLCMkf9lETdUX5eZFBnNLw=9iWfmw>K-%0oV&0c4LMDD{HW zf?IEBmKY`~Bq^Y@^i50+k=N^hOaS+t(m-hrBc*^=2qY;aCl(aMmx3>C0?o#w*<6@X6Ea$xSRqZKRrj2Hhae!r~xslt5w_bRsmGTfpfOWDV>B?ff+4m31ILgJUf% zvk0_;pcr|nKUfmxOwa}DpmdL30-J!^_elyVMag(V1l+iX>c&#wnHYd88;~=xCoL1u z@tKeifcXQxQ)U8c$wQQYMwh|sV$i}O8I<9YOL8EQ0`A)BnV6xKGbRSfpy&hTJ#YlW zm7xqg7@8O)gKBHDG$i7G@{|iH0Ud;Ne1;BwB2N z);lLDz?>3ag4*ymMU*y>jtWMwm_pk3pkRThKrd}g4Z!s)LIJo$K}pl528N&{gHTeQ zh;jX(k)bK1tAJ32(P=U@Fam`wLIpVZK|zZ$Xbv_CRv8VGH3+rE26b^%?!XjCGgld;;vNGJZ@%S z3W{v#PI4^GTr)^Lf&IQyBSSL-Gq4-WLF-7-+y-u;fW~`3_tBxtfnpq7DrKVFzX&oB zTyDcQ1%iqe6ustKveY60rKct(cihTsMoXhs6Gqy)nW7LdXszW_6f zTR@74e9+-Zs6MuUlnnU=@!%W%;?b8<8W~!`jYYjx4&BX_z5u37VS4suY{Kh6bP<3bq?!E~YObW06Qo zAos9=$^!Ieh9zhh9g5vWsaQM=$$elG3lj4(lc9@vuviVwiWmy9dIX#;!S{=S$`Z7m zi6vyb5-g3y8gS7Js%Bu9fuUFSmY{8WNebXAiLmGgx6naet&C4b*>+}RXlV#;po4W{ zOgI`^f=(HSnu}#9(-M-eAzhWC)Z9eW*~K)d1}z{$S!fUP8@PxD83I;@(dw`?1h>e+Hej~bEe*j%cy3|^Za09- za8S&Ey3r`bk);th>6T<-%y1f7g0>DO!SA2J^gL(-VUhy);9AhoCAN?^0=Jhyb4{Qd zQPNOPkv1~4Gy;#mg4zIB@Y(=#?VG)2=3ZV7-!Vv5QjBOaM4ddB8Ps6#H6 zMrNSwUyzyu%FQ5SQ0D6mEfc}=sUSCiA{V3rbwte)bZ=jh0$2rjj}%A=%0#81Wg>X+ z7UG9^h%-?8PnL<`JOa8Q02H98O*c!>0=pyykR<5(fCALnUqj2pB+%?Hq#b}(u!7Es z0nLJdJcnLXC4x?nP6F+5FVQnGvOpcIPBaEj8iCSXL2@SO1obk^f;Q0@oP0s2FhfpR zFT-pBB^pB#Fm$C*W?mUa0g-47u0Li7{ijt80Y&}Cu1Jv+M zGzQln#U&}wVO|Wcnt+SZ;*u1|2r;HSxb*;9TvdWTJ&*|61LvdwTcd;OF3`p4 z`rv`oc+j~**{E@lXliVt;G_UqNEi>AiYm$nU!s6+5@?bR>;mwf4J?D)iJ)y_P70vC zRvG!lD7z|*3=>UFKn8%Fl8zw<9vI9oNX&uX=Za-iEYTD^^$l_Zs6;BrL`{Z?plxPO z3XpUL-kpTz12d2VQc6Hm2*}ITL2fe#4NQV(n^6zX1pVWL?INPB8g z5!y_5BIx>YC&*?`l;{R6-!TBMWJ)T{%qhvti-)e1LF+!^REN<`fT(m*h)+dZ;DnIK HOW^_l`taNM literal 0 HcmV?d00001 diff --git a/roms/Makefile b/roms/Makefile index 88b3709d4d..b5e5a69e91 100644 --- a/roms/Makefile +++ b/roms/Makefile @@ -63,6 +63,7 @@ default: @echo " efirom -- update nic roms (bios+efi, this needs" @echo " the EfiRom utility from edk2 / tianocore)" @echo " slof -- update slof.bin" + @echo " skiboot -- update skiboot.lid" @echo " u-boot.e500 -- update u-boot.e500" bios: build-seabios-config-seabios-128k build-seabios-config-seabios-256k @@ -103,7 +104,7 @@ build-lgplvgabios: $(MAKE) -C vgabios $(vgabios_targets) -.PHONY: sgabios +.PHONY: sgabios skiboot sgabios: $(MAKE) -C sgabios cp sgabios/sgabios.bin ../pc-bios @@ -146,6 +147,10 @@ u-boot.e500: $(powerpc_cross_prefix)strip u-boot/build.e500/u-boot -o \ ../pc-bios/u-boot.e500 +skiboot: + $(MAKE) -C skiboot CROSS=$(powerpc64_cross_prefix) + cp skiboot/skiboot.lid ../pc-bios/skiboot.lid + clean: rm -rf seabios/.config seabios/out seabios/builds $(MAKE) -C vgabios clean @@ -155,3 +160,4 @@ clean: $(MAKE) -C ipxe/src veryclean $(MAKE) -C SLOF clean rm -rf u-boot/build.e500 + $(MAKE) -C skiboot clean diff --git a/roms/skiboot b/roms/skiboot new file mode 160000 index 0000000000..762d0082f1 --- /dev/null +++ b/roms/skiboot @@ -0,0 +1 @@ +Subproject commit 762d0082f18e4fb921a2d44a1051b02d8b0f6381 From 225a9ab8833e5191d180e23a23b8fb381fbaf9c3 Mon Sep 17 00:00:00 2001 From: Alexey Kardashevskiy Date: Wed, 26 Oct 2016 13:18:03 +1100 Subject: [PATCH 23/73] configure, ppc64: Copy skiboot.lid to build directory when configuring When configured to compile out of tree, the configure script copies BIOS blobs to the build directory. However since the PPC64 powernv machine ROM has .lid extension, it is ignored and "make check" fails when trying the powernv machine. This adds *.lid to the list of copied blobs. Signed-off-by: Alexey Kardashevskiy Signed-off-by: David Gibson --- configure | 1 + 1 file changed, 1 insertion(+) diff --git a/configure b/configure index 8e10059607..7b8e77f45b 100755 --- a/configure +++ b/configure @@ -6131,6 +6131,7 @@ FILES="$FILES roms/seabios/Makefile roms/vgabios/Makefile" FILES="$FILES pc-bios/qemu-icon.bmp" for bios_file in \ $source_path/pc-bios/*.bin \ + $source_path/pc-bios/*.lid \ $source_path/pc-bios/*.aml \ $source_path/pc-bios/*.rom \ $source_path/pc-bios/*.dtb \ From 9e933f4a620ca485356205f5cac8a6c3db0b861d Mon Sep 17 00:00:00 2001 From: Benjamin Herrenschmidt Date: Sat, 22 Oct 2016 11:46:35 +0200 Subject: [PATCH 24/73] ppc/pnv: add skeleton PowerNV platform MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The goal is to emulate a PowerNV system at the level of the skiboot firmware, which loads the OS and provides some runtime services. Power Systems have a lower firmware (HostBoot) that does low level system initialization, like DRAM training. This is beyond the scope of what qemu will address in a PowerNV guest. No devices yet, not even an interrupt controller. Just to get started, some RAM to load the skiboot firmware, the kernel and initrd. The device tree is fully created in the machine reset op. Signed-off-by: Benjamin Herrenschmidt [clg: - updated for qemu-2.7 - replaced fprintf by error_report - used a common definition of _FDT macro - removed VMStateDescription as migration is not yet supported - added IBM Copyright statements - reworked kernel_filename handling - merged PnvSystem and sPowerNVMachineState - removed PHANDLE_XICP - added ppc_create_page_sizes_prop helper - removed nmi support - removed kvm support - updated powernv machine to version 2.8 - removed chips and cpus, They will be provided in another patches - added a machine reset routine to initialize the device tree (also) - french has a squelette and english a skeleton. - improved commit log. - reworked prototypes parameters - added a check on the ram size (thanks to Michael Ellerman) - fixed chip-id cell - changed MAX_CPUS to 2048 - simplified memory node creation to one node only - removed machine version - rewrote the device tree creation with the fdt "rw" routines - s/sPowerNVMachineState/PnvMachineState/ - etc.] Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: David Gibson --- default-configs/ppc64-softmmu.mak | 1 + hw/ppc/Makefile.objs | 2 + hw/ppc/pnv.c | 226 ++++++++++++++++++++++++++++++ include/hw/ppc/pnv.h | 38 +++++ 4 files changed, 267 insertions(+) create mode 100644 hw/ppc/pnv.c create mode 100644 include/hw/ppc/pnv.h diff --git a/default-configs/ppc64-softmmu.mak b/default-configs/ppc64-softmmu.mak index db5a4d6f5e..67a9bcaa67 100644 --- a/default-configs/ppc64-softmmu.mak +++ b/default-configs/ppc64-softmmu.mak @@ -39,6 +39,7 @@ CONFIG_I8259=y CONFIG_XILINX=y CONFIG_XILINX_ETHLITE=y CONFIG_PSERIES=y +CONFIG_POWERNV=y CONFIG_PREP=y CONFIG_MAC=y CONFIG_E500=y diff --git a/hw/ppc/Makefile.objs b/hw/ppc/Makefile.objs index 99a0d4e581..8105db7d56 100644 --- a/hw/ppc/Makefile.objs +++ b/hw/ppc/Makefile.objs @@ -5,6 +5,8 @@ obj-$(CONFIG_PSERIES) += spapr.o spapr_vio.o spapr_events.o obj-$(CONFIG_PSERIES) += spapr_hcall.o spapr_iommu.o spapr_rtas.o obj-$(CONFIG_PSERIES) += spapr_pci.o spapr_rtc.o spapr_drc.o spapr_rng.o obj-$(CONFIG_PSERIES) += spapr_cpu_core.o +# IBM PowerNV +obj-$(CONFIG_POWERNV) += pnv.o ifeq ($(CONFIG_PCI)$(CONFIG_PSERIES)$(CONFIG_LINUX), yyy) obj-y += spapr_pci_vfio.o endif diff --git a/hw/ppc/pnv.c b/hw/ppc/pnv.c new file mode 100644 index 0000000000..8d9850989b --- /dev/null +++ b/hw/ppc/pnv.c @@ -0,0 +1,226 @@ +/* + * QEMU PowerPC PowerNV machine model + * + * Copyright (c) 2016, IBM Corporation. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, see . + */ + +#include "qemu/osdep.h" +#include "qapi/error.h" +#include "sysemu/sysemu.h" +#include "sysemu/numa.h" +#include "hw/hw.h" +#include "target-ppc/cpu.h" +#include "qemu/log.h" +#include "hw/ppc/fdt.h" +#include "hw/ppc/ppc.h" +#include "hw/ppc/pnv.h" +#include "hw/loader.h" +#include "exec/address-spaces.h" +#include "qemu/cutils.h" + +#include + +#define FDT_MAX_SIZE 0x00100000 + +#define FW_FILE_NAME "skiboot.lid" +#define FW_LOAD_ADDR 0x0 +#define FW_MAX_SIZE 0x00400000 + +#define KERNEL_LOAD_ADDR 0x20000000 +#define INITRD_LOAD_ADDR 0x40000000 + +/* + * On Power Systems E880 (POWER8), the max cpus (threads) should be : + * 4 * 4 sockets * 12 cores * 8 threads = 1536 + * Let's make it 2^11 + */ +#define MAX_CPUS 2048 + +/* + * Memory nodes are created by hostboot, one for each range of memory + * that has a different "affinity". In practice, it means one range + * per chip. + */ +static void powernv_populate_memory_node(void *fdt, int chip_id, hwaddr start, + hwaddr size) +{ + char *mem_name; + uint64_t mem_reg_property[2]; + int off; + + mem_reg_property[0] = cpu_to_be64(start); + mem_reg_property[1] = cpu_to_be64(size); + + mem_name = g_strdup_printf("memory@%"HWADDR_PRIx, start); + off = fdt_add_subnode(fdt, 0, mem_name); + g_free(mem_name); + + _FDT((fdt_setprop_string(fdt, off, "device_type", "memory"))); + _FDT((fdt_setprop(fdt, off, "reg", mem_reg_property, + sizeof(mem_reg_property)))); + _FDT((fdt_setprop_cell(fdt, off, "ibm,chip-id", chip_id))); +} + +static void *powernv_create_fdt(MachineState *machine) +{ + const char plat_compat[] = "qemu,powernv\0ibm,powernv"; + PnvMachineState *pnv = POWERNV_MACHINE(machine); + void *fdt; + char *buf; + int off; + + fdt = g_malloc0(FDT_MAX_SIZE); + _FDT((fdt_create_empty_tree(fdt, FDT_MAX_SIZE))); + + /* Root node */ + _FDT((fdt_setprop_cell(fdt, 0, "#address-cells", 0x2))); + _FDT((fdt_setprop_cell(fdt, 0, "#size-cells", 0x2))); + _FDT((fdt_setprop_string(fdt, 0, "model", + "IBM PowerNV (emulated by qemu)"))); + _FDT((fdt_setprop(fdt, 0, "compatible", plat_compat, + sizeof(plat_compat)))); + + buf = qemu_uuid_unparse_strdup(&qemu_uuid); + _FDT((fdt_setprop_string(fdt, 0, "vm,uuid", buf))); + if (qemu_uuid_set) { + _FDT((fdt_property_string(fdt, "system-id", buf))); + } + g_free(buf); + + off = fdt_add_subnode(fdt, 0, "chosen"); + if (machine->kernel_cmdline) { + _FDT((fdt_setprop_string(fdt, off, "bootargs", + machine->kernel_cmdline))); + } + + if (pnv->initrd_size) { + uint32_t start_prop = cpu_to_be32(pnv->initrd_base); + uint32_t end_prop = cpu_to_be32(pnv->initrd_base + pnv->initrd_size); + + _FDT((fdt_setprop(fdt, off, "linux,initrd-start", + &start_prop, sizeof(start_prop)))); + _FDT((fdt_setprop(fdt, off, "linux,initrd-end", + &end_prop, sizeof(end_prop)))); + } + + /* TODO: put all the memory in one node on chip 0 until we find a + * way to specify different ranges for each chip + */ + powernv_populate_memory_node(fdt, 0, 0, machine->ram_size); + + return fdt; +} + +static void ppc_powernv_reset(void) +{ + MachineState *machine = MACHINE(qdev_get_machine()); + void *fdt; + + qemu_devices_reset(); + + fdt = powernv_create_fdt(machine); + + /* Pack resulting tree */ + _FDT((fdt_pack(fdt))); + + cpu_physical_memory_write(PNV_FDT_ADDR, fdt, fdt_totalsize(fdt)); +} + +static void ppc_powernv_init(MachineState *machine) +{ + PnvMachineState *pnv = POWERNV_MACHINE(machine); + MemoryRegion *ram; + char *fw_filename; + long fw_size; + + /* allocate RAM */ + if (machine->ram_size < (1 * G_BYTE)) { + error_report("Warning: skiboot may not work with < 1GB of RAM"); + } + + ram = g_new(MemoryRegion, 1); + memory_region_allocate_system_memory(ram, NULL, "ppc_powernv.ram", + machine->ram_size); + memory_region_add_subregion(get_system_memory(), 0, ram); + + /* load skiboot firmware */ + if (bios_name == NULL) { + bios_name = FW_FILE_NAME; + } + + fw_filename = qemu_find_file(QEMU_FILE_TYPE_BIOS, bios_name); + + fw_size = load_image_targphys(fw_filename, FW_LOAD_ADDR, FW_MAX_SIZE); + if (fw_size < 0) { + hw_error("qemu: could not load OPAL '%s'\n", fw_filename); + exit(1); + } + g_free(fw_filename); + + /* load kernel */ + if (machine->kernel_filename) { + long kernel_size; + + kernel_size = load_image_targphys(machine->kernel_filename, + KERNEL_LOAD_ADDR, 0x2000000); + if (kernel_size < 0) { + hw_error("qemu: could not load kernel'%s'\n", + machine->kernel_filename); + exit(1); + } + } + + /* load initrd */ + if (machine->initrd_filename) { + pnv->initrd_base = INITRD_LOAD_ADDR; + pnv->initrd_size = load_image_targphys(machine->initrd_filename, + pnv->initrd_base, 0x10000000); /* 128MB max */ + if (pnv->initrd_size < 0) { + error_report("qemu: could not load initial ram disk '%s'", + machine->initrd_filename); + exit(1); + } + } +} + +static void powernv_machine_class_init(ObjectClass *oc, void *data) +{ + MachineClass *mc = MACHINE_CLASS(oc); + + mc->desc = "IBM PowerNV (Non-Virtualized)"; + mc->init = ppc_powernv_init; + mc->reset = ppc_powernv_reset; + mc->max_cpus = MAX_CPUS; + mc->block_default_type = IF_IDE; /* Pnv provides a AHCI device for + * storage */ + mc->no_parallel = 1; + mc->default_boot_order = NULL; + mc->default_ram_size = 1 * G_BYTE; +} + +static const TypeInfo powernv_machine_info = { + .name = TYPE_POWERNV_MACHINE, + .parent = TYPE_MACHINE, + .instance_size = sizeof(PnvMachineState), + .class_init = powernv_machine_class_init, +}; + +static void powernv_machine_register_types(void) +{ + type_register_static(&powernv_machine_info); +} + +type_init(powernv_machine_register_types) diff --git a/include/hw/ppc/pnv.h b/include/hw/ppc/pnv.h new file mode 100644 index 0000000000..474fe9c697 --- /dev/null +++ b/include/hw/ppc/pnv.h @@ -0,0 +1,38 @@ +/* + * QEMU PowerPC PowerNV various definitions + * + * Copyright (c) 2014-2016 BenH, IBM Corporation. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, see . + */ +#ifndef _PPC_PNV_H +#define _PPC_PNV_H + +#include "hw/boards.h" + +#define TYPE_POWERNV_MACHINE MACHINE_TYPE_NAME("powernv") +#define POWERNV_MACHINE(obj) \ + OBJECT_CHECK(PnvMachineState, (obj), TYPE_POWERNV_MACHINE) + +typedef struct PnvMachineState { + /*< private >*/ + MachineState parent_obj; + + uint32_t initrd_base; + long initrd_size; +} PnvMachineState; + +#define PNV_FDT_ADDR 0x01000000 + +#endif /* _PPC_PNV_H */ From e997040e3f02f6d1c6ab76e569f3593f5e3670fe Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= Date: Sat, 22 Oct 2016 11:46:36 +0200 Subject: [PATCH 25/73] ppc/pnv: add a PnvChip object MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This is is an abstraction of a POWER8 chip which is a set of cores plus other 'units', like the pervasive unit, the interrupt controller, the memory controller, the on-chip microcontroller, etc. The whole can be seen as a socket. It depends on a cpu model and its characteristics: max cores and specific inits are defined in a PnvChipClass. We start with an near empty PnvChip with only a few cpu constants which we will grow in the subsequent patches with the controllers required to run the system. The Chip CFAM (Common FRU Access Module) ID gives the model of the chip and its version number. It is generally the first thing firmwares fetch, available at XSCOM PCB address 0xf000f, to start initialization. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: David Gibson --- hw/ppc/pnv.c | 213 ++++++++++++++++++++++++++++++++++++++++++- include/hw/ppc/pnv.h | 63 +++++++++++++ 2 files changed, 271 insertions(+), 5 deletions(-) diff --git a/hw/ppc/pnv.c b/hw/ppc/pnv.c index 8d9850989b..aeafd7e894 100644 --- a/hw/ppc/pnv.c +++ b/hw/ppc/pnv.c @@ -30,6 +30,7 @@ #include "hw/loader.h" #include "exec/address-spaces.h" #include "qemu/cutils.h" +#include "qapi/visitor.h" #include @@ -74,6 +75,14 @@ static void powernv_populate_memory_node(void *fdt, int chip_id, hwaddr start, _FDT((fdt_setprop_cell(fdt, off, "ibm,chip-id", chip_id))); } +static void powernv_populate_chip(PnvChip *chip, void *fdt) +{ + if (chip->ram_size) { + powernv_populate_memory_node(fdt, chip->chip_id, chip->ram_start, + chip->ram_size); + } +} + static void *powernv_create_fdt(MachineState *machine) { const char plat_compat[] = "qemu,powernv\0ibm,powernv"; @@ -81,6 +90,7 @@ static void *powernv_create_fdt(MachineState *machine) void *fdt; char *buf; int off; + int i; fdt = g_malloc0(FDT_MAX_SIZE); _FDT((fdt_create_empty_tree(fdt, FDT_MAX_SIZE))); @@ -116,11 +126,10 @@ static void *powernv_create_fdt(MachineState *machine) &end_prop, sizeof(end_prop)))); } - /* TODO: put all the memory in one node on chip 0 until we find a - * way to specify different ranges for each chip - */ - powernv_populate_memory_node(fdt, 0, 0, machine->ram_size); - + /* Populate device tree for each chip */ + for (i = 0; i < pnv->num_chips; i++) { + powernv_populate_chip(pnv->chips[i], fdt); + } return fdt; } @@ -145,6 +154,8 @@ static void ppc_powernv_init(MachineState *machine) MemoryRegion *ram; char *fw_filename; long fw_size; + int i; + char *chip_typename; /* allocate RAM */ if (machine->ram_size < (1 * G_BYTE)) { @@ -194,6 +205,190 @@ static void ppc_powernv_init(MachineState *machine) exit(1); } } + + /* We need some cpu model to instantiate the PnvChip class */ + if (machine->cpu_model == NULL) { + machine->cpu_model = "POWER8"; + } + + /* Create the processor chips */ + chip_typename = g_strdup_printf(TYPE_PNV_CHIP "-%s", machine->cpu_model); + if (!object_class_by_name(chip_typename)) { + error_report("qemu: invalid CPU model '%s' for %s machine", + machine->cpu_model, MACHINE_GET_CLASS(machine)->name); + exit(1); + } + + pnv->chips = g_new0(PnvChip *, pnv->num_chips); + for (i = 0; i < pnv->num_chips; i++) { + char chip_name[32]; + Object *chip = object_new(chip_typename); + + pnv->chips[i] = PNV_CHIP(chip); + + /* TODO: put all the memory in one node on chip 0 until we find a + * way to specify different ranges for each chip + */ + if (i == 0) { + object_property_set_int(chip, machine->ram_size, "ram-size", + &error_fatal); + } + + snprintf(chip_name, sizeof(chip_name), "chip[%d]", PNV_CHIP_HWID(i)); + object_property_add_child(OBJECT(pnv), chip_name, chip, &error_fatal); + object_property_set_int(chip, PNV_CHIP_HWID(i), "chip-id", + &error_fatal); + object_property_set_bool(chip, true, "realized", &error_fatal); + } + g_free(chip_typename); +} + +static void pnv_chip_power8e_class_init(ObjectClass *klass, void *data) +{ + DeviceClass *dc = DEVICE_CLASS(klass); + PnvChipClass *k = PNV_CHIP_CLASS(klass); + + k->cpu_model = "POWER8E"; + k->chip_type = PNV_CHIP_POWER8E; + k->chip_cfam_id = 0x221ef04980000000ull; /* P8 Murano DD2.1 */ + dc->desc = "PowerNV Chip POWER8E"; +} + +static const TypeInfo pnv_chip_power8e_info = { + .name = TYPE_PNV_CHIP_POWER8E, + .parent = TYPE_PNV_CHIP, + .instance_size = sizeof(PnvChip), + .class_init = pnv_chip_power8e_class_init, +}; + +static void pnv_chip_power8_class_init(ObjectClass *klass, void *data) +{ + DeviceClass *dc = DEVICE_CLASS(klass); + PnvChipClass *k = PNV_CHIP_CLASS(klass); + + k->cpu_model = "POWER8"; + k->chip_type = PNV_CHIP_POWER8; + k->chip_cfam_id = 0x220ea04980000000ull; /* P8 Venice DD2.0 */ + dc->desc = "PowerNV Chip POWER8"; +} + +static const TypeInfo pnv_chip_power8_info = { + .name = TYPE_PNV_CHIP_POWER8, + .parent = TYPE_PNV_CHIP, + .instance_size = sizeof(PnvChip), + .class_init = pnv_chip_power8_class_init, +}; + +static void pnv_chip_power8nvl_class_init(ObjectClass *klass, void *data) +{ + DeviceClass *dc = DEVICE_CLASS(klass); + PnvChipClass *k = PNV_CHIP_CLASS(klass); + + k->cpu_model = "POWER8NVL"; + k->chip_type = PNV_CHIP_POWER8NVL; + k->chip_cfam_id = 0x120d304980000000ull; /* P8 Naples DD1.0 */ + dc->desc = "PowerNV Chip POWER8NVL"; +} + +static const TypeInfo pnv_chip_power8nvl_info = { + .name = TYPE_PNV_CHIP_POWER8NVL, + .parent = TYPE_PNV_CHIP, + .instance_size = sizeof(PnvChip), + .class_init = pnv_chip_power8nvl_class_init, +}; + +static void pnv_chip_power9_class_init(ObjectClass *klass, void *data) +{ + DeviceClass *dc = DEVICE_CLASS(klass); + PnvChipClass *k = PNV_CHIP_CLASS(klass); + + k->cpu_model = "POWER9"; + k->chip_type = PNV_CHIP_POWER9; + k->chip_cfam_id = 0x100d104980000000ull; /* P9 Nimbus DD1.0 */ + dc->desc = "PowerNV Chip POWER9"; +} + +static const TypeInfo pnv_chip_power9_info = { + .name = TYPE_PNV_CHIP_POWER9, + .parent = TYPE_PNV_CHIP, + .instance_size = sizeof(PnvChip), + .class_init = pnv_chip_power9_class_init, +}; + +static void pnv_chip_realize(DeviceState *dev, Error **errp) +{ + /* left purposely empty */ +} + +static Property pnv_chip_properties[] = { + DEFINE_PROP_UINT32("chip-id", PnvChip, chip_id, 0), + DEFINE_PROP_UINT64("ram-start", PnvChip, ram_start, 0), + DEFINE_PROP_UINT64("ram-size", PnvChip, ram_size, 0), + DEFINE_PROP_END_OF_LIST(), +}; + +static void pnv_chip_class_init(ObjectClass *klass, void *data) +{ + DeviceClass *dc = DEVICE_CLASS(klass); + + dc->realize = pnv_chip_realize; + dc->props = pnv_chip_properties; + dc->desc = "PowerNV Chip"; +} + +static const TypeInfo pnv_chip_info = { + .name = TYPE_PNV_CHIP, + .parent = TYPE_SYS_BUS_DEVICE, + .class_init = pnv_chip_class_init, + .class_size = sizeof(PnvChipClass), + .abstract = true, +}; + +static void pnv_get_num_chips(Object *obj, Visitor *v, const char *name, + void *opaque, Error **errp) +{ + visit_type_uint32(v, name, &POWERNV_MACHINE(obj)->num_chips, errp); +} + +static void pnv_set_num_chips(Object *obj, Visitor *v, const char *name, + void *opaque, Error **errp) +{ + PnvMachineState *pnv = POWERNV_MACHINE(obj); + uint32_t num_chips; + Error *local_err = NULL; + + visit_type_uint32(v, name, &num_chips, &local_err); + if (local_err) { + error_propagate(errp, local_err); + return; + } + + /* + * TODO: should we decide on how many chips we can create based + * on #cores and Venice vs. Murano vs. Naples chip type etc..., + */ + if (!is_power_of_2(num_chips) || num_chips > 4) { + error_setg(errp, "invalid number of chips: '%d'", num_chips); + return; + } + + pnv->num_chips = num_chips; +} + +static void powernv_machine_initfn(Object *obj) +{ + PnvMachineState *pnv = POWERNV_MACHINE(obj); + pnv->num_chips = 1; +} + +static void powernv_machine_class_props_init(ObjectClass *oc) +{ + object_class_property_add(oc, "num-chips", "uint32_t", + pnv_get_num_chips, pnv_set_num_chips, + NULL, NULL, NULL); + object_class_property_set_description(oc, "num-chips", + "Specifies the number of processor chips", + NULL); } static void powernv_machine_class_init(ObjectClass *oc, void *data) @@ -209,18 +404,26 @@ static void powernv_machine_class_init(ObjectClass *oc, void *data) mc->no_parallel = 1; mc->default_boot_order = NULL; mc->default_ram_size = 1 * G_BYTE; + + powernv_machine_class_props_init(oc); } static const TypeInfo powernv_machine_info = { .name = TYPE_POWERNV_MACHINE, .parent = TYPE_MACHINE, .instance_size = sizeof(PnvMachineState), + .instance_init = powernv_machine_initfn, .class_init = powernv_machine_class_init, }; static void powernv_machine_register_types(void) { type_register_static(&powernv_machine_info); + type_register_static(&pnv_chip_info); + type_register_static(&pnv_chip_power8e_info); + type_register_static(&pnv_chip_power8_info); + type_register_static(&pnv_chip_power8nvl_info); + type_register_static(&pnv_chip_power9_info); } type_init(powernv_machine_register_types) diff --git a/include/hw/ppc/pnv.h b/include/hw/ppc/pnv.h index 474fe9c697..7189961e1f 100644 --- a/include/hw/ppc/pnv.h +++ b/include/hw/ppc/pnv.h @@ -20,6 +20,66 @@ #define _PPC_PNV_H #include "hw/boards.h" +#include "hw/sysbus.h" + +#define TYPE_PNV_CHIP "powernv-chip" +#define PNV_CHIP(obj) OBJECT_CHECK(PnvChip, (obj), TYPE_PNV_CHIP) +#define PNV_CHIP_CLASS(klass) \ + OBJECT_CLASS_CHECK(PnvChipClass, (klass), TYPE_PNV_CHIP) +#define PNV_CHIP_GET_CLASS(obj) \ + OBJECT_GET_CLASS(PnvChipClass, (obj), TYPE_PNV_CHIP) + +typedef enum PnvChipType { + PNV_CHIP_POWER8E, /* AKA Murano (default) */ + PNV_CHIP_POWER8, /* AKA Venice */ + PNV_CHIP_POWER8NVL, /* AKA Naples */ + PNV_CHIP_POWER9, /* AKA Nimbus */ +} PnvChipType; + +typedef struct PnvChip { + /*< private >*/ + SysBusDevice parent_obj; + + /*< public >*/ + uint32_t chip_id; + uint64_t ram_start; + uint64_t ram_size; +} PnvChip; + +typedef struct PnvChipClass { + /*< private >*/ + SysBusDeviceClass parent_class; + + /*< public >*/ + const char *cpu_model; + PnvChipType chip_type; + uint64_t chip_cfam_id; +} PnvChipClass; + +#define TYPE_PNV_CHIP_POWER8E TYPE_PNV_CHIP "-POWER8E" +#define PNV_CHIP_POWER8E(obj) \ + OBJECT_CHECK(PnvChip, (obj), TYPE_PNV_CHIP_POWER8E) + +#define TYPE_PNV_CHIP_POWER8 TYPE_PNV_CHIP "-POWER8" +#define PNV_CHIP_POWER8(obj) \ + OBJECT_CHECK(PnvChip, (obj), TYPE_PNV_CHIP_POWER8) + +#define TYPE_PNV_CHIP_POWER8NVL TYPE_PNV_CHIP "-POWER8NVL" +#define PNV_CHIP_POWER8NVL(obj) \ + OBJECT_CHECK(PnvChip, (obj), TYPE_PNV_CHIP_POWER8NVL) + +#define TYPE_PNV_CHIP_POWER9 TYPE_PNV_CHIP "-POWER9" +#define PNV_CHIP_POWER9(obj) \ + OBJECT_CHECK(PnvChip, (obj), TYPE_PNV_CHIP_POWER9) + +/* + * This generates a HW chip id depending on an index: + * + * 0x0, 0x1, 0x10, 0x11 + * + * 4 chips should be the maximum + */ +#define PNV_CHIP_HWID(i) ((((i) & 0x3e) << 3) | ((i) & 0x1)) #define TYPE_POWERNV_MACHINE MACHINE_TYPE_NAME("powernv") #define POWERNV_MACHINE(obj) \ @@ -31,6 +91,9 @@ typedef struct PnvMachineState { uint32_t initrd_base; long initrd_size; + + uint32_t num_chips; + PnvChip **chips; } PnvMachineState; #define PNV_FDT_ADDR 0x01000000 From 397a79e7575c4ea98507ff9d1d2629b58725d484 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= Date: Sat, 22 Oct 2016 11:46:37 +0200 Subject: [PATCH 26/73] ppc/pnv: add a core mask to PnvChip MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This will be used to build real HW ids for the cores and enforce some limits on the available cores per chip. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: David Gibson --- hw/ppc/pnv.c | 73 +++++++++++++++++++++++++++++++++++++++++++- include/hw/ppc/pnv.h | 4 +++ 2 files changed, 76 insertions(+), 1 deletion(-) diff --git a/hw/ppc/pnv.c b/hw/ppc/pnv.c index aeafd7e894..1705699ef8 100644 --- a/hw/ppc/pnv.c +++ b/hw/ppc/pnv.c @@ -238,11 +238,38 @@ static void ppc_powernv_init(MachineState *machine) object_property_add_child(OBJECT(pnv), chip_name, chip, &error_fatal); object_property_set_int(chip, PNV_CHIP_HWID(i), "chip-id", &error_fatal); + object_property_set_int(chip, smp_cores, "nr-cores", &error_fatal); object_property_set_bool(chip, true, "realized", &error_fatal); } g_free(chip_typename); } +/* Allowed core identifiers on a POWER8 Processor Chip : + * + * + * EX1 - Venice only + * EX2 - Venice only + * EX3 - Venice only + * EX4 + * EX5 + * EX6 + * + * EX9 - Venice only + * EX10 - Venice only + * EX11 - Venice only + * EX12 + * EX13 + * EX14 + * + */ +#define POWER8E_CORE_MASK (0x7070ull) +#define POWER8_CORE_MASK (0x7e7eull) + +/* + * POWER9 has 24 cores, ids starting at 0x20 + */ +#define POWER9_CORE_MASK (0xffffff00000000ull) + static void pnv_chip_power8e_class_init(ObjectClass *klass, void *data) { DeviceClass *dc = DEVICE_CLASS(klass); @@ -251,6 +278,7 @@ static void pnv_chip_power8e_class_init(ObjectClass *klass, void *data) k->cpu_model = "POWER8E"; k->chip_type = PNV_CHIP_POWER8E; k->chip_cfam_id = 0x221ef04980000000ull; /* P8 Murano DD2.1 */ + k->cores_mask = POWER8E_CORE_MASK; dc->desc = "PowerNV Chip POWER8E"; } @@ -269,6 +297,7 @@ static void pnv_chip_power8_class_init(ObjectClass *klass, void *data) k->cpu_model = "POWER8"; k->chip_type = PNV_CHIP_POWER8; k->chip_cfam_id = 0x220ea04980000000ull; /* P8 Venice DD2.0 */ + k->cores_mask = POWER8_CORE_MASK; dc->desc = "PowerNV Chip POWER8"; } @@ -287,6 +316,7 @@ static void pnv_chip_power8nvl_class_init(ObjectClass *klass, void *data) k->cpu_model = "POWER8NVL"; k->chip_type = PNV_CHIP_POWER8NVL; k->chip_cfam_id = 0x120d304980000000ull; /* P8 Naples DD1.0 */ + k->cores_mask = POWER8_CORE_MASK; dc->desc = "PowerNV Chip POWER8NVL"; } @@ -305,6 +335,7 @@ static void pnv_chip_power9_class_init(ObjectClass *klass, void *data) k->cpu_model = "POWER9"; k->chip_type = PNV_CHIP_POWER9; k->chip_cfam_id = 0x100d104980000000ull; /* P9 Nimbus DD1.0 */ + k->cores_mask = POWER9_CORE_MASK; dc->desc = "PowerNV Chip POWER9"; } @@ -315,15 +346,55 @@ static const TypeInfo pnv_chip_power9_info = { .class_init = pnv_chip_power9_class_init, }; +static void pnv_chip_core_sanitize(PnvChip *chip, Error **errp) +{ + PnvChipClass *pcc = PNV_CHIP_GET_CLASS(chip); + int cores_max; + + /* + * No custom mask for this chip, let's use the default one from * + * the chip class + */ + if (!chip->cores_mask) { + chip->cores_mask = pcc->cores_mask; + } + + /* filter alien core ids ! some are reserved */ + if ((chip->cores_mask & pcc->cores_mask) != chip->cores_mask) { + error_setg(errp, "warning: invalid core mask for chip Ox%"PRIx64" !", + chip->cores_mask); + return; + } + chip->cores_mask &= pcc->cores_mask; + + /* now that we have a sane layout, let check the number of cores */ + cores_max = hweight_long(chip->cores_mask); + if (chip->nr_cores > cores_max) { + error_setg(errp, "warning: too many cores for chip ! Limit is %d", + cores_max); + return; + } +} + static void pnv_chip_realize(DeviceState *dev, Error **errp) { - /* left purposely empty */ + PnvChip *chip = PNV_CHIP(dev); + Error *error = NULL; + + /* Early checks on the core settings */ + pnv_chip_core_sanitize(chip, &error); + if (error) { + error_propagate(errp, error); + return; + } } static Property pnv_chip_properties[] = { DEFINE_PROP_UINT32("chip-id", PnvChip, chip_id, 0), DEFINE_PROP_UINT64("ram-start", PnvChip, ram_start, 0), DEFINE_PROP_UINT64("ram-size", PnvChip, ram_size, 0), + DEFINE_PROP_UINT32("nr-cores", PnvChip, nr_cores, 1), + DEFINE_PROP_UINT64("cores-mask", PnvChip, cores_mask, 0x0), DEFINE_PROP_END_OF_LIST(), }; diff --git a/include/hw/ppc/pnv.h b/include/hw/ppc/pnv.h index 7189961e1f..e084a8c303 100644 --- a/include/hw/ppc/pnv.h +++ b/include/hw/ppc/pnv.h @@ -44,6 +44,9 @@ typedef struct PnvChip { uint32_t chip_id; uint64_t ram_start; uint64_t ram_size; + + uint32_t nr_cores; + uint64_t cores_mask; } PnvChip; typedef struct PnvChipClass { @@ -54,6 +57,7 @@ typedef struct PnvChipClass { const char *cpu_model; PnvChipType chip_type; uint64_t chip_cfam_id; + uint64_t cores_mask; } PnvChipClass; #define TYPE_PNV_CHIP_POWER8E TYPE_PNV_CHIP "-POWER8E" From 631adaff31d9e127fecccb4a811c20ae13cd7194 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= Date: Sat, 22 Oct 2016 11:46:38 +0200 Subject: [PATCH 27/73] ppc/pnv: add a PIR handler to PnvChip MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The Processor Identification Register (PIR) is a register that holds a processor identifier which is used for bus transactions (XSCOM) and for processor differentiation in multiprocessor systems. It also used in the interrupt vector entries (IVE) to identify the thread serving the interrupts. P9 and P8 have some differences in the CPU PIR encoding. Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: David Gibson --- hw/ppc/pnv.c | 30 ++++++++++++++++++++++++++++++ include/hw/ppc/pnv.h | 2 ++ 2 files changed, 32 insertions(+) diff --git a/hw/ppc/pnv.c b/hw/ppc/pnv.c index 1705699ef8..825d28ca75 100644 --- a/hw/ppc/pnv.c +++ b/hw/ppc/pnv.c @@ -244,6 +244,32 @@ static void ppc_powernv_init(MachineState *machine) g_free(chip_typename); } +/* + * 0:21 Reserved - Read as zeros + * 22:24 Chip ID + * 25:28 Core number + * 29:31 Thread ID + */ +static uint32_t pnv_chip_core_pir_p8(PnvChip *chip, uint32_t core_id) +{ + return (chip->chip_id << 7) | (core_id << 3); +} + +/* + * 0:48 Reserved - Read as zeroes + * 49:52 Node ID + * 53:55 Chip ID + * 56 Reserved - Read as zero + * 57:61 Core number + * 62:63 Thread ID + * + * We only care about the lower bits. uint32_t is fine for the moment. + */ +static uint32_t pnv_chip_core_pir_p9(PnvChip *chip, uint32_t core_id) +{ + return (chip->chip_id << 8) | (core_id << 2); +} + /* Allowed core identifiers on a POWER8 Processor Chip : * * @@ -279,6 +305,7 @@ static void pnv_chip_power8e_class_init(ObjectClass *klass, void *data) k->chip_type = PNV_CHIP_POWER8E; k->chip_cfam_id = 0x221ef04980000000ull; /* P8 Murano DD2.1 */ k->cores_mask = POWER8E_CORE_MASK; + k->core_pir = pnv_chip_core_pir_p8; dc->desc = "PowerNV Chip POWER8E"; } @@ -298,6 +325,7 @@ static void pnv_chip_power8_class_init(ObjectClass *klass, void *data) k->chip_type = PNV_CHIP_POWER8; k->chip_cfam_id = 0x220ea04980000000ull; /* P8 Venice DD2.0 */ k->cores_mask = POWER8_CORE_MASK; + k->core_pir = pnv_chip_core_pir_p8; dc->desc = "PowerNV Chip POWER8"; } @@ -317,6 +345,7 @@ static void pnv_chip_power8nvl_class_init(ObjectClass *klass, void *data) k->chip_type = PNV_CHIP_POWER8NVL; k->chip_cfam_id = 0x120d304980000000ull; /* P8 Naples DD1.0 */ k->cores_mask = POWER8_CORE_MASK; + k->core_pir = pnv_chip_core_pir_p8; dc->desc = "PowerNV Chip POWER8NVL"; } @@ -336,6 +365,7 @@ static void pnv_chip_power9_class_init(ObjectClass *klass, void *data) k->chip_type = PNV_CHIP_POWER9; k->chip_cfam_id = 0x100d104980000000ull; /* P9 Nimbus DD1.0 */ k->cores_mask = POWER9_CORE_MASK; + k->core_pir = pnv_chip_core_pir_p9; dc->desc = "PowerNV Chip POWER9"; } diff --git a/include/hw/ppc/pnv.h b/include/hw/ppc/pnv.h index e084a8c303..b7987f8208 100644 --- a/include/hw/ppc/pnv.h +++ b/include/hw/ppc/pnv.h @@ -58,6 +58,8 @@ typedef struct PnvChipClass { PnvChipType chip_type; uint64_t chip_cfam_id; uint64_t cores_mask; + + uint32_t (*core_pir)(PnvChip *chip, uint32_t core_id); } PnvChipClass; #define TYPE_PNV_CHIP_POWER8E TYPE_PNV_CHIP "-POWER8E" From d2fd9612eedfbfda8461d1a5f897546e3c457abb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= Date: Sat, 22 Oct 2016 11:46:39 +0200 Subject: [PATCH 28/73] ppc/pnv: add a PnvCore object MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This is largy inspired by sPAPRCPUCore with some simplification, no hotplug for instance. A set of PnvCore objects is added to the PnvChip and the device tree is populated looping on these cores. Real HW cpu ids are now generated depending on the chip cpu model, the chip id and a core mask. The id is propagated to the CPU object, using properties, to set the SPR_PIR (Processor Identification Register) Signed-off-by: Cédric Le Goater Signed-off-by: David Gibson --- hw/ppc/Makefile.objs | 2 +- hw/ppc/pnv.c | 189 +++++++++++++++++++++++++++++++++++++- hw/ppc/pnv_core.c | 182 ++++++++++++++++++++++++++++++++++++ include/hw/ppc/pnv.h | 2 + include/hw/ppc/pnv_core.h | 48 ++++++++++ 5 files changed, 421 insertions(+), 2 deletions(-) create mode 100644 hw/ppc/pnv_core.c create mode 100644 include/hw/ppc/pnv_core.h diff --git a/hw/ppc/Makefile.objs b/hw/ppc/Makefile.objs index 8105db7d56..f8c7d1db9a 100644 --- a/hw/ppc/Makefile.objs +++ b/hw/ppc/Makefile.objs @@ -6,7 +6,7 @@ obj-$(CONFIG_PSERIES) += spapr_hcall.o spapr_iommu.o spapr_rtas.o obj-$(CONFIG_PSERIES) += spapr_pci.o spapr_rtc.o spapr_drc.o spapr_rng.o obj-$(CONFIG_PSERIES) += spapr_cpu_core.o # IBM PowerNV -obj-$(CONFIG_POWERNV) += pnv.o +obj-$(CONFIG_POWERNV) += pnv.o pnv_core.o ifeq ($(CONFIG_PCI)$(CONFIG_PSERIES)$(CONFIG_LINUX), yyy) obj-y += spapr_pci_vfio.o endif diff --git a/hw/ppc/pnv.c b/hw/ppc/pnv.c index 825d28ca75..3413107697 100644 --- a/hw/ppc/pnv.c +++ b/hw/ppc/pnv.c @@ -27,6 +27,7 @@ #include "hw/ppc/fdt.h" #include "hw/ppc/ppc.h" #include "hw/ppc/pnv.h" +#include "hw/ppc/pnv_core.h" #include "hw/loader.h" #include "exec/address-spaces.h" #include "qemu/cutils.h" @@ -75,12 +76,160 @@ static void powernv_populate_memory_node(void *fdt, int chip_id, hwaddr start, _FDT((fdt_setprop_cell(fdt, off, "ibm,chip-id", chip_id))); } +static int get_cpus_node(void *fdt) +{ + int cpus_offset = fdt_path_offset(fdt, "/cpus"); + + if (cpus_offset < 0) { + cpus_offset = fdt_add_subnode(fdt, fdt_path_offset(fdt, "/"), + "cpus"); + if (cpus_offset) { + _FDT((fdt_setprop_cell(fdt, cpus_offset, "#address-cells", 0x1))); + _FDT((fdt_setprop_cell(fdt, cpus_offset, "#size-cells", 0x0))); + } + } + _FDT(cpus_offset); + return cpus_offset; +} + +/* + * The PowerNV cores (and threads) need to use real HW ids and not an + * incremental index like it has been done on other platforms. This HW + * id is stored in the CPU PIR, it is used to create cpu nodes in the + * device tree, used in XSCOM to address cores and in interrupt + * servers. + */ +static void powernv_create_core_node(PnvChip *chip, PnvCore *pc, void *fdt) +{ + CPUState *cs = CPU(DEVICE(pc->threads)); + DeviceClass *dc = DEVICE_GET_CLASS(cs); + PowerPCCPU *cpu = POWERPC_CPU(cs); + int smt_threads = ppc_get_compat_smt_threads(cpu); + CPUPPCState *env = &cpu->env; + PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cs); + uint32_t servers_prop[smt_threads]; + int i; + uint32_t segs[] = {cpu_to_be32(28), cpu_to_be32(40), + 0xffffffff, 0xffffffff}; + uint32_t tbfreq = PNV_TIMEBASE_FREQ; + uint32_t cpufreq = 1000000000; + uint32_t page_sizes_prop[64]; + size_t page_sizes_prop_size; + const uint8_t pa_features[] = { 24, 0, + 0xf6, 0x3f, 0xc7, 0xc0, 0x80, 0xf0, + 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x80, 0x00, + 0x80, 0x00, 0x80, 0x00, 0x80, 0x00 }; + int offset; + char *nodename; + int cpus_offset = get_cpus_node(fdt); + + nodename = g_strdup_printf("%s@%x", dc->fw_name, pc->pir); + offset = fdt_add_subnode(fdt, cpus_offset, nodename); + _FDT(offset); + g_free(nodename); + + _FDT((fdt_setprop_cell(fdt, offset, "ibm,chip-id", chip->chip_id))); + + _FDT((fdt_setprop_cell(fdt, offset, "reg", pc->pir))); + _FDT((fdt_setprop_cell(fdt, offset, "ibm,pir", pc->pir))); + _FDT((fdt_setprop_string(fdt, offset, "device_type", "cpu"))); + + _FDT((fdt_setprop_cell(fdt, offset, "cpu-version", env->spr[SPR_PVR]))); + _FDT((fdt_setprop_cell(fdt, offset, "d-cache-block-size", + env->dcache_line_size))); + _FDT((fdt_setprop_cell(fdt, offset, "d-cache-line-size", + env->dcache_line_size))); + _FDT((fdt_setprop_cell(fdt, offset, "i-cache-block-size", + env->icache_line_size))); + _FDT((fdt_setprop_cell(fdt, offset, "i-cache-line-size", + env->icache_line_size))); + + if (pcc->l1_dcache_size) { + _FDT((fdt_setprop_cell(fdt, offset, "d-cache-size", + pcc->l1_dcache_size))); + } else { + error_report("Warning: Unknown L1 dcache size for cpu"); + } + if (pcc->l1_icache_size) { + _FDT((fdt_setprop_cell(fdt, offset, "i-cache-size", + pcc->l1_icache_size))); + } else { + error_report("Warning: Unknown L1 icache size for cpu"); + } + + _FDT((fdt_setprop_cell(fdt, offset, "timebase-frequency", tbfreq))); + _FDT((fdt_setprop_cell(fdt, offset, "clock-frequency", cpufreq))); + _FDT((fdt_setprop_cell(fdt, offset, "ibm,slb-size", env->slb_nr))); + _FDT((fdt_setprop_string(fdt, offset, "status", "okay"))); + _FDT((fdt_setprop(fdt, offset, "64-bit", NULL, 0))); + + if (env->spr_cb[SPR_PURR].oea_read) { + _FDT((fdt_setprop(fdt, offset, "ibm,purr", NULL, 0))); + } + + if (env->mmu_model & POWERPC_MMU_1TSEG) { + _FDT((fdt_setprop(fdt, offset, "ibm,processor-segment-sizes", + segs, sizeof(segs)))); + } + + /* Advertise VMX/VSX (vector extensions) if available + * 0 / no property == no vector extensions + * 1 == VMX / Altivec available + * 2 == VSX available */ + if (env->insns_flags & PPC_ALTIVEC) { + uint32_t vmx = (env->insns_flags2 & PPC2_VSX) ? 2 : 1; + + _FDT((fdt_setprop_cell(fdt, offset, "ibm,vmx", vmx))); + } + + /* Advertise DFP (Decimal Floating Point) if available + * 0 / no property == no DFP + * 1 == DFP available */ + if (env->insns_flags2 & PPC2_DFP) { + _FDT((fdt_setprop_cell(fdt, offset, "ibm,dfp", 1))); + } + + page_sizes_prop_size = ppc_create_page_sizes_prop(env, page_sizes_prop, + sizeof(page_sizes_prop)); + if (page_sizes_prop_size) { + _FDT((fdt_setprop(fdt, offset, "ibm,segment-page-sizes", + page_sizes_prop, page_sizes_prop_size))); + } + + _FDT((fdt_setprop(fdt, offset, "ibm,pa-features", + pa_features, sizeof(pa_features)))); + + if (cpu->cpu_version) { + _FDT((fdt_setprop_cell(fdt, offset, "cpu-version", cpu->cpu_version))); + } + + /* Build interrupt servers properties */ + for (i = 0; i < smt_threads; i++) { + servers_prop[i] = cpu_to_be32(pc->pir + i); + } + _FDT((fdt_setprop(fdt, offset, "ibm,ppc-interrupt-server#s", + servers_prop, sizeof(servers_prop)))); +} + static void powernv_populate_chip(PnvChip *chip, void *fdt) { + PnvChipClass *pcc = PNV_CHIP_GET_CLASS(chip); + char *typename = pnv_core_typename(pcc->cpu_model); + size_t typesize = object_type_get_instance_size(typename); + int i; + + for (i = 0; i < chip->nr_cores; i++) { + PnvCore *pnv_core = PNV_CORE(chip->cores + i * typesize); + + powernv_create_core_node(chip, pnv_core, fdt); + } + if (chip->ram_size) { powernv_populate_memory_node(fdt, chip->chip_id, chip->ram_start, chip->ram_size); } + g_free(typename); } static void *powernv_create_fdt(MachineState *machine) @@ -410,13 +559,51 @@ static void pnv_chip_realize(DeviceState *dev, Error **errp) { PnvChip *chip = PNV_CHIP(dev); Error *error = NULL; + PnvChipClass *pcc = PNV_CHIP_GET_CLASS(chip); + char *typename = pnv_core_typename(pcc->cpu_model); + size_t typesize = object_type_get_instance_size(typename); + int i, core_hwid; - /* Early checks on the core settings */ + if (!object_class_by_name(typename)) { + error_setg(errp, "Unable to find PowerNV CPU Core '%s'", typename); + return; + } + + /* Cores */ pnv_chip_core_sanitize(chip, &error); if (error) { error_propagate(errp, error); return; } + + chip->cores = g_malloc0(typesize * chip->nr_cores); + + for (i = 0, core_hwid = 0; (core_hwid < sizeof(chip->cores_mask) * 8) + && (i < chip->nr_cores); core_hwid++) { + char core_name[32]; + void *pnv_core = chip->cores + i * typesize; + + if (!(chip->cores_mask & (1ull << core_hwid))) { + continue; + } + + object_initialize(pnv_core, typesize, typename); + snprintf(core_name, sizeof(core_name), "core[%d]", core_hwid); + object_property_add_child(OBJECT(chip), core_name, OBJECT(pnv_core), + &error_fatal); + object_property_set_int(OBJECT(pnv_core), smp_threads, "nr-threads", + &error_fatal); + object_property_set_int(OBJECT(pnv_core), core_hwid, + CPU_CORE_PROP_CORE_ID, &error_fatal); + object_property_set_int(OBJECT(pnv_core), + pcc->core_pir(chip, core_hwid), + "pir", &error_fatal); + object_property_set_bool(OBJECT(pnv_core), true, "realized", + &error_fatal); + object_unref(OBJECT(pnv_core)); + i++; + } + g_free(typename); } static Property pnv_chip_properties[] = { diff --git a/hw/ppc/pnv_core.c b/hw/ppc/pnv_core.c new file mode 100644 index 0000000000..04713caa3b --- /dev/null +++ b/hw/ppc/pnv_core.c @@ -0,0 +1,182 @@ +/* + * QEMU PowerPC PowerNV CPU Core model + * + * Copyright (c) 2016, IBM Corporation. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public License + * as published by the Free Software Foundation; either version 2 of + * the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, see . + */ +#include "qemu/osdep.h" +#include "sysemu/sysemu.h" +#include "qapi/error.h" +#include "target-ppc/cpu.h" +#include "hw/ppc/ppc.h" +#include "hw/ppc/pnv.h" +#include "hw/ppc/pnv_core.h" + +static void powernv_cpu_reset(void *opaque) +{ + PowerPCCPU *cpu = opaque; + CPUState *cs = CPU(cpu); + CPUPPCState *env = &cpu->env; + + cpu_reset(cs); + + /* + * the skiboot firmware elects a primary thread to initialize the + * system and it can be any. + */ + env->gpr[3] = PNV_FDT_ADDR; + env->nip = 0x10; + env->msr |= MSR_HVB; /* Hypervisor mode */ +} + +static void powernv_cpu_init(PowerPCCPU *cpu, Error **errp) +{ + CPUPPCState *env = &cpu->env; + int core_pir; + int thread_index = 0; /* TODO: TCG supports only one thread */ + ppc_spr_t *pir = &env->spr_cb[SPR_PIR]; + + core_pir = object_property_get_int(OBJECT(cpu), "core-pir", &error_abort); + + /* + * The PIR of a thread is the core PIR + the thread index. We will + * need to find a way to get the thread index when TCG supports + * more than 1. We could use the object name ? + */ + pir->default_value = core_pir + thread_index; + + /* Set time-base frequency to 512 MHz */ + cpu_ppc_tb_init(env, PNV_TIMEBASE_FREQ); + + qemu_register_reset(powernv_cpu_reset, cpu); +} + +static void pnv_core_realize_child(Object *child, Error **errp) +{ + Error *local_err = NULL; + CPUState *cs = CPU(child); + PowerPCCPU *cpu = POWERPC_CPU(cs); + + object_property_set_bool(child, true, "realized", &local_err); + if (local_err) { + error_propagate(errp, local_err); + return; + } + + powernv_cpu_init(cpu, &local_err); + if (local_err) { + error_propagate(errp, local_err); + return; + } +} + +static void pnv_core_realize(DeviceState *dev, Error **errp) +{ + PnvCore *pc = PNV_CORE(OBJECT(dev)); + CPUCore *cc = CPU_CORE(OBJECT(dev)); + PnvCoreClass *pcc = PNV_CORE_GET_CLASS(OBJECT(dev)); + const char *typename = object_class_get_name(pcc->cpu_oc); + size_t size = object_type_get_instance_size(typename); + Error *local_err = NULL; + void *obj; + int i, j; + char name[32]; + + pc->threads = g_malloc0(size * cc->nr_threads); + for (i = 0; i < cc->nr_threads; i++) { + obj = pc->threads + i * size; + + object_initialize(obj, size, typename); + + snprintf(name, sizeof(name), "thread[%d]", i); + object_property_add_child(OBJECT(pc), name, obj, &local_err); + object_property_add_alias(obj, "core-pir", OBJECT(pc), + "pir", &local_err); + if (local_err) { + goto err; + } + object_unref(obj); + } + + for (j = 0; j < cc->nr_threads; j++) { + obj = pc->threads + j * size; + + pnv_core_realize_child(obj, &local_err); + if (local_err) { + goto err; + } + } + return; + +err: + while (--i >= 0) { + obj = pc->threads + i * size; + object_unparent(obj); + } + g_free(pc->threads); + error_propagate(errp, local_err); +} + +static Property pnv_core_properties[] = { + DEFINE_PROP_UINT32("pir", PnvCore, pir, 0), + DEFINE_PROP_END_OF_LIST(), +}; + +static void pnv_core_class_init(ObjectClass *oc, void *data) +{ + DeviceClass *dc = DEVICE_CLASS(oc); + PnvCoreClass *pcc = PNV_CORE_CLASS(oc); + + dc->realize = pnv_core_realize; + dc->props = pnv_core_properties; + pcc->cpu_oc = cpu_class_by_name(TYPE_POWERPC_CPU, data); +} + +static const TypeInfo pnv_core_info = { + .name = TYPE_PNV_CORE, + .parent = TYPE_CPU_CORE, + .instance_size = sizeof(PnvCore), + .class_size = sizeof(PnvCoreClass), + .abstract = true, +}; + +static const char *pnv_core_models[] = { + "POWER8E", "POWER8", "POWER8NVL", "POWER9" +}; + +static void pnv_core_register_types(void) +{ + int i ; + + type_register_static(&pnv_core_info); + for (i = 0; i < ARRAY_SIZE(pnv_core_models); ++i) { + TypeInfo ti = { + .parent = TYPE_PNV_CORE, + .instance_size = sizeof(PnvCore), + .class_init = pnv_core_class_init, + .class_data = (void *) pnv_core_models[i], + }; + ti.name = pnv_core_typename(pnv_core_models[i]); + type_register(&ti); + g_free((void *)ti.name); + } +} + +type_init(pnv_core_register_types) + +char *pnv_core_typename(const char *model) +{ + return g_strdup_printf(TYPE_PNV_CORE "-%s", model); +} diff --git a/include/hw/ppc/pnv.h b/include/hw/ppc/pnv.h index b7987f8208..cec869ce6b 100644 --- a/include/hw/ppc/pnv.h +++ b/include/hw/ppc/pnv.h @@ -47,6 +47,7 @@ typedef struct PnvChip { uint32_t nr_cores; uint64_t cores_mask; + void *cores; } PnvChip; typedef struct PnvChipClass { @@ -103,5 +104,6 @@ typedef struct PnvMachineState { } PnvMachineState; #define PNV_FDT_ADDR 0x01000000 +#define PNV_TIMEBASE_FREQ 512000000ULL #endif /* _PPC_PNV_H */ diff --git a/include/hw/ppc/pnv_core.h b/include/hw/ppc/pnv_core.h new file mode 100644 index 0000000000..a151e281c0 --- /dev/null +++ b/include/hw/ppc/pnv_core.h @@ -0,0 +1,48 @@ +/* + * QEMU PowerPC PowerNV CPU Core model + * + * Copyright (c) 2016, IBM Corporation. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public License + * as published by the Free Software Foundation; either version 2 of + * the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, see . + */ +#ifndef _PPC_PNV_CORE_H +#define _PPC_PNV_CORE_H + +#include "hw/cpu/core.h" + +#define TYPE_PNV_CORE "powernv-cpu-core" +#define PNV_CORE(obj) \ + OBJECT_CHECK(PnvCore, (obj), TYPE_PNV_CORE) +#define PNV_CORE_CLASS(klass) \ + OBJECT_CLASS_CHECK(PnvCoreClass, (klass), TYPE_PNV_CORE) +#define PNV_CORE_GET_CLASS(obj) \ + OBJECT_GET_CLASS(PnvCoreClass, (obj), TYPE_PNV_CORE) + +typedef struct PnvCore { + /*< private >*/ + CPUCore parent_obj; + + /*< public >*/ + void *threads; + uint32_t pir; +} PnvCore; + +typedef struct PnvCoreClass { + DeviceClass parent_class; + ObjectClass *cpu_oc; +} PnvCoreClass; + +extern char *pnv_core_typename(const char *model); + +#endif /* _PPC_PNV_CORE_H */ From 967b75230b9720ea2b3ae49f38f8287026125f9f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= Date: Sat, 22 Oct 2016 11:46:40 +0200 Subject: [PATCH 29/73] ppc/pnv: add XSCOM infrastructure MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit On a real POWER8 system, the Pervasive Interconnect Bus (PIB) serves as a backbone to connect different units of the system. The host firmware connects to the PIB through a bridge unit, the Alter-Display-Unit (ADU), which gives him access to all the chiplets on the PCB network (Pervasive Connect Bus), the PIB acting as the root of this network. XSCOM (serial communication) is the interface to the sideband bus provided by the POWER8 pervasive unit to read and write to chiplets resources. This is needed by the host firmware, OPAL and to a lesser extent, Linux. This is among others how the PCI Host bridges get configured at boot or how the LPC bus is accessed. To represent the ADU of a real system, we introduce a specific AddressSpace to dispatch XSCOM accesses to the targeted chiplets. The translation of an XSCOM address into a PCB register address is slightly different between the P9 and the P8. This is handled before the dispatch using a 8byte alignment for all. To customize the device tree, a QOM InterfaceClass, PnvXScomInterface, is provided with a populate() handler. The chip populates the device tree by simply looping on its children. Therefore, each model needing custom nodes should not forget to declare itself as a child at instantiation time. Based on previous work done by : Benjamin Herrenschmidt Signed-off-by: Cédric Le Goater [dwg: Added cpu parameter to xscom_complete()] Signed-off-by: David Gibson --- hw/ppc/Makefile.objs | 2 +- hw/ppc/pnv.c | 25 ++++ hw/ppc/pnv_xscom.c | 275 +++++++++++++++++++++++++++++++++++++ include/hw/ppc/pnv.h | 15 ++ include/hw/ppc/pnv_xscom.h | 56 ++++++++ 5 files changed, 372 insertions(+), 1 deletion(-) create mode 100644 hw/ppc/pnv_xscom.c create mode 100644 include/hw/ppc/pnv_xscom.h diff --git a/hw/ppc/Makefile.objs b/hw/ppc/Makefile.objs index f8c7d1db9a..08c213c406 100644 --- a/hw/ppc/Makefile.objs +++ b/hw/ppc/Makefile.objs @@ -6,7 +6,7 @@ obj-$(CONFIG_PSERIES) += spapr_hcall.o spapr_iommu.o spapr_rtas.o obj-$(CONFIG_PSERIES) += spapr_pci.o spapr_rtc.o spapr_drc.o spapr_rng.o obj-$(CONFIG_PSERIES) += spapr_cpu_core.o # IBM PowerNV -obj-$(CONFIG_POWERNV) += pnv.o pnv_core.o +obj-$(CONFIG_POWERNV) += pnv.o pnv_xscom.o pnv_core.o ifeq ($(CONFIG_PCI)$(CONFIG_PSERIES)$(CONFIG_LINUX), yyy) obj-y += spapr_pci_vfio.o endif diff --git a/hw/ppc/pnv.c b/hw/ppc/pnv.c index 3413107697..96ba36cc27 100644 --- a/hw/ppc/pnv.c +++ b/hw/ppc/pnv.c @@ -33,6 +33,8 @@ #include "qemu/cutils.h" #include "qapi/visitor.h" +#include "hw/ppc/pnv_xscom.h" + #include #define FDT_MAX_SIZE 0x00100000 @@ -219,6 +221,8 @@ static void powernv_populate_chip(PnvChip *chip, void *fdt) size_t typesize = object_type_get_instance_size(typename); int i; + pnv_xscom_populate(chip, fdt, 0); + for (i = 0; i < chip->nr_cores; i++) { PnvCore *pnv_core = PNV_CORE(chip->cores + i * typesize); @@ -455,6 +459,7 @@ static void pnv_chip_power8e_class_init(ObjectClass *klass, void *data) k->chip_cfam_id = 0x221ef04980000000ull; /* P8 Murano DD2.1 */ k->cores_mask = POWER8E_CORE_MASK; k->core_pir = pnv_chip_core_pir_p8; + k->xscom_base = 0x003fc0000000000ull; dc->desc = "PowerNV Chip POWER8E"; } @@ -475,6 +480,7 @@ static void pnv_chip_power8_class_init(ObjectClass *klass, void *data) k->chip_cfam_id = 0x220ea04980000000ull; /* P8 Venice DD2.0 */ k->cores_mask = POWER8_CORE_MASK; k->core_pir = pnv_chip_core_pir_p8; + k->xscom_base = 0x003fc0000000000ull; dc->desc = "PowerNV Chip POWER8"; } @@ -495,6 +501,7 @@ static void pnv_chip_power8nvl_class_init(ObjectClass *klass, void *data) k->chip_cfam_id = 0x120d304980000000ull; /* P8 Naples DD1.0 */ k->cores_mask = POWER8_CORE_MASK; k->core_pir = pnv_chip_core_pir_p8; + k->xscom_base = 0x003fc0000000000ull; dc->desc = "PowerNV Chip POWER8NVL"; } @@ -515,6 +522,7 @@ static void pnv_chip_power9_class_init(ObjectClass *klass, void *data) k->chip_cfam_id = 0x100d104980000000ull; /* P9 Nimbus DD1.0 */ k->cores_mask = POWER9_CORE_MASK; k->core_pir = pnv_chip_core_pir_p9; + k->xscom_base = 0x00603fc00000000ull; dc->desc = "PowerNV Chip POWER9"; } @@ -555,6 +563,14 @@ static void pnv_chip_core_sanitize(PnvChip *chip, Error **errp) } } +static void pnv_chip_init(Object *obj) +{ + PnvChip *chip = PNV_CHIP(obj); + PnvChipClass *pcc = PNV_CHIP_GET_CLASS(chip); + + chip->xscom_base = pcc->xscom_base; +} + static void pnv_chip_realize(DeviceState *dev, Error **errp) { PnvChip *chip = PNV_CHIP(dev); @@ -569,6 +585,14 @@ static void pnv_chip_realize(DeviceState *dev, Error **errp) return; } + /* XSCOM bridge */ + pnv_xscom_realize(chip, &error); + if (error) { + error_propagate(errp, error); + return; + } + sysbus_mmio_map(SYS_BUS_DEVICE(chip), 0, PNV_XSCOM_BASE(chip)); + /* Cores */ pnv_chip_core_sanitize(chip, &error); if (error) { @@ -628,6 +652,7 @@ static const TypeInfo pnv_chip_info = { .name = TYPE_PNV_CHIP, .parent = TYPE_SYS_BUS_DEVICE, .class_init = pnv_chip_class_init, + .instance_init = pnv_chip_init, .class_size = sizeof(PnvChipClass), .abstract = true, }; diff --git a/hw/ppc/pnv_xscom.c b/hw/ppc/pnv_xscom.c new file mode 100644 index 0000000000..5aaa264bd7 --- /dev/null +++ b/hw/ppc/pnv_xscom.c @@ -0,0 +1,275 @@ +/* + * QEMU PowerPC PowerNV XSCOM bus + * + * Copyright (c) 2016, IBM Corporation. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, see . + */ +#include "qemu/osdep.h" +#include "qapi/error.h" +#include "hw/hw.h" +#include "qemu/log.h" +#include "sysemu/kvm.h" +#include "target-ppc/cpu.h" +#include "hw/sysbus.h" + +#include "hw/ppc/fdt.h" +#include "hw/ppc/pnv_xscom.h" +#include "hw/ppc/pnv.h" + +#include + +static void xscom_complete(CPUState *cs, uint64_t hmer_bits) +{ + /* + * TODO: When the read/write comes from the monitor, NULL is + * passed for the cpu, and no CPU completion is generated. + */ + if (cs) { + PowerPCCPU *cpu = POWERPC_CPU(cs); + CPUPPCState *env = &cpu->env; + + /* + * TODO: Need a CPU helper to set HMER, also handle generation + * of HMIs + */ + cpu_synchronize_state(cs); + env->spr[SPR_HMER] |= hmer_bits; + } +} + +static uint32_t pnv_xscom_pcba(PnvChip *chip, uint64_t addr) +{ + PnvChipClass *pcc = PNV_CHIP_GET_CLASS(chip); + + addr &= (PNV_XSCOM_SIZE - 1); + if (pcc->chip_type == PNV_CHIP_POWER9) { + return addr >> 3; + } else { + return ((addr >> 4) & ~0xfull) | ((addr >> 3) & 0xf); + } +} + +static uint64_t xscom_read_default(PnvChip *chip, uint32_t pcba) +{ + switch (pcba) { + case 0xf000f: + return PNV_CHIP_GET_CLASS(chip)->chip_cfam_id; + case 0x1010c00: /* PIBAM FIR */ + case 0x1010c03: /* PIBAM FIR MASK */ + case 0x2020007: /* ADU stuff */ + case 0x2020009: /* ADU stuff */ + case 0x202000f: /* ADU stuff */ + return 0; + case 0x2013f00: /* PBA stuff */ + case 0x2013f01: /* PBA stuff */ + case 0x2013f02: /* PBA stuff */ + case 0x2013f03: /* PBA stuff */ + case 0x2013f04: /* PBA stuff */ + case 0x2013f05: /* PBA stuff */ + case 0x2013f06: /* PBA stuff */ + case 0x2013f07: /* PBA stuff */ + return 0; + case 0x2013028: /* CAPP stuff */ + case 0x201302a: /* CAPP stuff */ + case 0x2013801: /* CAPP stuff */ + case 0x2013802: /* CAPP stuff */ + return 0; + default: + return -1; + } +} + +static bool xscom_write_default(PnvChip *chip, uint32_t pcba, uint64_t val) +{ + /* We ignore writes to these */ + switch (pcba) { + case 0xf000f: /* chip id is RO */ + case 0x1010c00: /* PIBAM FIR */ + case 0x1010c01: /* PIBAM FIR */ + case 0x1010c02: /* PIBAM FIR */ + case 0x1010c03: /* PIBAM FIR MASK */ + case 0x1010c04: /* PIBAM FIR MASK */ + case 0x1010c05: /* PIBAM FIR MASK */ + case 0x2020007: /* ADU stuff */ + case 0x2020009: /* ADU stuff */ + case 0x202000f: /* ADU stuff */ + return true; + default: + return false; + } +} + +static uint64_t xscom_read(void *opaque, hwaddr addr, unsigned width) +{ + PnvChip *chip = opaque; + uint32_t pcba = pnv_xscom_pcba(chip, addr); + uint64_t val = 0; + MemTxResult result; + + /* Handle some SCOMs here before dispatch */ + val = xscom_read_default(chip, pcba); + if (val != -1) { + goto complete; + } + + val = address_space_ldq(&chip->xscom_as, pcba << 3, MEMTXATTRS_UNSPECIFIED, + &result); + if (result != MEMTX_OK) { + qemu_log_mask(LOG_GUEST_ERROR, "XSCOM read failed at @0x%" + HWADDR_PRIx " pcba=0x%08x\n", addr, pcba); + xscom_complete(current_cpu, HMER_XSCOM_FAIL | HMER_XSCOM_DONE); + return 0; + } + +complete: + xscom_complete(current_cpu, HMER_XSCOM_DONE); + return val; +} + +static void xscom_write(void *opaque, hwaddr addr, uint64_t val, + unsigned width) +{ + PnvChip *chip = opaque; + uint32_t pcba = pnv_xscom_pcba(chip, addr); + MemTxResult result; + + /* Handle some SCOMs here before dispatch */ + if (xscom_write_default(chip, pcba, val)) { + goto complete; + } + + address_space_stq(&chip->xscom_as, pcba << 3, val, MEMTXATTRS_UNSPECIFIED, + &result); + if (result != MEMTX_OK) { + qemu_log_mask(LOG_GUEST_ERROR, "XSCOM write failed at @0x%" + HWADDR_PRIx " pcba=0x%08x data=0x%" PRIx64 "\n", + addr, pcba, val); + xscom_complete(current_cpu, HMER_XSCOM_FAIL | HMER_XSCOM_DONE); + return; + } + +complete: + xscom_complete(current_cpu, HMER_XSCOM_DONE); +} + +const MemoryRegionOps pnv_xscom_ops = { + .read = xscom_read, + .write = xscom_write, + .valid.min_access_size = 8, + .valid.max_access_size = 8, + .impl.min_access_size = 8, + .impl.max_access_size = 8, + .endianness = DEVICE_BIG_ENDIAN, +}; + +void pnv_xscom_realize(PnvChip *chip, Error **errp) +{ + SysBusDevice *sbd = SYS_BUS_DEVICE(chip); + char *name; + + name = g_strdup_printf("xscom-%x", chip->chip_id); + memory_region_init_io(&chip->xscom_mmio, OBJECT(chip), &pnv_xscom_ops, + chip, name, PNV_XSCOM_SIZE); + sysbus_init_mmio(sbd, &chip->xscom_mmio); + + memory_region_init(&chip->xscom, OBJECT(chip), name, PNV_XSCOM_SIZE); + address_space_init(&chip->xscom_as, &chip->xscom, name); + g_free(name); +} + +static const TypeInfo pnv_xscom_interface_info = { + .name = TYPE_PNV_XSCOM_INTERFACE, + .parent = TYPE_INTERFACE, + .class_size = sizeof(PnvXScomInterfaceClass), +}; + +static void pnv_xscom_register_types(void) +{ + type_register_static(&pnv_xscom_interface_info); +} + +type_init(pnv_xscom_register_types) + +typedef struct ForeachPopulateArgs { + void *fdt; + int xscom_offset; +} ForeachPopulateArgs; + +static int xscom_populate_child(Object *child, void *opaque) +{ + if (object_dynamic_cast(child, TYPE_PNV_XSCOM_INTERFACE)) { + ForeachPopulateArgs *args = opaque; + PnvXScomInterface *xd = PNV_XSCOM_INTERFACE(child); + PnvXScomInterfaceClass *xc = PNV_XSCOM_INTERFACE_GET_CLASS(xd); + + if (xc->populate) { + _FDT((xc->populate(xd, args->fdt, args->xscom_offset))); + } + } + return 0; +} + +static const char compat_p8[] = "ibm,power8-xscom\0ibm,xscom"; +static const char compat_p9[] = "ibm,power9-xscom\0ibm,xscom"; + +int pnv_xscom_populate(PnvChip *chip, void *fdt, int root_offset) +{ + uint64_t reg[] = { cpu_to_be64(PNV_XSCOM_BASE(chip)), + cpu_to_be64(PNV_XSCOM_SIZE) }; + int xscom_offset; + ForeachPopulateArgs args; + char *name; + PnvChipClass *pcc = PNV_CHIP_GET_CLASS(chip); + + name = g_strdup_printf("xscom@%" PRIx64, be64_to_cpu(reg[0])); + xscom_offset = fdt_add_subnode(fdt, root_offset, name); + _FDT(xscom_offset); + g_free(name); + _FDT((fdt_setprop_cell(fdt, xscom_offset, "ibm,chip-id", chip->chip_id))); + _FDT((fdt_setprop_cell(fdt, xscom_offset, "#address-cells", 1))); + _FDT((fdt_setprop_cell(fdt, xscom_offset, "#size-cells", 1))); + _FDT((fdt_setprop(fdt, xscom_offset, "reg", reg, sizeof(reg)))); + + if (pcc->chip_type == PNV_CHIP_POWER9) { + _FDT((fdt_setprop(fdt, xscom_offset, "compatible", compat_p9, + sizeof(compat_p9)))); + } else { + _FDT((fdt_setprop(fdt, xscom_offset, "compatible", compat_p8, + sizeof(compat_p8)))); + } + + _FDT((fdt_setprop(fdt, xscom_offset, "scom-controller", NULL, 0))); + + args.fdt = fdt; + args.xscom_offset = xscom_offset; + + object_child_foreach(OBJECT(chip), xscom_populate_child, &args); + return 0; +} + +void pnv_xscom_add_subregion(PnvChip *chip, hwaddr offset, MemoryRegion *mr) +{ + memory_region_add_subregion(&chip->xscom, offset << 3, mr); +} + +void pnv_xscom_region_init(MemoryRegion *mr, + struct Object *owner, + const MemoryRegionOps *ops, + void *opaque, + const char *name, + uint64_t size) +{ + memory_region_init_io(mr, owner, ops, opaque, name, size << 3); +} diff --git a/include/hw/ppc/pnv.h b/include/hw/ppc/pnv.h index cec869ce6b..7db922e285 100644 --- a/include/hw/ppc/pnv.h +++ b/include/hw/ppc/pnv.h @@ -21,6 +21,7 @@ #include "hw/boards.h" #include "hw/sysbus.h" +#include "hw/ppc/pnv_xscom.h" #define TYPE_PNV_CHIP "powernv-chip" #define PNV_CHIP(obj) OBJECT_CHECK(PnvChip, (obj), TYPE_PNV_CHIP) @@ -48,6 +49,11 @@ typedef struct PnvChip { uint32_t nr_cores; uint64_t cores_mask; void *cores; + + hwaddr xscom_base; + MemoryRegion xscom_mmio; + MemoryRegion xscom; + AddressSpace xscom_as; } PnvChip; typedef struct PnvChipClass { @@ -60,6 +66,8 @@ typedef struct PnvChipClass { uint64_t chip_cfam_id; uint64_t cores_mask; + hwaddr xscom_base; + uint32_t (*core_pir)(PnvChip *chip, uint32_t core_id); } PnvChipClass; @@ -106,4 +114,11 @@ typedef struct PnvMachineState { #define PNV_FDT_ADDR 0x01000000 #define PNV_TIMEBASE_FREQ 512000000ULL +/* + * POWER8 MMIO base addresses + */ +#define PNV_XSCOM_SIZE 0x800000000ull +#define PNV_XSCOM_BASE(chip) \ + (chip->xscom_base + ((uint64_t)(chip)->chip_id) * PNV_XSCOM_SIZE) + #endif /* _PPC_PNV_H */ diff --git a/include/hw/ppc/pnv_xscom.h b/include/hw/ppc/pnv_xscom.h new file mode 100644 index 0000000000..ee25ec455e --- /dev/null +++ b/include/hw/ppc/pnv_xscom.h @@ -0,0 +1,56 @@ +/* + * QEMU PowerPC PowerNV XSCOM bus definitions + * + * Copyright (c) 2016, IBM Corporation. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, see . + */ +#ifndef _PPC_PNV_XSCOM_H +#define _PPC_PNV_XSCOM_H + +#include "qom/object.h" + +typedef struct PnvChip PnvChip; + +typedef struct PnvXScomInterface { + Object parent; +} PnvXScomInterface; + +#define TYPE_PNV_XSCOM_INTERFACE "pnv-xscom-interface" +#define PNV_XSCOM_INTERFACE(obj) \ + OBJECT_CHECK(PnvXScomInterface, (obj), TYPE_PNV_XSCOM_INTERFACE) +#define PNV_XSCOM_INTERFACE_CLASS(klass) \ + OBJECT_CLASS_CHECK(PnvXScomInterfaceClass, (klass), \ + TYPE_PNV_XSCOM_INTERFACE) +#define PNV_XSCOM_INTERFACE_GET_CLASS(obj) \ + OBJECT_GET_CLASS(PnvXScomInterfaceClass, (obj), TYPE_PNV_XSCOM_INTERFACE) + +typedef struct PnvXScomInterfaceClass { + InterfaceClass parent; + int (*populate)(PnvXScomInterface *dev, void *fdt, int offset); +} PnvXScomInterfaceClass; + +extern void pnv_xscom_realize(PnvChip *chip, Error **errp); +extern int pnv_xscom_populate(PnvChip *chip, void *fdt, int offset); + +extern void pnv_xscom_add_subregion(PnvChip *chip, hwaddr offset, + MemoryRegion *mr); +extern void pnv_xscom_region_init(MemoryRegion *mr, + struct Object *owner, + const MemoryRegionOps *ops, + void *opaque, + const char *name, + uint64_t size); + +#endif /* _PPC_PNV_XSCOM_H */ From 24ece072504b8c8b03861168d601d174a7948099 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= Date: Sat, 22 Oct 2016 11:46:41 +0200 Subject: [PATCH 30/73] ppc/pnv: add XSCOM handlers to PnvCore MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Now that we are using real HW ids for the cores in PowerNV chips, we can route the XSCOM accesses to them. We just need to attach a specific XSCOM memory region to each core in the appropriate window for the core number. To start with, let's install the DTS (Digital Thermal Sensor) handlers which should return 38°C for each core. Signed-off-by: Cédric Le Goater Signed-off-by: David Gibson --- hw/ppc/pnv.c | 4 +++ hw/ppc/pnv_core.c | 50 ++++++++++++++++++++++++++++++++++++++ include/hw/ppc/pnv_core.h | 2 ++ include/hw/ppc/pnv_xscom.h | 19 +++++++++++++++ 4 files changed, 75 insertions(+) diff --git a/hw/ppc/pnv.c b/hw/ppc/pnv.c index 96ba36cc27..df55a89cb9 100644 --- a/hw/ppc/pnv.c +++ b/hw/ppc/pnv.c @@ -625,6 +625,10 @@ static void pnv_chip_realize(DeviceState *dev, Error **errp) object_property_set_bool(OBJECT(pnv_core), true, "realized", &error_fatal); object_unref(OBJECT(pnv_core)); + + /* Each core has an XSCOM MMIO region */ + pnv_xscom_add_subregion(chip, PNV_XSCOM_EX_CORE_BASE(core_hwid), + &PNV_CORE(pnv_core)->xscom_regs); i++; } g_free(typename); diff --git a/hw/ppc/pnv_core.c b/hw/ppc/pnv_core.c index 04713caa3b..2acda9637d 100644 --- a/hw/ppc/pnv_core.c +++ b/hw/ppc/pnv_core.c @@ -19,6 +19,7 @@ #include "qemu/osdep.h" #include "sysemu/sysemu.h" #include "qapi/error.h" +#include "qemu/log.h" #include "target-ppc/cpu.h" #include "hw/ppc/ppc.h" #include "hw/ppc/pnv.h" @@ -63,6 +64,51 @@ static void powernv_cpu_init(PowerPCCPU *cpu, Error **errp) qemu_register_reset(powernv_cpu_reset, cpu); } +/* + * These values are read by the PowerNV HW monitors under Linux + */ +#define PNV_XSCOM_EX_DTS_RESULT0 0x50000 +#define PNV_XSCOM_EX_DTS_RESULT1 0x50001 + +static uint64_t pnv_core_xscom_read(void *opaque, hwaddr addr, + unsigned int width) +{ + uint32_t offset = addr >> 3; + uint64_t val = 0; + + /* The result should be 38 C */ + switch (offset) { + case PNV_XSCOM_EX_DTS_RESULT0: + val = 0x26f024f023f0000ull; + break; + case PNV_XSCOM_EX_DTS_RESULT1: + val = 0x24f000000000000ull; + break; + default: + qemu_log_mask(LOG_UNIMP, "Warning: reading reg=0x%" HWADDR_PRIx, + addr); + } + + return val; +} + +static void pnv_core_xscom_write(void *opaque, hwaddr addr, uint64_t val, + unsigned int width) +{ + qemu_log_mask(LOG_UNIMP, "Warning: writing to reg=0x%" HWADDR_PRIx, + addr); +} + +static const MemoryRegionOps pnv_core_xscom_ops = { + .read = pnv_core_xscom_read, + .write = pnv_core_xscom_write, + .valid.min_access_size = 8, + .valid.max_access_size = 8, + .impl.min_access_size = 8, + .impl.max_access_size = 8, + .endianness = DEVICE_BIG_ENDIAN, +}; + static void pnv_core_realize_child(Object *child, Error **errp) { Error *local_err = NULL; @@ -118,6 +164,10 @@ static void pnv_core_realize(DeviceState *dev, Error **errp) goto err; } } + + snprintf(name, sizeof(name), "xscom-core.%d", cc->core_id); + pnv_xscom_region_init(&pc->xscom_regs, OBJECT(dev), &pnv_core_xscom_ops, + pc, name, PNV_XSCOM_EX_CORE_SIZE); return; err: diff --git a/include/hw/ppc/pnv_core.h b/include/hw/ppc/pnv_core.h index a151e281c0..2955a41c90 100644 --- a/include/hw/ppc/pnv_core.h +++ b/include/hw/ppc/pnv_core.h @@ -36,6 +36,8 @@ typedef struct PnvCore { /*< public >*/ void *threads; uint32_t pir; + + MemoryRegion xscom_regs; } PnvCore; typedef struct PnvCoreClass { diff --git a/include/hw/ppc/pnv_xscom.h b/include/hw/ppc/pnv_xscom.h index ee25ec455e..5da6e92e69 100644 --- a/include/hw/ppc/pnv_xscom.h +++ b/include/hw/ppc/pnv_xscom.h @@ -41,6 +41,25 @@ typedef struct PnvXScomInterfaceClass { int (*populate)(PnvXScomInterface *dev, void *fdt, int offset); } PnvXScomInterfaceClass; +/* + * Layout of the XSCOM PCB addresses of EX core 1 + * + * GPIO 0x1100xxxx + * SCOM 0x1101xxxx + * OHA 0x1102xxxx + * CLOCK CTL 0x1103xxxx + * FIR 0x1104xxxx + * THERM 0x1105xxxx + * 0x1106xxxx + * .. + * 0x110Exxxx + * PCB SLAVE 0x110Fxxxx + */ + +#define PNV_XSCOM_EX_BASE 0x10000000 +#define PNV_XSCOM_EX_CORE_BASE(i) (PNV_XSCOM_EX_BASE | (((uint64_t)i) << 24)) +#define PNV_XSCOM_EX_CORE_SIZE 0x100000 + extern void pnv_xscom_realize(PnvChip *chip, Error **errp); extern int pnv_xscom_populate(PnvChip *chip, void *fdt, int offset); From a3980bf51702d05690f07db2f6f07ab0f55d49b9 Mon Sep 17 00:00:00 2001 From: Benjamin Herrenschmidt Date: Sat, 22 Oct 2016 11:46:42 +0200 Subject: [PATCH 31/73] ppc/pnv: add a LPC controller MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The LPC (Low Pin Count) interface on a POWER8 is made accessible to the system through the ADU (XSCOM interface). This interface is part of set of units connected together via a local OPB (On-Chip Peripheral Bus) which act as a bridge between the ADU and the off chip LPC endpoints, like external flash modules. The most important units of this OPB are : - OPB Master: contains the ADU slave logic, a set of internal registers and the logic to control the OPB. - LPCHC (LPC HOST Controller): which implements a OPB Slave, a set of internal registers and the LPC HOST Controller to control the LPC interface. Four address spaces are provided to the ADU : - LPC Bus Firmware Memory - LPC Bus Memory - LPC Bus I/O (ISA bus) - and the registers for the OPB Master and the LPC Host Controller On POWER8, an intermediate hop is necessary to reach the OPB, through a unit called the ECCB. OPB commands are simply mangled in ECCB write commands. On POWER9, the OPB master address space can be accessed via MMIO. The logic is same but the code will be simpler as the XSCOM and ECCB hops are not necessary anymore. This version of the LPC controller model doesn't yet implement support for the SerIRQ deserializer present in the Naples version of the chip though some preliminary work is there. Signed-off-by: Benjamin Herrenschmidt [clg: - updated for qemu-2.7 - ported on latest PowerNV patchset - changed the XSCOM interface to fit new model - QOMified the model - moved the ISA hunks in another patch - removed printf logging - added a couple of UNIMP logging - rewrote commit log ] Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson Signed-off-by: David Gibson --- hw/ppc/Makefile.objs | 2 +- hw/ppc/pnv.c | 8 + hw/ppc/pnv_lpc.c | 471 +++++++++++++++++++++++++++++++++++++ include/hw/ppc/pnv.h | 3 + include/hw/ppc/pnv_lpc.h | 67 ++++++ include/hw/ppc/pnv_xscom.h | 3 + 6 files changed, 553 insertions(+), 1 deletion(-) create mode 100644 hw/ppc/pnv_lpc.c create mode 100644 include/hw/ppc/pnv_lpc.h diff --git a/hw/ppc/Makefile.objs b/hw/ppc/Makefile.objs index 08c213c406..ebc72af0a7 100644 --- a/hw/ppc/Makefile.objs +++ b/hw/ppc/Makefile.objs @@ -6,7 +6,7 @@ obj-$(CONFIG_PSERIES) += spapr_hcall.o spapr_iommu.o spapr_rtas.o obj-$(CONFIG_PSERIES) += spapr_pci.o spapr_rtc.o spapr_drc.o spapr_rng.o obj-$(CONFIG_PSERIES) += spapr_cpu_core.o # IBM PowerNV -obj-$(CONFIG_POWERNV) += pnv.o pnv_xscom.o pnv_core.o +obj-$(CONFIG_POWERNV) += pnv.o pnv_xscom.o pnv_core.o pnv_lpc.o ifeq ($(CONFIG_PCI)$(CONFIG_PSERIES)$(CONFIG_LINUX), yyy) obj-y += spapr_pci_vfio.o endif diff --git a/hw/ppc/pnv.c b/hw/ppc/pnv.c index df55a89cb9..aa712fd6f5 100644 --- a/hw/ppc/pnv.c +++ b/hw/ppc/pnv.c @@ -569,6 +569,9 @@ static void pnv_chip_init(Object *obj) PnvChipClass *pcc = PNV_CHIP_GET_CLASS(chip); chip->xscom_base = pcc->xscom_base; + + object_initialize(&chip->lpc, sizeof(chip->lpc), TYPE_PNV_LPC); + object_property_add_child(obj, "lpc", OBJECT(&chip->lpc), NULL); } static void pnv_chip_realize(DeviceState *dev, Error **errp) @@ -632,6 +635,11 @@ static void pnv_chip_realize(DeviceState *dev, Error **errp) i++; } g_free(typename); + + /* Create LPC controller */ + object_property_set_bool(OBJECT(&chip->lpc), true, "realized", + &error_fatal); + pnv_xscom_add_subregion(chip, PNV_XSCOM_LPC_BASE, &chip->lpc.xscom_regs); } static Property pnv_chip_properties[] = { diff --git a/hw/ppc/pnv_lpc.c b/hw/ppc/pnv_lpc.c new file mode 100644 index 0000000000..00dbd8b07b --- /dev/null +++ b/hw/ppc/pnv_lpc.c @@ -0,0 +1,471 @@ +/* + * QEMU PowerPC PowerNV LPC controller + * + * Copyright (c) 2016, IBM Corporation. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, see . + */ + +#include "qemu/osdep.h" +#include "sysemu/sysemu.h" +#include "target-ppc/cpu.h" +#include "qapi/error.h" +#include "qemu/log.h" + +#include "hw/ppc/pnv_lpc.h" +#include "hw/ppc/pnv.h" +#include "hw/ppc/fdt.h" + +#include + +enum { + ECCB_CTL = 0, + ECCB_RESET = 1, + ECCB_STAT = 2, + ECCB_DATA = 3, +}; + +/* OPB Master LS registers */ +#define OPB_MASTER_LS_IRQ_STAT 0x50 +#define OPB_MASTER_IRQ_LPC 0x00000800 +#define OPB_MASTER_LS_IRQ_MASK 0x54 +#define OPB_MASTER_LS_IRQ_POL 0x58 +#define OPB_MASTER_LS_IRQ_INPUT 0x5c + +/* LPC HC registers */ +#define LPC_HC_FW_SEG_IDSEL 0x24 +#define LPC_HC_FW_RD_ACC_SIZE 0x28 +#define LPC_HC_FW_RD_1B 0x00000000 +#define LPC_HC_FW_RD_2B 0x01000000 +#define LPC_HC_FW_RD_4B 0x02000000 +#define LPC_HC_FW_RD_16B 0x04000000 +#define LPC_HC_FW_RD_128B 0x07000000 +#define LPC_HC_IRQSER_CTRL 0x30 +#define LPC_HC_IRQSER_EN 0x80000000 +#define LPC_HC_IRQSER_QMODE 0x40000000 +#define LPC_HC_IRQSER_START_MASK 0x03000000 +#define LPC_HC_IRQSER_START_4CLK 0x00000000 +#define LPC_HC_IRQSER_START_6CLK 0x01000000 +#define LPC_HC_IRQSER_START_8CLK 0x02000000 +#define LPC_HC_IRQMASK 0x34 /* same bit defs as LPC_HC_IRQSTAT */ +#define LPC_HC_IRQSTAT 0x38 +#define LPC_HC_IRQ_SERIRQ0 0x80000000 /* all bits down to ... */ +#define LPC_HC_IRQ_SERIRQ16 0x00008000 /* IRQ16=IOCHK#, IRQ2=SMI# */ +#define LPC_HC_IRQ_SERIRQ_ALL 0xffff8000 +#define LPC_HC_IRQ_LRESET 0x00000400 +#define LPC_HC_IRQ_SYNC_ABNORM_ERR 0x00000080 +#define LPC_HC_IRQ_SYNC_NORESP_ERR 0x00000040 +#define LPC_HC_IRQ_SYNC_NORM_ERR 0x00000020 +#define LPC_HC_IRQ_SYNC_TIMEOUT_ERR 0x00000010 +#define LPC_HC_IRQ_SYNC_TARG_TAR_ERR 0x00000008 +#define LPC_HC_IRQ_SYNC_BM_TAR_ERR 0x00000004 +#define LPC_HC_IRQ_SYNC_BM0_REQ 0x00000002 +#define LPC_HC_IRQ_SYNC_BM1_REQ 0x00000001 +#define LPC_HC_ERROR_ADDRESS 0x40 + +#define LPC_OPB_SIZE 0x100000000ull + +#define ISA_IO_SIZE 0x00010000 +#define ISA_MEM_SIZE 0x10000000 +#define LPC_IO_OPB_ADDR 0xd0010000 +#define LPC_IO_OPB_SIZE 0x00010000 +#define LPC_MEM_OPB_ADDR 0xe0010000 +#define LPC_MEM_OPB_SIZE 0x10000000 +#define LPC_FW_OPB_ADDR 0xf0000000 +#define LPC_FW_OPB_SIZE 0x10000000 + +#define LPC_OPB_REGS_OPB_ADDR 0xc0010000 +#define LPC_OPB_REGS_OPB_SIZE 0x00002000 +#define LPC_HC_REGS_OPB_ADDR 0xc0012000 +#define LPC_HC_REGS_OPB_SIZE 0x00001000 + + +/* + * TODO: the "primary" cell should only be added on chip 0. This is + * how skiboot chooses the default LPC controller on multichip + * systems. + * + * It would be easly done if we can change the populate() interface to + * replace the PnvXScomInterface parameter by a PnvChip one + */ +static int pnv_lpc_populate(PnvXScomInterface *dev, void *fdt, int xscom_offset) +{ + const char compat[] = "ibm,power8-lpc\0ibm,lpc"; + char *name; + int offset; + uint32_t lpc_pcba = PNV_XSCOM_LPC_BASE; + uint32_t reg[] = { + cpu_to_be32(lpc_pcba), + cpu_to_be32(PNV_XSCOM_LPC_SIZE) + }; + + name = g_strdup_printf("isa@%x", lpc_pcba); + offset = fdt_add_subnode(fdt, xscom_offset, name); + _FDT(offset); + g_free(name); + + _FDT((fdt_setprop(fdt, offset, "reg", reg, sizeof(reg)))); + _FDT((fdt_setprop_cell(fdt, offset, "#address-cells", 2))); + _FDT((fdt_setprop_cell(fdt, offset, "#size-cells", 1))); + _FDT((fdt_setprop(fdt, offset, "primary", NULL, 0))); + _FDT((fdt_setprop(fdt, offset, "compatible", compat, sizeof(compat)))); + return 0; +} + +/* + * These read/write handlers of the OPB address space should be common + * with the P9 LPC Controller which uses direct MMIOs. + * + * TODO: rework to use address_space_stq() and address_space_ldq() + * instead. + */ +static bool opb_read(PnvLpcController *lpc, uint32_t addr, uint8_t *data, + int sz) +{ + bool success; + + /* XXX Handle access size limits and FW read caching here */ + success = !address_space_rw(&lpc->opb_as, addr, MEMTXATTRS_UNSPECIFIED, + data, sz, false); + + return success; +} + +static bool opb_write(PnvLpcController *lpc, uint32_t addr, uint8_t *data, + int sz) +{ + bool success; + + /* XXX Handle access size limits here */ + success = !address_space_rw(&lpc->opb_as, addr, MEMTXATTRS_UNSPECIFIED, + data, sz, true); + + return success; +} + +#define ECCB_CTL_READ (1ull << (63 - 15)) +#define ECCB_CTL_SZ_LSH (63 - 7) +#define ECCB_CTL_SZ_MASK (0xfull << ECCB_CTL_SZ_LSH) +#define ECCB_CTL_ADDR_MASK 0xffffffffu; + +#define ECCB_STAT_OP_DONE (1ull << (63 - 52)) +#define ECCB_STAT_OP_ERR (1ull << (63 - 52)) +#define ECCB_STAT_RD_DATA_LSH (63 - 37) +#define ECCB_STAT_RD_DATA_MASK (0xffffffff << ECCB_STAT_RD_DATA_LSH) + +static void pnv_lpc_do_eccb(PnvLpcController *lpc, uint64_t cmd) +{ + /* XXX Check for magic bits at the top, addr size etc... */ + unsigned int sz = (cmd & ECCB_CTL_SZ_MASK) >> ECCB_CTL_SZ_LSH; + uint32_t opb_addr = cmd & ECCB_CTL_ADDR_MASK; + uint8_t data[4]; + bool success; + + if (cmd & ECCB_CTL_READ) { + success = opb_read(lpc, opb_addr, data, sz); + if (success) { + lpc->eccb_stat_reg = ECCB_STAT_OP_DONE | + (((uint64_t)data[0]) << 24 | + ((uint64_t)data[1]) << 16 | + ((uint64_t)data[2]) << 8 | + ((uint64_t)data[3])) << ECCB_STAT_RD_DATA_LSH; + } else { + lpc->eccb_stat_reg = ECCB_STAT_OP_DONE | + (0xffffffffull << ECCB_STAT_RD_DATA_LSH); + } + } else { + data[0] = lpc->eccb_data_reg >> 24; + data[1] = lpc->eccb_data_reg >> 16; + data[2] = lpc->eccb_data_reg >> 8; + data[3] = lpc->eccb_data_reg; + + success = opb_write(lpc, opb_addr, data, sz); + lpc->eccb_stat_reg = ECCB_STAT_OP_DONE; + } + /* XXX Which error bit (if any) to signal OPB error ? */ +} + +static uint64_t pnv_lpc_xscom_read(void *opaque, hwaddr addr, unsigned size) +{ + PnvLpcController *lpc = PNV_LPC(opaque); + uint32_t offset = addr >> 3; + uint64_t val = 0; + + switch (offset & 3) { + case ECCB_CTL: + case ECCB_RESET: + val = 0; + break; + case ECCB_STAT: + val = lpc->eccb_stat_reg; + lpc->eccb_stat_reg = 0; + break; + case ECCB_DATA: + val = ((uint64_t)lpc->eccb_data_reg) << 32; + break; + } + return val; +} + +static void pnv_lpc_xscom_write(void *opaque, hwaddr addr, + uint64_t val, unsigned size) +{ + PnvLpcController *lpc = PNV_LPC(opaque); + uint32_t offset = addr >> 3; + + switch (offset & 3) { + case ECCB_CTL: + pnv_lpc_do_eccb(lpc, val); + break; + case ECCB_RESET: + /* XXXX */ + break; + case ECCB_STAT: + break; + case ECCB_DATA: + lpc->eccb_data_reg = val >> 32; + break; + } +} + +static const MemoryRegionOps pnv_lpc_xscom_ops = { + .read = pnv_lpc_xscom_read, + .write = pnv_lpc_xscom_write, + .valid.min_access_size = 8, + .valid.max_access_size = 8, + .impl.min_access_size = 8, + .impl.max_access_size = 8, + .endianness = DEVICE_BIG_ENDIAN, +}; + +static uint64_t lpc_hc_read(void *opaque, hwaddr addr, unsigned size) +{ + PnvLpcController *lpc = opaque; + uint64_t val = 0xfffffffffffffffful; + + switch (addr) { + case LPC_HC_FW_SEG_IDSEL: + val = lpc->lpc_hc_fw_seg_idsel; + break; + case LPC_HC_FW_RD_ACC_SIZE: + val = lpc->lpc_hc_fw_rd_acc_size; + break; + case LPC_HC_IRQSER_CTRL: + val = lpc->lpc_hc_irqser_ctrl; + break; + case LPC_HC_IRQMASK: + val = lpc->lpc_hc_irqmask; + break; + case LPC_HC_IRQSTAT: + val = lpc->lpc_hc_irqstat; + break; + case LPC_HC_ERROR_ADDRESS: + val = lpc->lpc_hc_error_addr; + break; + default: + qemu_log_mask(LOG_UNIMP, "LPC HC Unimplemented register: Ox%" + HWADDR_PRIx "\n", addr); + } + return val; +} + +static void lpc_hc_write(void *opaque, hwaddr addr, uint64_t val, + unsigned size) +{ + PnvLpcController *lpc = opaque; + + /* XXX Filter out reserved bits */ + + switch (addr) { + case LPC_HC_FW_SEG_IDSEL: + /* XXX Actually figure out how that works as this impact + * memory regions/aliases + */ + lpc->lpc_hc_fw_seg_idsel = val; + break; + case LPC_HC_FW_RD_ACC_SIZE: + lpc->lpc_hc_fw_rd_acc_size = val; + break; + case LPC_HC_IRQSER_CTRL: + lpc->lpc_hc_irqser_ctrl = val; + break; + case LPC_HC_IRQMASK: + lpc->lpc_hc_irqmask = val; + break; + case LPC_HC_IRQSTAT: + lpc->lpc_hc_irqstat &= ~val; + break; + case LPC_HC_ERROR_ADDRESS: + break; + default: + qemu_log_mask(LOG_UNIMP, "LPC HC Unimplemented register: Ox%" + HWADDR_PRIx "\n", addr); + } +} + +static const MemoryRegionOps lpc_hc_ops = { + .read = lpc_hc_read, + .write = lpc_hc_write, + .endianness = DEVICE_BIG_ENDIAN, + .valid = { + .min_access_size = 4, + .max_access_size = 4, + }, + .impl = { + .min_access_size = 4, + .max_access_size = 4, + }, +}; + +static uint64_t opb_master_read(void *opaque, hwaddr addr, unsigned size) +{ + PnvLpcController *lpc = opaque; + uint64_t val = 0xfffffffffffffffful; + + switch (addr) { + case OPB_MASTER_LS_IRQ_STAT: + val = lpc->opb_irq_stat; + break; + case OPB_MASTER_LS_IRQ_MASK: + val = lpc->opb_irq_mask; + break; + case OPB_MASTER_LS_IRQ_POL: + val = lpc->opb_irq_pol; + break; + case OPB_MASTER_LS_IRQ_INPUT: + val = lpc->opb_irq_input; + break; + default: + qemu_log_mask(LOG_UNIMP, "OPB MASTER Unimplemented register: Ox%" + HWADDR_PRIx "\n", addr); + } + + return val; +} + +static void opb_master_write(void *opaque, hwaddr addr, + uint64_t val, unsigned size) +{ + PnvLpcController *lpc = opaque; + + switch (addr) { + case OPB_MASTER_LS_IRQ_STAT: + lpc->opb_irq_stat &= ~val; + break; + case OPB_MASTER_LS_IRQ_MASK: + /* XXX Filter out reserved bits */ + lpc->opb_irq_mask = val; + break; + case OPB_MASTER_LS_IRQ_POL: + /* XXX Filter out reserved bits */ + lpc->opb_irq_pol = val; + break; + case OPB_MASTER_LS_IRQ_INPUT: + /* Read only */ + break; + default: + qemu_log_mask(LOG_UNIMP, "OPB MASTER Unimplemented register: Ox%" + HWADDR_PRIx "\n", addr); + } +} + +static const MemoryRegionOps opb_master_ops = { + .read = opb_master_read, + .write = opb_master_write, + .endianness = DEVICE_BIG_ENDIAN, + .valid = { + .min_access_size = 4, + .max_access_size = 4, + }, + .impl = { + .min_access_size = 4, + .max_access_size = 4, + }, +}; + +static void pnv_lpc_realize(DeviceState *dev, Error **errp) +{ + PnvLpcController *lpc = PNV_LPC(dev); + + /* Reg inits */ + lpc->lpc_hc_fw_rd_acc_size = LPC_HC_FW_RD_4B; + + /* Create address space and backing MR for the OPB bus */ + memory_region_init(&lpc->opb_mr, OBJECT(dev), "lpc-opb", 0x100000000ull); + address_space_init(&lpc->opb_as, &lpc->opb_mr, "lpc-opb"); + + /* Create ISA IO and Mem space regions which are the root of + * the ISA bus (ie, ISA address spaces). We don't create a + * separate one for FW which we alias to memory. + */ + memory_region_init(&lpc->isa_io, OBJECT(dev), "isa-io", ISA_IO_SIZE); + memory_region_init(&lpc->isa_mem, OBJECT(dev), "isa-mem", ISA_MEM_SIZE); + + /* Create windows from the OPB space to the ISA space */ + memory_region_init_alias(&lpc->opb_isa_io, OBJECT(dev), "lpc-isa-io", + &lpc->isa_io, 0, LPC_IO_OPB_SIZE); + memory_region_add_subregion(&lpc->opb_mr, LPC_IO_OPB_ADDR, + &lpc->opb_isa_io); + memory_region_init_alias(&lpc->opb_isa_mem, OBJECT(dev), "lpc-isa-mem", + &lpc->isa_mem, 0, LPC_MEM_OPB_SIZE); + memory_region_add_subregion(&lpc->opb_mr, LPC_MEM_OPB_ADDR, + &lpc->opb_isa_mem); + memory_region_init_alias(&lpc->opb_isa_fw, OBJECT(dev), "lpc-isa-fw", + &lpc->isa_mem, 0, LPC_FW_OPB_SIZE); + memory_region_add_subregion(&lpc->opb_mr, LPC_FW_OPB_ADDR, + &lpc->opb_isa_fw); + + /* Create MMIO regions for LPC HC and OPB registers */ + memory_region_init_io(&lpc->opb_master_regs, OBJECT(dev), &opb_master_ops, + lpc, "lpc-opb-master", LPC_OPB_REGS_OPB_SIZE); + memory_region_add_subregion(&lpc->opb_mr, LPC_OPB_REGS_OPB_ADDR, + &lpc->opb_master_regs); + memory_region_init_io(&lpc->lpc_hc_regs, OBJECT(dev), &lpc_hc_ops, lpc, + "lpc-hc", LPC_HC_REGS_OPB_SIZE); + memory_region_add_subregion(&lpc->opb_mr, LPC_HC_REGS_OPB_ADDR, + &lpc->lpc_hc_regs); + + /* XScom region for LPC registers */ + pnv_xscom_region_init(&lpc->xscom_regs, OBJECT(dev), + &pnv_lpc_xscom_ops, lpc, "xscom-lpc", + PNV_XSCOM_LPC_SIZE); +} + +static void pnv_lpc_class_init(ObjectClass *klass, void *data) +{ + DeviceClass *dc = DEVICE_CLASS(klass); + PnvXScomInterfaceClass *xdc = PNV_XSCOM_INTERFACE_CLASS(klass); + + xdc->populate = pnv_lpc_populate; + + dc->realize = pnv_lpc_realize; +} + +static const TypeInfo pnv_lpc_info = { + .name = TYPE_PNV_LPC, + .parent = TYPE_DEVICE, + .instance_size = sizeof(PnvLpcController), + .class_init = pnv_lpc_class_init, + .interfaces = (InterfaceInfo[]) { + { TYPE_PNV_XSCOM_INTERFACE }, + { } + } +}; + +static void pnv_lpc_register_types(void) +{ + type_register_static(&pnv_lpc_info); +} + +type_init(pnv_lpc_register_types) diff --git a/include/hw/ppc/pnv.h b/include/hw/ppc/pnv.h index 7db922e285..ce16e47724 100644 --- a/include/hw/ppc/pnv.h +++ b/include/hw/ppc/pnv.h @@ -22,6 +22,7 @@ #include "hw/boards.h" #include "hw/sysbus.h" #include "hw/ppc/pnv_xscom.h" +#include "hw/ppc/pnv_lpc.h" #define TYPE_PNV_CHIP "powernv-chip" #define PNV_CHIP(obj) OBJECT_CHECK(PnvChip, (obj), TYPE_PNV_CHIP) @@ -54,6 +55,8 @@ typedef struct PnvChip { MemoryRegion xscom_mmio; MemoryRegion xscom; AddressSpace xscom_as; + + PnvLpcController lpc; } PnvChip; typedef struct PnvChipClass { diff --git a/include/hw/ppc/pnv_lpc.h b/include/hw/ppc/pnv_lpc.h new file mode 100644 index 0000000000..38e5506975 --- /dev/null +++ b/include/hw/ppc/pnv_lpc.h @@ -0,0 +1,67 @@ +/* + * QEMU PowerPC PowerNV LPC controller + * + * Copyright (c) 2016, IBM Corporation. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, see . + */ +#ifndef _PPC_PNV_LPC_H +#define _PPC_PNV_LPC_H + +#define TYPE_PNV_LPC "pnv-lpc" +#define PNV_LPC(obj) \ + OBJECT_CHECK(PnvLpcController, (obj), TYPE_PNV_LPC) + +typedef struct PnvLpcController { + DeviceState parent; + + uint64_t eccb_stat_reg; + uint32_t eccb_data_reg; + + /* OPB bus */ + MemoryRegion opb_mr; + AddressSpace opb_as; + + /* ISA IO and Memory space */ + MemoryRegion isa_io; + MemoryRegion isa_mem; + + /* Windows from OPB to ISA (aliases) */ + MemoryRegion opb_isa_io; + MemoryRegion opb_isa_mem; + MemoryRegion opb_isa_fw; + + /* Registers */ + MemoryRegion lpc_hc_regs; + MemoryRegion opb_master_regs; + + /* OPB Master LS registers */ + uint32_t opb_irq_stat; + uint32_t opb_irq_mask; + uint32_t opb_irq_pol; + uint32_t opb_irq_input; + + /* LPC HC registers */ + uint32_t lpc_hc_fw_seg_idsel; + uint32_t lpc_hc_fw_rd_acc_size; + uint32_t lpc_hc_irqser_ctrl; + uint32_t lpc_hc_irqmask; + uint32_t lpc_hc_irqstat; + uint32_t lpc_hc_error_addr; + + /* XSCOM registers */ + MemoryRegion xscom_regs; +} PnvLpcController; + +#endif /* _PPC_PNV_LPC_H */ diff --git a/include/hw/ppc/pnv_xscom.h b/include/hw/ppc/pnv_xscom.h index 5da6e92e69..c0a2fbb9f6 100644 --- a/include/hw/ppc/pnv_xscom.h +++ b/include/hw/ppc/pnv_xscom.h @@ -60,6 +60,9 @@ typedef struct PnvXScomInterfaceClass { #define PNV_XSCOM_EX_CORE_BASE(i) (PNV_XSCOM_EX_BASE | (((uint64_t)i) << 24)) #define PNV_XSCOM_EX_CORE_SIZE 0x100000 +#define PNV_XSCOM_LPC_BASE 0xb0020 +#define PNV_XSCOM_LPC_SIZE 0x4 + extern void pnv_xscom_realize(PnvChip *chip, Error **errp); extern int pnv_xscom_populate(PnvChip *chip, void *fdt, int offset); From 3495b6b6101e680b6a7b27674f5d3e446b1cf013 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?C=C3=A9dric=20Le=20Goater?= Date: Sat, 22 Oct 2016 11:46:43 +0200 Subject: [PATCH 32/73] ppc/pnv: add a ISA bus MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit As Qemu only supports a single instance of the ISA bus, we use the LPC controller of chip 0 to create one and plug in a couple of useful devices, like an UART and RTC. An IPMI BT device, which is also an ISA device, can be defined on the command line to connect an external BMC. That is for later. The PowerNV machine now has a console. Skiboot should load a kernel and jump into it but execution will stop quite early because we lack a model for the native XICS controller for the moment : [ 0.000000] NR_IRQS:512 nr_irqs:512 16 [ 0.000000] XICS: Cannot find a Presentation Controller ! [ 0.000000] ------------[ cut here ]------------ [ 0.000000] WARNING: at arch/powerpc/platforms/powernv/setup.c:81 ... [ 0.000000] NIP [c00000000079d65c] pnv_init_IRQ+0x30/0x44 You can still do a few things under xmon. Based on previous work from : Benjamin Herrenschmidt Signed-off-by: Cédric Le Goater Reviewed-by: David Gibson [dwg: Trivial fix for a change in the serial_hds_isa_init() interface] Signed-off-by: David Gibson --- hw/ppc/pnv.c | 65 ++++++++++++++++++++++++++++++++++++++++++++ include/hw/ppc/pnv.h | 2 ++ 2 files changed, 67 insertions(+) diff --git a/hw/ppc/pnv.c b/hw/ppc/pnv.c index aa712fd6f5..82276e0857 100644 --- a/hw/ppc/pnv.c +++ b/hw/ppc/pnv.c @@ -35,6 +35,10 @@ #include "hw/ppc/pnv_xscom.h" +#include "hw/isa/isa.h" +#include "hw/char/serial.h" +#include "hw/timer/mc146818rtc.h" + #include #define FDT_MAX_SIZE 0x00100000 @@ -301,6 +305,58 @@ static void ppc_powernv_reset(void) cpu_physical_memory_write(PNV_FDT_ADDR, fdt, fdt_totalsize(fdt)); } +/* If we don't use the built-in LPC interrupt deserializer, we need + * to provide a set of qirqs for the ISA bus or things will go bad. + * + * Most machines using pre-Naples chips (without said deserializer) + * have a CPLD that will collect the SerIRQ and shoot them as a + * single level interrupt to the P8 chip. So let's setup a hook + * for doing just that. + * + * Note: The actual interrupt input isn't emulated yet, this will + * come with the PSI bridge model. + */ +static void pnv_lpc_isa_irq_handler_cpld(void *opaque, int n, int level) +{ + /* We don't yet emulate the PSI bridge which provides the external + * interrupt, so just drop interrupts on the floor + */ +} + +static void pnv_lpc_isa_irq_handler(void *opaque, int n, int level) +{ + /* XXX TODO */ +} + +static ISABus *pnv_isa_create(PnvChip *chip) +{ + PnvLpcController *lpc = &chip->lpc; + ISABus *isa_bus; + qemu_irq *irqs; + PnvChipClass *pcc = PNV_CHIP_GET_CLASS(chip); + + /* let isa_bus_new() create its own bridge on SysBus otherwise + * devices speficied on the command line won't find the bus and + * will fail to create. + */ + isa_bus = isa_bus_new(NULL, &lpc->isa_mem, &lpc->isa_io, + &error_fatal); + + /* Not all variants have a working serial irq decoder. If not, + * handling of LPC interrupts becomes a platform issue (some + * platforms have a CPLD to do it). + */ + if (pcc->chip_type == PNV_CHIP_POWER8NVL) { + irqs = qemu_allocate_irqs(pnv_lpc_isa_irq_handler, chip, ISA_NUM_IRQS); + } else { + irqs = qemu_allocate_irqs(pnv_lpc_isa_irq_handler_cpld, chip, + ISA_NUM_IRQS); + } + + isa_bus_irqs(isa_bus, irqs); + return isa_bus; +} + static void ppc_powernv_init(MachineState *machine) { PnvMachineState *pnv = POWERNV_MACHINE(machine); @@ -395,6 +451,15 @@ static void ppc_powernv_init(MachineState *machine) object_property_set_bool(chip, true, "realized", &error_fatal); } g_free(chip_typename); + + /* Instantiate ISA bus on chip 0 */ + pnv->isa_bus = pnv_isa_create(pnv->chips[0]); + + /* Create serial port */ + serial_hds_isa_init(pnv->isa_bus, 0, MAX_SERIAL_PORTS); + + /* Create an RTC ISA device too */ + rtc_init(pnv->isa_bus, 2000, NULL); } /* diff --git a/include/hw/ppc/pnv.h b/include/hw/ppc/pnv.h index ce16e47724..02ac1c5f42 100644 --- a/include/hw/ppc/pnv.h +++ b/include/hw/ppc/pnv.h @@ -112,6 +112,8 @@ typedef struct PnvMachineState { uint32_t num_chips; PnvChip **chips; + + ISABus *isa_bus; } PnvMachineState; #define PNV_FDT_ADDR 0x01000000 From 37ad52ba7ae415e7a78676aa7bb5e9f4fc6c8030 Mon Sep 17 00:00:00 2001 From: Vasant Hegde Date: Mon, 24 Oct 2016 14:44:58 +0530 Subject: [PATCH 33/73] target-ppc: add vmul10[u,eu,cu,ecu]q instructions vmul10uq : Vector Multiply-by-10 Unsigned Quadword VX-form vmul10euq : Vector Multiply-by-10 Extended Unsigned Quadword VX-form vmul10cuq : Vector Multiply-by-10 & write Carry Unsigned Quadword VX-form vmul10ecuq: Vector Multiply-by-10 Extended & write Carry Unsigned Quadword VX-form Signed-off-by: Vasant Hegde [ Add GEN_VXFORM_DUAL_EXT with invalid bit mask ] Signed-off-by: Nikunj A Dadhania Signed-off-by: David Gibson --- target-ppc/translate/vmx-impl.inc.c | 72 +++++++++++++++++++++++++++++ target-ppc/translate/vmx-ops.inc.c | 8 ++-- 2 files changed, 76 insertions(+), 4 deletions(-) diff --git a/target-ppc/translate/vmx-impl.inc.c b/target-ppc/translate/vmx-impl.inc.c index 563f101642..fc612d9f37 100644 --- a/target-ppc/translate/vmx-impl.inc.c +++ b/target-ppc/translate/vmx-impl.inc.c @@ -182,6 +182,52 @@ static void gen_mtvscr(DisasContext *ctx) tcg_temp_free_ptr(p); } +#define GEN_VX_VMUL10(name, add_cin, ret_carry) \ +static void glue(gen_, name)(DisasContext *ctx) \ +{ \ + TCGv_i64 t0 = tcg_temp_new_i64(); \ + TCGv_i64 t1 = tcg_temp_new_i64(); \ + TCGv_i64 t2 = tcg_temp_new_i64(); \ + TCGv_i64 ten, z; \ + \ + if (unlikely(!ctx->altivec_enabled)) { \ + gen_exception(ctx, POWERPC_EXCP_VPU); \ + return; \ + } \ + \ + ten = tcg_const_i64(10); \ + z = tcg_const_i64(0); \ + \ + if (add_cin) { \ + tcg_gen_mulu2_i64(t0, t1, cpu_avrl[rA(ctx->opcode)], ten); \ + tcg_gen_andi_i64(t2, cpu_avrl[rB(ctx->opcode)], 0xF); \ + tcg_gen_add2_i64(cpu_avrl[rD(ctx->opcode)], t2, t0, t1, t2, z); \ + } else { \ + tcg_gen_mulu2_i64(cpu_avrl[rD(ctx->opcode)], t2, \ + cpu_avrl[rA(ctx->opcode)], ten); \ + } \ + \ + if (ret_carry) { \ + tcg_gen_mulu2_i64(t0, t1, cpu_avrh[rA(ctx->opcode)], ten); \ + tcg_gen_add2_i64(t0, cpu_avrl[rD(ctx->opcode)], t0, t1, t2, z); \ + tcg_gen_movi_i64(cpu_avrh[rD(ctx->opcode)], 0); \ + } else { \ + tcg_gen_mul_i64(t0, cpu_avrh[rA(ctx->opcode)], ten); \ + tcg_gen_add_i64(cpu_avrh[rD(ctx->opcode)], t0, t2); \ + } \ + \ + tcg_temp_free_i64(t0); \ + tcg_temp_free_i64(t1); \ + tcg_temp_free_i64(t2); \ + tcg_temp_free_i64(ten); \ + tcg_temp_free_i64(z); \ +} \ + +GEN_VX_VMUL10(vmul10uq, 0, 0); +GEN_VX_VMUL10(vmul10euq, 1, 0); +GEN_VX_VMUL10(vmul10cuq, 0, 1); +GEN_VX_VMUL10(vmul10ecuq, 1, 1); + /* Logical operations */ #define GEN_VX_LOGICAL(name, tcg_op, opc2, opc3) \ static void glue(gen_, name)(DisasContext *ctx) \ @@ -276,8 +322,30 @@ static void glue(gen_, name0##_##name1)(DisasContext *ctx) \ } \ } +/* Adds support to provide invalid mask */ +#define GEN_VXFORM_DUAL_EXT(name0, flg0, flg2_0, inval0, \ + name1, flg1, flg2_1, inval1) \ +static void glue(gen_, name0##_##name1)(DisasContext *ctx) \ +{ \ + if ((Rc(ctx->opcode) == 0) && \ + ((ctx->insns_flags & flg0) || (ctx->insns_flags2 & flg2_0)) && \ + !(ctx->opcode & inval0)) { \ + gen_##name0(ctx); \ + } else if ((Rc(ctx->opcode) == 1) && \ + ((ctx->insns_flags & flg1) || (ctx->insns_flags2 & flg2_1)) && \ + !(ctx->opcode & inval1)) { \ + gen_##name1(ctx); \ + } else { \ + gen_inval_exception(ctx, POWERPC_EXCP_INVAL_INVAL); \ + } \ +} + GEN_VXFORM(vaddubm, 0, 0); +GEN_VXFORM_DUAL_EXT(vaddubm, PPC_ALTIVEC, PPC_NONE, 0, \ + vmul10cuq, PPC_NONE, PPC2_ISA300, 0x0000F800) GEN_VXFORM(vadduhm, 0, 1); +GEN_VXFORM_DUAL(vadduhm, PPC_ALTIVEC, PPC_NONE, \ + vmul10ecuq, PPC_NONE, PPC2_ISA300) GEN_VXFORM(vadduwm, 0, 2); GEN_VXFORM(vaddudm, 0, 3); GEN_VXFORM(vsububm, 0, 16); @@ -390,7 +458,11 @@ GEN_VXFORM(vsro, 6, 17); GEN_VXFORM(vaddcuw, 0, 6); GEN_VXFORM(vsubcuw, 0, 22); GEN_VXFORM_ENV(vaddubs, 0, 8); +GEN_VXFORM_DUAL_EXT(vaddubs, PPC_ALTIVEC, PPC_NONE, 0, \ + vmul10uq, PPC_NONE, PPC2_ISA300, 0x0000F800) GEN_VXFORM_ENV(vadduhs, 0, 9); +GEN_VXFORM_DUAL(vadduhs, PPC_ALTIVEC, PPC_NONE, \ + vmul10euq, PPC_NONE, PPC2_ISA300) GEN_VXFORM_ENV(vadduws, 0, 10); GEN_VXFORM_ENV(vaddsbs, 0, 12); GEN_VXFORM_ENV(vaddshs, 0, 13); diff --git a/target-ppc/translate/vmx-ops.inc.c b/target-ppc/translate/vmx-ops.inc.c index ab64ab2e01..cc7ed7eeed 100644 --- a/target-ppc/translate/vmx-ops.inc.c +++ b/target-ppc/translate/vmx-ops.inc.c @@ -55,8 +55,8 @@ GEN_HANDLER_E(name0##_##name1, 0x4, opc2, opc3, 0x00000000, type0, type1) GEN_HANDLER_E(name0##_##name1, 0x4, opc2, opc3, 0x00000000, tp0, tp1), \ GEN_HANDLER_E(name0##_##name1, 0x4, opc2, (opc3 | 0x10), 0x00000000, tp0, tp1), -GEN_VXFORM(vaddubm, 0, 0), -GEN_VXFORM(vadduhm, 0, 1), +GEN_VXFORM_DUAL(vaddubm, vmul10cuq, 0, 0, PPC_ALTIVEC, PPC_NONE), +GEN_VXFORM_DUAL(vadduhm, vmul10ecuq, 0, 1, PPC_ALTIVEC, PPC_NONE), GEN_VXFORM(vadduwm, 0, 2), GEN_VXFORM_207(vaddudm, 0, 3), GEN_VXFORM_DUAL(vsububm, bcdadd, 0, 16, PPC_ALTIVEC, PPC_NONE), @@ -123,8 +123,8 @@ GEN_VXFORM(vslo, 6, 16), GEN_VXFORM(vsro, 6, 17), GEN_VXFORM(vaddcuw, 0, 6), GEN_VXFORM(vsubcuw, 0, 22), -GEN_VXFORM(vaddubs, 0, 8), -GEN_VXFORM(vadduhs, 0, 9), +GEN_VXFORM_DUAL(vaddubs, vmul10uq, 0, 8, PPC_ALTIVEC, PPC_NONE), +GEN_VXFORM_DUAL(vadduhs, vmul10euq, 0, 9, PPC_ALTIVEC, PPC_NONE), GEN_VXFORM(vadduws, 0, 10), GEN_VXFORM(vaddsbs, 0, 12), GEN_VXFORM(vaddshs, 0, 13), From 997b6cfc3d13aa145fcdbf294521e581d6617bde Mon Sep 17 00:00:00 2001 From: David Gibson Date: Tue, 25 Oct 2016 11:51:33 +1100 Subject: [PATCH 34/73] pseries: Split device tree construction from device tree load spapr_finalize_fdt() both finishes building the device tree for the guest and loads it into guest memory. For future cleanups, it's going to be more convenient to do these two things separately. The loading portion is pretty trivial, so we move it inline into the caller, ppc_spapr_reset(). We also rename spapr_finalize_fdt(), because the current name is going to become inaccurate. Signed-off-by: David Gibson Reviewed-by: Michael Roth Reviewed-by: Alexey Kardashevskiy --- hw/ppc/spapr.c | 42 ++++++++++++++++++++++------------------- hw/ppc/spapr_cpu_core.c | 2 +- 2 files changed, 24 insertions(+), 20 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 486f57d6f6..874f53d8f0 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -900,10 +900,9 @@ int spapr_h_cas_compose_response(sPAPRMachineState *spapr, return 0; } -static void spapr_finalize_fdt(sPAPRMachineState *spapr, - hwaddr fdt_addr, - hwaddr rtas_addr, - hwaddr rtas_size) +static void *spapr_build_fdt(sPAPRMachineState *spapr, + hwaddr rtas_addr, + hwaddr rtas_size) { MachineState *machine = MACHINE(qdev_get_machine()); MachineClass *mc = MACHINE_GET_CLASS(machine); @@ -999,19 +998,8 @@ static void spapr_finalize_fdt(sPAPRMachineState *spapr, } } - _FDT((fdt_pack(fdt))); - - if (fdt_totalsize(fdt) > FDT_MAX_SIZE) { - error_report("FDT too big ! 0x%x bytes (max is 0x%x)", - fdt_totalsize(fdt), FDT_MAX_SIZE); - exit(1); - } - - qemu_fdt_dumpdtb(fdt, fdt_totalsize(fdt)); - cpu_physical_memory_write(fdt_addr, fdt, fdt_totalsize(fdt)); - g_free(bootlist); - g_free(fdt); + return fdt; } static uint64_t translate_kernel_address(void *opaque, uint64_t addr) @@ -1147,6 +1135,8 @@ static void ppc_spapr_reset(void) sPAPRMachineState *spapr = SPAPR_MACHINE(machine); PowerPCCPU *first_ppc_cpu; uint32_t rtas_limit; + void *fdt; + int rc; /* Check for unknown sysbus devices */ foreach_dynamic_sysbus_device(find_unknown_sysbus_device, NULL); @@ -1173,14 +1163,28 @@ static void ppc_spapr_reset(void) spapr->rtas_addr = rtas_limit - RTAS_MAX_SIZE; spapr->fdt_addr = spapr->rtas_addr - FDT_MAX_SIZE; - /* Load the fdt */ - spapr_finalize_fdt(spapr, spapr->fdt_addr, spapr->rtas_addr, - spapr->rtas_size); + fdt = spapr_build_fdt(spapr, spapr->rtas_addr, spapr->rtas_size); /* Copy RTAS over */ cpu_physical_memory_write(spapr->rtas_addr, spapr->rtas_blob, spapr->rtas_size); + rc = fdt_pack(fdt); + + /* Should only fail if we've built a corrupted tree */ + assert(rc == 0); + + if (fdt_totalsize(fdt) > FDT_MAX_SIZE) { + error_report("FDT too big ! 0x%x bytes (max is 0x%x)", + fdt_totalsize(fdt), FDT_MAX_SIZE); + exit(1); + } + + /* Load the fdt */ + qemu_fdt_dumpdtb(fdt, fdt_totalsize(fdt)); + cpu_physical_memory_write(spapr->fdt_addr, fdt, fdt_totalsize(fdt)); + g_free(fdt); + /* Set up the entry state */ first_ppc_cpu = POWERPC_CPU(first_cpu); first_ppc_cpu->env.gpr[3] = spapr->fdt_addr; diff --git a/hw/ppc/spapr_cpu_core.c b/hw/ppc/spapr_cpu_core.c index bc922bc86f..e0c14f6b77 100644 --- a/hw/ppc/spapr_cpu_core.c +++ b/hw/ppc/spapr_cpu_core.c @@ -184,7 +184,7 @@ void spapr_core_plug(HotplugHandler *hotplug_dev, DeviceState *dev, /* * Setup CPU DT entries only for hotplugged CPUs. For boot time or - * coldplugged CPUs DT entries are setup in spapr_finalize_fdt(). + * coldplugged CPUs DT entries are setup in spapr_build_fdt(). */ if (dev->hotplugged) { fdt = spapr_populate_hotplug_cpu_dt(cs, &fdt_offset, spapr); From cae172ab6daa18e1edc789c237a11d6dbc858ee0 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 20 Oct 2016 15:30:53 +1100 Subject: [PATCH 35/73] pseries: Remove rtas_addr and fdt_addr fields from machinestate These values are used only within ppc_spapr_reset(), so just change them to local variables. Signed-off-by: David Gibson Reviewed-by: Thomas Huth Reviewed-by: Alexey Kardashevskiy Reviewed-by: Michael Roth --- hw/ppc/spapr.c | 14 +++++++------- include/hw/ppc/spapr.h | 1 - 2 files changed, 7 insertions(+), 8 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 874f53d8f0..9c38fe04b4 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -1135,6 +1135,7 @@ static void ppc_spapr_reset(void) sPAPRMachineState *spapr = SPAPR_MACHINE(machine); PowerPCCPU *first_ppc_cpu; uint32_t rtas_limit; + hwaddr rtas_addr, fdt_addr; void *fdt; int rc; @@ -1160,14 +1161,13 @@ static void ppc_spapr_reset(void) * processed with 32-bit real mode code if necessary */ rtas_limit = MIN(spapr->rma_size, RTAS_MAX_ADDR); - spapr->rtas_addr = rtas_limit - RTAS_MAX_SIZE; - spapr->fdt_addr = spapr->rtas_addr - FDT_MAX_SIZE; + rtas_addr = rtas_limit - RTAS_MAX_SIZE; + fdt_addr = rtas_addr - FDT_MAX_SIZE; - fdt = spapr_build_fdt(spapr, spapr->rtas_addr, spapr->rtas_size); + fdt = spapr_build_fdt(spapr, rtas_addr, spapr->rtas_size); /* Copy RTAS over */ - cpu_physical_memory_write(spapr->rtas_addr, spapr->rtas_blob, - spapr->rtas_size); + cpu_physical_memory_write(rtas_addr, spapr->rtas_blob, spapr->rtas_size); rc = fdt_pack(fdt); @@ -1182,12 +1182,12 @@ static void ppc_spapr_reset(void) /* Load the fdt */ qemu_fdt_dumpdtb(fdt, fdt_totalsize(fdt)); - cpu_physical_memory_write(spapr->fdt_addr, fdt, fdt_totalsize(fdt)); + cpu_physical_memory_write(fdt_addr, fdt, fdt_totalsize(fdt)); g_free(fdt); /* Set up the entry state */ first_ppc_cpu = POWERPC_CPU(first_cpu); - first_ppc_cpu->env.gpr[3] = spapr->fdt_addr; + first_ppc_cpu->env.gpr[3] = fdt_addr; first_ppc_cpu->env.gpr[5] = 0; first_cpu->halted = 0; first_ppc_cpu->env.nip = SPAPR_ENTRY_POINT; diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index aeaba3edf9..1174741d0b 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -63,7 +63,6 @@ struct sPAPRMachineState { uint32_t htab_shift; hwaddr rma_size; int vrma_adjust; - hwaddr fdt_addr, rtas_addr; ssize_t rtas_size; void *rtas_blob; void *fdt_skel; From a19f7fb0456b3d1329a2086d81418a49c1eae9b9 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 20 Oct 2016 15:31:45 +1100 Subject: [PATCH 36/73] pseries: Make spapr_create_fdt_skel() get information from machine state Currently spapr_create_fdt_skel() takes a bunch of individual parameters for various things it will put in the device tree. Some of these can already be taken directly from sPAPRMachineState. This patch alters it so that all of them can be taken from there, which will allow this code to be moved away from its current caller in future. Signed-off-by: David Gibson Reviewed-by: Alexey Kardashevskiy Reviewed-by: Thomas Huth Reviewed-by: Michael Roth --- hw/ppc/spapr.c | 79 +++++++++++++++++++----------------------- include/hw/ppc/spapr.h | 4 +++ 2 files changed, 39 insertions(+), 44 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 9c38fe04b4..3b23920f5d 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -271,16 +271,12 @@ static void add_str(GString *s, const gchar *s1) g_string_append_len(s, s1, strlen(s1) + 1); } -static void *spapr_create_fdt_skel(hwaddr initrd_base, - hwaddr initrd_size, - hwaddr kernel_size, - bool little_endian, - const char *kernel_cmdline, - uint32_t epow_irq) +static void *spapr_create_fdt_skel(sPAPRMachineState *spapr) { + MachineState *machine = MACHINE(spapr); void *fdt; - uint32_t start_prop = cpu_to_be32(initrd_base); - uint32_t end_prop = cpu_to_be32(initrd_base + initrd_size); + uint32_t start_prop = cpu_to_be32(spapr->initrd_base); + uint32_t end_prop = cpu_to_be32(spapr->initrd_base + spapr->initrd_size); GString *hypertas = g_string_sized_new(256); GString *qemu_hypertas = g_string_sized_new(256); uint32_t refpoints[] = {cpu_to_be32(0x4), cpu_to_be32(0x4)}; @@ -305,11 +301,13 @@ static void *spapr_create_fdt_skel(hwaddr initrd_base, fdt = g_malloc0(FDT_MAX_SIZE); _FDT((fdt_create(fdt, FDT_MAX_SIZE))); - if (kernel_size) { - _FDT((fdt_add_reservemap_entry(fdt, KERNEL_LOAD_ADDR, kernel_size))); + if (spapr->kernel_size) { + _FDT((fdt_add_reservemap_entry(fdt, KERNEL_LOAD_ADDR, + spapr->kernel_size))); } - if (initrd_size) { - _FDT((fdt_add_reservemap_entry(fdt, initrd_base, initrd_size))); + if (spapr->initrd_size) { + _FDT((fdt_add_reservemap_entry(fdt, spapr->initrd_base, + spapr->initrd_size))); } _FDT((fdt_finish_reservemap(fdt))); @@ -354,17 +352,17 @@ static void *spapr_create_fdt_skel(hwaddr initrd_base, /* Set Form1_affinity */ _FDT((fdt_property(fdt, "ibm,architecture-vec-5", vec5, sizeof(vec5)))); - _FDT((fdt_property_string(fdt, "bootargs", kernel_cmdline))); + _FDT((fdt_property_string(fdt, "bootargs", machine->kernel_cmdline))); _FDT((fdt_property(fdt, "linux,initrd-start", &start_prop, sizeof(start_prop)))); _FDT((fdt_property(fdt, "linux,initrd-end", &end_prop, sizeof(end_prop)))); - if (kernel_size) { + if (spapr->kernel_size) { uint64_t kprop[2] = { cpu_to_be64(KERNEL_LOAD_ADDR), - cpu_to_be64(kernel_size) }; + cpu_to_be64(spapr->kernel_size) }; _FDT((fdt_property(fdt, "qemu,boot-kernel", &kprop, sizeof(kprop)))); - if (little_endian) { + if (spapr->kernel_le) { _FDT((fdt_property(fdt, "qemu,boot-kernel-le", NULL, 0))); } } @@ -441,7 +439,7 @@ static void *spapr_create_fdt_skel(hwaddr initrd_base, _FDT((fdt_end_node(fdt))); /* event-sources */ - spapr_events_fdt_skel(fdt, epow_irq); + spapr_events_fdt_skel(fdt, spapr->check_exception_irq); /* /hypervisor node */ if (kvm_enabled()) { @@ -1686,7 +1684,6 @@ static void ppc_spapr_init(MachineState *machine) MachineClass *mc = MACHINE_GET_CLASS(machine); sPAPRMachineClass *smc = SPAPR_MACHINE_GET_CLASS(machine); const char *kernel_filename = machine->kernel_filename; - const char *kernel_cmdline = machine->kernel_cmdline; const char *initrd_filename = machine->initrd_filename; PCIHostState *phb; int i; @@ -1696,10 +1693,7 @@ static void ppc_spapr_init(MachineState *machine) void *rma = NULL; hwaddr rma_alloc_size; hwaddr node0_size = spapr_node0_size(); - uint32_t initrd_base = 0; - long kernel_size = 0, initrd_size = 0; long load_limit, fw_size; - bool kernel_le = false; char *filename; int smt = kvmppc_smt_threads(); int spapr_cores = smp_cpus / smp_threads; @@ -1972,19 +1966,19 @@ static void ppc_spapr_init(MachineState *machine) if (kernel_filename) { uint64_t lowaddr = 0; - kernel_size = load_elf(kernel_filename, translate_kernel_address, NULL, - NULL, &lowaddr, NULL, 1, PPC_ELF_MACHINE, - 0, 0); - if (kernel_size == ELF_LOAD_WRONG_ENDIAN) { - kernel_size = load_elf(kernel_filename, - translate_kernel_address, NULL, - NULL, &lowaddr, NULL, 0, PPC_ELF_MACHINE, - 0, 0); - kernel_le = kernel_size > 0; + spapr->kernel_size = load_elf(kernel_filename, translate_kernel_address, + NULL, NULL, &lowaddr, NULL, 1, + PPC_ELF_MACHINE, 0, 0); + if (spapr->kernel_size == ELF_LOAD_WRONG_ENDIAN) { + spapr->kernel_size = load_elf(kernel_filename, + translate_kernel_address, NULL, NULL, + &lowaddr, NULL, 0, PPC_ELF_MACHINE, + 0, 0); + spapr->kernel_le = spapr->kernel_size > 0; } - if (kernel_size < 0) { - error_report("error loading %s: %s", - kernel_filename, load_elf_strerror(kernel_size)); + if (spapr->kernel_size < 0) { + error_report("error loading %s: %s", kernel_filename, + load_elf_strerror(spapr->kernel_size)); exit(1); } @@ -1993,17 +1987,17 @@ static void ppc_spapr_init(MachineState *machine) /* Try to locate the initrd in the gap between the kernel * and the firmware. Add a bit of space just in case */ - initrd_base = (KERNEL_LOAD_ADDR + kernel_size + 0x1ffff) & ~0xffff; - initrd_size = load_image_targphys(initrd_filename, initrd_base, - load_limit - initrd_base); - if (initrd_size < 0) { + spapr->initrd_base = (KERNEL_LOAD_ADDR + spapr->kernel_size + + 0x1ffff) & ~0xffff; + spapr->initrd_size = load_image_targphys(initrd_filename, + spapr->initrd_base, + load_limit + - spapr->initrd_base); + if (spapr->initrd_size < 0) { error_report("could not load initial ram disk '%s'", initrd_filename); exit(1); } - } else { - initrd_base = 0; - initrd_size = 0; } } @@ -2030,10 +2024,7 @@ static void ppc_spapr_init(MachineState *machine) &savevm_htab_handlers, spapr); /* Prepare the device tree */ - spapr->fdt_skel = spapr_create_fdt_skel(initrd_base, initrd_size, - kernel_size, kernel_le, - kernel_cmdline, - spapr->check_exception_irq); + spapr->fdt_skel = spapr_create_fdt_skel(spapr); assert(spapr->fdt_skel != NULL); /* used by RTAS */ diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index 1174741d0b..a0b4bf80e0 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -65,6 +65,10 @@ struct sPAPRMachineState { int vrma_adjust; ssize_t rtas_size; void *rtas_blob; + long kernel_size; + bool kernel_le; + uint32_t initrd_base; + long initrd_size; void *fdt_skel; uint64_t rtc_offset; /* Now used only during incoming migration */ struct PPCTimebase tb; From cf6e522390126bdd20406481f3df79c194a431bd Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 20 Oct 2016 15:34:59 +1100 Subject: [PATCH 37/73] pseries: Move adding of fdt reserve map entries The flattened device tree passed to pseries guests contains a list of reserved memory areas. Currently we construct this list early in spapr_create_fdt_skel() as we sequentially write the fdt. This will be inconvenient for upcoming cleanups, so this patch moves the reserve map changes to the end of fdt construction. This changes fdt_add_reservemap_entry() calls - which work when writing the fdt sequentially to fdt_add_mem_rsv() calls used when altering the fdt in random access mode. Signed-off-by: David Gibson Reviewed-by: Thomas Huth Reviewed-by: Michael Roth --- hw/ppc/spapr.c | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 3b23920f5d..8e58d8670d 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -301,14 +301,6 @@ static void *spapr_create_fdt_skel(sPAPRMachineState *spapr) fdt = g_malloc0(FDT_MAX_SIZE); _FDT((fdt_create(fdt, FDT_MAX_SIZE))); - if (spapr->kernel_size) { - _FDT((fdt_add_reservemap_entry(fdt, KERNEL_LOAD_ADDR, - spapr->kernel_size))); - } - if (spapr->initrd_size) { - _FDT((fdt_add_reservemap_entry(fdt, spapr->initrd_base, - spapr->initrd_size))); - } _FDT((fdt_finish_reservemap(fdt))); /* Root node */ @@ -997,6 +989,15 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, } g_free(bootlist); + + /* Build memory reserve map */ + if (spapr->kernel_size) { + _FDT((fdt_add_mem_rsv(fdt, KERNEL_LOAD_ADDR, spapr->kernel_size))); + } + if (spapr->initrd_size) { + _FDT((fdt_add_mem_rsv(fdt, spapr->initrd_base, spapr->initrd_size))); + } + return fdt; } From 2cac78c12ade9a87b6251f8d854c2e43a30f41bf Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 20 Oct 2016 15:37:41 +1100 Subject: [PATCH 38/73] pseries: Consolidate RTAS loading At each system reset, the pseries machine needs to load RTAS (the runtime portion of the guest firmware) into the VM. This means copying the actual RTAS code into guest memory, and also updating the device tree so that the guest OS and boot firmware can locate it. For historical reasons the copy and update to the device tree were in different parts of the code. This cleanup brings them both together in an spapr_load_rtas() function. Signed-off-by: David Gibson Reviewed-by: Alexey Kardashevskiy Reviewed-by: Thomas Huth Reviewed-by: Michael Roth --- hw/ppc/spapr.c | 3 +- hw/ppc/spapr_rtas.c | 72 ++++++++++++++++++++++++------------------ include/hw/ppc/spapr.h | 1 + 3 files changed, 43 insertions(+), 33 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 8e58d8670d..17733dffa3 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -1165,8 +1165,7 @@ static void ppc_spapr_reset(void) fdt = spapr_build_fdt(spapr, rtas_addr, spapr->rtas_size); - /* Copy RTAS over */ - cpu_physical_memory_write(rtas_addr, spapr->rtas_blob, spapr->rtas_size); + spapr_load_rtas(spapr, fdt, rtas_addr); rc = fdt_pack(fdt); diff --git a/hw/ppc/spapr_rtas.c b/hw/ppc/spapr_rtas.c index 0db84c816d..54b4ad3305 100644 --- a/hw/ppc/spapr_rtas.c +++ b/hw/ppc/spapr_rtas.c @@ -721,37 +721,6 @@ int spapr_rtas_device_tree_setup(void *fdt, hwaddr rtas_addr, uint64_t max_hotplug_addr = spapr->hotplug_memory.base + memory_region_size(&spapr->hotplug_memory.mr); - ret = fdt_add_mem_rsv(fdt, rtas_addr, rtas_size); - if (ret < 0) { - error_report("Couldn't add RTAS reserve entry: %s", - fdt_strerror(ret)); - return ret; - } - - ret = qemu_fdt_setprop_cell(fdt, "/rtas", "linux,rtas-base", - rtas_addr); - if (ret < 0) { - error_report("Couldn't add linux,rtas-base property: %s", - fdt_strerror(ret)); - return ret; - } - - ret = qemu_fdt_setprop_cell(fdt, "/rtas", "linux,rtas-entry", - rtas_addr); - if (ret < 0) { - error_report("Couldn't add linux,rtas-entry property: %s", - fdt_strerror(ret)); - return ret; - } - - ret = qemu_fdt_setprop_cell(fdt, "/rtas", "rtas-size", - rtas_size); - if (ret < 0) { - error_report("Couldn't add rtas-size property: %s", - fdt_strerror(ret)); - return ret; - } - for (i = 0; i < RTAS_TOKEN_MAX - RTAS_TOKEN_BASE; i++) { struct rtas_call *call = &rtas_table[i]; @@ -784,6 +753,47 @@ int spapr_rtas_device_tree_setup(void *fdt, hwaddr rtas_addr, return 0; } +void spapr_load_rtas(sPAPRMachineState *spapr, void *fdt, hwaddr addr) +{ + int rtas_node; + int ret; + + /* Copy RTAS blob into guest RAM */ + cpu_physical_memory_write(addr, spapr->rtas_blob, spapr->rtas_size); + + ret = fdt_add_mem_rsv(fdt, addr, spapr->rtas_size); + if (ret < 0) { + error_report("Couldn't add RTAS reserve entry: %s", + fdt_strerror(ret)); + exit(1); + } + + /* Update the device tree with the blob's location */ + rtas_node = fdt_path_offset(fdt, "/rtas"); + assert(rtas_node >= 0); + + ret = fdt_setprop_cell(fdt, rtas_node, "linux,rtas-base", addr); + if (ret < 0) { + error_report("Couldn't add linux,rtas-base property: %s", + fdt_strerror(ret)); + exit(1); + } + + ret = fdt_setprop_cell(fdt, rtas_node, "linux,rtas-entry", addr); + if (ret < 0) { + error_report("Couldn't add linux,rtas-entry property: %s", + fdt_strerror(ret)); + exit(1); + } + + ret = fdt_setprop_cell(fdt, rtas_node, "rtas-size", spapr->rtas_size); + if (ret < 0) { + error_report("Couldn't add rtas-size property: %s", + fdt_strerror(ret)); + exit(1); + } +} + static void core_rtas_register_types(void) { spapr_rtas_register(RTAS_DISPLAY_CHARACTER, "display-character", diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index a0b4bf80e0..847ae88186 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -532,6 +532,7 @@ target_ulong spapr_rtas_call(PowerPCCPU *cpu, sPAPRMachineState *sm, uint32_t nret, target_ulong rets); int spapr_rtas_device_tree_setup(void *fdt, hwaddr rtas_addr, hwaddr rtas_size); +void spapr_load_rtas(sPAPRMachineState *spapr, void *fdt, hwaddr addr); #define SPAPR_TCE_PAGE_SHIFT 12 #define SPAPR_TCE_PAGE_SIZE (1ULL << SPAPR_TCE_PAGE_SHIFT) From 9b9a19080a6e548b91420ce7925f2ac81ef63ae8 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 20 Oct 2016 16:07:56 +1100 Subject: [PATCH 39/73] pseries: Move construction of /interrupt-controller fdt node Currently the device tree node for the XICS interrupt controller is in spapr_create_fdt_skel(). As part of consolidating device tree construction to reset time, this moves it to a function called from spapr_build_fdt(). In addition we move the actual code into hw/intc/xics_spapr.c with the rest of the PAPR specific interrupt controller code. Signed-off-by: David Gibson Reviewed-by: Thomas Huth Reviewed-by: Michael Roth --- hw/intc/xics_spapr.c | 22 ++++++++++++++++++++++ hw/ppc/spapr.c | 20 +++----------------- include/hw/ppc/xics.h | 1 + 3 files changed, 26 insertions(+), 17 deletions(-) diff --git a/hw/intc/xics_spapr.c b/hw/intc/xics_spapr.c index b4e55012e0..2e3f1c5e95 100644 --- a/hw/intc/xics_spapr.c +++ b/hw/intc/xics_spapr.c @@ -32,6 +32,7 @@ #include "qemu/timer.h" #include "hw/ppc/spapr.h" #include "hw/ppc/xics.h" +#include "hw/ppc/fdt.h" #include "qapi/visitor.h" #include "qapi/error.h" @@ -449,6 +450,27 @@ void xics_spapr_free(XICSState *xics, int irq, int num) } } +void spapr_dt_xics(XICSState *xics, void *fdt, uint32_t phandle) +{ + uint32_t interrupt_server_ranges_prop[] = { + 0, cpu_to_be32(xics->nr_servers), + }; + int node; + + _FDT(node = fdt_add_subnode(fdt, 0, "interrupt-controller")); + + _FDT(fdt_setprop_string(fdt, node, "device_type", + "PowerPC-External-Interrupt-Presentation")); + _FDT(fdt_setprop_string(fdt, node, "compatible", "IBM,ppc-xicp")); + _FDT(fdt_setprop(fdt, node, "interrupt-controller", NULL, 0)); + _FDT(fdt_setprop(fdt, node, "ibm,interrupt-server-ranges", + interrupt_server_ranges_prop, + sizeof(interrupt_server_ranges_prop))); + _FDT(fdt_setprop_cell(fdt, node, "#interrupt-cells", 2)); + _FDT(fdt_setprop_cell(fdt, node, "linux,phandle", phandle)); + _FDT(fdt_setprop_cell(fdt, node, "phandle", phandle)); +} + static void xics_spapr_register_types(void) { type_register_static(&xics_spapr_info); diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 17733dffa3..102f0081ec 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -280,7 +280,6 @@ static void *spapr_create_fdt_skel(sPAPRMachineState *spapr) GString *hypertas = g_string_sized_new(256); GString *qemu_hypertas = g_string_sized_new(256); uint32_t refpoints[] = {cpu_to_be32(0x4), cpu_to_be32(0x4)}; - uint32_t interrupt_server_ranges_prop[] = {0, cpu_to_be32(max_cpus)}; unsigned char vec5[] = {0x0, 0x0, 0x0, 0x0, 0x0, 0x80}; char *buf; @@ -402,22 +401,6 @@ static void *spapr_create_fdt_skel(sPAPRMachineState *spapr) _FDT((fdt_end_node(fdt))); - /* interrupt controller */ - _FDT((fdt_begin_node(fdt, "interrupt-controller"))); - - _FDT((fdt_property_string(fdt, "device_type", - "PowerPC-External-Interrupt-Presentation"))); - _FDT((fdt_property_string(fdt, "compatible", "IBM,ppc-xicp"))); - _FDT((fdt_property(fdt, "interrupt-controller", NULL, 0))); - _FDT((fdt_property(fdt, "ibm,interrupt-server-ranges", - interrupt_server_ranges_prop, - sizeof(interrupt_server_ranges_prop)))); - _FDT((fdt_property_cell(fdt, "#interrupt-cells", 2))); - _FDT((fdt_property_cell(fdt, "linux,phandle", PHANDLE_XICP))); - _FDT((fdt_property_cell(fdt, "phandle", PHANDLE_XICP))); - - _FDT((fdt_end_node(fdt))); - /* vdevice */ _FDT((fdt_begin_node(fdt, "vdevice"))); @@ -909,6 +892,9 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, /* open out the base tree into a temp buffer for the final tweaks */ _FDT((fdt_open_into(spapr->fdt_skel, fdt, FDT_MAX_SIZE))); + /* /interrupt controller */ + spapr_dt_xics(spapr->xics, fdt, PHANDLE_XICP); + ret = spapr_populate_memory(spapr, fdt); if (ret < 0) { error_report("couldn't setup memory nodes in fdt"); diff --git a/include/hw/ppc/xics.h b/include/hw/ppc/xics.h index 6e5a113332..3f0c31610a 100644 --- a/include/hw/ppc/xics.h +++ b/include/hw/ppc/xics.h @@ -187,6 +187,7 @@ int xics_spapr_alloc(XICSState *icp, int irq_hint, bool lsi, Error **errp); int xics_spapr_alloc_block(XICSState *icp, int num, bool lsi, bool align, Error **errp); void xics_spapr_free(XICSState *icp, int irq, int num); +void spapr_dt_xics(XICSState *xics, void *fdt, uint32_t phandle); void xics_cpu_setup(XICSState *icp, PowerPCCPU *cpu); void xics_cpu_destroy(XICSState *icp, PowerPCCPU *cpu); From 7c866c6a600e435cf92f764b831d9cb3234ca0b4 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Mon, 24 Oct 2016 12:05:57 +1100 Subject: [PATCH 40/73] pseries: Consolidate construction of /chosen device tree node For historical reasons, building the /chosen node in the guest device tree is split across several places and includes both parts which write the DT sequentially and others which use random access functions. This patch consolidates construction of the node into one place, using random access functions throughout. Signed-off-by: David Gibson Reviewed-by: Thomas Huth Reviewed-by: Michael Roth --- hw/ppc/spapr.c | 131 ++++++++++++++++++------------------- hw/ppc/spapr_vio.c | 17 ++--- include/hw/ppc/spapr_vio.h | 2 +- 3 files changed, 70 insertions(+), 80 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 102f0081ec..1d8dd7f5b9 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -273,14 +273,10 @@ static void add_str(GString *s, const gchar *s1) static void *spapr_create_fdt_skel(sPAPRMachineState *spapr) { - MachineState *machine = MACHINE(spapr); void *fdt; - uint32_t start_prop = cpu_to_be32(spapr->initrd_base); - uint32_t end_prop = cpu_to_be32(spapr->initrd_base + spapr->initrd_size); GString *hypertas = g_string_sized_new(256); GString *qemu_hypertas = g_string_sized_new(256); uint32_t refpoints[] = {cpu_to_be32(0x4), cpu_to_be32(0x4)}; - unsigned char vec5[] = {0x0, 0x0, 0x0, 0x0, 0x0, 0x80}; char *buf; add_str(hypertas, "hcall-pft"); @@ -337,35 +333,6 @@ static void *spapr_create_fdt_skel(sPAPRMachineState *spapr) _FDT((fdt_property_cell(fdt, "#address-cells", 0x2))); _FDT((fdt_property_cell(fdt, "#size-cells", 0x2))); - /* /chosen */ - _FDT((fdt_begin_node(fdt, "chosen"))); - - /* Set Form1_affinity */ - _FDT((fdt_property(fdt, "ibm,architecture-vec-5", vec5, sizeof(vec5)))); - - _FDT((fdt_property_string(fdt, "bootargs", machine->kernel_cmdline))); - _FDT((fdt_property(fdt, "linux,initrd-start", - &start_prop, sizeof(start_prop)))); - _FDT((fdt_property(fdt, "linux,initrd-end", - &end_prop, sizeof(end_prop)))); - if (spapr->kernel_size) { - uint64_t kprop[2] = { cpu_to_be64(KERNEL_LOAD_ADDR), - cpu_to_be64(spapr->kernel_size) }; - - _FDT((fdt_property(fdt, "qemu,boot-kernel", &kprop, sizeof(kprop)))); - if (spapr->kernel_le) { - _FDT((fdt_property(fdt, "qemu,boot-kernel-le", NULL, 0))); - } - } - if (boot_menu) { - _FDT((fdt_property_cell(fdt, "qemu,boot-menu", boot_menu))); - } - _FDT((fdt_property_cell(fdt, "qemu,graphic-width", graphic_width))); - _FDT((fdt_property_cell(fdt, "qemu,graphic-height", graphic_height))); - _FDT((fdt_property_cell(fdt, "qemu,graphic-depth", graphic_depth))); - - _FDT((fdt_end_node(fdt))); - /* RTAS */ _FDT((fdt_begin_node(fdt, "rtas"))); @@ -873,6 +840,68 @@ int spapr_h_cas_compose_response(sPAPRMachineState *spapr, return 0; } +static void spapr_dt_chosen(sPAPRMachineState *spapr, void *fdt) +{ + MachineState *machine = MACHINE(spapr); + int chosen; + const char *boot_device = machine->boot_order; + char *stdout_path = spapr_vio_stdout_path(spapr->vio_bus); + size_t cb = 0; + char *bootlist = get_boot_devices_list(&cb, true); + unsigned char vec5[] = {0x0, 0x0, 0x0, 0x0, 0x0, 0x80}; + + _FDT(chosen = fdt_add_subnode(fdt, 0, "chosen")); + + /* Set Form1_affinity */ + _FDT(fdt_setprop(fdt, chosen, "ibm,architecture-vec-5", + vec5, sizeof(vec5))); + + _FDT(fdt_setprop_string(fdt, chosen, "bootargs", machine->kernel_cmdline)); + _FDT(fdt_setprop_cell(fdt, chosen, "linux,initrd-start", + spapr->initrd_base)); + _FDT(fdt_setprop_cell(fdt, chosen, "linux,initrd-end", + spapr->initrd_base + spapr->initrd_size)); + + if (spapr->kernel_size) { + uint64_t kprop[2] = { cpu_to_be64(KERNEL_LOAD_ADDR), + cpu_to_be64(spapr->kernel_size) }; + + _FDT(fdt_setprop(fdt, chosen, "qemu,boot-kernel", + &kprop, sizeof(kprop))); + if (spapr->kernel_le) { + _FDT(fdt_setprop(fdt, chosen, "qemu,boot-kernel-le", NULL, 0)); + } + } + if (boot_menu) { + _FDT((fdt_setprop_cell(fdt, chosen, "qemu,boot-menu", boot_menu))); + } + _FDT(fdt_setprop_cell(fdt, chosen, "qemu,graphic-width", graphic_width)); + _FDT(fdt_setprop_cell(fdt, chosen, "qemu,graphic-height", graphic_height)); + _FDT(fdt_setprop_cell(fdt, chosen, "qemu,graphic-depth", graphic_depth)); + + if (cb && bootlist) { + int i; + + for (i = 0; i < cb; i++) { + if (bootlist[i] == '\n') { + bootlist[i] = ' '; + } + } + _FDT(fdt_setprop_string(fdt, chosen, "qemu,boot-list", bootlist)); + } + + if (boot_device && strlen(boot_device)) { + _FDT(fdt_setprop_string(fdt, chosen, "qemu,boot-device", boot_device)); + } + + if (!spapr->has_graphics && stdout_path) { + _FDT(fdt_setprop_string(fdt, chosen, "linux,stdout-path", stdout_path)); + } + + g_free(stdout_path); + g_free(bootlist); +} + static void *spapr_build_fdt(sPAPRMachineState *spapr, hwaddr rtas_addr, hwaddr rtas_size) @@ -880,10 +909,7 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, MachineState *machine = MACHINE(qdev_get_machine()); MachineClass *mc = MACHINE_GET_CLASS(machine); sPAPRMachineClass *smc = SPAPR_MACHINE_GET_CLASS(machine); - const char *boot_device = machine->boot_order; - int ret, i; - size_t cb = 0; - char *bootlist; + int ret; void *fdt; sPAPRPHBState *phb; @@ -932,34 +958,6 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, /* cpus */ spapr_populate_cpus_dt_node(fdt, spapr); - bootlist = get_boot_devices_list(&cb, true); - if (cb && bootlist) { - int offset = fdt_path_offset(fdt, "/chosen"); - if (offset < 0) { - exit(1); - } - for (i = 0; i < cb; i++) { - if (bootlist[i] == '\n') { - bootlist[i] = ' '; - } - - } - ret = fdt_setprop_string(fdt, offset, "qemu,boot-list", bootlist); - } - - if (boot_device && strlen(boot_device)) { - int offset = fdt_path_offset(fdt, "/chosen"); - - if (offset < 0) { - exit(1); - } - fdt_setprop_string(fdt, offset, "qemu,boot-device", boot_device); - } - - if (!spapr->has_graphics) { - spapr_populate_chosen_stdout(fdt, spapr->vio_bus); - } - if (smc->dr_lmb_enabled) { _FDT(spapr_drc_populate_dt(fdt, 0, NULL, SPAPR_DR_CONNECTOR_TYPE_LMB)); } @@ -974,7 +972,8 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, } } - g_free(bootlist); + /* /chosen */ + spapr_dt_chosen(spapr, fdt); /* Build memory reserve map */ if (spapr->kernel_size) { diff --git a/hw/ppc/spapr_vio.c b/hw/ppc/spapr_vio.c index 3648aa5960..2b67df0a97 100644 --- a/hw/ppc/spapr_vio.c +++ b/hw/ppc/spapr_vio.c @@ -665,28 +665,19 @@ out: return ret; } -int spapr_populate_chosen_stdout(void *fdt, VIOsPAPRBus *bus) +gchar *spapr_vio_stdout_path(VIOsPAPRBus *bus) { VIOsPAPRDevice *dev; char *name, *path; - int ret, offset; dev = spapr_vty_get_default(bus); - if (!dev) - return 0; - - offset = fdt_path_offset(fdt, "/chosen"); - if (offset < 0) { - return offset; + if (!dev) { + return NULL; } name = spapr_vio_get_dev_name(DEVICE(dev)); path = g_strdup_printf("/vdevice/%s", name); - ret = fdt_setprop_string(fdt, offset, "linux,stdout-path", path); - g_free(name); - g_free(path); - - return ret; + return path; } diff --git a/include/hw/ppc/spapr_vio.h b/include/hw/ppc/spapr_vio.h index 0b025fd66b..a0e75424fa 100644 --- a/include/hw/ppc/spapr_vio.h +++ b/include/hw/ppc/spapr_vio.h @@ -81,7 +81,7 @@ struct VIOsPAPRBus { extern VIOsPAPRBus *spapr_vio_bus_init(void); extern VIOsPAPRDevice *spapr_vio_find_by_reg(VIOsPAPRBus *bus, uint32_t reg); extern int spapr_populate_vdevice(VIOsPAPRBus *bus, void *fdt); -extern int spapr_populate_chosen_stdout(void *fdt, VIOsPAPRBus *bus); +extern gchar *spapr_vio_stdout_path(VIOsPAPRBus *bus); static inline qemu_irq spapr_vio_qirq(VIOsPAPRDevice *dev) { From 3f5dabceba246e502555a9046b98174d7548e696 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 20 Oct 2016 15:55:36 +1100 Subject: [PATCH 41/73] pseries: Consolidate construction of /rtas device tree node For historical reasons construction of the /rtas node in the device tree (amongst others) is split into several places. In particular it's split between spapr_create_fdt_skel(), spapr_build_fdt() and spapr_rtas_device_tree_setup(). In fact, as well as adding the actual RTAS tokens to the device tree, spapr_rtas_device_tree_setup() just adds the ibm,lrdr-capacity property, which despite going in the /rtas node, doesn't have a lot to do with RTAS. This patch consolidates the code constructing /rtas together into a new spapr_dt_rtas() function. spapr_rtas_device_tree_setup() is renamed to spapr_dt_rtas_tokens() and now only adds the token properties. Signed-off-by: David Gibson Reviewed-by: Thomas Huth Reviewed-by: Michael Roth --- hw/ppc/spapr.c | 130 +++++++++++++++++++++++------------------ hw/ppc/spapr_rtas.c | 33 +---------- include/hw/ppc/spapr.h | 3 +- 3 files changed, 76 insertions(+), 90 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 1d8dd7f5b9..1b61de250d 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -274,25 +274,8 @@ static void add_str(GString *s, const gchar *s1) static void *spapr_create_fdt_skel(sPAPRMachineState *spapr) { void *fdt; - GString *hypertas = g_string_sized_new(256); - GString *qemu_hypertas = g_string_sized_new(256); - uint32_t refpoints[] = {cpu_to_be32(0x4), cpu_to_be32(0x4)}; char *buf; - add_str(hypertas, "hcall-pft"); - add_str(hypertas, "hcall-term"); - add_str(hypertas, "hcall-dabr"); - add_str(hypertas, "hcall-interrupt"); - add_str(hypertas, "hcall-tce"); - add_str(hypertas, "hcall-vio"); - add_str(hypertas, "hcall-splpar"); - add_str(hypertas, "hcall-bulk"); - add_str(hypertas, "hcall-set-mode"); - add_str(hypertas, "hcall-sprg0"); - add_str(hypertas, "hcall-copy"); - add_str(hypertas, "hcall-debug"); - add_str(qemu_hypertas, "hcall-memop1"); - fdt = g_malloc0(FDT_MAX_SIZE); _FDT((fdt_create(fdt, FDT_MAX_SIZE))); @@ -333,41 +316,6 @@ static void *spapr_create_fdt_skel(sPAPRMachineState *spapr) _FDT((fdt_property_cell(fdt, "#address-cells", 0x2))); _FDT((fdt_property_cell(fdt, "#size-cells", 0x2))); - /* RTAS */ - _FDT((fdt_begin_node(fdt, "rtas"))); - - if (!kvm_enabled() || kvmppc_spapr_use_multitce()) { - add_str(hypertas, "hcall-multi-tce"); - } - _FDT((fdt_property(fdt, "ibm,hypertas-functions", hypertas->str, - hypertas->len))); - g_string_free(hypertas, TRUE); - _FDT((fdt_property(fdt, "qemu,hypertas-functions", qemu_hypertas->str, - qemu_hypertas->len))); - g_string_free(qemu_hypertas, TRUE); - - _FDT((fdt_property(fdt, "ibm,associativity-reference-points", - refpoints, sizeof(refpoints)))); - - _FDT((fdt_property_cell(fdt, "rtas-error-log-max", RTAS_ERROR_LOG_MAX))); - _FDT((fdt_property_cell(fdt, "rtas-event-scan-rate", - RTAS_EVENT_SCAN_RATE))); - - if (msi_nonbroken) { - _FDT((fdt_property(fdt, "ibm,change-msix-capable", NULL, 0))); - } - - /* - * According to PAPR, rtas ibm,os-term does not guarantee a return - * back to the guest cpu. - * - * While an additional ibm,extended-os-term property indicates that - * rtas call return will always occur. Set this property. - */ - _FDT((fdt_property(fdt, "ibm,extended-os-term", NULL, 0))); - - _FDT((fdt_end_node(fdt))); - /* vdevice */ _FDT((fdt_begin_node(fdt, "vdevice"))); @@ -840,6 +788,75 @@ int spapr_h_cas_compose_response(sPAPRMachineState *spapr, return 0; } +static void spapr_dt_rtas(sPAPRMachineState *spapr, void *fdt) +{ + int rtas; + GString *hypertas = g_string_sized_new(256); + GString *qemu_hypertas = g_string_sized_new(256); + uint32_t refpoints[] = { cpu_to_be32(0x4), cpu_to_be32(0x4) }; + uint64_t max_hotplug_addr = spapr->hotplug_memory.base + + memory_region_size(&spapr->hotplug_memory.mr); + uint32_t lrdr_capacity[] = { + cpu_to_be32(max_hotplug_addr >> 32), + cpu_to_be32(max_hotplug_addr & 0xffffffff), + 0, cpu_to_be32(SPAPR_MEMORY_BLOCK_SIZE), + cpu_to_be32(max_cpus / smp_threads), + }; + + _FDT(rtas = fdt_add_subnode(fdt, 0, "rtas")); + + /* hypertas */ + add_str(hypertas, "hcall-pft"); + add_str(hypertas, "hcall-term"); + add_str(hypertas, "hcall-dabr"); + add_str(hypertas, "hcall-interrupt"); + add_str(hypertas, "hcall-tce"); + add_str(hypertas, "hcall-vio"); + add_str(hypertas, "hcall-splpar"); + add_str(hypertas, "hcall-bulk"); + add_str(hypertas, "hcall-set-mode"); + add_str(hypertas, "hcall-sprg0"); + add_str(hypertas, "hcall-copy"); + add_str(hypertas, "hcall-debug"); + add_str(qemu_hypertas, "hcall-memop1"); + + if (!kvm_enabled() || kvmppc_spapr_use_multitce()) { + add_str(hypertas, "hcall-multi-tce"); + } + _FDT(fdt_setprop(fdt, rtas, "ibm,hypertas-functions", + hypertas->str, hypertas->len)); + g_string_free(hypertas, TRUE); + _FDT(fdt_setprop(fdt, rtas, "qemu,hypertas-functions", + qemu_hypertas->str, qemu_hypertas->len)); + g_string_free(qemu_hypertas, TRUE); + + _FDT(fdt_setprop(fdt, rtas, "ibm,associativity-reference-points", + refpoints, sizeof(refpoints))); + + _FDT(fdt_setprop_cell(fdt, rtas, "rtas-error-log-max", + RTAS_ERROR_LOG_MAX)); + _FDT(fdt_setprop_cell(fdt, rtas, "rtas-event-scan-rate", + RTAS_EVENT_SCAN_RATE)); + + if (msi_nonbroken) { + _FDT(fdt_setprop(fdt, rtas, "ibm,change-msix-capable", NULL, 0)); + } + + /* + * According to PAPR, rtas ibm,os-term does not guarantee a return + * back to the guest cpu. + * + * While an additional ibm,extended-os-term property indicates + * that rtas call return will always occur. Set this property. + */ + _FDT(fdt_setprop(fdt, rtas, "ibm,extended-os-term", NULL, 0)); + + _FDT(fdt_setprop(fdt, rtas, "ibm,lrdr-capacity", + lrdr_capacity, sizeof(lrdr_capacity))); + + spapr_dt_rtas_tokens(fdt, rtas); +} + static void spapr_dt_chosen(sPAPRMachineState *spapr, void *fdt) { MachineState *machine = MACHINE(spapr); @@ -949,12 +966,6 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, } } - /* RTAS */ - ret = spapr_rtas_device_tree_setup(fdt, rtas_addr, rtas_size); - if (ret < 0) { - error_report("Couldn't set up RTAS device tree properties"); - } - /* cpus */ spapr_populate_cpus_dt_node(fdt, spapr); @@ -972,6 +983,9 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, } } + /* /rtas */ + spapr_dt_rtas(spapr, fdt); + /* /chosen */ spapr_dt_chosen(spapr, fdt); diff --git a/hw/ppc/spapr_rtas.c b/hw/ppc/spapr_rtas.c index 54b4ad3305..bb19944686 100644 --- a/hw/ppc/spapr_rtas.c +++ b/hw/ppc/spapr_rtas.c @@ -46,6 +46,7 @@ #include "hw/ppc/spapr_drc.h" #include "qemu/cutils.h" #include "trace.h" +#include "hw/ppc/fdt.h" static sPAPRConfigureConnectorState *spapr_ccs_find(sPAPRMachineState *spapr, uint32_t drc_index) @@ -710,16 +711,9 @@ void spapr_rtas_register(int token, const char *name, spapr_rtas_fn fn) rtas_table[token].fn = fn; } -int spapr_rtas_device_tree_setup(void *fdt, hwaddr rtas_addr, - hwaddr rtas_size) +void spapr_dt_rtas_tokens(void *fdt, int rtas) { - int ret; int i; - uint32_t lrdr_capacity[5]; - MachineState *machine = MACHINE(qdev_get_machine()); - sPAPRMachineState *spapr = SPAPR_MACHINE(machine); - uint64_t max_hotplug_addr = spapr->hotplug_memory.base + - memory_region_size(&spapr->hotplug_memory.mr); for (i = 0; i < RTAS_TOKEN_MAX - RTAS_TOKEN_BASE; i++) { struct rtas_call *call = &rtas_table[i]; @@ -728,29 +722,8 @@ int spapr_rtas_device_tree_setup(void *fdt, hwaddr rtas_addr, continue; } - ret = qemu_fdt_setprop_cell(fdt, "/rtas", call->name, - i + RTAS_TOKEN_BASE); - if (ret < 0) { - error_report("Couldn't add rtas token for %s: %s", - call->name, fdt_strerror(ret)); - return ret; - } - + _FDT(fdt_setprop_cell(fdt, rtas, call->name, i + RTAS_TOKEN_BASE)); } - - lrdr_capacity[0] = cpu_to_be32(max_hotplug_addr >> 32); - lrdr_capacity[1] = cpu_to_be32(max_hotplug_addr & 0xffffffff); - lrdr_capacity[2] = 0; - lrdr_capacity[3] = cpu_to_be32(SPAPR_MEMORY_BLOCK_SIZE); - lrdr_capacity[4] = cpu_to_be32(max_cpus/smp_threads); - ret = qemu_fdt_setprop(fdt, "/rtas", "ibm,lrdr-capacity", lrdr_capacity, - sizeof(lrdr_capacity)); - if (ret < 0) { - error_report("Couldn't add ibm,lrdr-capacity rtas property"); - return ret; - } - - return 0; } void spapr_load_rtas(sPAPRMachineState *spapr, void *fdt, hwaddr addr) diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index 847ae88186..8b8bb97634 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -530,8 +530,7 @@ void spapr_rtas_register(int token, const char *name, spapr_rtas_fn fn); target_ulong spapr_rtas_call(PowerPCCPU *cpu, sPAPRMachineState *sm, uint32_t token, uint32_t nargs, target_ulong args, uint32_t nret, target_ulong rets); -int spapr_rtas_device_tree_setup(void *fdt, hwaddr rtas_addr, - hwaddr rtas_size); +void spapr_dt_rtas_tokens(void *fdt, int rtas); void spapr_load_rtas(sPAPRMachineState *spapr, void *fdt, hwaddr addr); #define SPAPR_TCE_PAGE_SHIFT 12 From ffb1e275a67cfeb957d0d0df2ec1f0999e321f69 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 20 Oct 2016 15:56:48 +1100 Subject: [PATCH 42/73] pseries: Move /event-sources construction to spapr_build_fdt() The /event-sources device tree node is built from spapr_create_fdt_skel(). As part of consolidating device tree construction to reset time, this moves it to spapr_build_fdt(). Signed-off-by: David Gibson Reviewed-by: Thomas Huth Reviewed-by: Michael Roth --- hw/ppc/spapr.c | 6 +++--- hw/ppc/spapr_events.c | 21 ++++++++++----------- include/hw/ppc/spapr.h | 2 +- 3 files changed, 14 insertions(+), 15 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 1b61de250d..048fb3d7cb 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -328,9 +328,6 @@ static void *spapr_create_fdt_skel(sPAPRMachineState *spapr) _FDT((fdt_end_node(fdt))); - /* event-sources */ - spapr_events_fdt_skel(fdt, spapr->check_exception_irq); - /* /hypervisor node */ if (kvm_enabled()) { uint8_t hypercall[16]; @@ -983,6 +980,9 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, } } + /* /event-sources */ + spapr_dt_events(fdt, spapr->check_exception_irq); + /* /rtas */ spapr_dt_rtas(spapr, fdt); diff --git a/hw/ppc/spapr_events.c b/hw/ppc/spapr_events.c index 6d3534541c..89aa5a7926 100644 --- a/hw/ppc/spapr_events.c +++ b/hw/ppc/spapr_events.c @@ -211,23 +211,22 @@ struct hp_log_full { #define EVENT_MASK_HOTPLUG 0x10000000 #define EVENT_MASK_IO 0x08000000 -void spapr_events_fdt_skel(void *fdt, uint32_t check_exception_irq) +void spapr_dt_events(void *fdt, uint32_t check_exception_irq) { + int event_sources, epow_events; uint32_t irq_ranges[] = {cpu_to_be32(check_exception_irq), cpu_to_be32(1)}; uint32_t interrupts[] = {cpu_to_be32(check_exception_irq), 0}; - _FDT((fdt_begin_node(fdt, "event-sources"))); + _FDT(event_sources = fdt_add_subnode(fdt, 0, "event-sources")); - _FDT((fdt_property(fdt, "interrupt-controller", NULL, 0))); - _FDT((fdt_property_cell(fdt, "#interrupt-cells", 2))); - _FDT((fdt_property(fdt, "interrupt-ranges", - irq_ranges, sizeof(irq_ranges)))); + _FDT(fdt_setprop(fdt, event_sources, "interrupt-controller", NULL, 0)); + _FDT(fdt_setprop_cell(fdt, event_sources, "#interrupt-cells", 2)); + _FDT(fdt_setprop(fdt, event_sources, "interrupt-ranges", + irq_ranges, sizeof(irq_ranges))); - _FDT((fdt_begin_node(fdt, "epow-events"))); - _FDT((fdt_property(fdt, "interrupts", interrupts, sizeof(interrupts)))); - _FDT((fdt_end_node(fdt))); - - _FDT((fdt_end_node(fdt))); + _FDT(epow_events = fdt_add_subnode(fdt, event_sources, "epow-events")); + _FDT(fdt_setprop(fdt, epow_events, "interrupts", + interrupts, sizeof(interrupts))); } static void rtas_event_log_queue(int log_type, void *data, bool exception) diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index 8b8bb97634..ae7d1d7043 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -581,7 +581,7 @@ struct sPAPREventLogEntry { }; void spapr_events_init(sPAPRMachineState *sm); -void spapr_events_fdt_skel(void *fdt, uint32_t epow_irq); +void spapr_dt_events(void *fdt, uint32_t check_exception_irq); int spapr_h_cas_compose_response(sPAPRMachineState *sm, target_ulong addr, target_ulong size, bool cpu_update, bool memory_update); From fca5f2dc6ca03afa78a11835a9a6b6d223fa4575 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 20 Oct 2016 15:59:36 +1100 Subject: [PATCH 43/73] pseries: Move /hypervisor node construction to fdt_build_fdt() Currently the /hypervisor device tree node is constructed in spapr_create_fdt_skel(). As part of consolidating device tree construction to reset time, move it to a function called from spapr_build_fdt(). Signed-off-by: David Gibson Reviewed-by: Thomas Huth Reviewed-by: Michael Roth --- hw/ppc/spapr.c | 49 ++++++++++++++++++++++++++++--------------------- 1 file changed, 28 insertions(+), 21 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 048fb3d7cb..261be68920 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -328,27 +328,6 @@ static void *spapr_create_fdt_skel(sPAPRMachineState *spapr) _FDT((fdt_end_node(fdt))); - /* /hypervisor node */ - if (kvm_enabled()) { - uint8_t hypercall[16]; - - /* indicate KVM hypercall interface */ - _FDT((fdt_begin_node(fdt, "hypervisor"))); - _FDT((fdt_property_string(fdt, "compatible", "linux,kvm"))); - if (kvmppc_has_cap_fixup_hcalls()) { - /* - * Older KVM versions with older guest kernels were broken with the - * magic page, don't allow the guest to map it. - */ - if (!kvmppc_get_hypercall(first_cpu->env_ptr, hypercall, - sizeof(hypercall))) { - _FDT((fdt_property(fdt, "hcall-instructions", hypercall, - sizeof(hypercall)))); - } - } - _FDT((fdt_end_node(fdt))); - } - _FDT((fdt_end_node(fdt))); /* close root node */ _FDT((fdt_finish(fdt))); @@ -916,6 +895,29 @@ static void spapr_dt_chosen(sPAPRMachineState *spapr, void *fdt) g_free(bootlist); } +static void spapr_dt_hypervisor(sPAPRMachineState *spapr, void *fdt) +{ + /* The /hypervisor node isn't in PAPR - this is a hack to allow PR + * KVM to work under pHyp with some guest co-operation */ + int hypervisor; + uint8_t hypercall[16]; + + _FDT(hypervisor = fdt_add_subnode(fdt, 0, "hypervisor")); + /* indicate KVM hypercall interface */ + _FDT(fdt_setprop_string(fdt, hypervisor, "compatible", "linux,kvm")); + if (kvmppc_has_cap_fixup_hcalls()) { + /* + * Older KVM versions with older guest kernels were broken + * with the magic page, don't allow the guest to map it. + */ + if (!kvmppc_get_hypercall(first_cpu->env_ptr, hypercall, + sizeof(hypercall))) { + _FDT(fdt_setprop(fdt, hypervisor, "hcall-instructions", + hypercall, sizeof(hypercall))); + } + } +} + static void *spapr_build_fdt(sPAPRMachineState *spapr, hwaddr rtas_addr, hwaddr rtas_size) @@ -989,6 +991,11 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, /* /chosen */ spapr_dt_chosen(spapr, fdt); + /* /hypervisor */ + if (kvm_enabled()) { + spapr_dt_hypervisor(spapr, fdt); + } + /* Build memory reserve map */ if (spapr->kernel_size) { _FDT((fdt_add_mem_rsv(fdt, KERNEL_LOAD_ADDR, spapr->kernel_size))); From bf5a6696ba95ee6efa29489dd7d53b6fbcf18469 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 20 Oct 2016 16:01:17 +1100 Subject: [PATCH 44/73] pseries: Consolidate construction of /vdevice device tree node Construction of the /vdevice node (and its children) is divided between spapr_create_fdt_skel() (at init time), which creates the base node, and spapr_populate_vdevice() (at reset time) which creates the nodes for each individual virtual device. This consolidates both into a single function called from spapr_build_fdt(). Signed-off-by: David Gibson Reviewed-by: Thomas Huth Reviewed-by: Michael Roth --- hw/ppc/spapr.c | 19 ++----------------- hw/ppc/spapr_vio.c | 23 ++++++++++++++++------- include/hw/ppc/spapr_vio.h | 2 +- 3 files changed, 19 insertions(+), 25 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 261be68920..34846da81c 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -316,18 +316,6 @@ static void *spapr_create_fdt_skel(sPAPRMachineState *spapr) _FDT((fdt_property_cell(fdt, "#address-cells", 0x2))); _FDT((fdt_property_cell(fdt, "#size-cells", 0x2))); - /* vdevice */ - _FDT((fdt_begin_node(fdt, "vdevice"))); - - _FDT((fdt_property_string(fdt, "device_type", "vdevice"))); - _FDT((fdt_property_string(fdt, "compatible", "IBM,vdevice"))); - _FDT((fdt_property_cell(fdt, "#address-cells", 0x1))); - _FDT((fdt_property_cell(fdt, "#size-cells", 0x0))); - _FDT((fdt_property_cell(fdt, "#interrupt-cells", 0x2))); - _FDT((fdt_property(fdt, "interrupt-controller", NULL, 0))); - - _FDT((fdt_end_node(fdt))); - _FDT((fdt_end_node(fdt))); /* close root node */ _FDT((fdt_finish(fdt))); @@ -943,11 +931,8 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, exit(1); } - ret = spapr_populate_vdevice(spapr->vio_bus, fdt); - if (ret < 0) { - error_report("couldn't setup vio devices in fdt"); - exit(1); - } + /* /vdevice */ + spapr_dt_vdevice(spapr->vio_bus, fdt); if (object_resolve_path_type("", TYPE_SPAPR_RNG, NULL)) { ret = spapr_rng_populate_dt(fdt); diff --git a/hw/ppc/spapr_vio.c b/hw/ppc/spapr_vio.c index 2b67df0a97..cc1e09c568 100644 --- a/hw/ppc/spapr_vio.c +++ b/hw/ppc/spapr_vio.c @@ -36,6 +36,7 @@ #include "hw/ppc/spapr.h" #include "hw/ppc/spapr_vio.h" #include "hw/ppc/xics.h" +#include "hw/ppc/fdt.h" #include "trace.h" #include @@ -624,11 +625,21 @@ static int compare_reg(const void *p1, const void *p2) return 1; } -int spapr_populate_vdevice(VIOsPAPRBus *bus, void *fdt) +void spapr_dt_vdevice(VIOsPAPRBus *bus, void *fdt) { DeviceState *qdev, **qdevs; BusChild *kid; int i, num, ret = 0; + int node; + + _FDT(node = fdt_add_subnode(fdt, 0, "vdevice")); + + _FDT(fdt_setprop_string(fdt, node, "device_type", "vdevice")); + _FDT(fdt_setprop_string(fdt, node, "compatible", "IBM,vdevice")); + _FDT(fdt_setprop_cell(fdt, node, "#address-cells", 1)); + _FDT(fdt_setprop_cell(fdt, node, "#size-cells", 0)); + _FDT(fdt_setprop_cell(fdt, node, "#interrupt-cells", 2)); + _FDT(fdt_setprop(fdt, node, "interrupt-controller", NULL, 0)); /* Count qdevs on the bus list */ num = 0; @@ -650,19 +661,17 @@ int spapr_populate_vdevice(VIOsPAPRBus *bus, void *fdt) * to know that will mean they are in forward order in the tree. */ for (i = num - 1; i >= 0; i--) { VIOsPAPRDevice *dev = (VIOsPAPRDevice *)(qdevs[i]); + VIOsPAPRDeviceClass *vdc = VIO_SPAPR_DEVICE_GET_CLASS(dev); ret = vio_make_devnode(dev, fdt); - if (ret < 0) { - goto out; + error_report("Couldn't create device node /vdevice/%s@%"PRIx32, + vdc->dt_name, dev->reg); + exit(1); } } - ret = 0; -out: g_free(qdevs); - - return ret; } gchar *spapr_vio_stdout_path(VIOsPAPRBus *bus) diff --git a/include/hw/ppc/spapr_vio.h b/include/hw/ppc/spapr_vio.h index a0e75424fa..14f502240e 100644 --- a/include/hw/ppc/spapr_vio.h +++ b/include/hw/ppc/spapr_vio.h @@ -80,7 +80,7 @@ struct VIOsPAPRBus { extern VIOsPAPRBus *spapr_vio_bus_init(void); extern VIOsPAPRDevice *spapr_vio_find_by_reg(VIOsPAPRBus *bus, uint32_t reg); -extern int spapr_populate_vdevice(VIOsPAPRBus *bus, void *fdt); +void spapr_dt_vdevice(VIOsPAPRBus *bus, void *fdt); extern gchar *spapr_vio_stdout_path(VIOsPAPRBus *bus); static inline qemu_irq spapr_vio_qirq(VIOsPAPRDevice *dev) From 398a0bd5ae7e03b5b9bdde1dc76451ff57471a55 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 20 Oct 2016 16:05:00 +1100 Subject: [PATCH 45/73] pseries: Remove spapr_create_fdt_skel() For historical reasons construction of the guest device tree in spapr is divided between spapr_create_fdt_skel() which is called at init time, and spapr_build_fdt() which runs at reset time. Over time, more and more things have needed to be moved to reset time. Previous cleanups mean the only things left in spapr_create_fdt_skel() are the properties of the root node itself. Finish consolidating these two parts of device tree construction, by moving this to the start of spapr_build_fdt(), and removing spapr_create_fdt_skel() entirely. Signed-off-by: David Gibson Reviewed-by: Thomas Huth Reviewed-by: Michael Roth --- hw/ppc/spapr.c | 94 ++++++++++++++++-------------------------- include/hw/ppc/spapr.h | 1 - 2 files changed, 36 insertions(+), 59 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 34846da81c..209bc8404b 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -271,57 +271,6 @@ static void add_str(GString *s, const gchar *s1) g_string_append_len(s, s1, strlen(s1) + 1); } -static void *spapr_create_fdt_skel(sPAPRMachineState *spapr) -{ - void *fdt; - char *buf; - - fdt = g_malloc0(FDT_MAX_SIZE); - _FDT((fdt_create(fdt, FDT_MAX_SIZE))); - - _FDT((fdt_finish_reservemap(fdt))); - - /* Root node */ - _FDT((fdt_begin_node(fdt, ""))); - _FDT((fdt_property_string(fdt, "device_type", "chrp"))); - _FDT((fdt_property_string(fdt, "model", "IBM pSeries (emulated by qemu)"))); - _FDT((fdt_property_string(fdt, "compatible", "qemu,pseries"))); - - /* - * Add info to guest to indentify which host is it being run on - * and what is the uuid of the guest - */ - if (kvmppc_get_host_model(&buf)) { - _FDT((fdt_property_string(fdt, "host-model", buf))); - g_free(buf); - } - if (kvmppc_get_host_serial(&buf)) { - _FDT((fdt_property_string(fdt, "host-serial", buf))); - g_free(buf); - } - - buf = qemu_uuid_unparse_strdup(&qemu_uuid); - - _FDT((fdt_property_string(fdt, "vm,uuid", buf))); - if (qemu_uuid_set) { - _FDT((fdt_property_string(fdt, "system-id", buf))); - } - g_free(buf); - - if (qemu_get_vm_name()) { - _FDT((fdt_property_string(fdt, "ibm,partition-name", - qemu_get_vm_name()))); - } - - _FDT((fdt_property_cell(fdt, "#address-cells", 0x2))); - _FDT((fdt_property_cell(fdt, "#size-cells", 0x2))); - - _FDT((fdt_end_node(fdt))); /* close root node */ - _FDT((fdt_finish(fdt))); - - return fdt; -} - static int spapr_populate_memory_node(void *fdt, int nodeid, hwaddr start, hwaddr size) { @@ -916,11 +865,44 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, int ret; void *fdt; sPAPRPHBState *phb; + char *buf; - fdt = g_malloc(FDT_MAX_SIZE); + fdt = g_malloc0(FDT_MAX_SIZE); + _FDT((fdt_create_empty_tree(fdt, FDT_MAX_SIZE))); - /* open out the base tree into a temp buffer for the final tweaks */ - _FDT((fdt_open_into(spapr->fdt_skel, fdt, FDT_MAX_SIZE))); + /* Root node */ + _FDT(fdt_setprop_string(fdt, 0, "device_type", "chrp")); + _FDT(fdt_setprop_string(fdt, 0, "model", "IBM pSeries (emulated by qemu)")); + _FDT(fdt_setprop_string(fdt, 0, "compatible", "qemu,pseries")); + + /* + * Add info to guest to indentify which host is it being run on + * and what is the uuid of the guest + */ + if (kvmppc_get_host_model(&buf)) { + _FDT(fdt_setprop_string(fdt, 0, "host-model", buf)); + g_free(buf); + } + if (kvmppc_get_host_serial(&buf)) { + _FDT(fdt_setprop_string(fdt, 0, "host-serial", buf)); + g_free(buf); + } + + buf = qemu_uuid_unparse_strdup(&qemu_uuid); + + _FDT(fdt_setprop_string(fdt, 0, "vm,uuid", buf)); + if (qemu_uuid_set) { + _FDT(fdt_setprop_string(fdt, 0, "system-id", buf)); + } + g_free(buf); + + if (qemu_get_vm_name()) { + _FDT(fdt_setprop_string(fdt, 0, "ibm,partition-name", + qemu_get_vm_name())); + } + + _FDT(fdt_setprop_cell(fdt, 0, "#address-cells", 2)); + _FDT(fdt_setprop_cell(fdt, 0, "#size-cells", 2)); /* /interrupt controller */ spapr_dt_xics(spapr->xics, fdt, PHANDLE_XICP); @@ -2014,10 +1996,6 @@ static void ppc_spapr_init(MachineState *machine) register_savevm_live(NULL, "spapr/htab", -1, 1, &savevm_htab_handlers, spapr); - /* Prepare the device tree */ - spapr->fdt_skel = spapr_create_fdt_skel(spapr); - assert(spapr->fdt_skel != NULL); - /* used by RTAS */ QTAILQ_INIT(&spapr->ccs_list); qemu_register_reset(spapr_ccs_reset_hook, spapr); diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index ae7d1d7043..d5d6e57c41 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -69,7 +69,6 @@ struct sPAPRMachineState { bool kernel_le; uint32_t initrd_base; long initrd_size; - void *fdt_skel; uint64_t rtc_offset; /* Now used only during incoming migration */ struct PPCTimebase tb; bool has_graphics; From b20b7b7adda4e2228892670a94e0a4af41c065b9 Mon Sep 17 00:00:00 2001 From: Michael Roth Date: Mon, 24 Oct 2016 23:47:27 -0500 Subject: [PATCH 46/73] spapr_ovec: initial implementation of option vector helpers PAPR guests advertise their capabilities to the platform by passing an ibm,architecture-vec structure via an ibm,client-architecture-support hcall as described by LoPAPR v11, B.6.2.3. during early boot. Using this information, the platform enables the capabilities it supports, then encodes a subset of those enabled capabilities (the 5th option vector of the ibm,architecture-vec structure passed to ibm,client-architecture-support) into the guest device tree via "/chosen/ibm,architecture-vec-5". The logical format of these these option vectors is a bit-vector, where individual bits are addressed/documented based on the byte-wise offset from the beginning of the bit-vector, followed by the bit-wise index starting from the byte-wise offset. Thus the bits of each of these bytes are stored in reverse order. Additionally, the first byte of each option vector is encodes the length of the option vector, so byte offsets begin at 1, and bit offset at 0. This is not very intuitive for the purposes of mapping these bits to a particular documented capability, so this patch introduces a set of abstractions that encapsulate the work of parsing/encoding these options vectors and testing for individual capabilities. Cc: Bharata B Rao Signed-off-by: Michael Roth [dwg: Tweaked double-include protection to not trigger a checkpatch false positive] Signed-off-by: David Gibson --- hw/ppc/Makefile.objs | 2 +- hw/ppc/spapr_ovec.c | 242 ++++++++++++++++++++++++++++++++++++ include/hw/ppc/spapr_ovec.h | 62 +++++++++ 3 files changed, 305 insertions(+), 1 deletion(-) create mode 100644 hw/ppc/spapr_ovec.c create mode 100644 include/hw/ppc/spapr_ovec.h diff --git a/hw/ppc/Makefile.objs b/hw/ppc/Makefile.objs index ebc72af0a7..8025129377 100644 --- a/hw/ppc/Makefile.objs +++ b/hw/ppc/Makefile.objs @@ -4,7 +4,7 @@ obj-y += ppc.o ppc_booke.o fdt.o obj-$(CONFIG_PSERIES) += spapr.o spapr_vio.o spapr_events.o obj-$(CONFIG_PSERIES) += spapr_hcall.o spapr_iommu.o spapr_rtas.o obj-$(CONFIG_PSERIES) += spapr_pci.o spapr_rtc.o spapr_drc.o spapr_rng.o -obj-$(CONFIG_PSERIES) += spapr_cpu_core.o +obj-$(CONFIG_PSERIES) += spapr_cpu_core.o spapr_ovec.o # IBM PowerNV obj-$(CONFIG_POWERNV) += pnv.o pnv_xscom.o pnv_core.o pnv_lpc.o ifeq ($(CONFIG_PCI)$(CONFIG_PSERIES)$(CONFIG_LINUX), yyy) diff --git a/hw/ppc/spapr_ovec.c b/hw/ppc/spapr_ovec.c new file mode 100644 index 0000000000..c2a0d18577 --- /dev/null +++ b/hw/ppc/spapr_ovec.c @@ -0,0 +1,242 @@ +/* + * QEMU SPAPR Architecture Option Vector Helper Functions + * + * Copyright IBM Corp. 2016 + * + * Authors: + * Bharata B Rao + * Michael Roth + * + * This work is licensed under the terms of the GNU GPL, version 2 or later. + * See the COPYING file in the top-level directory. + */ + +#include "qemu/osdep.h" +#include "hw/ppc/spapr_ovec.h" +#include "qemu/bitmap.h" +#include "exec/address-spaces.h" +#include "qemu/error-report.h" +#include + +/* #define DEBUG_SPAPR_OVEC */ + +#ifdef DEBUG_SPAPR_OVEC +#define DPRINTFN(fmt, ...) \ + do { fprintf(stderr, fmt "\n", ## __VA_ARGS__); } while (0) +#else +#define DPRINTFN(fmt, ...) \ + do { } while (0) +#endif + +#define OV_MAXBYTES 256 /* not including length byte */ +#define OV_MAXBITS (OV_MAXBYTES * BITS_PER_BYTE) + +/* we *could* work with bitmaps directly, but handling the bitmap privately + * allows us to more safely make assumptions about the bitmap size and + * simplify the calling code somewhat + */ +struct sPAPROptionVector { + unsigned long *bitmap; +}; + +sPAPROptionVector *spapr_ovec_new(void) +{ + sPAPROptionVector *ov; + + ov = g_new0(sPAPROptionVector, 1); + ov->bitmap = bitmap_new(OV_MAXBITS); + + return ov; +} + +sPAPROptionVector *spapr_ovec_clone(sPAPROptionVector *ov_orig) +{ + sPAPROptionVector *ov; + + g_assert(ov_orig); + + ov = spapr_ovec_new(); + bitmap_copy(ov->bitmap, ov_orig->bitmap, OV_MAXBITS); + + return ov; +} + +void spapr_ovec_intersect(sPAPROptionVector *ov, + sPAPROptionVector *ov1, + sPAPROptionVector *ov2) +{ + g_assert(ov); + g_assert(ov1); + g_assert(ov2); + + bitmap_and(ov->bitmap, ov1->bitmap, ov2->bitmap, OV_MAXBITS); +} + +/* returns true if options bits were removed, false otherwise */ +bool spapr_ovec_diff(sPAPROptionVector *ov, + sPAPROptionVector *ov_old, + sPAPROptionVector *ov_new) +{ + unsigned long *change_mask = bitmap_new(OV_MAXBITS); + unsigned long *removed_bits = bitmap_new(OV_MAXBITS); + bool bits_were_removed = false; + + g_assert(ov); + g_assert(ov_old); + g_assert(ov_new); + + bitmap_xor(change_mask, ov_old->bitmap, ov_new->bitmap, OV_MAXBITS); + bitmap_and(ov->bitmap, ov_new->bitmap, change_mask, OV_MAXBITS); + bitmap_and(removed_bits, ov_old->bitmap, change_mask, OV_MAXBITS); + + if (!bitmap_empty(removed_bits, OV_MAXBITS)) { + bits_were_removed = true; + } + + g_free(change_mask); + g_free(removed_bits); + + return bits_were_removed; +} + +void spapr_ovec_cleanup(sPAPROptionVector *ov) +{ + if (ov) { + g_free(ov->bitmap); + g_free(ov); + } +} + +void spapr_ovec_set(sPAPROptionVector *ov, long bitnr) +{ + g_assert(ov); + g_assert_cmpint(bitnr, <, OV_MAXBITS); + + set_bit(bitnr, ov->bitmap); +} + +void spapr_ovec_clear(sPAPROptionVector *ov, long bitnr) +{ + g_assert(ov); + g_assert_cmpint(bitnr, <, OV_MAXBITS); + + clear_bit(bitnr, ov->bitmap); +} + +bool spapr_ovec_test(sPAPROptionVector *ov, long bitnr) +{ + g_assert(ov); + g_assert_cmpint(bitnr, <, OV_MAXBITS); + + return test_bit(bitnr, ov->bitmap) ? true : false; +} + +static void guest_byte_to_bitmap(uint8_t entry, unsigned long *bitmap, + long bitmap_offset) +{ + int i; + + for (i = 0; i < BITS_PER_BYTE; i++) { + if (entry & (1 << (BITS_PER_BYTE - 1 - i))) { + bitmap_set(bitmap, bitmap_offset + i, 1); + } + } +} + +static uint8_t guest_byte_from_bitmap(unsigned long *bitmap, long bitmap_offset) +{ + uint8_t entry = 0; + int i; + + for (i = 0; i < BITS_PER_BYTE; i++) { + if (test_bit(bitmap_offset + i, bitmap)) { + entry |= (1 << (BITS_PER_BYTE - 1 - i)); + } + } + + return entry; +} + +static target_ulong vector_addr(target_ulong table_addr, int vector) +{ + uint16_t vector_count, vector_len; + int i; + + vector_count = ldub_phys(&address_space_memory, table_addr) + 1; + if (vector > vector_count) { + return 0; + } + table_addr++; /* skip nr option vectors */ + + for (i = 0; i < vector - 1; i++) { + vector_len = ldub_phys(&address_space_memory, table_addr) + 1; + table_addr += vector_len + 1; /* bit-vector + length byte */ + } + return table_addr; +} + +sPAPROptionVector *spapr_ovec_parse_vector(target_ulong table_addr, int vector) +{ + sPAPROptionVector *ov; + target_ulong addr; + uint16_t vector_len; + int i; + + g_assert(table_addr); + g_assert_cmpint(vector, >=, 1); /* vector numbering starts at 1 */ + + addr = vector_addr(table_addr, vector); + if (!addr) { + /* specified vector isn't present */ + return NULL; + } + + vector_len = ldub_phys(&address_space_memory, addr++) + 1; + g_assert_cmpint(vector_len, <=, OV_MAXBYTES); + ov = spapr_ovec_new(); + + for (i = 0; i < vector_len; i++) { + uint8_t entry = ldub_phys(&address_space_memory, addr + i); + if (entry) { + DPRINTFN("read guest vector %2d, byte %3d / %3d: 0x%.2x", + vector, i + 1, vector_len, entry); + guest_byte_to_bitmap(entry, ov->bitmap, i * BITS_PER_BYTE); + } + } + + return ov; +} + +int spapr_ovec_populate_dt(void *fdt, int fdt_offset, + sPAPROptionVector *ov, const char *name) +{ + uint8_t vec[OV_MAXBYTES + 1]; + uint16_t vec_len; + unsigned long lastbit; + int i; + + g_assert(ov); + + lastbit = find_last_bit(ov->bitmap, OV_MAXBITS); + /* if no bits are set, include at least 1 byte of the vector so we can + * still encoded this in the device tree while abiding by the same + * encoding/sizing expected in ibm,client-architecture-support + */ + vec_len = (lastbit == OV_MAXBITS) ? 1 : lastbit / BITS_PER_BYTE + 1; + g_assert_cmpint(vec_len, <=, OV_MAXBYTES); + /* guest expects vector len encoded as vec_len - 1, since the length byte + * is assumed and not included, and the first byte of the vector + * is assumed as well + */ + vec[0] = vec_len - 1; + + for (i = 1; i < vec_len + 1; i++) { + vec[i] = guest_byte_from_bitmap(ov->bitmap, (i - 1) * BITS_PER_BYTE); + if (vec[i]) { + DPRINTFN("encoding guest vector byte %3d / %3d: 0x%.2x", + i, vec_len, vec[i]); + } + } + + return fdt_setprop(fdt, fdt_offset, name, vec, vec_len); +} diff --git a/include/hw/ppc/spapr_ovec.h b/include/hw/ppc/spapr_ovec.h new file mode 100644 index 0000000000..7ee07770c4 --- /dev/null +++ b/include/hw/ppc/spapr_ovec.h @@ -0,0 +1,62 @@ +/* + * QEMU SPAPR Option/Architecture Vector Definitions + * + * Each architecture option is organized/documented by the following + * in LoPAPR 1.1, Table 244: + * + * : the bit-vector in which the option is located + * : the byte offset of the vector entry + * : the bit offset within the vector entry + * + * where each vector entry can be one or more bytes. + * + * Firmware expects a somewhat literal encoding of this bit-vector + * structure, where each entry is stored in little-endian so that the + * byte ordering reflects that of the documentation, but where each bit + * offset is from "left-to-right" in the traditional representation of + * a byte value where the MSB is the left-most bit. Thus, each + * individual byte encodes the option bits in reverse order of the + * documented bit. + * + * These definitions/helpers attempt to abstract away this internal + * representation so that we can define/set/test for individual option + * bits using only the documented values. This is done mainly by relying + * on a bitmap to approximate the documented "bit-vector" structure and + * handling conversations to-from the internal representation under the + * covers. + * + * Copyright IBM Corp. 2016 + * + * Authors: + * Michael Roth + * + * This work is licensed under the terms of the GNU GPL, version 2 or later. + * See the COPYING file in the top-level directory. + */ +#ifndef _SPAPR_OVEC_H +#define _SPAPR_OVEC_H + +#include "cpu.h" + +typedef struct sPAPROptionVector sPAPROptionVector; + +#define OV_BIT(byte, bit) ((byte - 1) * BITS_PER_BYTE + bit) + +/* interfaces */ +sPAPROptionVector *spapr_ovec_new(void); +sPAPROptionVector *spapr_ovec_clone(sPAPROptionVector *ov_orig); +void spapr_ovec_intersect(sPAPROptionVector *ov, + sPAPROptionVector *ov1, + sPAPROptionVector *ov2); +bool spapr_ovec_diff(sPAPROptionVector *ov, + sPAPROptionVector *ov_old, + sPAPROptionVector *ov_new); +void spapr_ovec_cleanup(sPAPROptionVector *ov); +void spapr_ovec_set(sPAPROptionVector *ov, long bitnr); +void spapr_ovec_clear(sPAPROptionVector *ov, long bitnr); +bool spapr_ovec_test(sPAPROptionVector *ov, long bitnr); +sPAPROptionVector *spapr_ovec_parse_vector(target_ulong table_addr, int vector); +int spapr_ovec_populate_dt(void *fdt, int fdt_offset, + sPAPROptionVector *ov, const char *name); + +#endif /* !defined (_SPAPR_OVEC_H) */ From facdb8b63baf56bc7c0ce2f16a32900866889f03 Mon Sep 17 00:00:00 2001 From: Michael Roth Date: Mon, 24 Oct 2016 23:47:28 -0500 Subject: [PATCH 47/73] spapr_hcall: use spapr_ovec_* interfaces for CAS options Currently we access individual bytes of an option vector via ldub_phys() to test for the presence of a particular capability within that byte. Currently this is only done for the "dynamic reconfiguration memory" capability bit. If that bit is present, we pass a boolean value to spapr_h_cas_compose_response() to generate a modified device tree segment with the additional properties required to enable this functionality. As more capability bits are added, will would need to modify the code to add additional option vector accesses and extend the param list for spapr_h_cas_compose_response() to include similar boolean values for these parameters. Avoid this by switching to spapr_ovec_* helpers so we can do all the parsing in one shot and then test for these additional bits within spapr_h_cas_compose_response() directly. Cc: Bharata B Rao Signed-off-by: Michael Roth Reviewed-by: David Gibson Reviewed-by: Bharata B Rao Signed-off-by: David Gibson --- hw/ppc/spapr.c | 10 +++++-- hw/ppc/spapr_hcall.c | 56 ++++++++++--------------------------- include/hw/ppc/spapr.h | 5 +++- include/hw/ppc/spapr_ovec.h | 3 ++ 4 files changed, 30 insertions(+), 44 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 209bc8404b..9300824c2a 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -657,7 +657,7 @@ out: int spapr_h_cas_compose_response(sPAPRMachineState *spapr, target_ulong addr, target_ulong size, - bool cpu_update, bool memory_update) + bool cpu_update) { void *fdt, *fdt_skel; sPAPRDeviceTreeUpdateHeader hdr = { .version_id = 1 }; @@ -681,7 +681,8 @@ int spapr_h_cas_compose_response(sPAPRMachineState *spapr, } /* Generate ibm,dynamic-reconfiguration-memory node if required */ - if (memory_update && smc->dr_lmb_enabled) { + if (spapr_ovec_test(spapr->ov5_cas, OV5_DRCONF_MEMORY)) { + g_assert(smc->dr_lmb_enabled); _FDT((spapr_populate_drconf_memory(spapr, fdt))); } @@ -1740,7 +1741,12 @@ static void ppc_spapr_init(MachineState *machine) DIV_ROUND_UP(max_cpus * smt, smp_threads), XICS_IRQS_SPAPR, &error_fatal); + /* Set up containers for ibm,client-set-architecture negotiated options */ + spapr->ov5 = spapr_ovec_new(); + spapr->ov5_cas = spapr_ovec_new(); + if (smc->dr_lmb_enabled) { + spapr_ovec_set(spapr->ov5, OV5_DRCONF_MEMORY); spapr_validate_node_memory(machine, &error_fatal); } diff --git a/hw/ppc/spapr_hcall.c b/hw/ppc/spapr_hcall.c index c5e7e8c995..f1d081b095 100644 --- a/hw/ppc/spapr_hcall.c +++ b/hw/ppc/spapr_hcall.c @@ -11,6 +11,7 @@ #include "trace.h" #include "sysemu/kvm.h" #include "kvm_ppc.h" +#include "hw/ppc/spapr_ovec.h" struct SPRSyncState { int spr; @@ -880,32 +881,6 @@ static target_ulong h_set_mode(PowerPCCPU *cpu, sPAPRMachineState *spapr, return ret; } -/* - * Return the offset to the requested option vector @vector in the - * option vector table @table. - */ -static target_ulong cas_get_option_vector(int vector, target_ulong table) -{ - int i; - char nr_vectors, nr_entries; - - if (!table) { - return 0; - } - - nr_vectors = (ldl_phys(&address_space_memory, table) >> 24) + 1; - if (!vector || vector > nr_vectors) { - return 0; - } - table++; /* skip nr option vectors */ - - for (i = 0; i < vector - 1; i++) { - nr_entries = ldl_phys(&address_space_memory, table) >> 24; - table += nr_entries + 2; - } - return table; -} - typedef struct { uint32_t cpu_version; Error *err; @@ -961,23 +936,21 @@ static void cas_handle_compat_cpu(PowerPCCPUClass *pcc, uint32_t pvr, } } -#define OV5_DRCONF_MEMORY 0x20 - static target_ulong h_client_architecture_support(PowerPCCPU *cpu_, sPAPRMachineState *spapr, target_ulong opcode, target_ulong *args) { target_ulong list = ppc64_phys_to_real(args[0]); - target_ulong ov_table, ov5; + target_ulong ov_table; PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu_); CPUState *cs; - bool cpu_match = false, cpu_update = true, memory_update = false; + bool cpu_match = false, cpu_update = true; unsigned old_cpu_version = cpu_->cpu_version; unsigned compat_lvl = 0, cpu_version = 0; unsigned max_lvl = get_compat_level(cpu_->max_compat); int counter; - char ov5_byte2; + sPAPROptionVector *ov5_guest; /* Parse PVR list */ for (counter = 0; counter < 512; ++counter) { @@ -1033,19 +1006,20 @@ static target_ulong h_client_architecture_support(PowerPCCPU *cpu_, /* For the future use: here @ov_table points to the first option vector */ ov_table = list; - ov5 = cas_get_option_vector(5, ov_table); - if (!ov5) { - return H_SUCCESS; - } + ov5_guest = spapr_ovec_parse_vector(ov_table, 5); - /* @list now points to OV 5 */ - ov5_byte2 = ldub_phys(&address_space_memory, ov5 + 2); - if (ov5_byte2 & OV5_DRCONF_MEMORY) { - memory_update = true; - } + /* NOTE: there are actually a number of ov5 bits where input from the + * guest is always zero, and the platform/QEMU enables them independently + * of guest input. To model these properly we'd want some sort of mask, + * but since they only currently apply to memory migration as defined + * by LoPAPR 1.1, 14.5.4.8, which QEMU doesn't implement, we don't need + * to worry about this. + */ + spapr_ovec_intersect(spapr->ov5_cas, spapr->ov5, ov5_guest); + spapr_ovec_cleanup(ov5_guest); if (spapr_h_cas_compose_response(spapr, args[1], args[2], - cpu_update, memory_update)) { + cpu_update)) { qemu_system_reset_request(); } diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index d5d6e57c41..a37eee870f 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -6,6 +6,7 @@ #include "hw/ppc/xics.h" #include "hw/ppc/spapr_drc.h" #include "hw/mem/pc-dimm.h" +#include "hw/ppc/spapr_ovec.h" struct VIOsPAPRBus; struct sPAPRPHBState; @@ -72,6 +73,8 @@ struct sPAPRMachineState { uint64_t rtc_offset; /* Now used only during incoming migration */ struct PPCTimebase tb; bool has_graphics; + sPAPROptionVector *ov5; /* QEMU-supported option vectors */ + sPAPROptionVector *ov5_cas; /* negotiated (via CAS) option vectors */ uint32_t check_exception_irq; Notifier epow_notifier; @@ -583,7 +586,7 @@ void spapr_events_init(sPAPRMachineState *sm); void spapr_dt_events(void *fdt, uint32_t check_exception_irq); int spapr_h_cas_compose_response(sPAPRMachineState *sm, target_ulong addr, target_ulong size, - bool cpu_update, bool memory_update); + bool cpu_update); sPAPRTCETable *spapr_tce_new_table(DeviceState *owner, uint32_t liobn); void spapr_tce_table_enable(sPAPRTCETable *tcet, uint32_t page_shift, uint64_t bus_offset, diff --git a/include/hw/ppc/spapr_ovec.h b/include/hw/ppc/spapr_ovec.h index 7ee07770c4..a9a3f3a5bb 100644 --- a/include/hw/ppc/spapr_ovec.h +++ b/include/hw/ppc/spapr_ovec.h @@ -42,6 +42,9 @@ typedef struct sPAPROptionVector sPAPROptionVector; #define OV_BIT(byte, bit) ((byte - 1) * BITS_PER_BYTE + bit) +/* option vector 5 */ +#define OV5_DRCONF_MEMORY OV_BIT(2, 2) + /* interfaces */ sPAPROptionVector *spapr_ovec_new(void); sPAPROptionVector *spapr_ovec_clone(sPAPROptionVector *ov_orig); From 6787d27b04a79524c547c60701400eb0418e3533 Mon Sep 17 00:00:00 2001 From: Michael Roth Date: Mon, 24 Oct 2016 23:47:29 -0500 Subject: [PATCH 48/73] spapr: add option vector handling in CAS-generated resets In some cases, ibm,client-architecture-support calls can fail. This could happen in the current code for situations where the modified device tree segment exceeds the buffer size provided by the guest via the call parameters. In these cases, QEMU will reset, allowing an opportunity to regenerate the device tree from scratch via boot-time handling. There are potentially other scenarios as well, not currently reachable in the current code, but possible in theory, such as cases where device-tree properties or nodes need to be removed. We currently don't handle either of these properly for option vector capabilities however. Instead of carrying the negotiated capability beyond the reset and creating the boot-time device tree accordingly, we start from scratch, generating the same boot-time device tree as we did prior to the CAS-generated and the same device tree updates as we did before. This could (in theory) cause us to get stuck in a reset loop. This hasn't been observed, but depending on the extensiveness of CAS-induced device tree updates in the future, could eventually become an issue. Address this by pulling capability-related device tree updates resulting from CAS calls into a common routine, spapr_dt_cas_updates(), and adding an sPAPROptionVector* parameter that allows us to test for newly-negotiated capabilities. We invoke it as follows: 1) When ibm,client-architecture-support gets called, we call spapr_dt_cas_updates() with the set of capabilities added since the previous call to ibm,client-architecture-support. For the initial boot, or a system reset generated by something other than the CAS call itself, this set will consist of *all* options supported both the platform and the guest. For calls to ibm,client-architecture-support immediately after a CAS-induced reset, we call spapr_dt_cas_updates() with only the set of capabilities added since the previous call, since the other capabilities will have already been addressed by the boot-time device-tree this time around. In the unlikely event that capabilities are *removed* since the previous CAS, we will generate a CAS-induced reset. In the unlikely event that we cannot fit the device-tree updates into the buffer provided by the guest, well generate a CAS-induced reset. 2) When a CAS update results in the need to reset the machine and include the updates in the boot-time device tree, we call the spapr_dt_cas_updates() using the full set of negotiated capabilities as part of the reset path. At initial boot, or after a reset generated by something other than the CAS call itself, this set will be empty, resulting in what should be the same boot-time device-tree as we generated prior to this patch. For CAS-induced reset, this routine will be called with the full set of capabilities negotiated by the platform/guest in the previous CAS call, which should result in CAS updates from previous call being accounted for in the initial boot-time device tree. Signed-off-by: Michael Roth Reviewed-by: David Gibson [dwg: Changed an int -> bool conversion to be more explicit] Signed-off-by: David Gibson --- hw/ppc/spapr.c | 40 ++++++++++++++++++++++++++++++++++------ hw/ppc/spapr_hcall.c | 22 ++++++++++++++++++---- include/hw/ppc/spapr.h | 4 +++- 3 files changed, 55 insertions(+), 11 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 9300824c2a..aa6a07073d 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -655,13 +655,28 @@ out: return ret; } +static int spapr_dt_cas_updates(sPAPRMachineState *spapr, void *fdt, + sPAPROptionVector *ov5_updates) +{ + sPAPRMachineClass *smc = SPAPR_MACHINE_GET_CLASS(spapr); + int ret = 0; + + /* Generate ibm,dynamic-reconfiguration-memory node if required */ + if (spapr_ovec_test(ov5_updates, OV5_DRCONF_MEMORY)) { + g_assert(smc->dr_lmb_enabled); + ret = spapr_populate_drconf_memory(spapr, fdt); + } + + return ret; +} + int spapr_h_cas_compose_response(sPAPRMachineState *spapr, target_ulong addr, target_ulong size, - bool cpu_update) + bool cpu_update, + sPAPROptionVector *ov5_updates) { void *fdt, *fdt_skel; sPAPRDeviceTreeUpdateHeader hdr = { .version_id = 1 }; - sPAPRMachineClass *smc = SPAPR_MACHINE_GET_CLASS(qdev_get_machine()); size -= sizeof(hdr); @@ -680,10 +695,8 @@ int spapr_h_cas_compose_response(sPAPRMachineState *spapr, _FDT((spapr_fixup_cpu_dt(fdt, spapr))); } - /* Generate ibm,dynamic-reconfiguration-memory node if required */ - if (spapr_ovec_test(spapr->ov5_cas, OV5_DRCONF_MEMORY)) { - g_assert(smc->dr_lmb_enabled); - _FDT((spapr_populate_drconf_memory(spapr, fdt))); + if (spapr_dt_cas_updates(spapr, fdt, ov5_updates)) { + return -1; } /* Pack resulting tree */ @@ -972,6 +985,13 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, _FDT((fdt_add_mem_rsv(fdt, spapr->initrd_base, spapr->initrd_size))); } + /* ibm,client-architecture-support updates */ + ret = spapr_dt_cas_updates(spapr, fdt, spapr->ov5_cas); + if (ret < 0) { + error_report("couldn't setup CAS properties fdt"); + exit(1); + } + return fdt; } @@ -1137,6 +1157,13 @@ static void ppc_spapr_reset(void) rtas_addr = rtas_limit - RTAS_MAX_SIZE; fdt_addr = rtas_addr - FDT_MAX_SIZE; + /* if this reset wasn't generated by CAS, we should reset our + * negotiated options and start from scratch */ + if (!spapr->cas_reboot) { + spapr_ovec_cleanup(spapr->ov5_cas); + spapr->ov5_cas = spapr_ovec_new(); + } + fdt = spapr_build_fdt(spapr, rtas_addr, spapr->rtas_size); spapr_load_rtas(spapr, fdt, rtas_addr); @@ -1164,6 +1191,7 @@ static void ppc_spapr_reset(void) first_cpu->halted = 0; first_ppc_cpu->env.nip = SPAPR_ENTRY_POINT; + spapr->cas_reboot = false; } static void spapr_create_nvram(sPAPRMachineState *spapr) diff --git a/hw/ppc/spapr_hcall.c b/hw/ppc/spapr_hcall.c index f1d081b095..7c46d4625b 100644 --- a/hw/ppc/spapr_hcall.c +++ b/hw/ppc/spapr_hcall.c @@ -950,7 +950,7 @@ static target_ulong h_client_architecture_support(PowerPCCPU *cpu_, unsigned compat_lvl = 0, cpu_version = 0; unsigned max_lvl = get_compat_level(cpu_->max_compat); int counter; - sPAPROptionVector *ov5_guest; + sPAPROptionVector *ov5_guest, *ov5_cas_old, *ov5_updates; /* Parse PVR list */ for (counter = 0; counter < 512; ++counter) { @@ -1013,13 +1013,27 @@ static target_ulong h_client_architecture_support(PowerPCCPU *cpu_, * of guest input. To model these properly we'd want some sort of mask, * but since they only currently apply to memory migration as defined * by LoPAPR 1.1, 14.5.4.8, which QEMU doesn't implement, we don't need - * to worry about this. + * to worry about this for now. */ + ov5_cas_old = spapr_ovec_clone(spapr->ov5_cas); + /* full range of negotiated ov5 capabilities */ spapr_ovec_intersect(spapr->ov5_cas, spapr->ov5, ov5_guest); spapr_ovec_cleanup(ov5_guest); + /* capabilities that have been added since CAS-generated guest reset. + * if capabilities have since been removed, generate another reset + */ + ov5_updates = spapr_ovec_new(); + spapr->cas_reboot = spapr_ovec_diff(ov5_updates, + ov5_cas_old, spapr->ov5_cas); - if (spapr_h_cas_compose_response(spapr, args[1], args[2], - cpu_update)) { + if (!spapr->cas_reboot) { + spapr->cas_reboot = + (spapr_h_cas_compose_response(spapr, args[1], args[2], cpu_update, + ov5_updates) != 0); + } + spapr_ovec_cleanup(ov5_updates); + + if (spapr->cas_reboot) { qemu_system_reset_request(); } diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index a37eee870f..b6f9f1b632 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -75,6 +75,7 @@ struct sPAPRMachineState { bool has_graphics; sPAPROptionVector *ov5; /* QEMU-supported option vectors */ sPAPROptionVector *ov5_cas; /* negotiated (via CAS) option vectors */ + bool cas_reboot; uint32_t check_exception_irq; Notifier epow_notifier; @@ -586,7 +587,8 @@ void spapr_events_init(sPAPRMachineState *sm); void spapr_dt_events(void *fdt, uint32_t check_exception_irq); int spapr_h_cas_compose_response(sPAPRMachineState *sm, target_ulong addr, target_ulong size, - bool cpu_update); + bool cpu_update, + sPAPROptionVector *ov5_updates); sPAPRTCETable *spapr_tce_new_table(DeviceState *owner, uint32_t liobn); void spapr_tce_table_enable(sPAPRTCETable *tcet, uint32_t page_shift, uint64_t bus_offset, From 417ece33fc1095f8acfa31208a5502bb8957f000 Mon Sep 17 00:00:00 2001 From: Michael Roth Date: Mon, 24 Oct 2016 23:47:30 -0500 Subject: [PATCH 49/73] spapr: improve ibm,architecture-vec-5 property handling ibm,architecture-vec-5 is supposed to encode all option vector 5 bits negotiated between platform/guest. Currently we hardcode this property in the boot-time device tree to advertise a single negotiated capability, "Form 1" NUMA Affinity, regardless of whether or not CAS has been invoked or that capability has actually been negotiated. Improve this by generating ibm,architecture-vec-5 based on the full set of option vector 5 capabilities negotiated via CAS. Signed-off-by: Michael Roth Signed-off-by: David Gibson --- hw/ppc/spapr.c | 23 +++++++++++++++++------ include/hw/ppc/spapr_ovec.h | 1 + 2 files changed, 18 insertions(+), 6 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index aa6a07073d..0b3820bbcf 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -659,14 +659,28 @@ static int spapr_dt_cas_updates(sPAPRMachineState *spapr, void *fdt, sPAPROptionVector *ov5_updates) { sPAPRMachineClass *smc = SPAPR_MACHINE_GET_CLASS(spapr); - int ret = 0; + int ret = 0, offset; /* Generate ibm,dynamic-reconfiguration-memory node if required */ if (spapr_ovec_test(ov5_updates, OV5_DRCONF_MEMORY)) { g_assert(smc->dr_lmb_enabled); ret = spapr_populate_drconf_memory(spapr, fdt); + if (ret) { + goto out; + } } + offset = fdt_path_offset(fdt, "/chosen"); + if (offset < 0) { + offset = fdt_add_subnode(fdt, 0, "chosen"); + if (offset < 0) { + return offset; + } + } + ret = spapr_ovec_populate_dt(fdt, offset, spapr->ov5_cas, + "ibm,architecture-vec-5"); + +out: return ret; } @@ -792,14 +806,9 @@ static void spapr_dt_chosen(sPAPRMachineState *spapr, void *fdt) char *stdout_path = spapr_vio_stdout_path(spapr->vio_bus); size_t cb = 0; char *bootlist = get_boot_devices_list(&cb, true); - unsigned char vec5[] = {0x0, 0x0, 0x0, 0x0, 0x0, 0x80}; _FDT(chosen = fdt_add_subnode(fdt, 0, "chosen")); - /* Set Form1_affinity */ - _FDT(fdt_setprop(fdt, chosen, "ibm,architecture-vec-5", - vec5, sizeof(vec5))); - _FDT(fdt_setprop_string(fdt, chosen, "bootargs", machine->kernel_cmdline)); _FDT(fdt_setprop_cell(fdt, chosen, "linux,initrd-start", spapr->initrd_base)); @@ -1778,6 +1787,8 @@ static void ppc_spapr_init(MachineState *machine) spapr_validate_node_memory(machine, &error_fatal); } + spapr_ovec_set(spapr->ov5, OV5_FORM1_AFFINITY); + /* init CPUs */ if (machine->cpu_model == NULL) { machine->cpu_model = kvm_enabled() ? "host" : smc->tcg_default_cpu; diff --git a/include/hw/ppc/spapr_ovec.h b/include/hw/ppc/spapr_ovec.h index a9a3f3a5bb..81cdd14f64 100644 --- a/include/hw/ppc/spapr_ovec.h +++ b/include/hw/ppc/spapr_ovec.h @@ -44,6 +44,7 @@ typedef struct sPAPROptionVector sPAPROptionVector; /* option vector 5 */ #define OV5_DRCONF_MEMORY OV_BIT(2, 2) +#define OV5_FORM1_AFFINITY OV_BIT(5, 0) /* interfaces */ sPAPROptionVector *spapr_ovec_new(void); From a37eb9fccdd423e4f430b0261ee78c1692b7c252 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Herv=C3=A9=20Poussineau?= Date: Tue, 25 Oct 2016 09:01:01 +0200 Subject: [PATCH 50/73] adb: change handler only when recognized MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ADB devices must take new handler into account only when they recognize it. This lets operating systems probe for valid/invalid handles, to know device capabilities. Add a FIXME in keyboard handler, which should use a different translation table depending of the selected handler. Signed-off-by: Hervé Poussineau Signed-off-by: David Gibson --- hw/input/adb.c | 26 +++++++++++++++++++++++--- 1 file changed, 23 insertions(+), 3 deletions(-) diff --git a/hw/input/adb.c b/hw/input/adb.c index 3d39368909..43d3205472 100644 --- a/hw/input/adb.c +++ b/hw/input/adb.c @@ -396,9 +396,15 @@ static int adb_kbd_request(ADBDevice *d, uint8_t *obuf, d->devaddr = buf[1] & 0xf; break; default: - /* XXX: check this */ d->devaddr = buf[1] & 0xf; - d->handler = buf[2]; + /* we support handlers: + * 1: Apple Standard Keyboard + * 2: Apple Extended Keyboard (LShift = RShift) + * 3: Apple Extended Keyboard (LShift != RShift) + */ + if (buf[2] == 1 || buf[2] == 2 || buf[2] == 3) { + d->handler = buf[2]; + } break; } } @@ -437,6 +443,7 @@ static void adb_keyboard_event(DeviceState *dev, QemuConsole *src, if (qcode >= ARRAY_SIZE(qcode_to_adb_keycode)) { return; } + /* FIXME: take handler into account when translating qcode */ keycode = qcode_to_adb_keycode[qcode]; if (keycode == NO_KEY) { /* We don't want to send this to the guest */ ADB_DPRINTF("Ignoring NO_KEY\n"); @@ -631,8 +638,21 @@ static int adb_mouse_request(ADBDevice *d, uint8_t *obuf, d->devaddr = buf[1] & 0xf; break; default: - /* XXX: check this */ d->devaddr = buf[1] & 0xf; + /* we support handlers: + * 0x01: Classic Apple Mouse Protocol / 100 cpi operations + * 0x02: Classic Apple Mouse Protocol / 200 cpi operations + * we don't support handlers (at least): + * 0x03: Mouse systems A3 trackball + * 0x04: Extended Apple Mouse Protocol + * 0x2f: Microspeed mouse + * 0x42: Macally + * 0x5f: Microspeed mouse + * 0x66: Microspeed mouse + */ + if (buf[2] == 1 || buf[2] == 2) { + d->handler = buf[2]; + } break; } } From 246fc0fb66cbf861b0e76320626b059e2d49ea12 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Thu, 20 Oct 2016 14:08:07 +1100 Subject: [PATCH 51/73] libqos: Give qvirtio_config_read*() consistent semantics The 'addr' parameter to qvirtio_config_read*() doesn't have a consistent meaning: when using the virtio-pci versions, it's a full PCI space address, but for virtio-mmio, it's an offset from the device's base mmio address. This means that the callers need to do different things to calculate the addresses in the two cases, which rather defeats the purpose of function pointer backends. All the current users of these functions are using them to retrieve variables from the device specific portion of the virtio config space. So, this patch alters the semantics to always be an offset into that device specific config area. Signed-off-by: David Gibson Reviewed-by: Laurent Vivier Reviewed-by: Greg Kurz --- tests/libqos/virtio-mmio.c | 16 +++++++-------- tests/libqos/virtio-pci.c | 25 +++++++++++++---------- tests/virtio-9p-test.c | 8 ++------ tests/virtio-blk-test.c | 42 ++++++++++---------------------------- tests/virtio-scsi-test.c | 4 +--- 5 files changed, 36 insertions(+), 59 deletions(-) diff --git a/tests/libqos/virtio-mmio.c b/tests/libqos/virtio-mmio.c index bced6803e6..7aa8383338 100644 --- a/tests/libqos/virtio-mmio.c +++ b/tests/libqos/virtio-mmio.c @@ -15,28 +15,28 @@ #include "libqos/malloc-generic.h" #include "standard-headers/linux/virtio_ring.h" -static uint8_t qvirtio_mmio_config_readb(QVirtioDevice *d, uint64_t addr) +static uint8_t qvirtio_mmio_config_readb(QVirtioDevice *d, uint64_t off) { QVirtioMMIODevice *dev = (QVirtioMMIODevice *)d; - return readb(dev->addr + addr); + return readb(dev->addr + QVIRTIO_MMIO_DEVICE_SPECIFIC + off); } -static uint16_t qvirtio_mmio_config_readw(QVirtioDevice *d, uint64_t addr) +static uint16_t qvirtio_mmio_config_readw(QVirtioDevice *d, uint64_t off) { QVirtioMMIODevice *dev = (QVirtioMMIODevice *)d; - return readw(dev->addr + addr); + return readw(dev->addr + QVIRTIO_MMIO_DEVICE_SPECIFIC + off); } -static uint32_t qvirtio_mmio_config_readl(QVirtioDevice *d, uint64_t addr) +static uint32_t qvirtio_mmio_config_readl(QVirtioDevice *d, uint64_t off) { QVirtioMMIODevice *dev = (QVirtioMMIODevice *)d; - return readl(dev->addr + addr); + return readl(dev->addr + QVIRTIO_MMIO_DEVICE_SPECIFIC + off); } -static uint64_t qvirtio_mmio_config_readq(QVirtioDevice *d, uint64_t addr) +static uint64_t qvirtio_mmio_config_readq(QVirtioDevice *d, uint64_t off) { QVirtioMMIODevice *dev = (QVirtioMMIODevice *)d; - return readq(dev->addr + addr); + return readq(dev->addr + QVIRTIO_MMIO_DEVICE_SPECIFIC + off); } static uint32_t qvirtio_mmio_get_features(QVirtioDevice *d) diff --git a/tests/libqos/virtio-pci.c b/tests/libqos/virtio-pci.c index 7e60b3a427..fa82132ab7 100644 --- a/tests/libqos/virtio-pci.c +++ b/tests/libqos/virtio-pci.c @@ -62,10 +62,13 @@ static void qvirtio_pci_assign_device(QVirtioDevice *d, void *data) *vpcidev = (QVirtioPCIDevice *)d; } -static uint8_t qvirtio_pci_config_readb(QVirtioDevice *d, uint64_t addr) +#define CONFIG_BASE(dev) \ + ((dev)->addr + VIRTIO_PCI_CONFIG_OFF((dev)->pdev->msix_enabled)) + +static uint8_t qvirtio_pci_config_readb(QVirtioDevice *d, uint64_t off) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - return qpci_io_readb(dev->pdev, (void *)(uintptr_t)addr); + return qpci_io_readb(dev->pdev, CONFIG_BASE(dev) + off); } /* PCI is always read in little-endian order @@ -76,31 +79,31 @@ static uint8_t qvirtio_pci_config_readb(QVirtioDevice *d, uint64_t addr) * case will be managed inside qvirtio_is_big_endian() */ -static uint16_t qvirtio_pci_config_readw(QVirtioDevice *d, uint64_t addr) +static uint16_t qvirtio_pci_config_readw(QVirtioDevice *d, uint64_t off) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; uint16_t value; - value = qpci_io_readw(dev->pdev, (void *)(uintptr_t)addr); + value = qpci_io_readw(dev->pdev, CONFIG_BASE(dev) + off); if (qvirtio_is_big_endian(d)) { value = bswap16(value); } return value; } -static uint32_t qvirtio_pci_config_readl(QVirtioDevice *d, uint64_t addr) +static uint32_t qvirtio_pci_config_readl(QVirtioDevice *d, uint64_t off) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; uint32_t value; - value = qpci_io_readl(dev->pdev, (void *)(uintptr_t)addr); + value = qpci_io_readl(dev->pdev, CONFIG_BASE(dev) + off); if (qvirtio_is_big_endian(d)) { value = bswap32(value); } return value; } -static uint64_t qvirtio_pci_config_readq(QVirtioDevice *d, uint64_t addr) +static uint64_t qvirtio_pci_config_readq(QVirtioDevice *d, uint64_t off) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; int i; @@ -108,13 +111,13 @@ static uint64_t qvirtio_pci_config_readq(QVirtioDevice *d, uint64_t addr) if (qvirtio_is_big_endian(d)) { for (i = 0; i < 8; ++i) { - u64 |= (uint64_t)qpci_io_readb(dev->pdev, - (void *)(uintptr_t)addr + i) << (7 - i) * 8; + u64 |= (uint64_t)qpci_io_readb(dev->pdev, CONFIG_BASE(dev) + + off + i) << (7 - i) * 8; } } else { for (i = 0; i < 8; ++i) { - u64 |= (uint64_t)qpci_io_readb(dev->pdev, - (void *)(uintptr_t)addr + i) << i * 8; + u64 |= (uint64_t)qpci_io_readb(dev->pdev, CONFIG_BASE(dev) + + off + i) << i * 8; } } diff --git a/tests/virtio-9p-test.c b/tests/virtio-9p-test.c index 693920af5f..9c4f6cb406 100644 --- a/tests/virtio-9p-test.c +++ b/tests/virtio-9p-test.c @@ -95,7 +95,6 @@ static void qvirtio_9p_pci_free(QVirtIO9P *v9p) static void pci_basic_config(void) { QVirtIO9P *v9p; - void *addr; size_t tag_len; char *tag; int i; @@ -104,15 +103,12 @@ static void pci_basic_config(void) qs = qvirtio_9p_start(); v9p = qvirtio_9p_pci_init(qs); - addr = ((QVirtioPCIDevice *) v9p->dev)->addr + VIRTIO_PCI_CONFIG_OFF(false); - tag_len = qvirtio_config_readw(v9p->dev, - (uint64_t)(uintptr_t)addr); + tag_len = qvirtio_config_readw(v9p->dev, 0); g_assert_cmpint(tag_len, ==, strlen(mount_tag)); - addr += sizeof(uint16_t); tag = g_malloc(tag_len); for (i = 0; i < tag_len; i++) { - tag[i] = qvirtio_config_readb(v9p->dev, (uint64_t)(uintptr_t)addr + i); + tag[i] = qvirtio_config_readb(v9p->dev, i + 2); } g_assert_cmpmem(tag, tag_len, mount_tag, tag_len); g_free(tag); diff --git a/tests/virtio-blk-test.c b/tests/virtio-blk-test.c index f737c406e3..0e32e416dd 100644 --- a/tests/virtio-blk-test.c +++ b/tests/virtio-blk-test.c @@ -155,7 +155,7 @@ static uint64_t virtio_blk_request(QGuestAllocator *alloc, QVirtioDevice *d, } static void test_basic(QVirtioDevice *dev, QGuestAllocator *alloc, - QVirtQueue *vq, uint64_t device_specific) + QVirtQueue *vq) { QVirtioBlkReq req; uint64_t req_addr; @@ -165,7 +165,7 @@ static void test_basic(QVirtioDevice *dev, QGuestAllocator *alloc, uint8_t status; char *data; - capacity = qvirtio_config_readq(dev, device_specific); + capacity = qvirtio_config_readq(dev, 0); g_assert_cmpint(capacity, ==, TEST_IMAGE_SIZE / 512); @@ -285,17 +285,13 @@ static void pci_basic(void) QVirtioPCIDevice *dev; QOSState *qs; QVirtQueuePCI *vqpci; - void *addr; qs = pci_test_start(); dev = virtio_blk_pci_init(qs->pcibus, PCI_SLOT); vqpci = (QVirtQueuePCI *)qvirtqueue_setup(&dev->vdev, qs->alloc, 0); - /* MSI-X is not enabled */ - addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(false); - - test_basic(&dev->vdev, qs->alloc, &vqpci->vq, (uint64_t)(uintptr_t)addr); + test_basic(&dev->vdev, qs->alloc, &vqpci->vq); /* End test */ qvirtqueue_cleanup(dev->vdev.bus, &vqpci->vq, qs->alloc); @@ -311,7 +307,6 @@ static void pci_indirect(void) QOSState *qs; QVirtioBlkReq req; QVRingIndirectDesc *indirect; - void *addr; uint64_t req_addr; uint64_t capacity; uint32_t features; @@ -323,10 +318,7 @@ static void pci_indirect(void) dev = virtio_blk_pci_init(qs->pcibus, PCI_SLOT); - /* MSI-X is not enabled */ - addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(false); - - capacity = qvirtio_config_readq(&dev->vdev, (uint64_t)(uintptr_t)addr); + capacity = qvirtio_config_readq(&dev->vdev, 0); g_assert_cmpint(capacity, ==, TEST_IMAGE_SIZE / 512); features = qvirtio_get_features(&dev->vdev); @@ -406,17 +398,13 @@ static void pci_config(void) QVirtioPCIDevice *dev; QOSState *qs; int n_size = TEST_IMAGE_SIZE / 2; - void *addr; uint64_t capacity; qs = pci_test_start(); dev = virtio_blk_pci_init(qs->pcibus, PCI_SLOT); - /* MSI-X is not enabled */ - addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(false); - - capacity = qvirtio_config_readq(&dev->vdev, (uint64_t)(uintptr_t)addr); + capacity = qvirtio_config_readq(&dev->vdev, 0); g_assert_cmpint(capacity, ==, TEST_IMAGE_SIZE / 512); qvirtio_set_driver_ok(&dev->vdev); @@ -425,7 +413,7 @@ static void pci_config(void) " 'size': %d } }", n_size); qvirtio_wait_config_isr(&dev->vdev, QVIRTIO_BLK_TIMEOUT_US); - capacity = qvirtio_config_readq(&dev->vdev, (uint64_t)(uintptr_t)addr); + capacity = qvirtio_config_readq(&dev->vdev, 0); g_assert_cmpint(capacity, ==, n_size / 512); qvirtio_pci_device_disable(dev); @@ -441,7 +429,6 @@ static void pci_msix(void) QVirtQueuePCI *vqpci; QVirtioBlkReq req; int n_size = TEST_IMAGE_SIZE / 2; - void *addr; uint64_t req_addr; uint64_t capacity; uint32_t features; @@ -456,10 +443,7 @@ static void pci_msix(void) qvirtio_pci_set_msix_configuration_vector(dev, qs->alloc, 0); - /* MSI-X is enabled */ - addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(true); - - capacity = qvirtio_config_readq(&dev->vdev, (uint64_t)(uintptr_t)addr); + capacity = qvirtio_config_readq(&dev->vdev, 0); g_assert_cmpint(capacity, ==, TEST_IMAGE_SIZE / 512); features = qvirtio_get_features(&dev->vdev); @@ -479,7 +463,7 @@ static void pci_msix(void) qvirtio_wait_config_isr(&dev->vdev, QVIRTIO_BLK_TIMEOUT_US); - capacity = qvirtio_config_readq(&dev->vdev, (uintptr_t)addr); + capacity = qvirtio_config_readq(&dev->vdev, 0); g_assert_cmpint(capacity, ==, n_size / 512); /* Write request */ @@ -550,7 +534,6 @@ static void pci_idx(void) QOSState *qs; QVirtQueuePCI *vqpci; QVirtioBlkReq req; - void *addr; uint64_t req_addr; uint64_t capacity; uint32_t features; @@ -565,10 +548,7 @@ static void pci_idx(void) qvirtio_pci_set_msix_configuration_vector(dev, qs->alloc, 0); - /* MSI-X is enabled */ - addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(true); - - capacity = qvirtio_config_readq(&dev->vdev, (uint64_t)(uintptr_t)addr); + capacity = qvirtio_config_readq(&dev->vdev, 0); g_assert_cmpint(capacity, ==, TEST_IMAGE_SIZE / 512); features = qvirtio_get_features(&dev->vdev); @@ -709,14 +689,14 @@ static void mmio_basic(void) alloc = generic_alloc_init(MMIO_RAM_ADDR, MMIO_RAM_SIZE, MMIO_PAGE_SIZE); vq = qvirtqueue_setup(&dev->vdev, alloc, 0); - test_basic(&dev->vdev, alloc, vq, QVIRTIO_MMIO_DEVICE_SPECIFIC); + test_basic(&dev->vdev, alloc, vq); qmp("{ 'execute': 'block_resize', 'arguments': { 'device': 'drive0', " " 'size': %d } }", n_size); qvirtio_wait_queue_isr(&dev->vdev, vq, QVIRTIO_BLK_TIMEOUT_US); - capacity = qvirtio_config_readq(&dev->vdev, QVIRTIO_MMIO_DEVICE_SPECIFIC); + capacity = qvirtio_config_readq(&dev->vdev, 0); g_assert_cmpint(capacity, ==, n_size / 512); /* End test */ diff --git a/tests/virtio-scsi-test.c b/tests/virtio-scsi-test.c index 60dc9abd60..69220ef07b 100644 --- a/tests/virtio-scsi-test.c +++ b/tests/virtio-scsi-test.c @@ -143,7 +143,6 @@ static QVirtIOSCSI *qvirtio_scsi_pci_init(int slot) QVirtIOSCSI *vs; QVirtioPCIDevice *dev; struct virtio_scsi_cmd_resp resp; - void *addr; int i; vs = g_new0(QVirtIOSCSI, 1); @@ -161,8 +160,7 @@ static QVirtIOSCSI *qvirtio_scsi_pci_init(int slot) qvirtio_set_acknowledge(vs->dev); qvirtio_set_driver(vs->dev); - addr = dev->addr + VIRTIO_PCI_CONFIG_OFF(false); - vs->num_queues = qvirtio_config_readl(vs->dev, (uint64_t)(uintptr_t)addr); + vs->num_queues = qvirtio_config_readl(vs->dev, 0); g_assert_cmpint(vs->num_queues, <, MAX_NUM_QUEUES); From a795fc08f2636013fe097e51bdac62d089ac505a Mon Sep 17 00:00:00 2001 From: David Gibson Date: Tue, 18 Oct 2016 17:02:49 +1100 Subject: [PATCH 52/73] libqos: Handle PCI IO de-multiplexing in common code The PCI IO space (aka PIO, aka legacy IO) and PCI memory space (aka MMIO) are distinct address spaces by the PCI spec (although parts of one might be aliased to parts of the other in some cases). However, qpci_io_read*() and qpci_io_write*() can perform accesses to either space depending on parameter. That's convenient for test case drivers, since there are a fair few devices which can be controlled via either a PIO or MMIO BAR but with an otherwise identical driver. This is implemented by having addresses below 64kiB treated as PIO, and those above treated as MMIO. This works because low addresses in memory space are generally reserved for DMA rather than MMIO. At the moment, this demultiplexing must be handled by each PCI backend (pc and spapr, so far). There's no real reason for this - the current encoding is likely to work for all platforms, and even if it doesn't we can still use a more complex common encoding since the value returned from iomap are semi-opaque. This patch moves the demultiplexing into the common part of the libqos PCI code, with the backends having simpler, separate accessors for PIO and MMIO space. This also means we have a way of explicitly accessing either space if it's necessary for some special case. Signed-off-by: David Gibson Reviewed-by: Laurent Vivier Reviewed-by: Greg Kurz --- tests/libqos/pci-pc.c | 117 ++++++++++++++++++-------------------- tests/libqos/pci-spapr.c | 118 ++++++++++++++++++++------------------- tests/libqos/pci.c | 49 +++++++++++++--- tests/libqos/pci.h | 22 ++++++-- 4 files changed, 175 insertions(+), 131 deletions(-) diff --git a/tests/libqos/pci-pc.c b/tests/libqos/pci-pc.c index 9600ed6e41..51dff8a7fa 100644 --- a/tests/libqos/pci-pc.c +++ b/tests/libqos/pci-pc.c @@ -36,79 +36,64 @@ typedef struct QPCIBusPC uint16_t pci_iohole_alloc; } QPCIBusPC; -static uint8_t qpci_pc_io_readb(QPCIBus *bus, void *addr) +static uint8_t qpci_pc_pio_readb(QPCIBus *bus, uint32_t addr) { - uintptr_t port = (uintptr_t)addr; - uint8_t value; - - if (port < 0x10000) { - value = inb(port); - } else { - value = readb(port); - } - - return value; + return inb(addr); } -static uint16_t qpci_pc_io_readw(QPCIBus *bus, void *addr) +static uint8_t qpci_pc_mmio_readb(QPCIBus *bus, uint32_t addr) { - uintptr_t port = (uintptr_t)addr; - uint16_t value; - - if (port < 0x10000) { - value = inw(port); - } else { - value = readw(port); - } - - return value; + return readb(addr); } -static uint32_t qpci_pc_io_readl(QPCIBus *bus, void *addr) +static void qpci_pc_pio_writeb(QPCIBus *bus, uint32_t addr, uint8_t val) { - uintptr_t port = (uintptr_t)addr; - uint32_t value; - - if (port < 0x10000) { - value = inl(port); - } else { - value = readl(port); - } - - return value; + outb(addr, val); } -static void qpci_pc_io_writeb(QPCIBus *bus, void *addr, uint8_t value) +static void qpci_pc_mmio_writeb(QPCIBus *bus, uint32_t addr, uint8_t val) { - uintptr_t port = (uintptr_t)addr; - - if (port < 0x10000) { - outb(port, value); - } else { - writeb(port, value); - } + writeb(addr, val); } -static void qpci_pc_io_writew(QPCIBus *bus, void *addr, uint16_t value) +static uint16_t qpci_pc_pio_readw(QPCIBus *bus, uint32_t addr) { - uintptr_t port = (uintptr_t)addr; - - if (port < 0x10000) { - outw(port, value); - } else { - writew(port, value); - } + return inw(addr); } -static void qpci_pc_io_writel(QPCIBus *bus, void *addr, uint32_t value) +static uint16_t qpci_pc_mmio_readw(QPCIBus *bus, uint32_t addr) { - uintptr_t port = (uintptr_t)addr; + return readw(addr); +} - if (port < 0x10000) { - outl(port, value); - } else { - writel(port, value); - } +static void qpci_pc_pio_writew(QPCIBus *bus, uint32_t addr, uint16_t val) +{ + outw(addr, val); +} + +static void qpci_pc_mmio_writew(QPCIBus *bus, uint32_t addr, uint16_t val) +{ + writew(addr, val); +} + +static uint32_t qpci_pc_pio_readl(QPCIBus *bus, uint32_t addr) +{ + return inl(addr); +} + +static uint32_t qpci_pc_mmio_readl(QPCIBus *bus, uint32_t addr) +{ + return readl(addr); +} + +static void qpci_pc_pio_writel(QPCIBus *bus, uint32_t addr, uint32_t val) +{ + outl(addr, val); +} + +static void qpci_pc_mmio_writel(QPCIBus *bus, uint32_t addr, uint32_t val) +{ + writel(addr, val); } static uint8_t qpci_pc_config_readb(QPCIBus *bus, int devfn, uint8_t offset) @@ -218,13 +203,21 @@ QPCIBus *qpci_init_pc(QGuestAllocator *alloc) ret = g_malloc(sizeof(*ret)); - ret->bus.io_readb = qpci_pc_io_readb; - ret->bus.io_readw = qpci_pc_io_readw; - ret->bus.io_readl = qpci_pc_io_readl; + ret->bus.pio_readb = qpci_pc_pio_readb; + ret->bus.pio_readw = qpci_pc_pio_readw; + ret->bus.pio_readl = qpci_pc_pio_readl; - ret->bus.io_writeb = qpci_pc_io_writeb; - ret->bus.io_writew = qpci_pc_io_writew; - ret->bus.io_writel = qpci_pc_io_writel; + ret->bus.pio_writeb = qpci_pc_pio_writeb; + ret->bus.pio_writew = qpci_pc_pio_writew; + ret->bus.pio_writel = qpci_pc_pio_writel; + + ret->bus.mmio_readb = qpci_pc_mmio_readb; + ret->bus.mmio_readw = qpci_pc_mmio_readw; + ret->bus.mmio_readl = qpci_pc_mmio_readl; + + ret->bus.mmio_writeb = qpci_pc_mmio_writeb; + ret->bus.mmio_writew = qpci_pc_mmio_writew; + ret->bus.mmio_writel = qpci_pc_mmio_writel; ret->bus.config_readb = qpci_pc_config_readb; ret->bus.config_readw = qpci_pc_config_readw; diff --git a/tests/libqos/pci-spapr.c b/tests/libqos/pci-spapr.c index 2eaaf9159a..2d26a94dab 100644 --- a/tests/libqos/pci-spapr.c +++ b/tests/libqos/pci-spapr.c @@ -50,78 +50,76 @@ typedef struct QPCIBusSPAPR { * so PCI accessors need to swap data endianness */ -static uint8_t qpci_spapr_io_readb(QPCIBus *bus, void *addr) +static uint8_t qpci_spapr_pio_readb(QPCIBus *bus, uint32_t addr) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - uint64_t port = (uintptr_t)addr; - uint8_t v; - if (port < s->pio.size) { - v = readb(s->pio_cpu_base + port); - } else { - v = readb(s->mmio32_cpu_base + port); - } - return v; + return readb(s->pio_cpu_base + addr); } -static uint16_t qpci_spapr_io_readw(QPCIBus *bus, void *addr) +static uint8_t qpci_spapr_mmio32_readb(QPCIBus *bus, uint32_t addr) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - uint64_t port = (uintptr_t)addr; - uint16_t v; - if (port < s->pio.size) { - v = readw(s->pio_cpu_base + port); - } else { - v = readw(s->mmio32_cpu_base + port); - } - return bswap16(v); + return readb(s->mmio32_cpu_base + addr); } -static uint32_t qpci_spapr_io_readl(QPCIBus *bus, void *addr) +static void qpci_spapr_pio_writeb(QPCIBus *bus, uint32_t addr, uint8_t val) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - uint64_t port = (uintptr_t)addr; - uint32_t v; - if (port < s->pio.size) { - v = readl(s->pio_cpu_base + port); - } else { - v = readl(s->mmio32_cpu_base + port); - } - return bswap32(v); + writeb(s->pio_cpu_base + addr, val); } -static void qpci_spapr_io_writeb(QPCIBus *bus, void *addr, uint8_t value) +static void qpci_spapr_mmio32_writeb(QPCIBus *bus, uint32_t addr, uint8_t val) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - uint64_t port = (uintptr_t)addr; - if (port < s->pio.size) { - writeb(s->pio_cpu_base + port, value); - } else { - writeb(s->mmio32_cpu_base + port, value); - } + writeb(s->mmio32_cpu_base + addr, val); } -static void qpci_spapr_io_writew(QPCIBus *bus, void *addr, uint16_t value) +static uint16_t qpci_spapr_pio_readw(QPCIBus *bus, uint32_t addr) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - uint64_t port = (uintptr_t)addr; - value = bswap16(value); - if (port < s->pio.size) { - writew(s->pio_cpu_base + port, value); - } else { - writew(s->mmio32_cpu_base + port, value); - } + return bswap16(readw(s->pio_cpu_base + addr)); } -static void qpci_spapr_io_writel(QPCIBus *bus, void *addr, uint32_t value) +static uint16_t qpci_spapr_mmio32_readw(QPCIBus *bus, uint32_t addr) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - uint64_t port = (uintptr_t)addr; - value = bswap32(value); - if (port < s->pio.size) { - writel(s->pio_cpu_base + port, value); - } else { - writel(s->mmio32_cpu_base + port, value); - } + return bswap16(readw(s->mmio32_cpu_base + addr)); +} + +static void qpci_spapr_pio_writew(QPCIBus *bus, uint32_t addr, uint16_t val) +{ + QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); + writew(s->pio_cpu_base + addr, bswap16(val)); +} + +static void qpci_spapr_mmio32_writew(QPCIBus *bus, uint32_t addr, uint16_t val) +{ + QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); + writew(s->mmio32_cpu_base + addr, bswap16(val)); +} + +static uint32_t qpci_spapr_pio_readl(QPCIBus *bus, uint32_t addr) +{ + QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); + return bswap32(readl(s->pio_cpu_base + addr)); +} + +static uint32_t qpci_spapr_mmio32_readl(QPCIBus *bus, uint32_t addr) +{ + QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); + return bswap32(readl(s->mmio32_cpu_base + addr)); +} + +static void qpci_spapr_pio_writel(QPCIBus *bus, uint32_t addr, uint32_t val) +{ + QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); + writel(s->pio_cpu_base + addr, bswap32(val)); +} + +static void qpci_spapr_mmio32_writel(QPCIBus *bus, uint32_t addr, uint32_t val) +{ + QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); + writel(s->mmio32_cpu_base + addr, bswap32(val)); } static uint8_t qpci_spapr_config_readb(QPCIBus *bus, int devfn, uint8_t offset) @@ -248,13 +246,21 @@ QPCIBus *qpci_init_spapr(QGuestAllocator *alloc) ret->alloc = alloc; - ret->bus.io_readb = qpci_spapr_io_readb; - ret->bus.io_readw = qpci_spapr_io_readw; - ret->bus.io_readl = qpci_spapr_io_readl; + ret->bus.pio_readb = qpci_spapr_pio_readb; + ret->bus.pio_readw = qpci_spapr_pio_readw; + ret->bus.pio_readl = qpci_spapr_pio_readl; - ret->bus.io_writeb = qpci_spapr_io_writeb; - ret->bus.io_writew = qpci_spapr_io_writew; - ret->bus.io_writel = qpci_spapr_io_writel; + ret->bus.pio_writeb = qpci_spapr_pio_writeb; + ret->bus.pio_writew = qpci_spapr_pio_writew; + ret->bus.pio_writel = qpci_spapr_pio_writel; + + ret->bus.mmio_readb = qpci_spapr_mmio32_readb; + ret->bus.mmio_readw = qpci_spapr_mmio32_readw; + ret->bus.mmio_readl = qpci_spapr_mmio32_readl; + + ret->bus.mmio_writeb = qpci_spapr_mmio32_writeb; + ret->bus.mmio_writew = qpci_spapr_mmio32_writew; + ret->bus.mmio_writel = qpci_spapr_mmio32_writel; ret->bus.config_readb = qpci_spapr_config_readb; ret->bus.config_readw = qpci_spapr_config_readw; diff --git a/tests/libqos/pci.c b/tests/libqos/pci.c index c3f3382b7c..55b01df37b 100644 --- a/tests/libqos/pci.c +++ b/tests/libqos/pci.c @@ -224,33 +224,68 @@ void qpci_config_writel(QPCIDevice *dev, uint8_t offset, uint32_t value) uint8_t qpci_io_readb(QPCIDevice *dev, void *data) { - return dev->bus->io_readb(dev->bus, data); + uintptr_t addr = (uintptr_t)data; + + if (addr < QPCI_PIO_LIMIT) { + return dev->bus->pio_readb(dev->bus, addr); + } else { + return dev->bus->mmio_readb(dev->bus, addr); + } } uint16_t qpci_io_readw(QPCIDevice *dev, void *data) { - return dev->bus->io_readw(dev->bus, data); + uintptr_t addr = (uintptr_t)data; + + if (addr < QPCI_PIO_LIMIT) { + return dev->bus->pio_readw(dev->bus, addr); + } else { + return dev->bus->mmio_readw(dev->bus, addr); + } } uint32_t qpci_io_readl(QPCIDevice *dev, void *data) { - return dev->bus->io_readl(dev->bus, data); -} + uintptr_t addr = (uintptr_t)data; + if (addr < QPCI_PIO_LIMIT) { + return dev->bus->pio_readl(dev->bus, addr); + } else { + return dev->bus->mmio_readl(dev->bus, addr); + } +} void qpci_io_writeb(QPCIDevice *dev, void *data, uint8_t value) { - dev->bus->io_writeb(dev->bus, data, value); + uintptr_t addr = (uintptr_t)data; + + if (addr < QPCI_PIO_LIMIT) { + dev->bus->pio_writeb(dev->bus, addr, value); + } else { + dev->bus->mmio_writeb(dev->bus, addr, value); + } } void qpci_io_writew(QPCIDevice *dev, void *data, uint16_t value) { - dev->bus->io_writew(dev->bus, data, value); + uintptr_t addr = (uintptr_t)data; + + if (addr < QPCI_PIO_LIMIT) { + dev->bus->pio_writew(dev->bus, addr, value); + } else { + dev->bus->mmio_writew(dev->bus, addr, value); + } } void qpci_io_writel(QPCIDevice *dev, void *data, uint32_t value) { - dev->bus->io_writel(dev->bus, data, value); + uintptr_t addr = (uintptr_t)data; + + if (addr < QPCI_PIO_LIMIT) { + dev->bus->pio_writel(dev->bus, addr, value); + } else { + dev->bus->mmio_writel(dev->bus, addr, value); + } } void *qpci_iomap(QPCIDevice *dev, int barno, uint64_t *sizeptr) diff --git a/tests/libqos/pci.h b/tests/libqos/pci.h index c06add8dbf..72a2245c05 100644 --- a/tests/libqos/pci.h +++ b/tests/libqos/pci.h @@ -15,6 +15,8 @@ #include "libqtest.h" +#define QPCI_PIO_LIMIT 0x10000 + #define QPCI_DEVFN(dev, fn) (((dev) << 3) | (fn)) typedef struct QPCIDevice QPCIDevice; @@ -22,13 +24,21 @@ typedef struct QPCIBus QPCIBus; struct QPCIBus { - uint8_t (*io_readb)(QPCIBus *bus, void *addr); - uint16_t (*io_readw)(QPCIBus *bus, void *addr); - uint32_t (*io_readl)(QPCIBus *bus, void *addr); + uint8_t (*pio_readb)(QPCIBus *bus, uint32_t addr); + uint16_t (*pio_readw)(QPCIBus *bus, uint32_t addr); + uint32_t (*pio_readl)(QPCIBus *bus, uint32_t addr); - void (*io_writeb)(QPCIBus *bus, void *addr, uint8_t value); - void (*io_writew)(QPCIBus *bus, void *addr, uint16_t value); - void (*io_writel)(QPCIBus *bus, void *addr, uint32_t value); + uint8_t (*mmio_readb)(QPCIBus *bus, uint32_t addr); + uint16_t (*mmio_readw)(QPCIBus *bus, uint32_t addr); + uint32_t (*mmio_readl)(QPCIBus *bus, uint32_t addr); + + void (*pio_writeb)(QPCIBus *bus, uint32_t addr, uint8_t value); + void (*pio_writew)(QPCIBus *bus, uint32_t addr, uint16_t value); + void (*pio_writel)(QPCIBus *bus, uint32_t addr, uint32_t value); + + void (*mmio_writeb)(QPCIBus *bus, uint32_t addr, uint8_t value); + void (*mmio_writew)(QPCIBus *bus, uint32_t addr, uint16_t value); + void (*mmio_writel)(QPCIBus *bus, uint32_t addr, uint32_t value); uint8_t (*config_readb)(QPCIBus *bus, int devfn, uint8_t offset); uint16_t (*config_readw)(QPCIBus *bus, int devfn, uint8_t offset); From b8cc4d0231b97c3dd7930d91ab91657b5a105b78 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Wed, 19 Oct 2016 14:06:51 +1100 Subject: [PATCH 53/73] libqos: Move BAR assignment to common code The PCI backends in libqos each supply an iomap() and iounmap() function which is used to set up a specified PCI BAR. But PCI BAR allocation takes place entirely within PCI space, so doesn't really need per-backend versions. For example, Linux includes generic BAR allocation code used on platforms where that isn't done by firmware. This patch merges the BAR allocation from the two existing backends into a single simplified copy. The back ends just need to set up some parameters describing the window of PCI IO and PCI memory addresses which are available for allocation. Like both the existing versions the new one uses a simple bump allocator. Note that (again like the existing versions) this doesn't really handle 64-bit memory BARs properly. It is actually used for such a BAR by the ivshmem test, and apparently the 32-bit MMIO BAR logic is close enough to work, as long as the BAR isn't too big. Fixing that to properly handle 64-bit BAR allocation is a problem for another time. Signed-off-by: David Gibson Reviewed-by: Laurent Vivier Reviewed-by: Greg Kurz --- tests/libqos/pci-pc.c | 87 ++------------------------------------- tests/libqos/pci-spapr.c | 89 ++-------------------------------------- tests/libqos/pci.c | 56 ++++++++++++++++++++++++- tests/libqos/pci.h | 7 ++-- 4 files changed, 63 insertions(+), 176 deletions(-) diff --git a/tests/libqos/pci-pc.c b/tests/libqos/pci-pc.c index 51dff8a7fa..d0eb84a134 100644 --- a/tests/libqos/pci-pc.c +++ b/tests/libqos/pci-pc.c @@ -17,7 +17,6 @@ #include "hw/pci/pci_regs.h" #include "qemu-common.h" -#include "qemu/host-utils.h" #define ACPI_PCIHP_ADDR 0xae00 @@ -26,14 +25,6 @@ typedef struct QPCIBusPC { QPCIBus bus; - - uint32_t pci_hole_start; - uint32_t pci_hole_size; - uint32_t pci_hole_alloc; - - uint16_t pci_iohole_start; - uint16_t pci_iohole_size; - uint16_t pci_iohole_alloc; } QPCIBusPC; static uint8_t qpci_pc_pio_readb(QPCIBus *bus, uint32_t addr) @@ -132,71 +123,6 @@ static void qpci_pc_config_writel(QPCIBus *bus, int devfn, uint8_t offset, uint3 outl(0xcfc, value); } -static void *qpci_pc_iomap(QPCIBus *bus, QPCIDevice *dev, int barno, uint64_t *sizeptr) -{ - QPCIBusPC *s = container_of(bus, QPCIBusPC, bus); - static const int bar_reg_map[] = { - PCI_BASE_ADDRESS_0, PCI_BASE_ADDRESS_1, PCI_BASE_ADDRESS_2, - PCI_BASE_ADDRESS_3, PCI_BASE_ADDRESS_4, PCI_BASE_ADDRESS_5, - }; - int bar_reg; - uint32_t addr; - uint64_t size; - uint32_t io_type; - - g_assert(barno >= 0 && barno <= 5); - bar_reg = bar_reg_map[barno]; - - qpci_config_writel(dev, bar_reg, 0xFFFFFFFF); - addr = qpci_config_readl(dev, bar_reg); - - io_type = addr & PCI_BASE_ADDRESS_SPACE; - if (io_type == PCI_BASE_ADDRESS_SPACE_IO) { - addr &= PCI_BASE_ADDRESS_IO_MASK; - } else { - addr &= PCI_BASE_ADDRESS_MEM_MASK; - } - - size = (1ULL << ctzl(addr)); - if (size == 0) { - return NULL; - } - if (sizeptr) { - *sizeptr = size; - } - - if (io_type == PCI_BASE_ADDRESS_SPACE_IO) { - uint16_t loc; - - g_assert(QEMU_ALIGN_UP(s->pci_iohole_alloc, size) + size - <= s->pci_iohole_size); - s->pci_iohole_alloc = QEMU_ALIGN_UP(s->pci_iohole_alloc, size); - loc = s->pci_iohole_start + s->pci_iohole_alloc; - s->pci_iohole_alloc += size; - - qpci_config_writel(dev, bar_reg, loc | PCI_BASE_ADDRESS_SPACE_IO); - - return (void *)(intptr_t)loc; - } else { - uint64_t loc; - - g_assert(QEMU_ALIGN_UP(s->pci_hole_alloc, size) + size - <= s->pci_hole_size); - s->pci_hole_alloc = QEMU_ALIGN_UP(s->pci_hole_alloc, size); - loc = s->pci_hole_start + s->pci_hole_alloc; - s->pci_hole_alloc += size; - - qpci_config_writel(dev, bar_reg, loc); - - return (void *)(intptr_t)loc; - } -} - -static void qpci_pc_iounmap(QPCIBus *bus, void *data) -{ - /* FIXME */ -} - QPCIBus *qpci_init_pc(QGuestAllocator *alloc) { QPCIBusPC *ret; @@ -227,16 +153,9 @@ QPCIBus *qpci_init_pc(QGuestAllocator *alloc) ret->bus.config_writew = qpci_pc_config_writew; ret->bus.config_writel = qpci_pc_config_writel; - ret->bus.iomap = qpci_pc_iomap; - ret->bus.iounmap = qpci_pc_iounmap; - - ret->pci_hole_start = 0xE0000000; - ret->pci_hole_size = 0x20000000; - ret->pci_hole_alloc = 0; - - ret->pci_iohole_start = 0xc000; - ret->pci_iohole_size = 0x4000; - ret->pci_iohole_alloc = 0; + ret->bus.pio_alloc_ptr = 0xc000; + ret->bus.mmio_alloc_ptr = 0xE0000000; + ret->bus.mmio_limit = 0x100000000ULL; return &ret->bus; } diff --git a/tests/libqos/pci-spapr.c b/tests/libqos/pci-spapr.c index 2d26a94dab..70a24b5579 100644 --- a/tests/libqos/pci-spapr.c +++ b/tests/libqos/pci-spapr.c @@ -34,14 +34,6 @@ typedef struct QPCIBusSPAPR { uint64_t mmio32_cpu_base; QPCIWindow mmio32; - - uint64_t pci_hole_start; - uint64_t pci_hole_size; - uint64_t pci_hole_alloc; - - uint32_t pci_iohole_start; - uint32_t pci_iohole_size; - uint32_t pci_iohole_alloc; } QPCIBusSPAPR; /* @@ -167,72 +159,6 @@ static void qpci_spapr_config_writel(QPCIBus *bus, int devfn, uint8_t offset, qrtas_ibm_write_pci_config(s->alloc, s->buid, config_addr, 4, value); } -static void *qpci_spapr_iomap(QPCIBus *bus, QPCIDevice *dev, int barno, - uint64_t *sizeptr) -{ - QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - static const int bar_reg_map[] = { - PCI_BASE_ADDRESS_0, PCI_BASE_ADDRESS_1, PCI_BASE_ADDRESS_2, - PCI_BASE_ADDRESS_3, PCI_BASE_ADDRESS_4, PCI_BASE_ADDRESS_5, - }; - int bar_reg; - uint32_t addr; - uint64_t size; - uint32_t io_type; - - g_assert(barno >= 0 && barno <= 5); - bar_reg = bar_reg_map[barno]; - - qpci_config_writel(dev, bar_reg, 0xFFFFFFFF); - addr = qpci_config_readl(dev, bar_reg); - - io_type = addr & PCI_BASE_ADDRESS_SPACE; - if (io_type == PCI_BASE_ADDRESS_SPACE_IO) { - addr &= PCI_BASE_ADDRESS_IO_MASK; - } else { - addr &= PCI_BASE_ADDRESS_MEM_MASK; - } - - size = (1ULL << ctzl(addr)); - if (size == 0) { - return NULL; - } - if (sizeptr) { - *sizeptr = size; - } - - if (io_type == PCI_BASE_ADDRESS_SPACE_IO) { - uint16_t loc; - - g_assert(QEMU_ALIGN_UP(s->pci_iohole_alloc, size) + size - <= s->pci_iohole_size); - s->pci_iohole_alloc = QEMU_ALIGN_UP(s->pci_iohole_alloc, size); - loc = s->pci_iohole_start + s->pci_iohole_alloc; - s->pci_iohole_alloc += size; - - qpci_config_writel(dev, bar_reg, loc | PCI_BASE_ADDRESS_SPACE_IO); - - return (void *)(unsigned long)loc; - } else { - uint64_t loc; - - g_assert(QEMU_ALIGN_UP(s->pci_hole_alloc, size) + size - <= s->pci_hole_size); - s->pci_hole_alloc = QEMU_ALIGN_UP(s->pci_hole_alloc, size); - loc = s->pci_hole_start + s->pci_hole_alloc; - s->pci_hole_alloc += size; - - qpci_config_writel(dev, bar_reg, loc); - - return (void *)(unsigned long)loc; - } -} - -static void qpci_spapr_iounmap(QPCIBus *bus, void *data) -{ - /* FIXME */ -} - #define SPAPR_PCI_BASE (1ULL << 45) #define SPAPR_PCI_MMIO32_WIN_SIZE 0x80000000 /* 2 GiB */ @@ -270,9 +196,6 @@ QPCIBus *qpci_init_spapr(QGuestAllocator *alloc) ret->bus.config_writew = qpci_spapr_config_writew; ret->bus.config_writel = qpci_spapr_config_writel; - ret->bus.iomap = qpci_spapr_iomap; - ret->bus.iounmap = qpci_spapr_iounmap; - /* FIXME: We assume the default location of the PHB for now. * Ideally we'd parse the device tree deposited in the guest to * get the window locations */ @@ -287,15 +210,9 @@ QPCIBus *qpci_init_spapr(QGuestAllocator *alloc) ret->mmio32.pci_base = 0x80000000; /* 2 GiB */ ret->mmio32.size = SPAPR_PCI_MMIO32_WIN_SIZE; - ret->pci_hole_start = 0xC0000000; - ret->pci_hole_size = - ret->mmio32.pci_base + ret->mmio32.size - ret->pci_hole_start; - ret->pci_hole_alloc = 0; - - ret->pci_iohole_start = 0xc000; - ret->pci_iohole_size = - ret->pio.pci_base + ret->pio.size - ret->pci_iohole_start; - ret->pci_iohole_alloc = 0; + ret->bus.pio_alloc_ptr = 0xc000; + ret->bus.mmio_alloc_ptr = ret->mmio32.pci_base; + ret->bus.mmio_limit = ret->mmio32.pci_base + ret->mmio32.size; return &ret->bus; } diff --git a/tests/libqos/pci.c b/tests/libqos/pci.c index 55b01df37b..bf1c53240b 100644 --- a/tests/libqos/pci.c +++ b/tests/libqos/pci.c @@ -14,6 +14,7 @@ #include "libqos/pci.h" #include "hw/pci/pci_regs.h" +#include "qemu/host-utils.h" void qpci_device_foreach(QPCIBus *bus, int vendor_id, int device_id, void (*func)(QPCIDevice *dev, int devfn, void *data), @@ -290,12 +291,63 @@ void qpci_io_writel(QPCIDevice *dev, void *data, uint32_t value) void *qpci_iomap(QPCIDevice *dev, int barno, uint64_t *sizeptr) { - return dev->bus->iomap(dev->bus, dev, barno, sizeptr); + QPCIBus *bus = dev->bus; + static const int bar_reg_map[] = { + PCI_BASE_ADDRESS_0, PCI_BASE_ADDRESS_1, PCI_BASE_ADDRESS_2, + PCI_BASE_ADDRESS_3, PCI_BASE_ADDRESS_4, PCI_BASE_ADDRESS_5, + }; + int bar_reg; + uint32_t addr, size; + uint32_t io_type; + uint64_t loc; + + g_assert(barno >= 0 && barno <= 5); + bar_reg = bar_reg_map[barno]; + + qpci_config_writel(dev, bar_reg, 0xFFFFFFFF); + addr = qpci_config_readl(dev, bar_reg); + + io_type = addr & PCI_BASE_ADDRESS_SPACE; + if (io_type == PCI_BASE_ADDRESS_SPACE_IO) { + addr &= PCI_BASE_ADDRESS_IO_MASK; + } else { + addr &= PCI_BASE_ADDRESS_MEM_MASK; + } + + g_assert(addr); /* Must have *some* size bits */ + + size = 1U << ctz32(addr); + if (sizeptr) { + *sizeptr = size; + } + + if (io_type == PCI_BASE_ADDRESS_SPACE_IO) { + loc = QEMU_ALIGN_UP(bus->pio_alloc_ptr, size); + + g_assert(loc >= bus->pio_alloc_ptr); + g_assert(loc + size <= QPCI_PIO_LIMIT); /* Keep PIO below 64kiB */ + + bus->pio_alloc_ptr = loc + size; + + qpci_config_writel(dev, bar_reg, loc | PCI_BASE_ADDRESS_SPACE_IO); + } else { + loc = QEMU_ALIGN_UP(bus->mmio_alloc_ptr, size); + + /* Check for space */ + g_assert(loc >= bus->mmio_alloc_ptr); + g_assert(loc + size <= bus->mmio_limit); + + bus->mmio_alloc_ptr = loc + size; + + qpci_config_writel(dev, bar_reg, loc); + } + + return (void *)(uintptr_t)loc; } void qpci_iounmap(QPCIDevice *dev, void *data) { - dev->bus->iounmap(dev->bus, data); + /* FIXME */ } void qpci_plug_device_test(const char *driver, const char *id, diff --git a/tests/libqos/pci.h b/tests/libqos/pci.h index 72a2245c05..f6f916dca7 100644 --- a/tests/libqos/pci.h +++ b/tests/libqos/pci.h @@ -22,8 +22,7 @@ typedef struct QPCIDevice QPCIDevice; typedef struct QPCIBus QPCIBus; -struct QPCIBus -{ +struct QPCIBus { uint8_t (*pio_readb)(QPCIBus *bus, uint32_t addr); uint16_t (*pio_readw)(QPCIBus *bus, uint32_t addr); uint32_t (*pio_readl)(QPCIBus *bus, uint32_t addr); @@ -51,8 +50,8 @@ struct QPCIBus void (*config_writel)(QPCIBus *bus, int devfn, uint8_t offset, uint32_t value); - void *(*iomap)(QPCIBus *bus, QPCIDevice *dev, int barno, uint64_t *sizeptr); - void (*iounmap)(QPCIBus *bus, void *data); + uint16_t pio_alloc_ptr; + uint64_t mmio_alloc_ptr, mmio_limit; }; struct QPCIDevice From a7b85b60623a862e2c55d5a6cd2e17f5fc26b256 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Wed, 19 Oct 2016 17:43:42 +1100 Subject: [PATCH 54/73] libqos: Better handling of PCI legacy IO The usual model for PCI IO with libqos is to use qpci_iomap() to map a specific BAR for a PCI device, then perform IOs within that BAR using qpci_io_{read,write}*(). However, certain devices also have legacy PCI IO. In this case, instead of (or as well as) being accessed via PCI BARs, the device can be accessed via certain well-known, fixed addresses in PCI IO space. Two existing tests use legacy PCI IO, and take different flawed approaches to it: * tco-test manually constructs a tco_io_base value instead of calling qpci_iomap(), which assumes internal knowledge of the structure of the value it shouldn't have * ide-test uses direct in*() and out*() calls instead of using qpci_io_*() accessors, meaning it's not portable to non-x86 machine types. This patch implements a new qpci_iomap_legacy() interface which gets a handle in the same format as qpci_iomap() but refers to a region in the legacy PIO space. For a device which has the same registers available both in a BAR and in legacy space (quite common), this allows the same test code to test both options with just a different iomap() at the beginning. Signed-off-by: David Gibson Reviewed-by: Laurent Vivier Reviewed-by: Greg Kurz --- tests/libqos/pci.c | 5 +++++ tests/libqos/pci.h | 1 + 2 files changed, 6 insertions(+) diff --git a/tests/libqos/pci.c b/tests/libqos/pci.c index bf1c53240b..98a2e56569 100644 --- a/tests/libqos/pci.c +++ b/tests/libqos/pci.c @@ -350,6 +350,11 @@ void qpci_iounmap(QPCIDevice *dev, void *data) /* FIXME */ } +void *qpci_legacy_iomap(QPCIDevice *dev, uint16_t addr) +{ + return (void *)(uintptr_t)addr; +} + void qpci_plug_device_test(const char *driver, const char *id, uint8_t slot, const char *opts) { diff --git a/tests/libqos/pci.h b/tests/libqos/pci.h index f6f916dca7..b6f855e3b6 100644 --- a/tests/libqos/pci.h +++ b/tests/libqos/pci.h @@ -94,6 +94,7 @@ void qpci_io_writel(QPCIDevice *dev, void *data, uint32_t value); void *qpci_iomap(QPCIDevice *dev, int barno, uint64_t *sizeptr); void qpci_iounmap(QPCIDevice *dev, void *data); +void *qpci_legacy_iomap(QPCIDevice *dev, uint16_t addr); void qpci_plug_device_test(const char *driver, const char *id, uint8_t slot, const char *opts); From 9ff50be2ffb3c116811cfc63dd1fa0ef8c4a9c75 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Wed, 19 Oct 2016 21:49:39 +1100 Subject: [PATCH 55/73] tests: Adjust tco-test to use qpci_legacy_iomap() Avoid tco-test making assumptions about the internal format of the address tokens passed to PCI IO accessors, by using the new qpci_legacy_iomap() function. Signed-off-by: David Gibson Reviewed-by: Laurent Vivier Reviewed-by: Greg Kurz --- tests/tco-test.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/tco-test.c b/tests/tco-test.c index 0d201b1fcb..129577d1c0 100644 --- a/tests/tco-test.c +++ b/tests/tco-test.c @@ -70,7 +70,7 @@ static void test_init(TestData *d) /* set Root Complex BAR */ qpci_config_writel(d->dev, ICH9_LPC_RCBA, RCBA_BASE_ADDR | 0x1); - d->tco_io_base = (void *)((uintptr_t)PM_IO_BASE_ADDR + 0x60); + d->tco_io_base = qpci_legacy_iomap(d->dev, PM_IO_BASE_ADDR + 0x60); } static void stop_tco(const TestData *d) From 9a84f889471de50144632100109f93aabea68ff6 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Wed, 19 Oct 2016 14:19:47 +1100 Subject: [PATCH 56/73] libqos: Add streaming accessors for PCI MMIO Currently PCI memory (aka MMIO) space is accessed via a set of readb/writeb style accessors. This is what we want for accessing discrete registers of a certain size. However, there are a few cases where we instead need a "bag of bytes" style streaming interface to PCI MMIO space. This can be either for streaming data style registers or when there's actual memory rather than registers in PCI space, for example frame buffers or ivshmem. This patch adds backend callbacks, and libqos wrappers for this type of byte address order preserving accesses. Signed-off-by: David Gibson Reviewed-by: Laurent Vivier Reviewed-by: Greg Kurz --- tests/libqos/pci-pc.c | 14 ++++++++++++++ tests/libqos/pci-spapr.c | 17 +++++++++++++++++ tests/libqos/pci.c | 16 ++++++++++++++++ tests/libqos/pci.h | 6 ++++++ 4 files changed, 53 insertions(+) diff --git a/tests/libqos/pci-pc.c b/tests/libqos/pci-pc.c index d0eb84a134..84aee25350 100644 --- a/tests/libqos/pci-pc.c +++ b/tests/libqos/pci-pc.c @@ -87,6 +87,17 @@ static void qpci_pc_mmio_writel(QPCIBus *bus, uint32_t addr, uint32_t val) writel(addr, val); } +static void qpci_pc_memread(QPCIBus *bus, uint32_t addr, void *buf, size_t len) +{ + memread(addr, buf, len); +} + +static void qpci_pc_memwrite(QPCIBus *bus, uint32_t addr, + const void *buf, size_t len) +{ + memwrite(addr, buf, len); +} + static uint8_t qpci_pc_config_readb(QPCIBus *bus, int devfn, uint8_t offset) { outl(0xcf8, (1U << 31) | (devfn << 8) | offset); @@ -145,6 +156,9 @@ QPCIBus *qpci_init_pc(QGuestAllocator *alloc) ret->bus.mmio_writew = qpci_pc_mmio_writew; ret->bus.mmio_writel = qpci_pc_mmio_writel; + ret->bus.memread = qpci_pc_memread; + ret->bus.memwrite = qpci_pc_memwrite; + ret->bus.config_readb = qpci_pc_config_readb; ret->bus.config_readw = qpci_pc_config_readw; ret->bus.config_readl = qpci_pc_config_readl; diff --git a/tests/libqos/pci-spapr.c b/tests/libqos/pci-spapr.c index 70a24b5579..ad12c2e582 100644 --- a/tests/libqos/pci-spapr.c +++ b/tests/libqos/pci-spapr.c @@ -114,6 +114,20 @@ static void qpci_spapr_mmio32_writel(QPCIBus *bus, uint32_t addr, uint32_t val) writel(s->mmio32_cpu_base + addr, bswap32(val)); } +static void qpci_spapr_memread(QPCIBus *bus, uint32_t addr, + void *buf, size_t len) +{ + QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); + memread(s->mmio32_cpu_base + addr, buf, len); +} + +static void qpci_spapr_memwrite(QPCIBus *bus, uint32_t addr, + const void *buf, size_t len) +{ + QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); + memwrite(s->mmio32_cpu_base + addr, buf, len); +} + static uint8_t qpci_spapr_config_readb(QPCIBus *bus, int devfn, uint8_t offset) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); @@ -188,6 +202,9 @@ QPCIBus *qpci_init_spapr(QGuestAllocator *alloc) ret->bus.mmio_writew = qpci_spapr_mmio32_writew; ret->bus.mmio_writel = qpci_spapr_mmio32_writel; + ret->bus.memread = qpci_spapr_memread; + ret->bus.memwrite = qpci_spapr_memwrite; + ret->bus.config_readb = qpci_spapr_config_readb; ret->bus.config_readw = qpci_spapr_config_readw; ret->bus.config_readl = qpci_spapr_config_readl; diff --git a/tests/libqos/pci.c b/tests/libqos/pci.c index 98a2e56569..146b06311c 100644 --- a/tests/libqos/pci.c +++ b/tests/libqos/pci.c @@ -289,6 +289,22 @@ void qpci_io_writel(QPCIDevice *dev, void *data, uint32_t value) } } +void qpci_memread(QPCIDevice *dev, void *data, void *buf, size_t len) +{ + uintptr_t addr = (uintptr_t)data; + + g_assert(addr >= QPCI_PIO_LIMIT); + dev->bus->memread(dev->bus, addr, buf, len); +} + +void qpci_memwrite(QPCIDevice *dev, void *data, const void *buf, size_t len) +{ + uintptr_t addr = (uintptr_t)data; + + g_assert(addr >= QPCI_PIO_LIMIT); + dev->bus->memwrite(dev->bus, addr, buf, len); +} + void *qpci_iomap(QPCIDevice *dev, int barno, uint64_t *sizeptr) { QPCIBus *bus = dev->bus; diff --git a/tests/libqos/pci.h b/tests/libqos/pci.h index b6f855e3b6..2b083624ef 100644 --- a/tests/libqos/pci.h +++ b/tests/libqos/pci.h @@ -39,6 +39,9 @@ struct QPCIBus { void (*mmio_writew)(QPCIBus *bus, uint32_t addr, uint16_t value); void (*mmio_writel)(QPCIBus *bus, uint32_t addr, uint32_t value); + void (*memread)(QPCIBus *bus, uint32_t addr, void *buf, size_t len); + void (*memwrite)(QPCIBus *bus, uint32_t addr, const void *buf, size_t len); + uint8_t (*config_readb)(QPCIBus *bus, int devfn, uint8_t offset); uint16_t (*config_readw)(QPCIBus *bus, int devfn, uint8_t offset); uint32_t (*config_readl)(QPCIBus *bus, int devfn, uint8_t offset); @@ -92,6 +95,9 @@ void qpci_io_writeb(QPCIDevice *dev, void *data, uint8_t value); void qpci_io_writew(QPCIDevice *dev, void *data, uint16_t value); void qpci_io_writel(QPCIDevice *dev, void *data, uint32_t value); +void qpci_memread(QPCIDevice *bus, void *data, void *buf, size_t len); +void qpci_memwrite(QPCIDevice *bus, void *data, const void *buf, size_t len); + void *qpci_iomap(QPCIDevice *dev, int barno, uint64_t *sizeptr); void qpci_iounmap(QPCIDevice *dev, void *data); void *qpci_legacy_iomap(QPCIDevice *dev, uint16_t addr); From 352d664cce514a94228fbf6e05d03920b2d6bd69 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Wed, 19 Oct 2016 14:20:44 +1100 Subject: [PATCH 57/73] libqos: Implement mmio accessors in terms of mem{read,write} In the libqos PCI code we now have accessors both for registers (byte significance preserving) and for streaming data (byte address order preserving). These exist in both the interface for qtest drivers and in the machine specific backends. However, the register-style accessors aren't actually necessary in the backend. They can be implemented in terms of the byte address order preserving accessors by the libqos wrappers. This works because PCI is always little endian. This does assume that the back end byte address order preserving accessors will perform the equivalent of a single bus transaction for short lengths. This is the case, and in fact they currently end up using the same cpu_physical_memory_rw() implementation within the qtest accelerator. Signed-off-by: David Gibson Reviewed-by: Laurent Vivier Reviewed-by: Greg Kurz --- tests/libqos/pci-pc.c | 38 ---------------------------------- tests/libqos/pci-spapr.c | 44 ---------------------------------------- tests/libqos/pci.c | 20 ++++++++++++------ tests/libqos/pci.h | 8 -------- 4 files changed, 14 insertions(+), 96 deletions(-) diff --git a/tests/libqos/pci-pc.c b/tests/libqos/pci-pc.c index 84aee25350..849ea56da4 100644 --- a/tests/libqos/pci-pc.c +++ b/tests/libqos/pci-pc.c @@ -32,61 +32,31 @@ static uint8_t qpci_pc_pio_readb(QPCIBus *bus, uint32_t addr) return inb(addr); } -static uint8_t qpci_pc_mmio_readb(QPCIBus *bus, uint32_t addr) -{ - return readb(addr); -} - static void qpci_pc_pio_writeb(QPCIBus *bus, uint32_t addr, uint8_t val) { outb(addr, val); } -static void qpci_pc_mmio_writeb(QPCIBus *bus, uint32_t addr, uint8_t val) -{ - writeb(addr, val); -} - static uint16_t qpci_pc_pio_readw(QPCIBus *bus, uint32_t addr) { return inw(addr); } -static uint16_t qpci_pc_mmio_readw(QPCIBus *bus, uint32_t addr) -{ - return readw(addr); -} - static void qpci_pc_pio_writew(QPCIBus *bus, uint32_t addr, uint16_t val) { outw(addr, val); } -static void qpci_pc_mmio_writew(QPCIBus *bus, uint32_t addr, uint16_t val) -{ - writew(addr, val); -} - static uint32_t qpci_pc_pio_readl(QPCIBus *bus, uint32_t addr) { return inl(addr); } -static uint32_t qpci_pc_mmio_readl(QPCIBus *bus, uint32_t addr) -{ - return readl(addr); -} - static void qpci_pc_pio_writel(QPCIBus *bus, uint32_t addr, uint32_t val) { outl(addr, val); } -static void qpci_pc_mmio_writel(QPCIBus *bus, uint32_t addr, uint32_t val) -{ - writel(addr, val); -} - static void qpci_pc_memread(QPCIBus *bus, uint32_t addr, void *buf, size_t len) { memread(addr, buf, len); @@ -148,14 +118,6 @@ QPCIBus *qpci_init_pc(QGuestAllocator *alloc) ret->bus.pio_writew = qpci_pc_pio_writew; ret->bus.pio_writel = qpci_pc_pio_writel; - ret->bus.mmio_readb = qpci_pc_mmio_readb; - ret->bus.mmio_readw = qpci_pc_mmio_readw; - ret->bus.mmio_readl = qpci_pc_mmio_readl; - - ret->bus.mmio_writeb = qpci_pc_mmio_writeb; - ret->bus.mmio_writew = qpci_pc_mmio_writew; - ret->bus.mmio_writel = qpci_pc_mmio_writel; - ret->bus.memread = qpci_pc_memread; ret->bus.memwrite = qpci_pc_memwrite; diff --git a/tests/libqos/pci-spapr.c b/tests/libqos/pci-spapr.c index ad12c2e582..f26488ae5e 100644 --- a/tests/libqos/pci-spapr.c +++ b/tests/libqos/pci-spapr.c @@ -48,72 +48,36 @@ static uint8_t qpci_spapr_pio_readb(QPCIBus *bus, uint32_t addr) return readb(s->pio_cpu_base + addr); } -static uint8_t qpci_spapr_mmio32_readb(QPCIBus *bus, uint32_t addr) -{ - QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - return readb(s->mmio32_cpu_base + addr); -} - static void qpci_spapr_pio_writeb(QPCIBus *bus, uint32_t addr, uint8_t val) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); writeb(s->pio_cpu_base + addr, val); } -static void qpci_spapr_mmio32_writeb(QPCIBus *bus, uint32_t addr, uint8_t val) -{ - QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - writeb(s->mmio32_cpu_base + addr, val); -} - static uint16_t qpci_spapr_pio_readw(QPCIBus *bus, uint32_t addr) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); return bswap16(readw(s->pio_cpu_base + addr)); } -static uint16_t qpci_spapr_mmio32_readw(QPCIBus *bus, uint32_t addr) -{ - QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - return bswap16(readw(s->mmio32_cpu_base + addr)); -} - static void qpci_spapr_pio_writew(QPCIBus *bus, uint32_t addr, uint16_t val) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); writew(s->pio_cpu_base + addr, bswap16(val)); } -static void qpci_spapr_mmio32_writew(QPCIBus *bus, uint32_t addr, uint16_t val) -{ - QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - writew(s->mmio32_cpu_base + addr, bswap16(val)); -} - static uint32_t qpci_spapr_pio_readl(QPCIBus *bus, uint32_t addr) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); return bswap32(readl(s->pio_cpu_base + addr)); } -static uint32_t qpci_spapr_mmio32_readl(QPCIBus *bus, uint32_t addr) -{ - QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - return bswap32(readl(s->mmio32_cpu_base + addr)); -} - static void qpci_spapr_pio_writel(QPCIBus *bus, uint32_t addr, uint32_t val) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); writel(s->pio_cpu_base + addr, bswap32(val)); } -static void qpci_spapr_mmio32_writel(QPCIBus *bus, uint32_t addr, uint32_t val) -{ - QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); - writel(s->mmio32_cpu_base + addr, bswap32(val)); -} - static void qpci_spapr_memread(QPCIBus *bus, uint32_t addr, void *buf, size_t len) { @@ -194,14 +158,6 @@ QPCIBus *qpci_init_spapr(QGuestAllocator *alloc) ret->bus.pio_writew = qpci_spapr_pio_writew; ret->bus.pio_writel = qpci_spapr_pio_writel; - ret->bus.mmio_readb = qpci_spapr_mmio32_readb; - ret->bus.mmio_readw = qpci_spapr_mmio32_readw; - ret->bus.mmio_readl = qpci_spapr_mmio32_readl; - - ret->bus.mmio_writeb = qpci_spapr_mmio32_writeb; - ret->bus.mmio_writew = qpci_spapr_mmio32_writew; - ret->bus.mmio_writel = qpci_spapr_mmio32_writel; - ret->bus.memread = qpci_spapr_memread; ret->bus.memwrite = qpci_spapr_memwrite; diff --git a/tests/libqos/pci.c b/tests/libqos/pci.c index 146b06311c..bdffeb3ec2 100644 --- a/tests/libqos/pci.c +++ b/tests/libqos/pci.c @@ -230,7 +230,9 @@ uint8_t qpci_io_readb(QPCIDevice *dev, void *data) if (addr < QPCI_PIO_LIMIT) { return dev->bus->pio_readb(dev->bus, addr); } else { - return dev->bus->mmio_readb(dev->bus, addr); + uint8_t val; + dev->bus->memread(dev->bus, addr, &val, sizeof(val)); + return val; } } @@ -241,7 +243,9 @@ uint16_t qpci_io_readw(QPCIDevice *dev, void *data) if (addr < QPCI_PIO_LIMIT) { return dev->bus->pio_readw(dev->bus, addr); } else { - return dev->bus->mmio_readw(dev->bus, addr); + uint16_t val; + dev->bus->memread(dev->bus, addr, &val, sizeof(val)); + return le16_to_cpu(val); } } @@ -252,7 +256,9 @@ uint32_t qpci_io_readl(QPCIDevice *dev, void *data) if (addr < QPCI_PIO_LIMIT) { return dev->bus->pio_readl(dev->bus, addr); } else { - return dev->bus->mmio_readl(dev->bus, addr); + uint32_t val; + dev->bus->memread(dev->bus, addr, &val, sizeof(val)); + return le32_to_cpu(val); } } @@ -263,7 +269,7 @@ void qpci_io_writeb(QPCIDevice *dev, void *data, uint8_t value) if (addr < QPCI_PIO_LIMIT) { dev->bus->pio_writeb(dev->bus, addr, value); } else { - dev->bus->mmio_writeb(dev->bus, addr, value); + dev->bus->memwrite(dev->bus, addr, &value, sizeof(value)); } } @@ -274,7 +280,8 @@ void qpci_io_writew(QPCIDevice *dev, void *data, uint16_t value) if (addr < QPCI_PIO_LIMIT) { dev->bus->pio_writew(dev->bus, addr, value); } else { - dev->bus->mmio_writew(dev->bus, addr, value); + value = cpu_to_le16(value); + dev->bus->memwrite(dev->bus, addr, &value, sizeof(value)); } } @@ -285,7 +292,8 @@ void qpci_io_writel(QPCIDevice *dev, void *data, uint32_t value) if (addr < QPCI_PIO_LIMIT) { dev->bus->pio_writel(dev->bus, addr, value); } else { - dev->bus->mmio_writel(dev->bus, addr, value); + value = cpu_to_le32(value); + dev->bus->memwrite(dev->bus, addr, &value, sizeof(value)); } } diff --git a/tests/libqos/pci.h b/tests/libqos/pci.h index 2b083624ef..ce6ed08f2a 100644 --- a/tests/libqos/pci.h +++ b/tests/libqos/pci.h @@ -27,18 +27,10 @@ struct QPCIBus { uint16_t (*pio_readw)(QPCIBus *bus, uint32_t addr); uint32_t (*pio_readl)(QPCIBus *bus, uint32_t addr); - uint8_t (*mmio_readb)(QPCIBus *bus, uint32_t addr); - uint16_t (*mmio_readw)(QPCIBus *bus, uint32_t addr); - uint32_t (*mmio_readl)(QPCIBus *bus, uint32_t addr); - void (*pio_writeb)(QPCIBus *bus, uint32_t addr, uint8_t value); void (*pio_writew)(QPCIBus *bus, uint32_t addr, uint16_t value); void (*pio_writel)(QPCIBus *bus, uint32_t addr, uint32_t value); - void (*mmio_writeb)(QPCIBus *bus, uint32_t addr, uint8_t value); - void (*mmio_writew)(QPCIBus *bus, uint32_t addr, uint16_t value); - void (*mmio_writel)(QPCIBus *bus, uint32_t addr, uint32_t value); - void (*memread)(QPCIBus *bus, uint32_t addr, void *buf, size_t len); void (*memwrite)(QPCIBus *bus, uint32_t addr, const void *buf, size_t len); From 9c268f8ae84ae18679ba2c3b16394e1828e9a006 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Fri, 21 Oct 2016 10:46:37 +1100 Subject: [PATCH 58/73] tests: Clean up IO handling in ide-test ide-test uses many explicit inb() / outb() operations for its IO, which means it's not portable to non-x86 platforms. This cleans it up to use the libqos PCI accessors instead. Signed-off-by: David Gibson Reviewed-by: Greg Kurz --- tests/ide-test.c | 179 +++++++++++++++++++++++++++++++---------------- 1 file changed, 118 insertions(+), 61 deletions(-) diff --git a/tests/ide-test.c b/tests/ide-test.c index a8a4081f78..86c4373792 100644 --- a/tests/ide-test.c +++ b/tests/ide-test.c @@ -137,7 +137,7 @@ static void ide_test_quit(void) qtest_end(); } -static QPCIDevice *get_pci_device(uint16_t *bmdma_base) +static QPCIDevice *get_pci_device(void **bmdma_base, void **ide_base) { QPCIDevice *dev; uint16_t vendor_id, device_id; @@ -156,7 +156,9 @@ static QPCIDevice *get_pci_device(uint16_t *bmdma_base) g_assert(device_id == PCI_DEVICE_ID_INTEL_82371SB_1); /* Map bmdma BAR */ - *bmdma_base = (uint16_t)(uintptr_t) qpci_iomap(dev, 4, NULL); + *bmdma_base = qpci_iomap(dev, 4, NULL); + + *ide_base = qpci_legacy_iomap(dev, IDE_BASE); qpci_device_enable(dev); @@ -179,17 +181,19 @@ typedef struct PrdtEntry { static int send_dma_request(int cmd, uint64_t sector, int nb_sectors, PrdtEntry *prdt, int prdt_entries, - void(*post_exec)(uint64_t sector, int nb_sectors)) + void(*post_exec)(QPCIDevice *dev, void *ide_base, + uint64_t sector, int nb_sectors)) { QPCIDevice *dev; - uint16_t bmdma_base; + void *bmdma_base; + void *ide_base; uintptr_t guest_prdt; size_t len; bool from_dev; uint8_t status; int flags; - dev = get_pci_device(&bmdma_base); + dev = get_pci_device(&bmdma_base, &ide_base); flags = cmd & ~0xff; cmd &= 0xff; @@ -214,59 +218,60 @@ static int send_dma_request(int cmd, uint64_t sector, int nb_sectors, } /* Select device 0 */ - outb(IDE_BASE + reg_device, 0 | LBA); + qpci_io_writeb(dev, ide_base + reg_device, 0 | LBA); /* Stop any running transfer, clear any pending interrupt */ - outb(bmdma_base + bmreg_cmd, 0); - outb(bmdma_base + bmreg_status, BM_STS_INTR); + qpci_io_writeb(dev, bmdma_base + bmreg_cmd, 0); + qpci_io_writeb(dev, bmdma_base + bmreg_status, BM_STS_INTR); /* Setup PRDT */ len = sizeof(*prdt) * prdt_entries; guest_prdt = guest_alloc(guest_malloc, len); memwrite(guest_prdt, prdt, len); - outl(bmdma_base + bmreg_prdt, guest_prdt); + qpci_io_writel(dev, bmdma_base + bmreg_prdt, guest_prdt); /* ATA DMA command */ if (cmd == CMD_PACKET) { /* Enables ATAPI DMA; otherwise PIO is attempted */ - outb(IDE_BASE + reg_feature, 0x01); + qpci_io_writeb(dev, ide_base + reg_feature, 0x01); } else { - outb(IDE_BASE + reg_nsectors, nb_sectors); - outb(IDE_BASE + reg_lba_low, sector & 0xff); - outb(IDE_BASE + reg_lba_middle, (sector >> 8) & 0xff); - outb(IDE_BASE + reg_lba_high, (sector >> 16) & 0xff); + qpci_io_writeb(dev, ide_base + reg_nsectors, nb_sectors); + qpci_io_writeb(dev, ide_base + reg_lba_low, sector & 0xff); + qpci_io_writeb(dev, ide_base + reg_lba_middle, (sector >> 8) & 0xff); + qpci_io_writeb(dev, ide_base + reg_lba_high, (sector >> 16) & 0xff); } - outb(IDE_BASE + reg_command, cmd); + qpci_io_writeb(dev, ide_base + reg_command, cmd); if (post_exec) { - post_exec(sector, nb_sectors); + post_exec(dev, ide_base, sector, nb_sectors); } /* Start DMA transfer */ - outb(bmdma_base + bmreg_cmd, BM_CMD_START | (from_dev ? BM_CMD_WRITE : 0)); + qpci_io_writeb(dev, bmdma_base + bmreg_cmd, + BM_CMD_START | (from_dev ? BM_CMD_WRITE : 0)); if (flags & CMDF_ABORT) { - outb(bmdma_base + bmreg_cmd, 0); + qpci_io_writeb(dev, bmdma_base + bmreg_cmd, 0); } /* Wait for the DMA transfer to complete */ do { - status = inb(bmdma_base + bmreg_status); + status = qpci_io_readb(dev, bmdma_base + bmreg_status); } while ((status & (BM_STS_ACTIVE | BM_STS_INTR)) == BM_STS_ACTIVE); g_assert_cmpint(get_irq(IDE_PRIMARY_IRQ), ==, !!(status & BM_STS_INTR)); /* Check IDE status code */ - assert_bit_set(inb(IDE_BASE + reg_status), DRDY); - assert_bit_clear(inb(IDE_BASE + reg_status), BSY | DRQ); + assert_bit_set(qpci_io_readb(dev, ide_base + reg_status), DRDY); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), BSY | DRQ); /* Reading the status register clears the IRQ */ g_assert(!get_irq(IDE_PRIMARY_IRQ)); /* Stop DMA transfer if still active */ if (status & BM_STS_ACTIVE) { - outb(bmdma_base + bmreg_cmd, 0); + qpci_io_writeb(dev, bmdma_base + bmreg_cmd, 0); } free_pci_device(dev); @@ -276,6 +281,8 @@ static int send_dma_request(int cmd, uint64_t sector, int nb_sectors, static void test_bmdma_simple_rw(void) { + QPCIDevice *dev; + void *bmdma_base, *ide_base; uint8_t status; uint8_t *buf; uint8_t *cmpbuf; @@ -289,6 +296,8 @@ static void test_bmdma_simple_rw(void) }, }; + dev = get_pci_device(&bmdma_base, &ide_base); + buf = g_malloc(len); cmpbuf = g_malloc(len); @@ -299,7 +308,7 @@ static void test_bmdma_simple_rw(void) status = send_dma_request(CMD_WRITE_DMA, 0, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_INTR); - assert_bit_clear(inb(IDE_BASE + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); /* Write 0xaa pattern to sector 1 */ memset(buf, 0xaa, len); @@ -308,14 +317,14 @@ static void test_bmdma_simple_rw(void) status = send_dma_request(CMD_WRITE_DMA, 1, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_INTR); - assert_bit_clear(inb(IDE_BASE + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); /* Read and verify 0x55 pattern in sector 0 */ memset(cmpbuf, 0x55, len); status = send_dma_request(CMD_READ_DMA, 0, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_INTR); - assert_bit_clear(inb(IDE_BASE + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); memread(guest_buf, buf, len); g_assert(memcmp(buf, cmpbuf, len) == 0); @@ -325,7 +334,7 @@ static void test_bmdma_simple_rw(void) status = send_dma_request(CMD_READ_DMA, 1, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_INTR); - assert_bit_clear(inb(IDE_BASE + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); memread(guest_buf, buf, len); g_assert(memcmp(buf, cmpbuf, len) == 0); @@ -337,6 +346,8 @@ static void test_bmdma_simple_rw(void) static void test_bmdma_short_prdt(void) { + QPCIDevice *dev; + void *bmdma_base, *ide_base; uint8_t status; PrdtEntry prdt[] = { @@ -346,21 +357,25 @@ static void test_bmdma_short_prdt(void) }, }; + dev = get_pci_device(&bmdma_base, &ide_base); + /* Normal request */ status = send_dma_request(CMD_READ_DMA, 0, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, 0); - assert_bit_clear(inb(IDE_BASE + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); /* Abort the request before it completes */ status = send_dma_request(CMD_READ_DMA | CMDF_ABORT, 0, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, 0); - assert_bit_clear(inb(IDE_BASE + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); } static void test_bmdma_one_sector_short_prdt(void) { + QPCIDevice *dev; + void *bmdma_base, *ide_base; uint8_t status; /* Read 2 sectors but only give 1 sector in PRDT */ @@ -371,21 +386,25 @@ static void test_bmdma_one_sector_short_prdt(void) }, }; + dev = get_pci_device(&bmdma_base, &ide_base); + /* Normal request */ status = send_dma_request(CMD_READ_DMA, 0, 2, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, 0); - assert_bit_clear(inb(IDE_BASE + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); /* Abort the request before it completes */ status = send_dma_request(CMD_READ_DMA | CMDF_ABORT, 0, 2, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, 0); - assert_bit_clear(inb(IDE_BASE + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); } static void test_bmdma_long_prdt(void) { + QPCIDevice *dev; + void *bmdma_base, *ide_base; uint8_t status; PrdtEntry prdt[] = { @@ -395,23 +414,29 @@ static void test_bmdma_long_prdt(void) }, }; + dev = get_pci_device(&bmdma_base, &ide_base); + /* Normal request */ status = send_dma_request(CMD_READ_DMA, 0, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_ACTIVE | BM_STS_INTR); - assert_bit_clear(inb(IDE_BASE + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); /* Abort the request before it completes */ status = send_dma_request(CMD_READ_DMA | CMDF_ABORT, 0, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_INTR); - assert_bit_clear(inb(IDE_BASE + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); } static void test_bmdma_no_busmaster(void) { + QPCIDevice *dev; + void *bmdma_base, *ide_base; uint8_t status; + dev = get_pci_device(&bmdma_base, &ide_base); + /* No PRDT_EOT, each entry addr 0/size 64k, and in theory qemu shouldn't be * able to access it anyway because the Bus Master bit in the PCI command * register isn't set. This is complete nonsense, but it used to be pretty @@ -424,7 +449,7 @@ static void test_bmdma_no_busmaster(void) /* Not entirely clear what the expected result is, but this is what we get * in practice. At least we want to be aware of any changes. */ g_assert_cmphex(status, ==, BM_STS_ACTIVE | BM_STS_INTR); - assert_bit_clear(inb(IDE_BASE + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); } static void test_bmdma_setup(void) @@ -454,6 +479,8 @@ static void string_cpu_to_be16(uint16_t *s, size_t bytes) static void test_identify(void) { + QPCIDevice *dev; + void *bmdma_base, *ide_base; uint8_t data; uint16_t buf[256]; int i; @@ -464,23 +491,25 @@ static void test_identify(void) "-global ide-hd.ver=%s", tmp_path, "testdisk", "version"); + dev = get_pci_device(&bmdma_base, &ide_base); + /* IDENTIFY command on device 0*/ - outb(IDE_BASE + reg_device, 0); - outb(IDE_BASE + reg_command, CMD_IDENTIFY); + qpci_io_writeb(dev, ide_base + reg_device, 0); + qpci_io_writeb(dev, ide_base + reg_command, CMD_IDENTIFY); /* Read in the IDENTIFY buffer and check registers */ - data = inb(IDE_BASE + reg_device); + data = qpci_io_readb(dev, ide_base + reg_device); g_assert_cmpint(data & DEV, ==, 0); for (i = 0; i < 256; i++) { - data = inb(IDE_BASE + reg_status); + data = qpci_io_readb(dev, ide_base + reg_status); assert_bit_set(data, DRDY | DRQ); assert_bit_clear(data, BSY | DF | ERR); - ((uint16_t*) buf)[i] = inw(IDE_BASE + reg_data); + buf[i] = qpci_io_readw(dev, ide_base + reg_data); } - data = inb(IDE_BASE + reg_status); + data = qpci_io_readb(dev, ide_base + reg_status); assert_bit_set(data, DRDY); assert_bit_clear(data, BSY | DF | ERR | DRQ); @@ -505,11 +534,15 @@ static void test_identify(void) */ static void make_dirty(uint8_t device) { + QPCIDevice *dev; + void *bmdma_base, *ide_base; uint8_t status; size_t len = 512; uintptr_t guest_buf; void* buf; + dev = get_pci_device(&bmdma_base, &ide_base); + guest_buf = guest_alloc(guest_malloc, len); buf = g_malloc(len); g_assert(guest_buf); @@ -527,19 +560,23 @@ static void make_dirty(uint8_t device) status = send_dma_request(CMD_WRITE_DMA, 1, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_INTR); - assert_bit_clear(inb(IDE_BASE + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); g_free(buf); } static void test_flush(void) { + QPCIDevice *dev; + void *bmdma_base, *ide_base; uint8_t data; ide_test_start( "-drive file=blkdebug::%s,if=ide,cache=writeback,format=raw", tmp_path); + dev = get_pci_device(&bmdma_base, &ide_base); + qtest_irq_intercept_in(global_qtest, "ioapic"); /* Dirty media so that CMD_FLUSH_CACHE will actually go to disk */ @@ -549,11 +586,11 @@ static void test_flush(void) g_free(hmp("qemu-io ide0-hd0 \"break flush_to_os A\"")); /* FLUSH CACHE command on device 0*/ - outb(IDE_BASE + reg_device, 0); - outb(IDE_BASE + reg_command, CMD_FLUSH_CACHE); + qpci_io_writeb(dev, ide_base + reg_device, 0); + qpci_io_writeb(dev, ide_base + reg_command, CMD_FLUSH_CACHE); /* Check status while request is in flight*/ - data = inb(IDE_BASE + reg_status); + data = qpci_io_readb(dev, ide_base + reg_status); assert_bit_set(data, BSY | DRDY); assert_bit_clear(data, DF | ERR | DRQ); @@ -561,11 +598,11 @@ static void test_flush(void) g_free(hmp("qemu-io ide0-hd0 \"resume A\"")); /* Check registers */ - data = inb(IDE_BASE + reg_device); + data = qpci_io_readb(dev, ide_base + reg_device); g_assert_cmpint(data & DEV, ==, 0); do { - data = inb(IDE_BASE + reg_status); + data = qpci_io_readb(dev, ide_base + reg_status); } while (data & BSY); assert_bit_set(data, DRDY); @@ -576,6 +613,8 @@ static void test_flush(void) static void test_retry_flush(const char *machine) { + QPCIDevice *dev; + void *bmdma_base, *ide_base; uint8_t data; const char *s; @@ -587,17 +626,19 @@ static void test_retry_flush(const char *machine) "rerror=stop,werror=stop", debug_path, tmp_path); + dev = get_pci_device(&bmdma_base, &ide_base); + qtest_irq_intercept_in(global_qtest, "ioapic"); /* Dirty media so that CMD_FLUSH_CACHE will actually go to disk */ make_dirty(0); /* FLUSH CACHE command on device 0*/ - outb(IDE_BASE + reg_device, 0); - outb(IDE_BASE + reg_command, CMD_FLUSH_CACHE); + qpci_io_writeb(dev, ide_base + reg_device, 0); + qpci_io_writeb(dev, ide_base + reg_command, CMD_FLUSH_CACHE); /* Check status while request is in flight*/ - data = inb(IDE_BASE + reg_status); + data = qpci_io_readb(dev, ide_base + reg_status); assert_bit_set(data, BSY | DRDY); assert_bit_clear(data, DF | ERR | DRQ); @@ -608,11 +649,11 @@ static void test_retry_flush(const char *machine) qmp_discard_response(s); /* Check registers */ - data = inb(IDE_BASE + reg_device); + data = qpci_io_readb(dev, ide_base + reg_device); g_assert_cmpint(data & DEV, ==, 0); do { - data = inb(IDE_BASE + reg_status); + data = qpci_io_readb(dev, ide_base + reg_status); } while (data & BSY); assert_bit_set(data, DRDY); @@ -623,11 +664,16 @@ static void test_retry_flush(const char *machine) static void test_flush_nodev(void) { + QPCIDevice *dev; + void *bmdma_base, *ide_base; + ide_test_start(""); + dev = get_pci_device(&bmdma_base, &ide_base); + /* FLUSH CACHE command on device 0*/ - outb(IDE_BASE + reg_device, 0); - outb(IDE_BASE + reg_command, CMD_FLUSH_CACHE); + qpci_io_writeb(dev, ide_base + reg_device, 0); + qpci_io_writeb(dev, ide_base + reg_command, CMD_FLUSH_CACHE); /* Just testing that qemu doesn't crash... */ @@ -654,7 +700,8 @@ typedef struct Read10CDB { uint16_t padding; } __attribute__((__packed__)) Read10CDB; -static void send_scsi_cdb_read10(uint64_t lba, int nblocks) +static void send_scsi_cdb_read10(QPCIDevice *dev, void *ide_base, + uint64_t lba, int nblocks) { Read10CDB pkt = { .padding = 0 }; int i; @@ -670,7 +717,8 @@ static void send_scsi_cdb_read10(uint64_t lba, int nblocks) /* Send Packet */ for (i = 0; i < sizeof(Read10CDB)/2; i++) { - outw(IDE_BASE + reg_data, cpu_to_le16(((uint16_t *)&pkt)[i])); + qpci_io_writew(dev, ide_base + reg_data, + le16_to_cpu(((uint16_t *)&pkt)[i])); } } @@ -683,13 +731,17 @@ static void nsleep(int64_t nsecs) static uint8_t ide_wait_clear(uint8_t flag) { + QPCIDevice *dev; + void *bmdma_base, *ide_base; uint8_t data; time_t st; + dev = get_pci_device(&bmdma_base, &ide_base); + /* Wait with a 5 second timeout */ time(&st); while (true) { - data = inb(IDE_BASE + reg_status); + data = qpci_io_readb(dev, ide_base + reg_status); if (!(data & flag)) { return data; } @@ -723,6 +775,8 @@ static void ide_wait_intr(int irq) static void cdrom_pio_impl(int nblocks) { + QPCIDevice *dev; + void *bmdma_base, *ide_base; FILE *fh; int patt_blocks = MAX(16, nblocks); size_t patt_len = ATAPI_BLOCK_SIZE * patt_blocks; @@ -741,13 +795,15 @@ static void cdrom_pio_impl(int nblocks) ide_test_start("-drive if=none,file=%s,media=cdrom,format=raw,id=sr0,index=0 " "-device ide-cd,drive=sr0,bus=ide.0", tmp_path); + dev = get_pci_device(&bmdma_base, &ide_base); qtest_irq_intercept_in(global_qtest, "ioapic"); /* PACKET command on device 0 */ - outb(IDE_BASE + reg_device, 0); - outb(IDE_BASE + reg_lba_middle, BYTE_COUNT_LIMIT & 0xFF); - outb(IDE_BASE + reg_lba_high, (BYTE_COUNT_LIMIT >> 8 & 0xFF)); - outb(IDE_BASE + reg_command, CMD_PACKET); + qpci_io_writeb(dev, ide_base + reg_device, 0); + qpci_io_writeb(dev, ide_base + reg_lba_middle, BYTE_COUNT_LIMIT & 0xFF); + qpci_io_writeb(dev, ide_base + reg_lba_high, + (BYTE_COUNT_LIMIT >> 8 & 0xFF)); + qpci_io_writeb(dev, ide_base + reg_command, CMD_PACKET); /* HP0: Check_Status_A State */ nsleep(400); data = ide_wait_clear(BSY); @@ -756,7 +812,7 @@ static void cdrom_pio_impl(int nblocks) assert_bit_clear(data, ERR | DF | BSY); /* SCSI CDB (READ10) -- read n*2048 bytes from block 0 */ - send_scsi_cdb_read10(0, nblocks); + send_scsi_cdb_read10(dev, ide_base, 0, nblocks); /* Read data back: occurs in bursts of 'BYTE_COUNT_LIMIT' bytes. * If BYTE_COUNT_LIMIT is odd, we transfer BYTE_COUNT_LIMIT - 1 bytes. @@ -780,7 +836,8 @@ static void cdrom_pio_impl(int nblocks) /* HP4: Transfer_Data */ for (j = 0; j < MIN((limit / 2), rem); j++) { - rx[offset + j] = le16_to_cpu(inw(IDE_BASE + reg_data)); + rx[offset + j] = cpu_to_le16(qpci_io_readw(dev, + ide_base + reg_data)); } } From f775f45ab866f8e2d26720de9cb3c8f0ba5684d3 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Wed, 19 Oct 2016 15:00:21 +1100 Subject: [PATCH 59/73] libqos: Add 64-bit PCI IO accessors Currently the libqos PCI layer includes accessor helpers for 8, 16 and 32 bit reads and writes. It's likely that we'll want 64-bit accesses in the future (plenty of modern peripherals will have 64-bit reigsters). This adds them. For PIO (not MMIO) accesses on the PC backend, this is implemented as two 32-bit ins or outs. That's not ideal but AFAICT x86 doesn't have 64-bit versions of in and out. This patch also converts the single current user of 64-bit accesses - virtio-pci.c to use the new mechanism, rather than a sequence of 8 byte reads. Signed-off-by: David Gibson Reviewed-by: Laurent Vivier Reviewed-by: Greg Kurz --- tests/libqos/pci-pc.c | 13 +++++++++++++ tests/libqos/pci-spapr.c | 14 ++++++++++++++ tests/libqos/pci.c | 25 +++++++++++++++++++++++++ tests/libqos/pci.h | 4 ++++ tests/libqos/virtio-pci.c | 16 ++++------------ 5 files changed, 60 insertions(+), 12 deletions(-) diff --git a/tests/libqos/pci-pc.c b/tests/libqos/pci-pc.c index 849ea56da4..ded1c54c06 100644 --- a/tests/libqos/pci-pc.c +++ b/tests/libqos/pci-pc.c @@ -57,6 +57,17 @@ static void qpci_pc_pio_writel(QPCIBus *bus, uint32_t addr, uint32_t val) outl(addr, val); } +static uint64_t qpci_pc_pio_readq(QPCIBus *bus, uint32_t addr) +{ + return (uint64_t)inl(addr) + ((uint64_t)inl(addr + 4) << 32); +} + +static void qpci_pc_pio_writeq(QPCIBus *bus, uint32_t addr, uint64_t val) +{ + outl(addr, val & 0xffffffff); + outl(addr + 4, val >> 32); +} + static void qpci_pc_memread(QPCIBus *bus, uint32_t addr, void *buf, size_t len) { memread(addr, buf, len); @@ -113,10 +124,12 @@ QPCIBus *qpci_init_pc(QGuestAllocator *alloc) ret->bus.pio_readb = qpci_pc_pio_readb; ret->bus.pio_readw = qpci_pc_pio_readw; ret->bus.pio_readl = qpci_pc_pio_readl; + ret->bus.pio_readq = qpci_pc_pio_readq; ret->bus.pio_writeb = qpci_pc_pio_writeb; ret->bus.pio_writew = qpci_pc_pio_writew; ret->bus.pio_writel = qpci_pc_pio_writel; + ret->bus.pio_writeq = qpci_pc_pio_writeq; ret->bus.memread = qpci_pc_memread; ret->bus.memwrite = qpci_pc_memwrite; diff --git a/tests/libqos/pci-spapr.c b/tests/libqos/pci-spapr.c index f26488ae5e..1e5d015bd4 100644 --- a/tests/libqos/pci-spapr.c +++ b/tests/libqos/pci-spapr.c @@ -78,6 +78,18 @@ static void qpci_spapr_pio_writel(QPCIBus *bus, uint32_t addr, uint32_t val) writel(s->pio_cpu_base + addr, bswap32(val)); } +static uint64_t qpci_spapr_pio_readq(QPCIBus *bus, uint32_t addr) +{ + QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); + return bswap64(readq(s->pio_cpu_base + addr)); +} + +static void qpci_spapr_pio_writeq(QPCIBus *bus, uint32_t addr, uint64_t val) +{ + QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); + writeq(s->pio_cpu_base + addr, bswap64(val)); +} + static void qpci_spapr_memread(QPCIBus *bus, uint32_t addr, void *buf, size_t len) { @@ -153,10 +165,12 @@ QPCIBus *qpci_init_spapr(QGuestAllocator *alloc) ret->bus.pio_readb = qpci_spapr_pio_readb; ret->bus.pio_readw = qpci_spapr_pio_readw; ret->bus.pio_readl = qpci_spapr_pio_readl; + ret->bus.pio_readq = qpci_spapr_pio_readq; ret->bus.pio_writeb = qpci_spapr_pio_writeb; ret->bus.pio_writew = qpci_spapr_pio_writew; ret->bus.pio_writel = qpci_spapr_pio_writel; + ret->bus.pio_writeq = qpci_spapr_pio_writeq; ret->bus.memread = qpci_spapr_memread; ret->bus.memwrite = qpci_spapr_memwrite; diff --git a/tests/libqos/pci.c b/tests/libqos/pci.c index bdffeb3ec2..3021651ee4 100644 --- a/tests/libqos/pci.c +++ b/tests/libqos/pci.c @@ -262,6 +262,19 @@ uint32_t qpci_io_readl(QPCIDevice *dev, void *data) } } +uint64_t qpci_io_readq(QPCIDevice *dev, void *data) +{ + uintptr_t addr = (uintptr_t)data; + + if (addr < QPCI_PIO_LIMIT) { + return dev->bus->pio_readq(dev->bus, addr); + } else { + uint64_t val; + dev->bus->memread(dev->bus, addr, &val, sizeof(val)); + return le64_to_cpu(val); + } +} + void qpci_io_writeb(QPCIDevice *dev, void *data, uint8_t value) { uintptr_t addr = (uintptr_t)data; @@ -297,6 +310,18 @@ void qpci_io_writel(QPCIDevice *dev, void *data, uint32_t value) } } +void qpci_io_writeq(QPCIDevice *dev, void *data, uint64_t value) +{ + uintptr_t addr = (uintptr_t)data; + + if (addr < QPCI_PIO_LIMIT) { + dev->bus->pio_writeq(dev->bus, addr, value); + } else { + value = cpu_to_le64(value); + dev->bus->memwrite(dev->bus, addr, &value, sizeof(value)); + } +} + void qpci_memread(QPCIDevice *dev, void *data, void *buf, size_t len) { uintptr_t addr = (uintptr_t)data; diff --git a/tests/libqos/pci.h b/tests/libqos/pci.h index ce6ed08f2a..531e3f79e9 100644 --- a/tests/libqos/pci.h +++ b/tests/libqos/pci.h @@ -26,10 +26,12 @@ struct QPCIBus { uint8_t (*pio_readb)(QPCIBus *bus, uint32_t addr); uint16_t (*pio_readw)(QPCIBus *bus, uint32_t addr); uint32_t (*pio_readl)(QPCIBus *bus, uint32_t addr); + uint64_t (*pio_readq)(QPCIBus *bus, uint32_t addr); void (*pio_writeb)(QPCIBus *bus, uint32_t addr, uint8_t value); void (*pio_writew)(QPCIBus *bus, uint32_t addr, uint16_t value); void (*pio_writel)(QPCIBus *bus, uint32_t addr, uint32_t value); + void (*pio_writeq)(QPCIBus *bus, uint32_t addr, uint64_t value); void (*memread)(QPCIBus *bus, uint32_t addr, void *buf, size_t len); void (*memwrite)(QPCIBus *bus, uint32_t addr, const void *buf, size_t len); @@ -82,10 +84,12 @@ void qpci_config_writel(QPCIDevice *dev, uint8_t offset, uint32_t value); uint8_t qpci_io_readb(QPCIDevice *dev, void *data); uint16_t qpci_io_readw(QPCIDevice *dev, void *data); uint32_t qpci_io_readl(QPCIDevice *dev, void *data); +uint64_t qpci_io_readq(QPCIDevice *dev, void *data); void qpci_io_writeb(QPCIDevice *dev, void *data, uint8_t value); void qpci_io_writew(QPCIDevice *dev, void *data, uint16_t value); void qpci_io_writel(QPCIDevice *dev, void *data, uint32_t value); +void qpci_io_writeq(QPCIDevice *dev, void *data, uint64_t value); void qpci_memread(QPCIDevice *bus, void *data, void *buf, size_t len); void qpci_memwrite(QPCIDevice *bus, void *data, const void *buf, size_t len); diff --git a/tests/libqos/virtio-pci.c b/tests/libqos/virtio-pci.c index fa82132ab7..c69d09ddb2 100644 --- a/tests/libqos/virtio-pci.c +++ b/tests/libqos/virtio-pci.c @@ -106,22 +106,14 @@ static uint32_t qvirtio_pci_config_readl(QVirtioDevice *d, uint64_t off) static uint64_t qvirtio_pci_config_readq(QVirtioDevice *d, uint64_t off) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - int i; - uint64_t u64 = 0; + uint64_t val; + val = qpci_io_readq(dev->pdev, CONFIG_BASE(dev) + off); if (qvirtio_is_big_endian(d)) { - for (i = 0; i < 8; ++i) { - u64 |= (uint64_t)qpci_io_readb(dev->pdev, CONFIG_BASE(dev) - + off + i) << (7 - i) * 8; - } - } else { - for (i = 0; i < 8; ++i) { - u64 |= (uint64_t)qpci_io_readb(dev->pdev, CONFIG_BASE(dev) - + off + i) << i * 8; - } + val = bswap64(val); } - return u64; + return val; } static uint32_t qvirtio_pci_get_features(QVirtioDevice *d) From 204e54b86d123d091f0b2d14541c491ece7b864f Mon Sep 17 00:00:00 2001 From: David Gibson Date: Tue, 18 Oct 2016 16:18:45 +1100 Subject: [PATCH 60/73] tests: Use qpci_mem{read,write} in ivshmem-test ivshmem implements a block of shared memory in a PCI BAR. Currently our test case accesses this using qtest_mem{read,write}. However, deducing the correct addresses for these requires making assumptions about the internel format returned by qpci_iomap(), along with some ugly casts. This patch changes the test to use the new qpci_mem{read,write} interfaces which is neater. Signed-off-by: David Gibson Reviewed-by: Laurent Vivier Reviewed-by: Greg Kurz --- tests/ivshmem-test.c | 35 +++++++++++++++++++++++++++-------- 1 file changed, 27 insertions(+), 8 deletions(-) diff --git a/tests/ivshmem-test.c b/tests/ivshmem-test.c index f36bfe7d0a..fbd8258c7b 100644 --- a/tests/ivshmem-test.c +++ b/tests/ivshmem-test.c @@ -93,6 +93,25 @@ static inline void out_reg(IVState *s, enum Reg reg, unsigned v) global_qtest = qtest; } +static inline void read_mem(IVState *s, uint64_t off, void *buf, size_t len) +{ + QTestState *qtest = global_qtest; + + global_qtest = s->qtest; + qpci_memread(s->dev, s->mem_base + off, buf, len); + global_qtest = qtest; +} + +static inline void write_mem(IVState *s, uint64_t off, + const void *buf, size_t len) +{ + QTestState *qtest = global_qtest; + + global_qtest = s->qtest; + qpci_memwrite(s->dev, s->mem_base + off, buf, len); + global_qtest = qtest; +} + static void cleanup_vm(IVState *s) { g_free(s->dev); @@ -169,7 +188,7 @@ static void test_ivshmem_single(void) for (i = 0; i < G_N_ELEMENTS(data); i++) { data[i] = i; } - qtest_memwrite(s->qtest, (uintptr_t)s->mem_base, data, sizeof(data)); + write_mem(s, 0, data, sizeof(data)); /* verify write */ for (i = 0; i < G_N_ELEMENTS(data); i++) { @@ -178,7 +197,7 @@ static void test_ivshmem_single(void) /* read it back and verify read */ memset(data, 0, sizeof(data)); - qtest_memread(s->qtest, (uintptr_t)s->mem_base, data, sizeof(data)); + read_mem(s, 0, data, sizeof(data)); for (i = 0; i < G_N_ELEMENTS(data); i++) { g_assert_cmpuint(data[i], ==, i); } @@ -201,29 +220,29 @@ static void test_ivshmem_pair(void) /* host write, guest 1 & 2 read */ memset(tmpshmem, 0x42, TMPSHMSIZE); - qtest_memread(s1->qtest, (uintptr_t)s1->mem_base, data, TMPSHMSIZE); + read_mem(s1, 0, data, TMPSHMSIZE); for (i = 0; i < TMPSHMSIZE; i++) { g_assert_cmpuint(data[i], ==, 0x42); } - qtest_memread(s2->qtest, (uintptr_t)s2->mem_base, data, TMPSHMSIZE); + read_mem(s2, 0, data, TMPSHMSIZE); for (i = 0; i < TMPSHMSIZE; i++) { g_assert_cmpuint(data[i], ==, 0x42); } /* guest 1 write, guest 2 read */ memset(data, 0x43, TMPSHMSIZE); - qtest_memwrite(s1->qtest, (uintptr_t)s1->mem_base, data, TMPSHMSIZE); + write_mem(s1, 0, data, TMPSHMSIZE); memset(data, 0, TMPSHMSIZE); - qtest_memread(s2->qtest, (uintptr_t)s2->mem_base, data, TMPSHMSIZE); + read_mem(s2, 0, data, TMPSHMSIZE); for (i = 0; i < TMPSHMSIZE; i++) { g_assert_cmpuint(data[i], ==, 0x43); } /* guest 2 write, guest 1 read */ memset(data, 0x44, TMPSHMSIZE); - qtest_memwrite(s2->qtest, (uintptr_t)s2->mem_base, data, TMPSHMSIZE); + write_mem(s2, 0, data, TMPSHMSIZE); memset(data, 0, TMPSHMSIZE); - qtest_memread(s1->qtest, (uintptr_t)s2->mem_base, data, TMPSHMSIZE); + read_mem(s1, 0, data, TMPSHMSIZE); for (i = 0; i < TMPSHMSIZE; i++) { g_assert_cmpuint(data[i], ==, 0x44); } From e7c8526b2a1482a9b14319fda9f8ad4bfda5b958 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Mon, 24 Oct 2016 15:50:22 +1100 Subject: [PATCH 61/73] tests: Don't assume structure of PCI IO base in ahci-test In a couple of places ahci-test makes assumptions about how the tokens returned from qpci_iomap() are formatted in ways it probably shouldn't. First in verify_state() it uses a non-NULL token to indicate that the AHCI device has been enabled (part of enabling is to iomap()). This changes it to use an explicit 'enabled' flag instead. Second, it uses the fact that the token contains a PCI address, stored when the BAR is mapped during initialization to check that the BAR has the same value after a migration. This changes it to explicitly read the BAR register before and after the migration and compare. Together, these changes will make the test more robust against changes to the internals of the libqos PCI layer. Signed-off-by: David Gibson Reviewed-by: John Snow Reviewed-by: Greg Kurz --- tests/ahci-test.c | 13 +++++++------ tests/libqos/ahci.c | 1 + tests/libqos/ahci.h | 1 + 3 files changed, 9 insertions(+), 6 deletions(-) diff --git a/tests/ahci-test.c b/tests/ahci-test.c index 9c0adce220..70bcafa9e4 100644 --- a/tests/ahci-test.c +++ b/tests/ahci-test.c @@ -78,25 +78,23 @@ static void string_bswap16(uint16_t *s, size_t bytes) /** * Verify that the transfer did not corrupt our state at all. */ -static void verify_state(AHCIQState *ahci) +static void verify_state(AHCIQState *ahci, uint64_t hba_old) { int i, j; uint32_t ahci_fingerprint; uint64_t hba_base; - uint64_t hba_stored; AHCICommandHeader cmd; ahci_fingerprint = qpci_config_readl(ahci->dev, PCI_VENDOR_ID); g_assert_cmphex(ahci_fingerprint, ==, ahci->fingerprint); /* If we haven't initialized, this is as much as can be validated. */ - if (!ahci->hba_base) { + if (!ahci->enabled) { return; } hba_base = (uint64_t)qpci_config_readl(ahci->dev, PCI_BASE_ADDRESS_5); - hba_stored = (uint64_t)(uintptr_t)ahci->hba_base; - g_assert_cmphex(hba_base, ==, hba_stored); + g_assert_cmphex(hba_base, ==, hba_old); g_assert_cmphex(ahci_rreg(ahci, AHCI_CAP), ==, ahci->cap); g_assert_cmphex(ahci_rreg(ahci, AHCI_CAP2), ==, ahci->cap2); @@ -119,12 +117,15 @@ static void ahci_migrate(AHCIQState *from, AHCIQState *to, const char *uri) QOSState *tmp = to->parent; QPCIDevice *dev = to->dev; char *uri_local = NULL; + uint64_t hba_old; if (uri == NULL) { uri_local = g_strdup_printf("%s%s", "unix:", mig_socket); uri = uri_local; } + hba_old = (uint64_t)qpci_config_readl(from->dev, PCI_BASE_ADDRESS_5); + /* context will be 'to' after completion. */ migrate(from->parent, to->parent, uri); @@ -141,7 +142,7 @@ static void ahci_migrate(AHCIQState *from, AHCIQState *to, const char *uri) from->parent = tmp; from->dev = dev; - verify_state(to); + verify_state(to, hba_old); g_free(uri_local); } diff --git a/tests/libqos/ahci.c b/tests/libqos/ahci.c index 716ab7939e..8e789d8407 100644 --- a/tests/libqos/ahci.c +++ b/tests/libqos/ahci.c @@ -351,6 +351,7 @@ void ahci_hba_enable(AHCIQState *ahci) reg = ahci_rreg(ahci, AHCI_GHC); ASSERT_BIT_SET(reg, AHCI_GHC_IE); + ahci->enabled = true; /* TODO: The device should now be idling and waiting for commands. * In the future, a small test-case to inspect the Register D2H FIS * and clear the initial interrupts might be good. */ diff --git a/tests/libqos/ahci.h b/tests/libqos/ahci.h index c69fb5ae90..9b0c1d705b 100644 --- a/tests/libqos/ahci.h +++ b/tests/libqos/ahci.h @@ -327,6 +327,7 @@ typedef struct AHCIQState { uint32_t cap; uint32_t cap2; AHCIPortQState port[32]; + bool enabled; } AHCIQState; /** From b4ba67d9a702507793c2724e56f98e9b0f7be02b Mon Sep 17 00:00:00 2001 From: David Gibson Date: Mon, 24 Oct 2016 15:52:06 +1100 Subject: [PATCH 62/73] libqos: Change PCI accessors to take opaque BAR handle The usual use model for the libqos PCI functions is to map a specific PCI BAR using qpci_iomap() then pass the returned token into IO accessor functions. This, and the fact that iomap() returns a (void *) which actually contains a PCI space address, kind of suggests that the return value from iomap is supposed to be an opaque token. ..except that the callers expect to be able to add offsets to it. Which also assumes the compiler will support pointer arithmetic on a (void *), and treat it as working with byte offsets. To clarify this situation change iomap() and the IO accessors to take a definitely opaque BAR handle (enforced with a wrapper struct) along with an offset within the BAR. This changes both the functions and all the callers. There were a number of places that checked if iomap() returned non-NULL, and or initialized it to NULL before hand. Since iomap() already assert()s if it fails to map the BAR, these tests were mostly pointless and are removed. Signed-off-by: David Gibson Reviewed-by: Greg Kurz --- tests/e1000e-test.c | 7 +- tests/ide-test.c | 176 +++++++++++++++++++------------------- tests/ivshmem-test.c | 16 ++-- tests/libqos/ahci.c | 3 +- tests/libqos/ahci.h | 6 +- tests/libqos/pci.c | 149 +++++++++++++++----------------- tests/libqos/pci.h | 42 +++++---- tests/libqos/usb.c | 6 +- tests/libqos/usb.h | 2 +- tests/libqos/virtio-pci.c | 95 ++++++++++---------- tests/libqos/virtio-pci.h | 2 +- tests/rtl8139-test.c | 10 +-- tests/tco-test.c | 80 ++++++++--------- tests/usb-hcd-ehci-test.c | 5 +- 14 files changed, 295 insertions(+), 304 deletions(-) diff --git a/tests/e1000e-test.c b/tests/e1000e-test.c index 3979b20bb0..8c42ca919f 100644 --- a/tests/e1000e-test.c +++ b/tests/e1000e-test.c @@ -87,7 +87,7 @@ typedef struct e1000e_device { QPCIDevice *pci_dev; - void *mac_regs; + QPCIBar mac_regs; uint64_t tx_ring; uint64_t rx_ring; @@ -119,12 +119,12 @@ static QPCIDevice *e1000e_device_find(QPCIBus *bus) static void e1000e_macreg_write(e1000e_device *d, uint32_t reg, uint32_t val) { - qpci_io_writel(d->pci_dev, d->mac_regs + reg, val); + qpci_io_writel(d->pci_dev, d->mac_regs, reg, val); } static uint32_t e1000e_macreg_read(e1000e_device *d, uint32_t reg) { - return qpci_io_readl(d->pci_dev, d->mac_regs + reg); + return qpci_io_readl(d->pci_dev, d->mac_regs, reg); } static void e1000e_device_init(QPCIBus *bus, e1000e_device *d) @@ -138,7 +138,6 @@ static void e1000e_device_init(QPCIBus *bus, e1000e_device *d) /* Map BAR0 (mac registers) */ d->mac_regs = qpci_iomap(d->pci_dev, 0, NULL); - g_assert_nonnull(d->mac_regs); /* Reset the device */ val = e1000e_macreg_read(d, E1000E_CTRL); diff --git a/tests/ide-test.c b/tests/ide-test.c index 86c4373792..67c7df0c8d 100644 --- a/tests/ide-test.c +++ b/tests/ide-test.c @@ -137,7 +137,7 @@ static void ide_test_quit(void) qtest_end(); } -static QPCIDevice *get_pci_device(void **bmdma_base, void **ide_base) +static QPCIDevice *get_pci_device(QPCIBar *bmdma_bar, QPCIBar *ide_bar) { QPCIDevice *dev; uint16_t vendor_id, device_id; @@ -156,9 +156,9 @@ static QPCIDevice *get_pci_device(void **bmdma_base, void **ide_base) g_assert(device_id == PCI_DEVICE_ID_INTEL_82371SB_1); /* Map bmdma BAR */ - *bmdma_base = qpci_iomap(dev, 4, NULL); + *bmdma_bar = qpci_iomap(dev, 4, NULL); - *ide_base = qpci_legacy_iomap(dev, IDE_BASE); + *ide_bar = qpci_legacy_iomap(dev, IDE_BASE); qpci_device_enable(dev); @@ -181,19 +181,18 @@ typedef struct PrdtEntry { static int send_dma_request(int cmd, uint64_t sector, int nb_sectors, PrdtEntry *prdt, int prdt_entries, - void(*post_exec)(QPCIDevice *dev, void *ide_base, + void(*post_exec)(QPCIDevice *dev, QPCIBar ide_bar, uint64_t sector, int nb_sectors)) { QPCIDevice *dev; - void *bmdma_base; - void *ide_base; + QPCIBar bmdma_bar, ide_bar; uintptr_t guest_prdt; size_t len; bool from_dev; uint8_t status; int flags; - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); flags = cmd & ~0xff; cmd &= 0xff; @@ -218,60 +217,60 @@ static int send_dma_request(int cmd, uint64_t sector, int nb_sectors, } /* Select device 0 */ - qpci_io_writeb(dev, ide_base + reg_device, 0 | LBA); + qpci_io_writeb(dev, ide_bar, reg_device, 0 | LBA); /* Stop any running transfer, clear any pending interrupt */ - qpci_io_writeb(dev, bmdma_base + bmreg_cmd, 0); - qpci_io_writeb(dev, bmdma_base + bmreg_status, BM_STS_INTR); + qpci_io_writeb(dev, bmdma_bar, bmreg_cmd, 0); + qpci_io_writeb(dev, bmdma_bar, bmreg_status, BM_STS_INTR); /* Setup PRDT */ len = sizeof(*prdt) * prdt_entries; guest_prdt = guest_alloc(guest_malloc, len); memwrite(guest_prdt, prdt, len); - qpci_io_writel(dev, bmdma_base + bmreg_prdt, guest_prdt); + qpci_io_writel(dev, bmdma_bar, bmreg_prdt, guest_prdt); /* ATA DMA command */ if (cmd == CMD_PACKET) { /* Enables ATAPI DMA; otherwise PIO is attempted */ - qpci_io_writeb(dev, ide_base + reg_feature, 0x01); + qpci_io_writeb(dev, ide_bar, reg_feature, 0x01); } else { - qpci_io_writeb(dev, ide_base + reg_nsectors, nb_sectors); - qpci_io_writeb(dev, ide_base + reg_lba_low, sector & 0xff); - qpci_io_writeb(dev, ide_base + reg_lba_middle, (sector >> 8) & 0xff); - qpci_io_writeb(dev, ide_base + reg_lba_high, (sector >> 16) & 0xff); + qpci_io_writeb(dev, ide_bar, reg_nsectors, nb_sectors); + qpci_io_writeb(dev, ide_bar, reg_lba_low, sector & 0xff); + qpci_io_writeb(dev, ide_bar, reg_lba_middle, (sector >> 8) & 0xff); + qpci_io_writeb(dev, ide_bar, reg_lba_high, (sector >> 16) & 0xff); } - qpci_io_writeb(dev, ide_base + reg_command, cmd); + qpci_io_writeb(dev, ide_bar, reg_command, cmd); if (post_exec) { - post_exec(dev, ide_base, sector, nb_sectors); + post_exec(dev, ide_bar, sector, nb_sectors); } /* Start DMA transfer */ - qpci_io_writeb(dev, bmdma_base + bmreg_cmd, + qpci_io_writeb(dev, bmdma_bar, bmreg_cmd, BM_CMD_START | (from_dev ? BM_CMD_WRITE : 0)); if (flags & CMDF_ABORT) { - qpci_io_writeb(dev, bmdma_base + bmreg_cmd, 0); + qpci_io_writeb(dev, bmdma_bar, bmreg_cmd, 0); } /* Wait for the DMA transfer to complete */ do { - status = qpci_io_readb(dev, bmdma_base + bmreg_status); + status = qpci_io_readb(dev, bmdma_bar, bmreg_status); } while ((status & (BM_STS_ACTIVE | BM_STS_INTR)) == BM_STS_ACTIVE); g_assert_cmpint(get_irq(IDE_PRIMARY_IRQ), ==, !!(status & BM_STS_INTR)); /* Check IDE status code */ - assert_bit_set(qpci_io_readb(dev, ide_base + reg_status), DRDY); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), BSY | DRQ); + assert_bit_set(qpci_io_readb(dev, ide_bar, reg_status), DRDY); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), BSY | DRQ); /* Reading the status register clears the IRQ */ g_assert(!get_irq(IDE_PRIMARY_IRQ)); /* Stop DMA transfer if still active */ if (status & BM_STS_ACTIVE) { - qpci_io_writeb(dev, bmdma_base + bmreg_cmd, 0); + qpci_io_writeb(dev, bmdma_bar, bmreg_cmd, 0); } free_pci_device(dev); @@ -282,7 +281,7 @@ static int send_dma_request(int cmd, uint64_t sector, int nb_sectors, static void test_bmdma_simple_rw(void) { QPCIDevice *dev; - void *bmdma_base, *ide_base; + QPCIBar bmdma_bar, ide_bar; uint8_t status; uint8_t *buf; uint8_t *cmpbuf; @@ -296,7 +295,7 @@ static void test_bmdma_simple_rw(void) }, }; - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); buf = g_malloc(len); cmpbuf = g_malloc(len); @@ -308,7 +307,7 @@ static void test_bmdma_simple_rw(void) status = send_dma_request(CMD_WRITE_DMA, 0, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_INTR); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), DF | ERR); /* Write 0xaa pattern to sector 1 */ memset(buf, 0xaa, len); @@ -317,14 +316,14 @@ static void test_bmdma_simple_rw(void) status = send_dma_request(CMD_WRITE_DMA, 1, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_INTR); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), DF | ERR); /* Read and verify 0x55 pattern in sector 0 */ memset(cmpbuf, 0x55, len); status = send_dma_request(CMD_READ_DMA, 0, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_INTR); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), DF | ERR); memread(guest_buf, buf, len); g_assert(memcmp(buf, cmpbuf, len) == 0); @@ -334,7 +333,7 @@ static void test_bmdma_simple_rw(void) status = send_dma_request(CMD_READ_DMA, 1, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_INTR); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), DF | ERR); memread(guest_buf, buf, len); g_assert(memcmp(buf, cmpbuf, len) == 0); @@ -347,7 +346,7 @@ static void test_bmdma_simple_rw(void) static void test_bmdma_short_prdt(void) { QPCIDevice *dev; - void *bmdma_base, *ide_base; + QPCIBar bmdma_bar, ide_bar; uint8_t status; PrdtEntry prdt[] = { @@ -357,25 +356,25 @@ static void test_bmdma_short_prdt(void) }, }; - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); /* Normal request */ status = send_dma_request(CMD_READ_DMA, 0, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, 0); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), DF | ERR); /* Abort the request before it completes */ status = send_dma_request(CMD_READ_DMA | CMDF_ABORT, 0, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, 0); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), DF | ERR); } static void test_bmdma_one_sector_short_prdt(void) { QPCIDevice *dev; - void *bmdma_base, *ide_base; + QPCIBar bmdma_bar, ide_bar; uint8_t status; /* Read 2 sectors but only give 1 sector in PRDT */ @@ -386,25 +385,25 @@ static void test_bmdma_one_sector_short_prdt(void) }, }; - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); /* Normal request */ status = send_dma_request(CMD_READ_DMA, 0, 2, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, 0); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), DF | ERR); /* Abort the request before it completes */ status = send_dma_request(CMD_READ_DMA | CMDF_ABORT, 0, 2, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, 0); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), DF | ERR); } static void test_bmdma_long_prdt(void) { QPCIDevice *dev; - void *bmdma_base, *ide_base; + QPCIBar bmdma_bar, ide_bar; uint8_t status; PrdtEntry prdt[] = { @@ -414,28 +413,28 @@ static void test_bmdma_long_prdt(void) }, }; - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); /* Normal request */ status = send_dma_request(CMD_READ_DMA, 0, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_ACTIVE | BM_STS_INTR); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), DF | ERR); /* Abort the request before it completes */ status = send_dma_request(CMD_READ_DMA | CMDF_ABORT, 0, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_INTR); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), DF | ERR); } static void test_bmdma_no_busmaster(void) { QPCIDevice *dev; - void *bmdma_base, *ide_base; + QPCIBar bmdma_bar, ide_bar; uint8_t status; - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); /* No PRDT_EOT, each entry addr 0/size 64k, and in theory qemu shouldn't be * able to access it anyway because the Bus Master bit in the PCI command @@ -449,7 +448,7 @@ static void test_bmdma_no_busmaster(void) /* Not entirely clear what the expected result is, but this is what we get * in practice. At least we want to be aware of any changes. */ g_assert_cmphex(status, ==, BM_STS_ACTIVE | BM_STS_INTR); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), DF | ERR); } static void test_bmdma_setup(void) @@ -480,7 +479,7 @@ static void string_cpu_to_be16(uint16_t *s, size_t bytes) static void test_identify(void) { QPCIDevice *dev; - void *bmdma_base, *ide_base; + QPCIBar bmdma_bar, ide_bar; uint8_t data; uint16_t buf[256]; int i; @@ -491,25 +490,25 @@ static void test_identify(void) "-global ide-hd.ver=%s", tmp_path, "testdisk", "version"); - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); /* IDENTIFY command on device 0*/ - qpci_io_writeb(dev, ide_base + reg_device, 0); - qpci_io_writeb(dev, ide_base + reg_command, CMD_IDENTIFY); + qpci_io_writeb(dev, ide_bar, reg_device, 0); + qpci_io_writeb(dev, ide_bar, reg_command, CMD_IDENTIFY); /* Read in the IDENTIFY buffer and check registers */ - data = qpci_io_readb(dev, ide_base + reg_device); + data = qpci_io_readb(dev, ide_bar, reg_device); g_assert_cmpint(data & DEV, ==, 0); for (i = 0; i < 256; i++) { - data = qpci_io_readb(dev, ide_base + reg_status); + data = qpci_io_readb(dev, ide_bar, reg_status); assert_bit_set(data, DRDY | DRQ); assert_bit_clear(data, BSY | DF | ERR); - buf[i] = qpci_io_readw(dev, ide_base + reg_data); + buf[i] = qpci_io_readw(dev, ide_bar, reg_data); } - data = qpci_io_readb(dev, ide_base + reg_status); + data = qpci_io_readb(dev, ide_bar, reg_status); assert_bit_set(data, DRDY); assert_bit_clear(data, BSY | DF | ERR | DRQ); @@ -535,13 +534,13 @@ static void test_identify(void) static void make_dirty(uint8_t device) { QPCIDevice *dev; - void *bmdma_base, *ide_base; + QPCIBar bmdma_bar, ide_bar; uint8_t status; size_t len = 512; uintptr_t guest_buf; void* buf; - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); guest_buf = guest_alloc(guest_malloc, len); buf = g_malloc(len); @@ -560,7 +559,7 @@ static void make_dirty(uint8_t device) status = send_dma_request(CMD_WRITE_DMA, 1, 1, prdt, ARRAY_SIZE(prdt), NULL); g_assert_cmphex(status, ==, BM_STS_INTR); - assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR); + assert_bit_clear(qpci_io_readb(dev, ide_bar, reg_status), DF | ERR); g_free(buf); } @@ -568,14 +567,14 @@ static void make_dirty(uint8_t device) static void test_flush(void) { QPCIDevice *dev; - void *bmdma_base, *ide_base; + QPCIBar bmdma_bar, ide_bar; uint8_t data; ide_test_start( "-drive file=blkdebug::%s,if=ide,cache=writeback,format=raw", tmp_path); - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); qtest_irq_intercept_in(global_qtest, "ioapic"); @@ -586,11 +585,11 @@ static void test_flush(void) g_free(hmp("qemu-io ide0-hd0 \"break flush_to_os A\"")); /* FLUSH CACHE command on device 0*/ - qpci_io_writeb(dev, ide_base + reg_device, 0); - qpci_io_writeb(dev, ide_base + reg_command, CMD_FLUSH_CACHE); + qpci_io_writeb(dev, ide_bar, reg_device, 0); + qpci_io_writeb(dev, ide_bar, reg_command, CMD_FLUSH_CACHE); /* Check status while request is in flight*/ - data = qpci_io_readb(dev, ide_base + reg_status); + data = qpci_io_readb(dev, ide_bar, reg_status); assert_bit_set(data, BSY | DRDY); assert_bit_clear(data, DF | ERR | DRQ); @@ -598,11 +597,11 @@ static void test_flush(void) g_free(hmp("qemu-io ide0-hd0 \"resume A\"")); /* Check registers */ - data = qpci_io_readb(dev, ide_base + reg_device); + data = qpci_io_readb(dev, ide_bar, reg_device); g_assert_cmpint(data & DEV, ==, 0); do { - data = qpci_io_readb(dev, ide_base + reg_status); + data = qpci_io_readb(dev, ide_bar, reg_status); } while (data & BSY); assert_bit_set(data, DRDY); @@ -614,7 +613,7 @@ static void test_flush(void) static void test_retry_flush(const char *machine) { QPCIDevice *dev; - void *bmdma_base, *ide_base; + QPCIBar bmdma_bar, ide_bar; uint8_t data; const char *s; @@ -626,7 +625,7 @@ static void test_retry_flush(const char *machine) "rerror=stop,werror=stop", debug_path, tmp_path); - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); qtest_irq_intercept_in(global_qtest, "ioapic"); @@ -634,11 +633,11 @@ static void test_retry_flush(const char *machine) make_dirty(0); /* FLUSH CACHE command on device 0*/ - qpci_io_writeb(dev, ide_base + reg_device, 0); - qpci_io_writeb(dev, ide_base + reg_command, CMD_FLUSH_CACHE); + qpci_io_writeb(dev, ide_bar, reg_device, 0); + qpci_io_writeb(dev, ide_bar, reg_command, CMD_FLUSH_CACHE); /* Check status while request is in flight*/ - data = qpci_io_readb(dev, ide_base + reg_status); + data = qpci_io_readb(dev, ide_bar, reg_status); assert_bit_set(data, BSY | DRDY); assert_bit_clear(data, DF | ERR | DRQ); @@ -649,11 +648,11 @@ static void test_retry_flush(const char *machine) qmp_discard_response(s); /* Check registers */ - data = qpci_io_readb(dev, ide_base + reg_device); + data = qpci_io_readb(dev, ide_bar, reg_device); g_assert_cmpint(data & DEV, ==, 0); do { - data = qpci_io_readb(dev, ide_base + reg_status); + data = qpci_io_readb(dev, ide_bar, reg_status); } while (data & BSY); assert_bit_set(data, DRDY); @@ -665,15 +664,15 @@ static void test_retry_flush(const char *machine) static void test_flush_nodev(void) { QPCIDevice *dev; - void *bmdma_base, *ide_base; + QPCIBar bmdma_bar, ide_bar; ide_test_start(""); - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); /* FLUSH CACHE command on device 0*/ - qpci_io_writeb(dev, ide_base + reg_device, 0); - qpci_io_writeb(dev, ide_base + reg_command, CMD_FLUSH_CACHE); + qpci_io_writeb(dev, ide_bar, reg_device, 0); + qpci_io_writeb(dev, ide_bar, reg_command, CMD_FLUSH_CACHE); /* Just testing that qemu doesn't crash... */ @@ -700,7 +699,7 @@ typedef struct Read10CDB { uint16_t padding; } __attribute__((__packed__)) Read10CDB; -static void send_scsi_cdb_read10(QPCIDevice *dev, void *ide_base, +static void send_scsi_cdb_read10(QPCIDevice *dev, QPCIBar ide_bar, uint64_t lba, int nblocks) { Read10CDB pkt = { .padding = 0 }; @@ -717,7 +716,7 @@ static void send_scsi_cdb_read10(QPCIDevice *dev, void *ide_base, /* Send Packet */ for (i = 0; i < sizeof(Read10CDB)/2; i++) { - qpci_io_writew(dev, ide_base + reg_data, + qpci_io_writew(dev, ide_bar, reg_data, le16_to_cpu(((uint16_t *)&pkt)[i])); } } @@ -732,16 +731,16 @@ static void nsleep(int64_t nsecs) static uint8_t ide_wait_clear(uint8_t flag) { QPCIDevice *dev; - void *bmdma_base, *ide_base; + QPCIBar bmdma_bar, ide_bar; uint8_t data; time_t st; - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); /* Wait with a 5 second timeout */ time(&st); while (true) { - data = qpci_io_readb(dev, ide_base + reg_status); + data = qpci_io_readb(dev, ide_bar, reg_status); if (!(data & flag)) { return data; } @@ -776,7 +775,7 @@ static void ide_wait_intr(int irq) static void cdrom_pio_impl(int nblocks) { QPCIDevice *dev; - void *bmdma_base, *ide_base; + QPCIBar bmdma_bar, ide_bar; FILE *fh; int patt_blocks = MAX(16, nblocks); size_t patt_len = ATAPI_BLOCK_SIZE * patt_blocks; @@ -795,15 +794,14 @@ static void cdrom_pio_impl(int nblocks) ide_test_start("-drive if=none,file=%s,media=cdrom,format=raw,id=sr0,index=0 " "-device ide-cd,drive=sr0,bus=ide.0", tmp_path); - dev = get_pci_device(&bmdma_base, &ide_base); + dev = get_pci_device(&bmdma_bar, &ide_bar); qtest_irq_intercept_in(global_qtest, "ioapic"); /* PACKET command on device 0 */ - qpci_io_writeb(dev, ide_base + reg_device, 0); - qpci_io_writeb(dev, ide_base + reg_lba_middle, BYTE_COUNT_LIMIT & 0xFF); - qpci_io_writeb(dev, ide_base + reg_lba_high, - (BYTE_COUNT_LIMIT >> 8 & 0xFF)); - qpci_io_writeb(dev, ide_base + reg_command, CMD_PACKET); + qpci_io_writeb(dev, ide_bar, reg_device, 0); + qpci_io_writeb(dev, ide_bar, reg_lba_middle, BYTE_COUNT_LIMIT & 0xFF); + qpci_io_writeb(dev, ide_bar, reg_lba_high, (BYTE_COUNT_LIMIT >> 8 & 0xFF)); + qpci_io_writeb(dev, ide_bar, reg_command, CMD_PACKET); /* HP0: Check_Status_A State */ nsleep(400); data = ide_wait_clear(BSY); @@ -812,7 +810,7 @@ static void cdrom_pio_impl(int nblocks) assert_bit_clear(data, ERR | DF | BSY); /* SCSI CDB (READ10) -- read n*2048 bytes from block 0 */ - send_scsi_cdb_read10(dev, ide_base, 0, nblocks); + send_scsi_cdb_read10(dev, ide_bar, 0, nblocks); /* Read data back: occurs in bursts of 'BYTE_COUNT_LIMIT' bytes. * If BYTE_COUNT_LIMIT is odd, we transfer BYTE_COUNT_LIMIT - 1 bytes. @@ -836,8 +834,8 @@ static void cdrom_pio_impl(int nblocks) /* HP4: Transfer_Data */ for (j = 0; j < MIN((limit / 2), rem); j++) { - rx[offset + j] = cpu_to_le16(qpci_io_readw(dev, - ide_base + reg_data)); + rx[offset + j] = cpu_to_le16(qpci_io_readw(dev, ide_bar, + reg_data)); } } diff --git a/tests/ivshmem-test.c b/tests/ivshmem-test.c index fbd8258c7b..04a5c5dc7d 100644 --- a/tests/ivshmem-test.c +++ b/tests/ivshmem-test.c @@ -41,7 +41,7 @@ static QPCIDevice *get_device(QPCIBus *pcibus) typedef struct _IVState { QTestState *qtest; - void *reg_base, *mem_base; + QPCIBar reg_bar, mem_bar; QPCIBus *pcibus; QPCIDevice *dev; } IVState; @@ -75,7 +75,7 @@ static inline unsigned in_reg(IVState *s, enum Reg reg) unsigned res; global_qtest = s->qtest; - res = qpci_io_readl(s->dev, s->reg_base + reg); + res = qpci_io_readl(s->dev, s->reg_bar, reg); g_test_message("*%s -> %x\n", name, res); global_qtest = qtest; @@ -89,7 +89,7 @@ static inline void out_reg(IVState *s, enum Reg reg, unsigned v) global_qtest = s->qtest; g_test_message("%x -> *%s\n", v, name); - qpci_io_writel(s->dev, s->reg_base + reg, v); + qpci_io_writel(s->dev, s->reg_bar, reg, v); global_qtest = qtest; } @@ -98,7 +98,7 @@ static inline void read_mem(IVState *s, uint64_t off, void *buf, size_t len) QTestState *qtest = global_qtest; global_qtest = s->qtest; - qpci_memread(s->dev, s->mem_base + off, buf, len); + qpci_memread(s->dev, s->mem_bar, off, buf, len); global_qtest = qtest; } @@ -108,7 +108,7 @@ static inline void write_mem(IVState *s, uint64_t off, QTestState *qtest = global_qtest; global_qtest = s->qtest; - qpci_memwrite(s->dev, s->mem_base + off, buf, len); + qpci_memwrite(s->dev, s->mem_bar, off, buf, len); global_qtest = qtest; } @@ -127,16 +127,14 @@ static void setup_vm_cmd(IVState *s, const char *cmd, bool msix) s->pcibus = qpci_init_pc(NULL); s->dev = get_device(s->pcibus); - s->reg_base = qpci_iomap(s->dev, 0, &barsize); - g_assert_nonnull(s->reg_base); + s->reg_bar = qpci_iomap(s->dev, 0, &barsize); g_assert_cmpuint(barsize, ==, 256); if (msix) { qpci_msix_enable(s->dev); } - s->mem_base = qpci_iomap(s->dev, 2, &barsize); - g_assert_nonnull(s->mem_base); + s->mem_bar = qpci_iomap(s->dev, 2, &barsize); g_assert_cmpuint(barsize, ==, TMPSHMSIZE); qpci_device_enable(s->dev); diff --git a/tests/libqos/ahci.c b/tests/libqos/ahci.c index 8e789d8407..5180d65279 100644 --- a/tests/libqos/ahci.c +++ b/tests/libqos/ahci.c @@ -210,8 +210,7 @@ void ahci_pci_enable(AHCIQState *ahci) void start_ahci_device(AHCIQState *ahci) { /* Map AHCI's ABAR (BAR5) */ - ahci->hba_base = qpci_iomap(ahci->dev, 5, &ahci->barsize); - g_assert(ahci->hba_base); + ahci->hba_bar = qpci_iomap(ahci->dev, 5, &ahci->barsize); /* turns on pci.cmd.iose, pci.cmd.mse and pci.cmd.bme */ qpci_device_enable(ahci->dev); diff --git a/tests/libqos/ahci.h b/tests/libqos/ahci.h index 9b0c1d705b..caaafe3fdf 100644 --- a/tests/libqos/ahci.h +++ b/tests/libqos/ahci.h @@ -321,7 +321,7 @@ typedef struct AHCIPortQState { typedef struct AHCIQState { QOSState *parent; QPCIDevice *dev; - void *hba_base; + QPCIBar hba_bar; uint64_t barsize; uint32_t fingerprint; uint32_t cap; @@ -489,12 +489,12 @@ typedef struct AHCIOpts { static inline uint32_t ahci_mread(AHCIQState *ahci, size_t offset) { - return qpci_io_readl(ahci->dev, ahci->hba_base + offset); + return qpci_io_readl(ahci->dev, ahci->hba_bar, offset); } static inline void ahci_mwrite(AHCIQState *ahci, size_t offset, uint32_t value) { - qpci_io_writel(ahci->dev, ahci->hba_base + offset, value); + qpci_io_writel(ahci->dev, ahci->hba_bar, offset, value); } static inline uint32_t ahci_rreg(AHCIQState *ahci, uint32_t reg_num) diff --git a/tests/libqos/pci.c b/tests/libqos/pci.c index 3021651ee4..2dcdeade2a 100644 --- a/tests/libqos/pci.c +++ b/tests/libqos/pci.c @@ -104,7 +104,6 @@ void qpci_msix_enable(QPCIDevice *dev) uint32_t table; uint8_t bir_table; uint8_t bir_pba; - void *offset; addr = qpci_find_capability(dev, PCI_CAP_ID_MSIX); g_assert_cmphex(addr, !=, 0); @@ -114,18 +113,16 @@ void qpci_msix_enable(QPCIDevice *dev) table = qpci_config_readl(dev, addr + PCI_MSIX_TABLE); bir_table = table & PCI_MSIX_FLAGS_BIRMASK; - offset = qpci_iomap(dev, bir_table, NULL); - dev->msix_table = offset + (table & ~PCI_MSIX_FLAGS_BIRMASK); + dev->msix_table_bar = qpci_iomap(dev, bir_table, NULL); + dev->msix_table_off = table & ~PCI_MSIX_FLAGS_BIRMASK; table = qpci_config_readl(dev, addr + PCI_MSIX_PBA); bir_pba = table & PCI_MSIX_FLAGS_BIRMASK; if (bir_pba != bir_table) { - offset = qpci_iomap(dev, bir_pba, NULL); + dev->msix_pba_bar = qpci_iomap(dev, bir_pba, NULL); } - dev->msix_pba = offset + (table & ~PCI_MSIX_FLAGS_BIRMASK); + dev->msix_pba_off = table & ~PCI_MSIX_FLAGS_BIRMASK; - g_assert(dev->msix_table != NULL); - g_assert(dev->msix_pba != NULL); dev->msix_enabled = true; } @@ -141,22 +138,23 @@ void qpci_msix_disable(QPCIDevice *dev) qpci_config_writew(dev, addr + PCI_MSIX_FLAGS, val & ~PCI_MSIX_FLAGS_ENABLE); - qpci_iounmap(dev, dev->msix_table); - qpci_iounmap(dev, dev->msix_pba); + qpci_iounmap(dev, dev->msix_table_bar); + qpci_iounmap(dev, dev->msix_pba_bar); dev->msix_enabled = 0; - dev->msix_table = NULL; - dev->msix_pba = NULL; + dev->msix_table_off = 0; + dev->msix_pba_off = 0; } bool qpci_msix_pending(QPCIDevice *dev, uint16_t entry) { uint32_t pba_entry; uint8_t bit_n = entry % 32; - void *addr = dev->msix_pba + (entry / 32) * PCI_MSIX_ENTRY_SIZE / 4; + uint64_t off = (entry / 32) * PCI_MSIX_ENTRY_SIZE / 4; g_assert(dev->msix_enabled); - pba_entry = qpci_io_readl(dev, addr); - qpci_io_writel(dev, addr, pba_entry & ~(1 << bit_n)); + pba_entry = qpci_io_readl(dev, dev->msix_pba_bar, dev->msix_pba_off + off); + qpci_io_writel(dev, dev->msix_pba_bar, dev->msix_pba_off + off, + pba_entry & ~(1 << bit_n)); return (pba_entry & (1 << bit_n)) != 0; } @@ -164,7 +162,7 @@ bool qpci_msix_masked(QPCIDevice *dev, uint16_t entry) { uint8_t addr; uint16_t val; - void *vector_addr = dev->msix_table + (entry * PCI_MSIX_ENTRY_SIZE); + uint64_t vector_off = dev->msix_table_off + entry * PCI_MSIX_ENTRY_SIZE; g_assert(dev->msix_enabled); addr = qpci_find_capability(dev, PCI_CAP_ID_MSIX); @@ -174,8 +172,9 @@ bool qpci_msix_masked(QPCIDevice *dev, uint16_t entry) if (val & PCI_MSIX_FLAGS_MASKALL) { return true; } else { - return (qpci_io_readl(dev, vector_addr + PCI_MSIX_ENTRY_VECTOR_CTRL) - & PCI_MSIX_ENTRY_CTRL_MASKBIT) != 0; + return (qpci_io_readl(dev, dev->msix_table_bar, + vector_off + PCI_MSIX_ENTRY_VECTOR_CTRL) + & PCI_MSIX_ENTRY_CTRL_MASKBIT) != 0; } } @@ -222,129 +221,115 @@ void qpci_config_writel(QPCIDevice *dev, uint8_t offset, uint32_t value) dev->bus->config_writel(dev->bus, dev->devfn, offset, value); } - -uint8_t qpci_io_readb(QPCIDevice *dev, void *data) +uint8_t qpci_io_readb(QPCIDevice *dev, QPCIBar token, uint64_t off) { - uintptr_t addr = (uintptr_t)data; - - if (addr < QPCI_PIO_LIMIT) { - return dev->bus->pio_readb(dev->bus, addr); + if (token.addr < QPCI_PIO_LIMIT) { + return dev->bus->pio_readb(dev->bus, token.addr + off); } else { uint8_t val; - dev->bus->memread(dev->bus, addr, &val, sizeof(val)); + dev->bus->memread(dev->bus, token.addr + off, &val, sizeof(val)); return val; } } -uint16_t qpci_io_readw(QPCIDevice *dev, void *data) +uint16_t qpci_io_readw(QPCIDevice *dev, QPCIBar token, uint64_t off) { - uintptr_t addr = (uintptr_t)data; - - if (addr < QPCI_PIO_LIMIT) { - return dev->bus->pio_readw(dev->bus, addr); + if (token.addr < QPCI_PIO_LIMIT) { + return dev->bus->pio_readw(dev->bus, token.addr + off); } else { uint16_t val; - dev->bus->memread(dev->bus, addr, &val, sizeof(val)); + dev->bus->memread(dev->bus, token.addr + off, &val, sizeof(val)); return le16_to_cpu(val); } } -uint32_t qpci_io_readl(QPCIDevice *dev, void *data) +uint32_t qpci_io_readl(QPCIDevice *dev, QPCIBar token, uint64_t off) { - uintptr_t addr = (uintptr_t)data; - - if (addr < QPCI_PIO_LIMIT) { - return dev->bus->pio_readl(dev->bus, addr); + if (token.addr < QPCI_PIO_LIMIT) { + return dev->bus->pio_readl(dev->bus, token.addr + off); } else { uint32_t val; - dev->bus->memread(dev->bus, addr, &val, sizeof(val)); + dev->bus->memread(dev->bus, token.addr + off, &val, sizeof(val)); return le32_to_cpu(val); } } -uint64_t qpci_io_readq(QPCIDevice *dev, void *data) +uint64_t qpci_io_readq(QPCIDevice *dev, QPCIBar token, uint64_t off) { - uintptr_t addr = (uintptr_t)data; - - if (addr < QPCI_PIO_LIMIT) { - return dev->bus->pio_readq(dev->bus, addr); + if (token.addr < QPCI_PIO_LIMIT) { + return dev->bus->pio_readq(dev->bus, token.addr + off); } else { uint64_t val; - dev->bus->memread(dev->bus, addr, &val, sizeof(val)); + dev->bus->memread(dev->bus, token.addr + off, &val, sizeof(val)); return le64_to_cpu(val); } } -void qpci_io_writeb(QPCIDevice *dev, void *data, uint8_t value) +void qpci_io_writeb(QPCIDevice *dev, QPCIBar token, uint64_t off, + uint8_t value) { - uintptr_t addr = (uintptr_t)data; - - if (addr < QPCI_PIO_LIMIT) { - dev->bus->pio_writeb(dev->bus, addr, value); + if (token.addr < QPCI_PIO_LIMIT) { + dev->bus->pio_writeb(dev->bus, token.addr + off, value); } else { - dev->bus->memwrite(dev->bus, addr, &value, sizeof(value)); + dev->bus->memwrite(dev->bus, token.addr + off, &value, sizeof(value)); } } -void qpci_io_writew(QPCIDevice *dev, void *data, uint16_t value) +void qpci_io_writew(QPCIDevice *dev, QPCIBar token, uint64_t off, + uint16_t value) { - uintptr_t addr = (uintptr_t)data; - - if (addr < QPCI_PIO_LIMIT) { - dev->bus->pio_writew(dev->bus, addr, value); + if (token.addr < QPCI_PIO_LIMIT) { + dev->bus->pio_writew(dev->bus, token.addr + off, value); } else { value = cpu_to_le16(value); - dev->bus->memwrite(dev->bus, addr, &value, sizeof(value)); + dev->bus->memwrite(dev->bus, token.addr + off, &value, sizeof(value)); } } -void qpci_io_writel(QPCIDevice *dev, void *data, uint32_t value) +void qpci_io_writel(QPCIDevice *dev, QPCIBar token, uint64_t off, + uint32_t value) { - uintptr_t addr = (uintptr_t)data; - - if (addr < QPCI_PIO_LIMIT) { - dev->bus->pio_writel(dev->bus, addr, value); + if (token.addr < QPCI_PIO_LIMIT) { + dev->bus->pio_writel(dev->bus, token.addr + off, value); } else { value = cpu_to_le32(value); - dev->bus->memwrite(dev->bus, addr, &value, sizeof(value)); + dev->bus->memwrite(dev->bus, token.addr + off, &value, sizeof(value)); } } -void qpci_io_writeq(QPCIDevice *dev, void *data, uint64_t value) +void qpci_io_writeq(QPCIDevice *dev, QPCIBar token, uint64_t off, + uint64_t value) { - uintptr_t addr = (uintptr_t)data; - - if (addr < QPCI_PIO_LIMIT) { - dev->bus->pio_writeq(dev->bus, addr, value); + if (token.addr < QPCI_PIO_LIMIT) { + dev->bus->pio_writeq(dev->bus, token.addr + off, value); } else { value = cpu_to_le64(value); - dev->bus->memwrite(dev->bus, addr, &value, sizeof(value)); + dev->bus->memwrite(dev->bus, token.addr + off, &value, sizeof(value)); } } -void qpci_memread(QPCIDevice *dev, void *data, void *buf, size_t len) +void qpci_memread(QPCIDevice *dev, QPCIBar token, uint64_t off, + void *buf, size_t len) { - uintptr_t addr = (uintptr_t)data; - - g_assert(addr >= QPCI_PIO_LIMIT); - dev->bus->memread(dev->bus, addr, buf, len); + g_assert(token.addr >= QPCI_PIO_LIMIT); + dev->bus->memread(dev->bus, token.addr + off, buf, len); } -void qpci_memwrite(QPCIDevice *dev, void *data, const void *buf, size_t len) +void qpci_memwrite(QPCIDevice *dev, QPCIBar token, uint64_t off, + const void *buf, size_t len) { - uintptr_t addr = (uintptr_t)data; - - g_assert(addr >= QPCI_PIO_LIMIT); - dev->bus->memwrite(dev->bus, addr, buf, len); + g_assert(token.addr >= QPCI_PIO_LIMIT); + dev->bus->memwrite(dev->bus, token.addr + off, buf, len); } -void *qpci_iomap(QPCIDevice *dev, int barno, uint64_t *sizeptr) +QPCIBar qpci_iomap(QPCIDevice *dev, int barno, uint64_t *sizeptr) { QPCIBus *bus = dev->bus; static const int bar_reg_map[] = { PCI_BASE_ADDRESS_0, PCI_BASE_ADDRESS_1, PCI_BASE_ADDRESS_2, PCI_BASE_ADDRESS_3, PCI_BASE_ADDRESS_4, PCI_BASE_ADDRESS_5, }; + QPCIBar bar; int bar_reg; uint32_t addr, size; uint32_t io_type; @@ -391,17 +376,19 @@ void *qpci_iomap(QPCIDevice *dev, int barno, uint64_t *sizeptr) qpci_config_writel(dev, bar_reg, loc); } - return (void *)(uintptr_t)loc; + bar.addr = loc; + return bar; } -void qpci_iounmap(QPCIDevice *dev, void *data) +void qpci_iounmap(QPCIDevice *dev, QPCIBar bar) { /* FIXME */ } -void *qpci_legacy_iomap(QPCIDevice *dev, uint16_t addr) +QPCIBar qpci_legacy_iomap(QPCIDevice *dev, uint16_t addr) { - return (void *)(uintptr_t)addr; + QPCIBar bar = { .addr = addr }; + return bar; } void qpci_plug_device_test(const char *driver, const char *id, diff --git a/tests/libqos/pci.h b/tests/libqos/pci.h index 531e3f79e9..ed480614ff 100644 --- a/tests/libqos/pci.h +++ b/tests/libqos/pci.h @@ -21,6 +21,7 @@ typedef struct QPCIDevice QPCIDevice; typedef struct QPCIBus QPCIBus; +typedef struct QPCIBar QPCIBar; struct QPCIBus { uint8_t (*pio_readb)(QPCIBus *bus, uint32_t addr); @@ -51,13 +52,17 @@ struct QPCIBus { uint64_t mmio_alloc_ptr, mmio_limit; }; +struct QPCIBar { + uint64_t addr; +}; + struct QPCIDevice { QPCIBus *bus; int devfn; bool msix_enabled; - void *msix_table; - void *msix_pba; + QPCIBar msix_table_bar, msix_pba_bar; + uint64_t msix_table_off, msix_pba_off; }; void qpci_device_foreach(QPCIBus *bus, int vendor_id, int device_id, @@ -81,22 +86,27 @@ void qpci_config_writeb(QPCIDevice *dev, uint8_t offset, uint8_t value); void qpci_config_writew(QPCIDevice *dev, uint8_t offset, uint16_t value); void qpci_config_writel(QPCIDevice *dev, uint8_t offset, uint32_t value); -uint8_t qpci_io_readb(QPCIDevice *dev, void *data); -uint16_t qpci_io_readw(QPCIDevice *dev, void *data); -uint32_t qpci_io_readl(QPCIDevice *dev, void *data); -uint64_t qpci_io_readq(QPCIDevice *dev, void *data); +uint8_t qpci_io_readb(QPCIDevice *dev, QPCIBar token, uint64_t off); +uint16_t qpci_io_readw(QPCIDevice *dev, QPCIBar token, uint64_t off); +uint32_t qpci_io_readl(QPCIDevice *dev, QPCIBar token, uint64_t off); +uint64_t qpci_io_readq(QPCIDevice *dev, QPCIBar token, uint64_t off); -void qpci_io_writeb(QPCIDevice *dev, void *data, uint8_t value); -void qpci_io_writew(QPCIDevice *dev, void *data, uint16_t value); -void qpci_io_writel(QPCIDevice *dev, void *data, uint32_t value); -void qpci_io_writeq(QPCIDevice *dev, void *data, uint64_t value); +void qpci_io_writeb(QPCIDevice *dev, QPCIBar token, uint64_t off, + uint8_t value); +void qpci_io_writew(QPCIDevice *dev, QPCIBar token, uint64_t off, + uint16_t value); +void qpci_io_writel(QPCIDevice *dev, QPCIBar token, uint64_t off, + uint32_t value); +void qpci_io_writeq(QPCIDevice *dev, QPCIBar token, uint64_t off, + uint64_t value); -void qpci_memread(QPCIDevice *bus, void *data, void *buf, size_t len); -void qpci_memwrite(QPCIDevice *bus, void *data, const void *buf, size_t len); - -void *qpci_iomap(QPCIDevice *dev, int barno, uint64_t *sizeptr); -void qpci_iounmap(QPCIDevice *dev, void *data); -void *qpci_legacy_iomap(QPCIDevice *dev, uint16_t addr); +void qpci_memread(QPCIDevice *bus, QPCIBar token, uint64_t off, + void *buf, size_t len); +void qpci_memwrite(QPCIDevice *bus, QPCIBar token, uint64_t off, + const void *buf, size_t len); +QPCIBar qpci_iomap(QPCIDevice *dev, int barno, uint64_t *sizeptr); +void qpci_iounmap(QPCIDevice *dev, QPCIBar addr); +QPCIBar qpci_legacy_iomap(QPCIDevice *dev, uint16_t addr); void qpci_plug_device_test(const char *driver, const char *id, uint8_t slot, const char *opts); diff --git a/tests/libqos/usb.c b/tests/libqos/usb.c index f794d92da5..72d7a961fe 100644 --- a/tests/libqos/usb.c +++ b/tests/libqos/usb.c @@ -21,14 +21,12 @@ void qusb_pci_init_one(QPCIBus *pcibus, struct qhc *hc, uint32_t devfn, int bar) hc->dev = qpci_device_find(pcibus, devfn); g_assert(hc->dev != NULL); qpci_device_enable(hc->dev); - hc->base = qpci_iomap(hc->dev, bar, NULL); - g_assert(hc->base != NULL); + hc->bar = qpci_iomap(hc->dev, bar, NULL); } void uhci_port_test(struct qhc *hc, int port, uint16_t expect) { - void *addr = hc->base + 0x10 + 2 * port; - uint16_t value = qpci_io_readw(hc->dev, addr); + uint16_t value = qpci_io_readw(hc->dev, hc->bar, 0x10 + 2 * port); uint16_t mask = ~(UHCI_PORT_WRITE_CLEAR | UHCI_PORT_RSVD1); g_assert((value & mask) == (expect & mask)); diff --git a/tests/libqos/usb.h b/tests/libqos/usb.h index 8fe56872b7..423dcfd82f 100644 --- a/tests/libqos/usb.h +++ b/tests/libqos/usb.h @@ -5,7 +5,7 @@ struct qhc { QPCIDevice *dev; - void *base; + QPCIBar bar; }; void qusb_pci_init_one(QPCIBus *pcibus, struct qhc *hc, diff --git a/tests/libqos/virtio-pci.c b/tests/libqos/virtio-pci.c index c69d09ddb2..d4bf841f23 100644 --- a/tests/libqos/virtio-pci.c +++ b/tests/libqos/virtio-pci.c @@ -62,13 +62,12 @@ static void qvirtio_pci_assign_device(QVirtioDevice *d, void *data) *vpcidev = (QVirtioPCIDevice *)d; } -#define CONFIG_BASE(dev) \ - ((dev)->addr + VIRTIO_PCI_CONFIG_OFF((dev)->pdev->msix_enabled)) +#define CONFIG_BASE(dev) (VIRTIO_PCI_CONFIG_OFF((dev)->pdev->msix_enabled)) static uint8_t qvirtio_pci_config_readb(QVirtioDevice *d, uint64_t off) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - return qpci_io_readb(dev->pdev, CONFIG_BASE(dev) + off); + return qpci_io_readb(dev->pdev, dev->bar, CONFIG_BASE(dev) + off); } /* PCI is always read in little-endian order @@ -84,7 +83,7 @@ static uint16_t qvirtio_pci_config_readw(QVirtioDevice *d, uint64_t off) QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; uint16_t value; - value = qpci_io_readw(dev->pdev, CONFIG_BASE(dev) + off); + value = qpci_io_readw(dev->pdev, dev->bar, CONFIG_BASE(dev) + off); if (qvirtio_is_big_endian(d)) { value = bswap16(value); } @@ -96,7 +95,7 @@ static uint32_t qvirtio_pci_config_readl(QVirtioDevice *d, uint64_t off) QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; uint32_t value; - value = qpci_io_readl(dev->pdev, CONFIG_BASE(dev) + off); + value = qpci_io_readl(dev->pdev, dev->bar, CONFIG_BASE(dev) + off); if (qvirtio_is_big_endian(d)) { value = bswap32(value); } @@ -108,7 +107,7 @@ static uint64_t qvirtio_pci_config_readq(QVirtioDevice *d, uint64_t off) QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; uint64_t val; - val = qpci_io_readq(dev->pdev, CONFIG_BASE(dev) + off); + val = qpci_io_readq(dev->pdev, dev->bar, CONFIG_BASE(dev) + off); if (qvirtio_is_big_endian(d)) { val = bswap64(val); } @@ -119,31 +118,31 @@ static uint64_t qvirtio_pci_config_readq(QVirtioDevice *d, uint64_t off) static uint32_t qvirtio_pci_get_features(QVirtioDevice *d) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - return qpci_io_readl(dev->pdev, dev->addr + VIRTIO_PCI_HOST_FEATURES); + return qpci_io_readl(dev->pdev, dev->bar, VIRTIO_PCI_HOST_FEATURES); } static void qvirtio_pci_set_features(QVirtioDevice *d, uint32_t features) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - qpci_io_writel(dev->pdev, dev->addr + VIRTIO_PCI_GUEST_FEATURES, features); + qpci_io_writel(dev->pdev, dev->bar, VIRTIO_PCI_GUEST_FEATURES, features); } static uint32_t qvirtio_pci_get_guest_features(QVirtioDevice *d) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - return qpci_io_readl(dev->pdev, dev->addr + VIRTIO_PCI_GUEST_FEATURES); + return qpci_io_readl(dev->pdev, dev->bar, VIRTIO_PCI_GUEST_FEATURES); } static uint8_t qvirtio_pci_get_status(QVirtioDevice *d) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - return qpci_io_readb(dev->pdev, dev->addr + VIRTIO_PCI_STATUS); + return qpci_io_readb(dev->pdev, dev->bar, VIRTIO_PCI_STATUS); } static void qvirtio_pci_set_status(QVirtioDevice *d, uint8_t status) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - qpci_io_writeb(dev->pdev, dev->addr + VIRTIO_PCI_STATUS, status); + qpci_io_writeb(dev->pdev, dev->bar, VIRTIO_PCI_STATUS, status); } static bool qvirtio_pci_get_queue_isr_status(QVirtioDevice *d, QVirtQueue *vq) @@ -167,7 +166,7 @@ static bool qvirtio_pci_get_queue_isr_status(QVirtioDevice *d, QVirtQueue *vq) } } } else { - return qpci_io_readb(dev->pdev, dev->addr + VIRTIO_PCI_ISR) & 1; + return qpci_io_readb(dev->pdev, dev->bar, VIRTIO_PCI_ISR) & 1; } } @@ -191,26 +190,26 @@ static bool qvirtio_pci_get_config_isr_status(QVirtioDevice *d) } } } else { - return qpci_io_readb(dev->pdev, dev->addr + VIRTIO_PCI_ISR) & 2; + return qpci_io_readb(dev->pdev, dev->bar, VIRTIO_PCI_ISR) & 2; } } static void qvirtio_pci_queue_select(QVirtioDevice *d, uint16_t index) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - qpci_io_writeb(dev->pdev, dev->addr + VIRTIO_PCI_QUEUE_SEL, index); + qpci_io_writeb(dev->pdev, dev->bar, VIRTIO_PCI_QUEUE_SEL, index); } static uint16_t qvirtio_pci_get_queue_size(QVirtioDevice *d) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - return qpci_io_readw(dev->pdev, dev->addr + VIRTIO_PCI_QUEUE_NUM); + return qpci_io_readw(dev->pdev, dev->bar, VIRTIO_PCI_QUEUE_NUM); } static void qvirtio_pci_set_queue_address(QVirtioDevice *d, uint32_t pfn) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - qpci_io_writel(dev->pdev, dev->addr + VIRTIO_PCI_QUEUE_PFN, pfn); + qpci_io_writel(dev->pdev, dev->bar, VIRTIO_PCI_QUEUE_PFN, pfn); } static QVirtQueue *qvirtio_pci_virtqueue_setup(QVirtioDevice *d, @@ -262,7 +261,7 @@ static void qvirtio_pci_virtqueue_cleanup(QVirtQueue *vq, static void qvirtio_pci_virtqueue_kick(QVirtioDevice *d, QVirtQueue *vq) { QVirtioPCIDevice *dev = (QVirtioPCIDevice *)d; - qpci_io_writew(dev->pdev, dev->addr + VIRTIO_PCI_QUEUE_NOTIFY, vq->index); + qpci_io_writew(dev->pdev, dev->bar, VIRTIO_PCI_QUEUE_NOTIFY, vq->index); } const QVirtioBus qvirtio_pci = { @@ -309,14 +308,12 @@ QVirtioPCIDevice *qvirtio_pci_device_find(QPCIBus *bus, uint16_t device_type) void qvirtio_pci_device_enable(QVirtioPCIDevice *d) { qpci_device_enable(d->pdev); - d->addr = qpci_iomap(d->pdev, 0, NULL); - g_assert(d->addr != NULL); + d->bar = qpci_iomap(d->pdev, 0, NULL); } void qvirtio_pci_device_disable(QVirtioPCIDevice *d) { - qpci_iounmap(d->pdev, d->addr); - d->addr = NULL; + qpci_iounmap(d->pdev, d->bar); } void qvirtqueue_pci_msix_setup(QVirtioPCIDevice *d, QVirtQueuePCI *vqpci, @@ -324,29 +321,33 @@ void qvirtqueue_pci_msix_setup(QVirtioPCIDevice *d, QVirtQueuePCI *vqpci, { uint16_t vector; uint32_t control; - void *addr; + uint64_t off; g_assert(d->pdev->msix_enabled); - addr = d->pdev->msix_table + (entry * 16); + off = d->pdev->msix_table_off + (entry * 16); g_assert_cmpint(entry, >=, 0); g_assert_cmpint(entry, <, qpci_msix_table_size(d->pdev)); vqpci->msix_entry = entry; vqpci->msix_addr = guest_alloc(alloc, 4); - qpci_io_writel(d->pdev, addr + PCI_MSIX_ENTRY_LOWER_ADDR, - vqpci->msix_addr & ~0UL); - qpci_io_writel(d->pdev, addr + PCI_MSIX_ENTRY_UPPER_ADDR, - (vqpci->msix_addr >> 32) & ~0UL); - qpci_io_writel(d->pdev, addr + PCI_MSIX_ENTRY_DATA, vqpci->msix_data); + qpci_io_writel(d->pdev, d->pdev->msix_table_bar, + off + PCI_MSIX_ENTRY_LOWER_ADDR, vqpci->msix_addr & ~0UL); + qpci_io_writel(d->pdev, d->pdev->msix_table_bar, + off + PCI_MSIX_ENTRY_UPPER_ADDR, + (vqpci->msix_addr >> 32) & ~0UL); + qpci_io_writel(d->pdev, d->pdev->msix_table_bar, + off + PCI_MSIX_ENTRY_DATA, vqpci->msix_data); - control = qpci_io_readl(d->pdev, addr + PCI_MSIX_ENTRY_VECTOR_CTRL); - qpci_io_writel(d->pdev, addr + PCI_MSIX_ENTRY_VECTOR_CTRL, - control & ~PCI_MSIX_ENTRY_CTRL_MASKBIT); + control = qpci_io_readl(d->pdev, d->pdev->msix_table_bar, + off + PCI_MSIX_ENTRY_VECTOR_CTRL); + qpci_io_writel(d->pdev, d->pdev->msix_table_bar, + off + PCI_MSIX_ENTRY_VECTOR_CTRL, + control & ~PCI_MSIX_ENTRY_CTRL_MASKBIT); qvirtio_pci_queue_select(&d->vdev, vqpci->vq.index); - qpci_io_writew(d->pdev, d->addr + VIRTIO_MSI_QUEUE_VECTOR, entry); - vector = qpci_io_readw(d->pdev, d->addr + VIRTIO_MSI_QUEUE_VECTOR); + qpci_io_writew(d->pdev, d->bar, VIRTIO_MSI_QUEUE_VECTOR, entry); + vector = qpci_io_readw(d->pdev, d->bar, VIRTIO_MSI_QUEUE_VECTOR); g_assert_cmphex(vector, !=, VIRTIO_MSI_NO_VECTOR); } @@ -355,10 +356,10 @@ void qvirtio_pci_set_msix_configuration_vector(QVirtioPCIDevice *d, { uint16_t vector; uint32_t control; - void *addr; + uint64_t off; g_assert(d->pdev->msix_enabled); - addr = d->pdev->msix_table + (entry * 16); + off = d->pdev->msix_table_off + (entry * 16); g_assert_cmpint(entry, >=, 0); g_assert_cmpint(entry, <, qpci_msix_table_size(d->pdev)); @@ -367,17 +368,21 @@ void qvirtio_pci_set_msix_configuration_vector(QVirtioPCIDevice *d, d->config_msix_data = 0x12345678; d->config_msix_addr = guest_alloc(alloc, 4); - qpci_io_writel(d->pdev, addr + PCI_MSIX_ENTRY_LOWER_ADDR, - d->config_msix_addr & ~0UL); - qpci_io_writel(d->pdev, addr + PCI_MSIX_ENTRY_UPPER_ADDR, - (d->config_msix_addr >> 32) & ~0UL); - qpci_io_writel(d->pdev, addr + PCI_MSIX_ENTRY_DATA, d->config_msix_data); + qpci_io_writel(d->pdev, d->pdev->msix_table_bar, + off + PCI_MSIX_ENTRY_LOWER_ADDR, d->config_msix_addr & ~0UL); + qpci_io_writel(d->pdev, d->pdev->msix_table_bar, + off + PCI_MSIX_ENTRY_UPPER_ADDR, + (d->config_msix_addr >> 32) & ~0UL); + qpci_io_writel(d->pdev, d->pdev->msix_table_bar, + off + PCI_MSIX_ENTRY_DATA, d->config_msix_data); - control = qpci_io_readl(d->pdev, addr + PCI_MSIX_ENTRY_VECTOR_CTRL); - qpci_io_writel(d->pdev, addr + PCI_MSIX_ENTRY_VECTOR_CTRL, - control & ~PCI_MSIX_ENTRY_CTRL_MASKBIT); + control = qpci_io_readl(d->pdev, d->pdev->msix_table_bar, + off + PCI_MSIX_ENTRY_VECTOR_CTRL); + qpci_io_writel(d->pdev, d->pdev->msix_table_bar, + off + PCI_MSIX_ENTRY_VECTOR_CTRL, + control & ~PCI_MSIX_ENTRY_CTRL_MASKBIT); - qpci_io_writew(d->pdev, d->addr + VIRTIO_MSI_CONFIG_VECTOR, entry); - vector = qpci_io_readw(d->pdev, d->addr + VIRTIO_MSI_CONFIG_VECTOR); + qpci_io_writew(d->pdev, d->bar, VIRTIO_MSI_CONFIG_VECTOR, entry); + vector = qpci_io_readw(d->pdev, d->bar, VIRTIO_MSI_CONFIG_VECTOR); g_assert_cmphex(vector, !=, VIRTIO_MSI_NO_VECTOR); } diff --git a/tests/libqos/virtio-pci.h b/tests/libqos/virtio-pci.h index efcac2d3de..38c54c63ea 100644 --- a/tests/libqos/virtio-pci.h +++ b/tests/libqos/virtio-pci.h @@ -16,7 +16,7 @@ typedef struct QVirtioPCIDevice { QVirtioDevice vdev; QPCIDevice *pdev; - void *addr; + QPCIBar bar; uint16_t config_msix_entry; uint64_t config_msix_addr; uint32_t config_msix_data; diff --git a/tests/rtl8139-test.c b/tests/rtl8139-test.c index c2f601a380..7de7dc45ae 100644 --- a/tests/rtl8139-test.c +++ b/tests/rtl8139-test.c @@ -22,7 +22,7 @@ static void nop(void) static QPCIBus *pcibus; static QPCIDevice *dev; -static void *dev_base; +static QPCIBar dev_bar; static void save_fn(QPCIDevice *dev, int devfn, void *data) { @@ -45,14 +45,14 @@ static QPCIDevice *get_device(void) #define PORT(name, len, val) \ static unsigned __attribute__((unused)) in_##name(void) \ { \ - unsigned res = qpci_io_read##len(dev, dev_base+(val)); \ + unsigned res = qpci_io_read##len(dev, dev_bar, (val)); \ g_test_message("*%s -> %x\n", #name, res); \ return res; \ } \ static void out_##name(unsigned v) \ { \ g_test_message("%x -> *%s\n", v, #name); \ - qpci_io_write##len(dev, dev_base+(val), v); \ + qpci_io_write##len(dev, dev_bar, (val), v); \ } PORT(Timer, l, 0x48) @@ -186,9 +186,7 @@ static void test_init(void) dev = get_device(); - dev_base = qpci_iomap(dev, 0, &barsize); - - g_assert(dev_base != NULL); + dev_bar = qpci_iomap(dev, 0, &barsize); qpci_device_enable(dev); diff --git a/tests/tco-test.c b/tests/tco-test.c index 129577d1c0..ef02ec5903 100644 --- a/tests/tco-test.c +++ b/tests/tco-test.c @@ -41,7 +41,7 @@ typedef struct { const char *args; bool noreboot; QPCIDevice *dev; - void *tco_io_base; + QPCIBar tco_io_bar; } TestData; static void test_init(TestData *d) @@ -70,42 +70,42 @@ static void test_init(TestData *d) /* set Root Complex BAR */ qpci_config_writel(d->dev, ICH9_LPC_RCBA, RCBA_BASE_ADDR | 0x1); - d->tco_io_base = qpci_legacy_iomap(d->dev, PM_IO_BASE_ADDR + 0x60); + d->tco_io_bar = qpci_legacy_iomap(d->dev, PM_IO_BASE_ADDR + 0x60); } static void stop_tco(const TestData *d) { uint32_t val; - val = qpci_io_readw(d->dev, d->tco_io_base + TCO1_CNT); + val = qpci_io_readw(d->dev, d->tco_io_bar, TCO1_CNT); val |= TCO_TMR_HLT; - qpci_io_writew(d->dev, d->tco_io_base + TCO1_CNT, val); + qpci_io_writew(d->dev, d->tco_io_bar, TCO1_CNT, val); } static void start_tco(const TestData *d) { uint32_t val; - val = qpci_io_readw(d->dev, d->tco_io_base + TCO1_CNT); + val = qpci_io_readw(d->dev, d->tco_io_bar, TCO1_CNT); val &= ~TCO_TMR_HLT; - qpci_io_writew(d->dev, d->tco_io_base + TCO1_CNT, val); + qpci_io_writew(d->dev, d->tco_io_bar, TCO1_CNT, val); } static void load_tco(const TestData *d) { - qpci_io_writew(d->dev, d->tco_io_base + TCO_RLD, 4); + qpci_io_writew(d->dev, d->tco_io_bar, TCO_RLD, 4); } static void set_tco_timeout(const TestData *d, uint16_t ticks) { - qpci_io_writew(d->dev, d->tco_io_base + TCO_TMR, ticks); + qpci_io_writew(d->dev, d->tco_io_bar, TCO_TMR, ticks); } static void clear_tco_status(const TestData *d) { - qpci_io_writew(d->dev, d->tco_io_base + TCO1_STS, 0x0008); - qpci_io_writew(d->dev, d->tco_io_base + TCO2_STS, 0x0002); - qpci_io_writew(d->dev, d->tco_io_base + TCO2_STS, 0x0004); + qpci_io_writew(d->dev, d->tco_io_bar, TCO1_STS, 0x0008); + qpci_io_writew(d->dev, d->tco_io_bar, TCO2_STS, 0x0002); + qpci_io_writew(d->dev, d->tco_io_bar, TCO2_STS, 0x0004); } static void reset_on_second_timeout(bool enable) @@ -128,25 +128,25 @@ static void test_tco_defaults(void) d.args = NULL; d.noreboot = true; test_init(&d); - g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_base + TCO_RLD), ==, + g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_bar, TCO_RLD), ==, TCO_RLD_DEFAULT); /* TCO_DAT_IN & TCO_DAT_OUT */ - g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_base + TCO_DAT_IN), ==, + g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_bar, TCO_DAT_IN), ==, (TCO_DAT_OUT_DEFAULT << 8) | TCO_DAT_IN_DEFAULT); /* TCO1_STS & TCO2_STS */ - g_assert_cmpint(qpci_io_readl(d.dev, d.tco_io_base + TCO1_STS), ==, + g_assert_cmpint(qpci_io_readl(d.dev, d.tco_io_bar, TCO1_STS), ==, (TCO2_STS_DEFAULT << 16) | TCO1_STS_DEFAULT); /* TCO1_CNT & TCO2_CNT */ - g_assert_cmpint(qpci_io_readl(d.dev, d.tco_io_base + TCO1_CNT), ==, + g_assert_cmpint(qpci_io_readl(d.dev, d.tco_io_bar, TCO1_CNT), ==, (TCO2_CNT_DEFAULT << 16) | TCO1_CNT_DEFAULT); /* TCO_MESSAGE1 & TCO_MESSAGE2 */ - g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_base + TCO_MESSAGE1), ==, + g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_bar, TCO_MESSAGE1), ==, (TCO_MESSAGE2_DEFAULT << 8) | TCO_MESSAGE1_DEFAULT); - g_assert_cmpint(qpci_io_readb(d.dev, d.tco_io_base + TCO_WDCNT), ==, + g_assert_cmpint(qpci_io_readb(d.dev, d.tco_io_bar, TCO_WDCNT), ==, TCO_WDCNT_DEFAULT); - g_assert_cmpint(qpci_io_readb(d.dev, d.tco_io_base + SW_IRQ_GEN), ==, + g_assert_cmpint(qpci_io_readb(d.dev, d.tco_io_bar, SW_IRQ_GEN), ==, SW_IRQ_GEN_DEFAULT); - g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_base + TCO_TMR), ==, + g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_bar, TCO_TMR), ==, TCO_TMR_DEFAULT); qtest_end(); } @@ -171,23 +171,23 @@ static void test_tco_timeout(void) clock_step(ticks * TCO_TICK_NSEC); /* test first timeout */ - val = qpci_io_readw(d.dev, d.tco_io_base + TCO1_STS); + val = qpci_io_readw(d.dev, d.tco_io_bar, TCO1_STS); ret = val & TCO_TIMEOUT ? 1 : 0; g_assert(ret == 1); /* test clearing timeout bit */ val |= TCO_TIMEOUT; - qpci_io_writew(d.dev, d.tco_io_base + TCO1_STS, val); - val = qpci_io_readw(d.dev, d.tco_io_base + TCO1_STS); + qpci_io_writew(d.dev, d.tco_io_bar, TCO1_STS, val); + val = qpci_io_readw(d.dev, d.tco_io_bar, TCO1_STS); ret = val & TCO_TIMEOUT ? 1 : 0; g_assert(ret == 0); /* test second timeout */ clock_step(ticks * TCO_TICK_NSEC); - val = qpci_io_readw(d.dev, d.tco_io_base + TCO1_STS); + val = qpci_io_readw(d.dev, d.tco_io_bar, TCO1_STS); ret = val & TCO_TIMEOUT ? 1 : 0; g_assert(ret == 1); - val = qpci_io_readw(d.dev, d.tco_io_base + TCO2_STS); + val = qpci_io_readw(d.dev, d.tco_io_bar, TCO2_STS); ret = val & TCO_SECOND_TO_STS ? 1 : 0; g_assert(ret == 1); @@ -214,13 +214,13 @@ static void test_tco_max_timeout(void) start_tco(&d); clock_step(((ticks & TCO_TMR_MASK) - 1) * TCO_TICK_NSEC); - val = qpci_io_readw(d.dev, d.tco_io_base + TCO_RLD); + val = qpci_io_readw(d.dev, d.tco_io_bar, TCO_RLD); g_assert_cmpint(val & TCO_RLD_MASK, ==, 1); - val = qpci_io_readw(d.dev, d.tco_io_base + TCO1_STS); + val = qpci_io_readw(d.dev, d.tco_io_bar, TCO1_STS); ret = val & TCO_TIMEOUT ? 1 : 0; g_assert(ret == 0); clock_step(TCO_TICK_NSEC); - val = qpci_io_readw(d.dev, d.tco_io_base + TCO1_STS); + val = qpci_io_readw(d.dev, d.tco_io_bar, TCO1_STS); ret = val & TCO_TIMEOUT ? 1 : 0; g_assert(ret == 1); @@ -358,11 +358,11 @@ static void test_tco_ticks_counter(void) start_tco(&d); do { - rld = qpci_io_readw(d.dev, d.tco_io_base + TCO_RLD) & TCO_RLD_MASK; + rld = qpci_io_readw(d.dev, d.tco_io_bar, TCO_RLD) & TCO_RLD_MASK; g_assert_cmpint(rld, ==, ticks); clock_step(TCO_TICK_NSEC); ticks--; - } while (!(qpci_io_readw(d.dev, d.tco_io_base + TCO1_STS) & TCO_TIMEOUT)); + } while (!(qpci_io_readw(d.dev, d.tco_io_bar, TCO1_STS) & TCO_TIMEOUT)); stop_tco(&d); qtest_end(); @@ -378,10 +378,10 @@ static void test_tco1_control_bits(void) test_init(&d); val = TCO_LOCK; - qpci_io_writew(d.dev, d.tco_io_base + TCO1_CNT, val); + qpci_io_writew(d.dev, d.tco_io_bar, TCO1_CNT, val); val &= ~TCO_LOCK; - qpci_io_writew(d.dev, d.tco_io_base + TCO1_CNT, val); - g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_base + TCO1_CNT), ==, + qpci_io_writew(d.dev, d.tco_io_bar, TCO1_CNT, val); + g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_bar, TCO1_CNT), ==, TCO_LOCK); qtest_end(); } @@ -405,13 +405,13 @@ static void test_tco1_status_bits(void) start_tco(&d); clock_step(ticks * TCO_TICK_NSEC); - qpci_io_writeb(d.dev, d.tco_io_base + TCO_DAT_IN, 0); - qpci_io_writeb(d.dev, d.tco_io_base + TCO_DAT_OUT, 0); - val = qpci_io_readw(d.dev, d.tco_io_base + TCO1_STS); + qpci_io_writeb(d.dev, d.tco_io_bar, TCO_DAT_IN, 0); + qpci_io_writeb(d.dev, d.tco_io_bar, TCO_DAT_OUT, 0); + val = qpci_io_readw(d.dev, d.tco_io_bar, TCO1_STS); ret = val & (TCO_TIMEOUT | SW_TCO_SMI | TCO_INT_STS) ? 1 : 0; g_assert(ret == 1); - qpci_io_writew(d.dev, d.tco_io_base + TCO1_STS, val); - g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_base + TCO1_STS), ==, 0); + qpci_io_writew(d.dev, d.tco_io_bar, TCO1_STS, val); + g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_bar, TCO1_STS), ==, 0); qtest_end(); } @@ -434,11 +434,11 @@ static void test_tco2_status_bits(void) start_tco(&d); clock_step(ticks * TCO_TICK_NSEC * 2); - val = qpci_io_readw(d.dev, d.tco_io_base + TCO2_STS); + val = qpci_io_readw(d.dev, d.tco_io_bar, TCO2_STS); ret = val & (TCO_SECOND_TO_STS | TCO_BOOT_STS) ? 1 : 0; g_assert(ret == 1); - qpci_io_writew(d.dev, d.tco_io_base + TCO2_STS, val); - g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_base + TCO2_STS), ==, 0); + qpci_io_writew(d.dev, d.tco_io_bar, TCO2_STS, val); + g_assert_cmpint(qpci_io_readw(d.dev, d.tco_io_bar, TCO2_STS), ==, 0); qtest_end(); } diff --git a/tests/usb-hcd-ehci-test.c b/tests/usb-hcd-ehci-test.c index a4ceeaaa43..57af8a034e 100644 --- a/tests/usb-hcd-ehci-test.c +++ b/tests/usb-hcd-ehci-test.c @@ -38,8 +38,7 @@ static void uhci_port_update(struct qhc *hc, int port, static void ehci_port_test(struct qhc *hc, int port, uint32_t expect) { - void *addr = hc->base + 0x64 + 4 * port; - uint32_t value = qpci_io_readl(hc->dev, addr); + uint32_t value = qpci_io_readl(hc->dev, hc->bar, 0x64 + 4 * port); uint16_t mask = ~(PORTSC_CSC | PORTSC_PEDC | PORTSC_OCC); #if 0 @@ -91,7 +90,7 @@ static void pci_ehci_port_1(void) static void pci_ehci_config(void) { /* hands over all ports from companion uhci to ehci */ - qpci_io_writew(ehci1.dev, ehci1.base + 0x60, 1); + qpci_io_writew(ehci1.dev, ehci1.bar, 0x60, 1); } static void pci_uhci_port_2(void) From 61f20b9dc5b78c603354a4ec170079479dcb6657 Mon Sep 17 00:00:00 2001 From: Thomas Huth Date: Wed, 26 Oct 2016 09:35:40 +0200 Subject: [PATCH 63/73] spapr_nvram: Pre-initialize the NVRAM to support the -prom-env parameter In case we do not load the NVRAM contents from a file and the user specified the "-prom-env" parameter, use the new CHRP NVRAM helper functions to pre-initialize the NVRAM partitions, so that the SLOF firmware now can pick up the environment variables from the -prom-env parameter, too. Signed-off-by: Thomas Huth Signed-off-by: David Gibson --- hw/nvram/spapr_nvram.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/hw/nvram/spapr_nvram.c b/hw/nvram/spapr_nvram.c index 4de5f705d8..eb42ea323f 100644 --- a/hw/nvram/spapr_nvram.c +++ b/hw/nvram/spapr_nvram.c @@ -31,6 +31,7 @@ #include "sysemu/block-backend.h" #include "sysemu/device_tree.h" #include "hw/sysbus.h" +#include "hw/nvram/chrp_nvram.h" #include "hw/ppc/spapr.h" #include "hw/ppc/spapr_vio.h" @@ -162,6 +163,11 @@ static void spapr_nvram_realize(VIOsPAPRDevice *dev, Error **errp) error_setg(errp, "can't read spapr-nvram contents"); return; } + } else if (nb_prom_envs > 0) { + /* Create a system partition to pass the -prom-env variables */ + chrp_nvram_create_system_partition(nvram->buf, MIN_NVRAM_SIZE / 4); + chrp_nvram_create_free_partition(&nvram->buf[MIN_NVRAM_SIZE / 4], + nvram->size - MIN_NVRAM_SIZE / 4); } spapr_rtas_register(RTAS_NVRAM_FETCH, "nvram-fetch", rtas_nvram_fetch); From 53687348813196551874409fecb49c94d20b1ae6 Mon Sep 17 00:00:00 2001 From: David Gibson Date: Fri, 28 Oct 2016 11:17:31 +1100 Subject: [PATCH 64/73] tests: Add pseries machine to the prom-env-test, too Now that we also support the "-prom-env" parameter for the pseries machine, we can enable this test for this machine, too. Since booting with TCG is rather slow with the pseries machine, we also enable the "-nodefaults" parameter for this test now, so that SLOF does not have to check that much devices during boot and thus runs a little bit faster. Signed-off-by: Thomas Huth [dwg: Don't add -nodefaults to the command line, it causes extra warnings for the sparc testcases] Signed-off-by: David Gibson --- tests/prom-env-test.c | 20 ++++++++++++-------- 1 file changed, 12 insertions(+), 8 deletions(-) diff --git a/tests/prom-env-test.c b/tests/prom-env-test.c index 7a628574c3..0ba6f48607 100644 --- a/tests/prom-env-test.c +++ b/tests/prom-env-test.c @@ -9,11 +9,12 @@ * This work is licensed under the terms of the GNU GPL, version 2 * or later. See the COPYING file in the top-level directory. * - * This test is used to check that some OpenBIOS machines can be started - * successfully in TCG mode. To do this, we first put some Forth code into - * the "boot-command" Open Firmware environment variable. This Forth code - * writes a well-known magic value to a known location in memory. Then we - * start the guest so that OpenBIOS can boot and finally run the Forth code. + * This test is used to check that some Open Firmware based machines (i.e. + * OpenBIOS or SLOF) can be started successfully in TCG mode. To do this, we + * first put some Forth code into the "boot-command" Open Firmware environment + * variable. This Forth code writes a well-known magic value to a known location + * in memory. Then we start the guest so that the firmware can boot and finally + * run the Forth code. * The testing code here then can finally check whether the value has been * successfully written into the guest memory. */ @@ -71,13 +72,16 @@ int main(int argc, char *argv[]) { const char *sparc_machines[] = { "SPARCbook", "Voyager", "SS-20", NULL }; const char *sparc64_machines[] = { "sun4u", "sun4v", NULL }; - const char *mac_machines[] = { "mac99", "g3beige", NULL }; + const char *ppc_machines[] = { "mac99", "g3beige", NULL }; + const char *ppc64_machines[] = { "mac99", "g3beige", "pseries", NULL }; const char *arch = qtest_get_arch(); g_test_init(&argc, &argv, NULL); - if (!strcmp(arch, "ppc") || !strcmp(arch, "ppc64")) { - add_tests(mac_machines); + if (!strcmp(arch, "ppc")) { + add_tests(ppc_machines); + } else if (!strcmp(arch, "ppc64")) { + add_tests(ppc64_machines); } else if (!strcmp(arch, "sparc")) { add_tests(sparc_machines); } else if (!strcmp(arch, "sparc64")) { From 6d1ff9a7b396b3193eaea1983b3d7283a743e60a Mon Sep 17 00:00:00 2001 From: Sandipan Das Date: Wed, 26 Oct 2016 11:56:24 +0530 Subject: [PATCH 65/73] target-ppc: add xscmp[eq,gt,ge,ne]dp instructions xscmpeqdp: VSX Scalar Compare Equal Double-Precision xscmpgedp: VSX Scalar Compare Greater Than or Equal Double-Precision xscmpgtdp: VSX Scalar Compare Greater Than Double-Precision xscmpnedp: VSX Scalar Compare Not Equal Double-Precision Signed-off-by: Sandipan Das Signed-off-by: Nikunj A Dadhania Signed-off-by: David Gibson --- target-ppc/fpu_helper.c | 52 +++++++++++++++++++++++++++++ target-ppc/helper.h | 4 +++ target-ppc/translate/vsx-impl.inc.c | 4 +++ target-ppc/translate/vsx-ops.inc.c | 4 +++ 4 files changed, 64 insertions(+) diff --git a/target-ppc/fpu_helper.c b/target-ppc/fpu_helper.c index b0760f041d..4906372ae4 100644 --- a/target-ppc/fpu_helper.c +++ b/target-ppc/fpu_helper.c @@ -2362,6 +2362,58 @@ VSX_MADD(xvnmaddmsp, 4, float32, VsrW(i), NMADD_FLGS, 0, 0, 0) VSX_MADD(xvnmsubasp, 4, float32, VsrW(i), NMSUB_FLGS, 1, 0, 0) VSX_MADD(xvnmsubmsp, 4, float32, VsrW(i), NMSUB_FLGS, 0, 0, 0) +/* VSX_SCALAR_CMP_DP - VSX scalar floating point compare double precision + * op - instruction mnemonic + * cmp - comparison operation + * exp - expected result of comparison + * svxvc - set VXVC bit + */ +#define VSX_SCALAR_CMP_DP(op, cmp, exp, svxvc) \ +void helper_##op(CPUPPCState *env, uint32_t opcode) \ +{ \ + ppc_vsr_t xt, xa, xb; \ + bool vxsnan_flag = false, vxvc_flag = false, vex_flag = false; \ + \ + getVSR(xA(opcode), &xa, env); \ + getVSR(xB(opcode), &xb, env); \ + getVSR(xT(opcode), &xt, env); \ + \ + if (float64_is_signaling_nan(xa.VsrD(0), &env->fp_status) || \ + float64_is_signaling_nan(xb.VsrD(0), &env->fp_status)) { \ + vxsnan_flag = true; \ + if (fpscr_ve == 0 && svxvc) { \ + vxvc_flag = true; \ + } \ + } else if (svxvc) { \ + vxvc_flag = float64_is_quiet_nan(xa.VsrD(0), &env->fp_status) || \ + float64_is_quiet_nan(xb.VsrD(0), &env->fp_status); \ + } \ + if (vxsnan_flag) { \ + float_invalid_op_excp(env, POWERPC_EXCP_FP_VXSNAN, 0); \ + } \ + if (vxvc_flag) { \ + float_invalid_op_excp(env, POWERPC_EXCP_FP_VXVC, 0); \ + } \ + vex_flag = fpscr_ve && (vxvc_flag || vxsnan_flag); \ + \ + if (!vex_flag) { \ + if (float64_##cmp(xb.VsrD(0), xa.VsrD(0), &env->fp_status) == exp) { \ + xt.VsrD(0) = -1; \ + xt.VsrD(1) = 0; \ + } else { \ + xt.VsrD(0) = 0; \ + xt.VsrD(1) = 0; \ + } \ + } \ + putVSR(xT(opcode), &xt, env); \ + helper_float_check_status(env); \ +} + +VSX_SCALAR_CMP_DP(xscmpeqdp, eq, 1, 0) +VSX_SCALAR_CMP_DP(xscmpgedp, le, 1, 1) +VSX_SCALAR_CMP_DP(xscmpgtdp, lt, 1, 1) +VSX_SCALAR_CMP_DP(xscmpnedp, eq, 0, 0) + #define VSX_SCALAR_CMP(op, ordered) \ void helper_##op(CPUPPCState *env, uint32_t opcode) \ { \ diff --git a/target-ppc/helper.h b/target-ppc/helper.h index 5fcc546078..0337292440 100644 --- a/target-ppc/helper.h +++ b/target-ppc/helper.h @@ -389,6 +389,10 @@ DEF_HELPER_2(xsnmaddadp, void, env, i32) DEF_HELPER_2(xsnmaddmdp, void, env, i32) DEF_HELPER_2(xsnmsubadp, void, env, i32) DEF_HELPER_2(xsnmsubmdp, void, env, i32) +DEF_HELPER_2(xscmpeqdp, void, env, i32) +DEF_HELPER_2(xscmpgtdp, void, env, i32) +DEF_HELPER_2(xscmpgedp, void, env, i32) +DEF_HELPER_2(xscmpnedp, void, env, i32) DEF_HELPER_2(xscmpodp, void, env, i32) DEF_HELPER_2(xscmpudp, void, env, i32) DEF_HELPER_2(xsmaxdp, void, env, i32) diff --git a/target-ppc/translate/vsx-impl.inc.c b/target-ppc/translate/vsx-impl.inc.c index 1508bd13e3..bf167d0488 100644 --- a/target-ppc/translate/vsx-impl.inc.c +++ b/target-ppc/translate/vsx-impl.inc.c @@ -620,6 +620,10 @@ GEN_VSX_HELPER_2(xsnmaddadp, 0x04, 0x14, 0, PPC2_VSX) GEN_VSX_HELPER_2(xsnmaddmdp, 0x04, 0x15, 0, PPC2_VSX) GEN_VSX_HELPER_2(xsnmsubadp, 0x04, 0x16, 0, PPC2_VSX) GEN_VSX_HELPER_2(xsnmsubmdp, 0x04, 0x17, 0, PPC2_VSX) +GEN_VSX_HELPER_2(xscmpeqdp, 0x0C, 0x00, 0, PPC2_ISA300) +GEN_VSX_HELPER_2(xscmpgtdp, 0x0C, 0x01, 0, PPC2_ISA300) +GEN_VSX_HELPER_2(xscmpgedp, 0x0C, 0x02, 0, PPC2_ISA300) +GEN_VSX_HELPER_2(xscmpnedp, 0x0C, 0x03, 0, PPC2_ISA300) GEN_VSX_HELPER_2(xscmpodp, 0x0C, 0x05, 0, PPC2_VSX) GEN_VSX_HELPER_2(xscmpudp, 0x0C, 0x04, 0, PPC2_VSX) GEN_VSX_HELPER_2(xsmaxdp, 0x00, 0x14, 0, PPC2_VSX) diff --git a/target-ppc/translate/vsx-ops.inc.c b/target-ppc/translate/vsx-ops.inc.c index af0d27e012..202c557fd8 100644 --- a/target-ppc/translate/vsx-ops.inc.c +++ b/target-ppc/translate/vsx-ops.inc.c @@ -114,6 +114,10 @@ GEN_XX3FORM(xsnmaddadp, 0x04, 0x14, PPC2_VSX), GEN_XX3FORM(xsnmaddmdp, 0x04, 0x15, PPC2_VSX), GEN_XX3FORM(xsnmsubadp, 0x04, 0x16, PPC2_VSX), GEN_XX3FORM(xsnmsubmdp, 0x04, 0x17, PPC2_VSX), +GEN_XX3FORM(xscmpeqdp, 0x0C, 0x00, PPC2_ISA300), +GEN_XX3FORM(xscmpgtdp, 0x0C, 0x01, PPC2_ISA300), +GEN_XX3FORM(xscmpgedp, 0x0C, 0x02, PPC2_ISA300), +GEN_XX3FORM(xscmpnedp, 0x0C, 0x03, PPC2_ISA300), GEN_XX2IFORM(xscmpodp, 0x0C, 0x05, PPC2_VSX), GEN_XX2IFORM(xscmpudp, 0x0C, 0x04, PPC2_VSX), GEN_XX3FORM(xsmaxdp, 0x00, 0x14, PPC2_VSX), From 6db246f93a7e308ff1d5aecf89d5772e83cafe61 Mon Sep 17 00:00:00 2001 From: Swapnil Bokade Date: Wed, 26 Oct 2016 11:56:29 +0530 Subject: [PATCH 66/73] target-ppc: Add xvcmpnesp, xvcmpnedp instructions xvcmpnedp[.]: VSX Vector Compare Not Equal Double-Precision xvcmpnesp[.]: VSX Vector Compare Not Equal Single-Precision Signed-off-by: Swapnil Bokade Signed-off-by: Nikunj A Dadhania Signed-off-by: David Gibson --- target-ppc/fpu_helper.c | 19 +++++++++++-------- target-ppc/helper.h | 2 ++ target-ppc/translate/vsx-impl.inc.c | 2 ++ target-ppc/translate/vsx-ops.inc.c | 2 ++ 4 files changed, 17 insertions(+), 8 deletions(-) diff --git a/target-ppc/fpu_helper.c b/target-ppc/fpu_helper.c index 4906372ae4..8a389e19af 100644 --- a/target-ppc/fpu_helper.c +++ b/target-ppc/fpu_helper.c @@ -2497,8 +2497,9 @@ VSX_MAX_MIN(xvminsp, minnum, 4, float32, VsrW(i)) * fld - vsr_t field (VsrD(*) or VsrW(*)) * cmp - comparison operation * svxvc - set VXVC bit + * exp - expected result of comparison */ -#define VSX_CMP(op, nels, tp, fld, cmp, svxvc) \ +#define VSX_CMP(op, nels, tp, fld, cmp, svxvc, exp) \ void helper_##op(CPUPPCState *env, uint32_t opcode) \ { \ ppc_vsr_t xt, xa, xb; \ @@ -2523,7 +2524,7 @@ void helper_##op(CPUPPCState *env, uint32_t opcode) \ xt.fld = 0; \ all_true = 0; \ } else { \ - if (tp##_##cmp(xb.fld, xa.fld, &env->fp_status) == 1) { \ + if (tp##_##cmp(xb.fld, xa.fld, &env->fp_status) == exp) { \ xt.fld = -1; \ all_false = 0; \ } else { \ @@ -2540,12 +2541,14 @@ void helper_##op(CPUPPCState *env, uint32_t opcode) \ float_check_status(env); \ } -VSX_CMP(xvcmpeqdp, 2, float64, VsrD(i), eq, 0) -VSX_CMP(xvcmpgedp, 2, float64, VsrD(i), le, 1) -VSX_CMP(xvcmpgtdp, 2, float64, VsrD(i), lt, 1) -VSX_CMP(xvcmpeqsp, 4, float32, VsrW(i), eq, 0) -VSX_CMP(xvcmpgesp, 4, float32, VsrW(i), le, 1) -VSX_CMP(xvcmpgtsp, 4, float32, VsrW(i), lt, 1) +VSX_CMP(xvcmpeqdp, 2, float64, VsrD(i), eq, 0, 1) +VSX_CMP(xvcmpgedp, 2, float64, VsrD(i), le, 1, 1) +VSX_CMP(xvcmpgtdp, 2, float64, VsrD(i), lt, 1, 1) +VSX_CMP(xvcmpnedp, 2, float64, VsrD(i), eq, 0, 0) +VSX_CMP(xvcmpeqsp, 4, float32, VsrW(i), eq, 0, 1) +VSX_CMP(xvcmpgesp, 4, float32, VsrW(i), le, 1, 1) +VSX_CMP(xvcmpgtsp, 4, float32, VsrW(i), lt, 1, 1) +VSX_CMP(xvcmpnesp, 4, float32, VsrW(i), eq, 0, 0) /* VSX_CVT_FP_TO_FP - VSX floating point/floating point conversion * op - instruction mnemonic diff --git a/target-ppc/helper.h b/target-ppc/helper.h index 0337292440..3916b2eddc 100644 --- a/target-ppc/helper.h +++ b/target-ppc/helper.h @@ -454,6 +454,7 @@ DEF_HELPER_2(xvmindp, void, env, i32) DEF_HELPER_2(xvcmpeqdp, void, env, i32) DEF_HELPER_2(xvcmpgedp, void, env, i32) DEF_HELPER_2(xvcmpgtdp, void, env, i32) +DEF_HELPER_2(xvcmpnedp, void, env, i32) DEF_HELPER_2(xvcvdpsp, void, env, i32) DEF_HELPER_2(xvcvdpsxds, void, env, i32) DEF_HELPER_2(xvcvdpsxws, void, env, i32) @@ -491,6 +492,7 @@ DEF_HELPER_2(xvminsp, void, env, i32) DEF_HELPER_2(xvcmpeqsp, void, env, i32) DEF_HELPER_2(xvcmpgesp, void, env, i32) DEF_HELPER_2(xvcmpgtsp, void, env, i32) +DEF_HELPER_2(xvcmpnesp, void, env, i32) DEF_HELPER_2(xvcvspdp, void, env, i32) DEF_HELPER_2(xvcvspsxds, void, env, i32) DEF_HELPER_2(xvcvspsxws, void, env, i32) diff --git a/target-ppc/translate/vsx-impl.inc.c b/target-ppc/translate/vsx-impl.inc.c index bf167d0488..5a27be4bd4 100644 --- a/target-ppc/translate/vsx-impl.inc.c +++ b/target-ppc/translate/vsx-impl.inc.c @@ -685,6 +685,7 @@ GEN_VSX_HELPER_2(xvmindp, 0x00, 0x1D, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvcmpeqdp, 0x0C, 0x0C, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvcmpgtdp, 0x0C, 0x0D, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvcmpgedp, 0x0C, 0x0E, 0, PPC2_VSX) +GEN_VSX_HELPER_2(xvcmpnedp, 0x0C, 0x0F, 0, PPC2_ISA300) GEN_VSX_HELPER_2(xvcvdpsp, 0x12, 0x18, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvcvdpsxds, 0x10, 0x1D, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvcvdpsxws, 0x10, 0x0D, 0, PPC2_VSX) @@ -722,6 +723,7 @@ GEN_VSX_HELPER_2(xvminsp, 0x00, 0x19, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvcmpeqsp, 0x0C, 0x08, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvcmpgtsp, 0x0C, 0x09, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvcmpgesp, 0x0C, 0x0A, 0, PPC2_VSX) +GEN_VSX_HELPER_2(xvcmpnesp, 0x0C, 0x0B, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvcvspdp, 0x12, 0x1C, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvcvspsxds, 0x10, 0x19, 0, PPC2_VSX) GEN_VSX_HELPER_2(xvcvspsxws, 0x10, 0x09, 0, PPC2_VSX) diff --git a/target-ppc/translate/vsx-ops.inc.c b/target-ppc/translate/vsx-ops.inc.c index 202c557fd8..3d9104155a 100644 --- a/target-ppc/translate/vsx-ops.inc.c +++ b/target-ppc/translate/vsx-ops.inc.c @@ -179,6 +179,7 @@ GEN_XX3FORM(xvmindp, 0x00, 0x1D, PPC2_VSX), GEN_XX3_RC_FORM(xvcmpeqdp, 0x0C, 0x0C, PPC2_VSX), GEN_XX3_RC_FORM(xvcmpgtdp, 0x0C, 0x0D, PPC2_VSX), GEN_XX3_RC_FORM(xvcmpgedp, 0x0C, 0x0E, PPC2_VSX), +GEN_XX3_RC_FORM(xvcmpnedp, 0x0C, 0x0F, PPC2_ISA300), GEN_XX2FORM(xvcvdpsp, 0x12, 0x18, PPC2_VSX), GEN_XX2FORM(xvcvdpsxds, 0x10, 0x1D, PPC2_VSX), GEN_XX2FORM(xvcvdpsxws, 0x10, 0x0D, PPC2_VSX), @@ -216,6 +217,7 @@ GEN_XX3FORM(xvminsp, 0x00, 0x19, PPC2_VSX), GEN_XX3_RC_FORM(xvcmpeqsp, 0x0C, 0x08, PPC2_VSX), GEN_XX3_RC_FORM(xvcmpgtsp, 0x0C, 0x09, PPC2_VSX), GEN_XX3_RC_FORM(xvcmpgesp, 0x0C, 0x0A, PPC2_VSX), +GEN_XX3_RC_FORM(xvcmpnesp, 0x0C, 0x0B, PPC2_ISA300), GEN_XX2FORM(xvcvspdp, 0x12, 0x1C, PPC2_VSX), GEN_XX2FORM(xvcvspsxds, 0x10, 0x19, PPC2_VSX), GEN_XX2FORM(xvcvspsxws, 0x10, 0x09, PPC2_VSX), From 9f992cca93de808bccbd02e14ce9200e8f25b8eb Mon Sep 17 00:00:00 2001 From: Michael Roth Date: Wed, 26 Oct 2016 21:20:25 -0500 Subject: [PATCH 67/73] spapr: update spapr hotplug documentation This updates the existing documentation to reflect recent updates to the hotplug event structure, which are in draft form but slated for inclusion in PAPR/LoPAPR. Signed-off-by: Michael Roth Reviewed-by: David Gibson Signed-off-by: David Gibson --- docs/specs/ppc-spapr-hotplug.txt | 55 ++++++++++++++++++++++++++------ 1 file changed, 46 insertions(+), 9 deletions(-) diff --git a/docs/specs/ppc-spapr-hotplug.txt b/docs/specs/ppc-spapr-hotplug.txt index 631b0cadae..f57e2a09c6 100644 --- a/docs/specs/ppc-spapr-hotplug.txt +++ b/docs/specs/ppc-spapr-hotplug.txt @@ -233,12 +233,27 @@ tools by host-level management such as an HMC. This level of management is not applicable to PowerKVM, hence the reason for extending the notification framework to support hotplug events. -Note that these events are not yet formally part of the PAPR+ specification, -but support for this format has already been implemented in DR-related -guest tools such as powerpc-utils/librtas, as well as kernel patches that have -been submitted to handle in-kernel processing of memory/cpu-related hotplug -events[1], and is planned for formal inclusion is PAPR+ specification. The -hotplug-specific payload is QEMU implemented as follows (with all values +The format for these EPOW-signalled events is described below under +"hotplug/unplug event structure". Note that these events are not +formally part of the PAPR+ specification, and have been superseded by a +newer format, also described below under "hotplug/unplug event structure", +and so are now deemed a "legacy" format. The formats are similar, but the +"modern" format contains additional fields/flags, which are denoted for the +purposes of this documentation with "#ifdef GUEST_SUPPORTS_MODERN" guards. + +QEMU should assume support only for "legacy" fields/flags unless the guest +advertises support for the "modern" format via ibm,client-architecture-support +hcall by setting byte 5, bit 6 of it's ibm,architecture-vec-5 option vector +structure (as described by LoPAPR v11, B.6.2.3). As with "legacy" format events, +"modern" format events are surfaced to the guest via check-exception RTAS calls, +but use a dedicated event source to signal the guest. This event source is +advertised to the guest by the addition of a "hot-plug-events" node under +"/event-sources" node of the guest's device tree using the standard format +described in LoPAPR v11, B.6.12.1. + +== hotplug/unplug event structure == + +The hotplug-specific payload in QEMU is implemented as follows (with all values encoded in big-endian format): struct rtas_event_log_v6_hp { @@ -263,14 +278,23 @@ struct rtas_event_log_v6_hp { #define RTAS_LOG_V6_HP_ACTION_ADD 1 #define RTAS_LOG_V6_HP_ACTION_REMOVE 2 uint8_t hotplug_action; /* action (add/remove) */ -#define RTAS_LOG_V6_HP_ID_DRC_NAME 1 -#define RTAS_LOG_V6_HP_ID_DRC_INDEX 2 -#define RTAS_LOG_V6_HP_ID_DRC_COUNT 3 +#define RTAS_LOG_V6_HP_ID_DRC_NAME 1 +#define RTAS_LOG_V6_HP_ID_DRC_INDEX 2 +#define RTAS_LOG_V6_HP_ID_DRC_COUNT 3 +#ifdef GUEST_SUPPORTS_MODERN +#define RTAS_LOG_V6_HP_ID_DRC_COUNT_INDEXED 4 +#endif uint8_t hotplug_identifier; /* type of the resource identifier, * which serves as the discriminator * for the 'drc' union field below */ +#ifdef GUEST_SUPPORTS_MODERN + uint8_t capabilities; /* capability flags, currently unused + * by QEMU + */ +#else uint8_t reserved; +#endif union { uint32_t index; /* DRC index of resource to take action * on @@ -278,6 +302,19 @@ struct rtas_event_log_v6_hp { uint32_t count; /* number of DR resources to take * action on (guest chooses which) */ +#ifdef GUEST_SUPPORTS_MODERN + struct { + uint32_t count; /* number of DR resources to take + * action on + */ + uint32_t index; /* DRC index of first resource to take + * action on. guest will take action + * on DRC index through + * DRC index in + * sequential order + */ + } count_indexed; +#endif char name[1]; /* string representing the name of the * DRC to take action on */ From ffbb1705a33df8e2fb12b24d96663d63b22eaf8b Mon Sep 17 00:00:00 2001 From: Michael Roth Date: Wed, 26 Oct 2016 21:20:26 -0500 Subject: [PATCH 68/73] spapr_events: add support for dedicated hotplug event source Hotplug events were previously delivered using an EPOW interrupt and were queued by linux guests into a circular buffer. For traditional EPOW events like shutdown/resets, this isn't an issue, but for hotplug events there are cases where this buffer can be exhausted, resulting in the loss of hotplug events, resets, etc. Newer-style hotplug event are delivered using a dedicated event source. We enable this in supported guests by adding standard an additional event source in the guest device-tree via /event-sources, and, if the guest advertises support for the newer-style hotplug events, using the corresponding interrupt to signal the available of hotplug/unplug events. Signed-off-by: Michael Roth Signed-off-by: David Gibson --- hw/ppc/spapr.c | 9 +- hw/ppc/spapr_events.c | 202 +++++++++++++++++++++++++++++------- include/hw/ppc/spapr.h | 6 +- include/hw/ppc/spapr_ovec.h | 1 + 4 files changed, 177 insertions(+), 41 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 0b3820bbcf..9ddf2ff520 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -973,7 +973,7 @@ static void *spapr_build_fdt(sPAPRMachineState *spapr, } /* /event-sources */ - spapr_dt_events(fdt, spapr->check_exception_irq); + spapr_dt_events(spapr, fdt); /* /rtas */ spapr_dt_rtas(spapr, fdt); @@ -1789,6 +1789,11 @@ static void ppc_spapr_init(MachineState *machine) spapr_ovec_set(spapr->ov5, OV5_FORM1_AFFINITY); + /* advertise support for dedicated HP event source to guests */ + if (spapr->use_hotplug_event_source) { + spapr_ovec_set(spapr->ov5, OV5_HP_EVT); + } + /* init CPUs */ if (machine->cpu_model == NULL) { machine->cpu_model = kvm_enabled() ? "host" : smc->tcg_default_cpu; @@ -1912,7 +1917,7 @@ static void ppc_spapr_init(MachineState *machine) } g_free(filename); - /* Set up EPOW events infrastructure */ + /* Set up RTAS event infrastructure */ spapr_events_init(spapr); /* Set up the RTC RTAS interfaces */ diff --git a/hw/ppc/spapr_events.c b/hw/ppc/spapr_events.c index 89aa5a7926..9b0bd410bb 100644 --- a/hw/ppc/spapr_events.c +++ b/hw/ppc/spapr_events.c @@ -40,6 +40,7 @@ #include "hw/ppc/spapr_drc.h" #include "qemu/help_option.h" #include "qemu/bcd.h" +#include "hw/ppc/spapr_ovec.h" #include struct rtas_error_log { @@ -206,27 +207,132 @@ struct hp_log_full { struct rtas_event_log_v6_hp hp; } QEMU_PACKED; -#define EVENT_MASK_INTERNAL_ERRORS 0x80000000 -#define EVENT_MASK_EPOW 0x40000000 -#define EVENT_MASK_HOTPLUG 0x10000000 -#define EVENT_MASK_IO 0x08000000 +typedef enum EventClass { + EVENT_CLASS_INTERNAL_ERRORS = 0, + EVENT_CLASS_EPOW = 1, + EVENT_CLASS_RESERVED = 2, + EVENT_CLASS_HOT_PLUG = 3, + EVENT_CLASS_IO = 4, + EVENT_CLASS_MAX +} EventClassIndex; +#define EVENT_CLASS_MASK(index) (1 << (31 - index)) -void spapr_dt_events(void *fdt, uint32_t check_exception_irq) +static const char * const event_names[EVENT_CLASS_MAX] = { + [EVENT_CLASS_INTERNAL_ERRORS] = "internal-errors", + [EVENT_CLASS_EPOW] = "epow-events", + [EVENT_CLASS_HOT_PLUG] = "hot-plug-events", + [EVENT_CLASS_IO] = "ibm,io-events", +}; + +struct sPAPREventSource { + int irq; + uint32_t mask; + bool enabled; +}; + +static sPAPREventSource *spapr_event_sources_new(void) { - int event_sources, epow_events; - uint32_t irq_ranges[] = {cpu_to_be32(check_exception_irq), cpu_to_be32(1)}; - uint32_t interrupts[] = {cpu_to_be32(check_exception_irq), 0}; + return g_new0(sPAPREventSource, EVENT_CLASS_MAX); +} + +static void spapr_event_sources_register(sPAPREventSource *event_sources, + EventClassIndex index, int irq) +{ + /* we only support 1 irq per event class at the moment */ + g_assert(event_sources); + g_assert(!event_sources[index].enabled); + event_sources[index].irq = irq; + event_sources[index].mask = EVENT_CLASS_MASK(index); + event_sources[index].enabled = true; +} + +static const sPAPREventSource * +spapr_event_sources_get_source(sPAPREventSource *event_sources, + EventClassIndex index) +{ + g_assert(index < EVENT_CLASS_MAX); + g_assert(event_sources); + + return &event_sources[index]; +} + +void spapr_dt_events(sPAPRMachineState *spapr, void *fdt) +{ + uint32_t irq_ranges[EVENT_CLASS_MAX * 2]; + int i, count = 0, event_sources; + sPAPREventSource *events = spapr->event_sources; + + g_assert(events); _FDT(event_sources = fdt_add_subnode(fdt, 0, "event-sources")); - _FDT(fdt_setprop(fdt, event_sources, "interrupt-controller", NULL, 0)); - _FDT(fdt_setprop_cell(fdt, event_sources, "#interrupt-cells", 2)); - _FDT(fdt_setprop(fdt, event_sources, "interrupt-ranges", - irq_ranges, sizeof(irq_ranges))); + for (i = 0, count = 0; i < EVENT_CLASS_MAX; i++) { + int node_offset; + uint32_t interrupts[2]; + const sPAPREventSource *source = + spapr_event_sources_get_source(events, i); + const char *source_name = event_names[i]; - _FDT(epow_events = fdt_add_subnode(fdt, event_sources, "epow-events")); - _FDT(fdt_setprop(fdt, epow_events, "interrupts", - interrupts, sizeof(interrupts))); + if (!source->enabled) { + continue; + } + + interrupts[0] = cpu_to_be32(source->irq); + interrupts[1] = 0; + + _FDT(node_offset = fdt_add_subnode(fdt, event_sources, source_name)); + _FDT(fdt_setprop(fdt, node_offset, "interrupts", interrupts, + sizeof(interrupts))); + + irq_ranges[count++] = interrupts[0]; + irq_ranges[count++] = cpu_to_be32(1); + } + + irq_ranges[count] = cpu_to_be32(count); + count++; + + _FDT((fdt_setprop(fdt, event_sources, "interrupt-controller", NULL, 0))); + _FDT((fdt_setprop_cell(fdt, event_sources, "#interrupt-cells", 2))); + _FDT((fdt_setprop(fdt, event_sources, "interrupt-ranges", + irq_ranges, count * sizeof(uint32_t)))); +} + +static const sPAPREventSource * +rtas_event_log_to_source(sPAPRMachineState *spapr, int log_type) +{ + const sPAPREventSource *source; + + g_assert(spapr->event_sources); + + switch (log_type) { + case RTAS_LOG_TYPE_HOTPLUG: + source = spapr_event_sources_get_source(spapr->event_sources, + EVENT_CLASS_HOT_PLUG); + if (spapr_ovec_test(spapr->ov5_cas, OV5_HP_EVT)) { + g_assert(source->enabled); + break; + } + /* fall back to epow for legacy hotplug interrupt source */ + case RTAS_LOG_TYPE_EPOW: + source = spapr_event_sources_get_source(spapr->event_sources, + EVENT_CLASS_EPOW); + break; + default: + source = NULL; + } + + return source; +} + +static int rtas_event_log_to_irq(sPAPRMachineState *spapr, int log_type) +{ + const sPAPREventSource *source; + + source = rtas_event_log_to_source(spapr, log_type); + g_assert(source); + g_assert(source->enabled); + + return source->irq; } static void rtas_event_log_queue(int log_type, void *data, bool exception) @@ -247,19 +353,15 @@ static sPAPREventLogEntry *rtas_event_log_dequeue(uint32_t event_mask, sPAPRMachineState *spapr = SPAPR_MACHINE(qdev_get_machine()); sPAPREventLogEntry *entry = NULL; - /* we only queue EPOW events atm. */ - if ((event_mask & EVENT_MASK_EPOW) == 0) { - return NULL; - } - QTAILQ_FOREACH(entry, &spapr->pending_events, next) { + const sPAPREventSource *source = + rtas_event_log_to_source(spapr, entry->log_type); + if (entry->exception != exception) { continue; } - /* EPOW and hotplug events are surfaced in the same manner */ - if (entry->log_type == RTAS_LOG_TYPE_EPOW || - entry->log_type == RTAS_LOG_TYPE_HOTPLUG) { + if (source->mask & event_mask) { break; } } @@ -276,19 +378,15 @@ static bool rtas_event_log_contains(uint32_t event_mask, bool exception) sPAPRMachineState *spapr = SPAPR_MACHINE(qdev_get_machine()); sPAPREventLogEntry *entry = NULL; - /* we only queue EPOW events atm. */ - if ((event_mask & EVENT_MASK_EPOW) == 0) { - return false; - } - QTAILQ_FOREACH(entry, &spapr->pending_events, next) { + const sPAPREventSource *source = + rtas_event_log_to_source(spapr, entry->log_type); + if (entry->exception != exception) { continue; } - /* EPOW and hotplug events are surfaced in the same manner */ - if (entry->log_type == RTAS_LOG_TYPE_EPOW || - entry->log_type == RTAS_LOG_TYPE_HOTPLUG) { + if (source->mask & event_mask) { return true; } } @@ -376,7 +474,9 @@ static void spapr_powerdown_req(Notifier *n, void *opaque) rtas_event_log_queue(RTAS_LOG_TYPE_EPOW, new_epow, true); - qemu_irq_pulse(xics_get_qirq(spapr->xics, spapr->check_exception_irq)); + qemu_irq_pulse(xics_get_qirq(spapr->xics, + rtas_event_log_to_irq(spapr, + RTAS_LOG_TYPE_EPOW))); } static void spapr_hotplug_set_signalled(uint32_t drc_index) @@ -458,7 +558,9 @@ static void spapr_hotplug_req_event(uint8_t hp_id, uint8_t hp_action, rtas_event_log_queue(RTAS_LOG_TYPE_HOTPLUG, new_hp, true); - qemu_irq_pulse(xics_get_qirq(spapr->xics, spapr->check_exception_irq)); + qemu_irq_pulse(xics_get_qirq(spapr->xics, + rtas_event_log_to_irq(spapr, + RTAS_LOG_TYPE_HOTPLUG))); } void spapr_hotplug_req_add_by_index(sPAPRDRConnector *drc) @@ -504,6 +606,7 @@ static void check_exception(PowerPCCPU *cpu, sPAPRMachineState *spapr, uint64_t xinfo; sPAPREventLogEntry *event; struct rtas_error_log *hdr; + int i; if ((nargs < 6) || (nargs > 7) || nret != 1) { rtas_st(rets, 0, RTAS_OUT_PARAM_ERROR); @@ -540,8 +643,14 @@ static void check_exception(PowerPCCPU *cpu, sPAPRMachineState *spapr, * do the latter here, since our code relies on edge-triggered * interrupts. */ - if (rtas_event_log_contains(mask, true)) { - qemu_irq_pulse(xics_get_qirq(spapr->xics, spapr->check_exception_irq)); + for (i = 0; i < EVENT_CLASS_MAX; i++) { + if (rtas_event_log_contains(EVENT_CLASS_MASK(i), true)) { + const sPAPREventSource *source = + spapr_event_sources_get_source(spapr->event_sources, i); + + g_assert(source->enabled); + qemu_irq_pulse(xics_get_qirq(spapr->xics, source->irq)); + } } return; @@ -593,8 +702,27 @@ out_no_events: void spapr_events_init(sPAPRMachineState *spapr) { QTAILQ_INIT(&spapr->pending_events); - spapr->check_exception_irq = xics_spapr_alloc(spapr->xics, 0, false, - &error_fatal); + + spapr->event_sources = spapr_event_sources_new(); + + spapr_event_sources_register(spapr->event_sources, EVENT_CLASS_EPOW, + xics_spapr_alloc(spapr->xics, 0, false, + &error_fatal)); + + /* NOTE: if machine supports modern/dedicated hotplug event source, + * we add it to the device-tree unconditionally. This means we may + * have cases where the source is enabled in QEMU, but unused by the + * guest because it does not support modern hotplug events, so we + * take care to rely on checking for negotiation of OV5_HP_EVT option + * before attempting to use it to signal events, rather than simply + * checking that it's enabled. + */ + if (spapr->use_hotplug_event_source) { + spapr_event_sources_register(spapr->event_sources, EVENT_CLASS_HOT_PLUG, + xics_spapr_alloc(spapr->xics, 0, false, + &error_fatal)); + } + spapr->epow_notifier.notify = spapr_powerdown_req; qemu_register_powerdown_notifier(&spapr->epow_notifier); spapr_rtas_register(RTAS_CHECK_EXCEPTION, "check-exception", diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index b6f9f1b632..21af971239 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -13,6 +13,7 @@ struct sPAPRPHBState; struct sPAPRNVRAM; typedef struct sPAPRConfigureConnectorState sPAPRConfigureConnectorState; typedef struct sPAPREventLogEntry sPAPREventLogEntry; +typedef struct sPAPREventSource sPAPREventSource; #define HPTE64_V_HPTE_DIRTY 0x0000000000000040ULL #define SPAPR_ENTRY_POINT 0x100 @@ -77,9 +78,10 @@ struct sPAPRMachineState { sPAPROptionVector *ov5_cas; /* negotiated (via CAS) option vectors */ bool cas_reboot; - uint32_t check_exception_irq; Notifier epow_notifier; QTAILQ_HEAD(, sPAPREventLogEntry) pending_events; + bool use_hotplug_event_source; + sPAPREventSource *event_sources; /* Migration state */ int htab_save_index; @@ -584,7 +586,7 @@ struct sPAPREventLogEntry { }; void spapr_events_init(sPAPRMachineState *sm); -void spapr_dt_events(void *fdt, uint32_t check_exception_irq); +void spapr_dt_events(sPAPRMachineState *sm, void *fdt); int spapr_h_cas_compose_response(sPAPRMachineState *sm, target_ulong addr, target_ulong size, bool cpu_update, diff --git a/include/hw/ppc/spapr_ovec.h b/include/hw/ppc/spapr_ovec.h index 81cdd14f64..6a06da32e6 100644 --- a/include/hw/ppc/spapr_ovec.h +++ b/include/hw/ppc/spapr_ovec.h @@ -45,6 +45,7 @@ typedef struct sPAPROptionVector sPAPROptionVector; /* option vector 5 */ #define OV5_DRCONF_MEMORY OV_BIT(2, 2) #define OV5_FORM1_AFFINITY OV_BIT(5, 0) +#define OV5_HP_EVT OV_BIT(6, 5) /* interfaces */ sPAPROptionVector *spapr_ovec_new(void); From f622921430adbb4ac5aa641534e13e2cafae099a Mon Sep 17 00:00:00 2001 From: Michael Roth Date: Wed, 26 Oct 2016 21:20:27 -0500 Subject: [PATCH 69/73] spapr: add hotplug interrupt machine options This adds machine options of the form: -machine pseries,modern-hotplug-events=true -machine pseries,modern-hotplug-events=false If false, QEMU will force the use of "legacy" style hotplug events, which are surfaced through EPOW events instead of a dedicated hot plug event source, and lack certain features necessary, mainly, for memory unplug support. If true, QEMU will enable support for "modern" dedicated hot plug event source. Note that we will still default to "legacy" style unless the guest advertises support for the "modern" hotplug events via ibm,client-architecture-support hcall during early boot. For pseries-2.7 and earlier we default to false, for newer machine types we default to true. Signed-off-by: Michael Roth Signed-off-by: David Gibson --- hw/ppc/spapr.c | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 9ddf2ff520..fe918833cc 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -2143,16 +2143,41 @@ static void spapr_set_kvm_type(Object *obj, const char *value, Error **errp) spapr->kvm_type = g_strdup(value); } +static bool spapr_get_modern_hotplug_events(Object *obj, Error **errp) +{ + sPAPRMachineState *spapr = SPAPR_MACHINE(obj); + + return spapr->use_hotplug_event_source; +} + +static void spapr_set_modern_hotplug_events(Object *obj, bool value, + Error **errp) +{ + sPAPRMachineState *spapr = SPAPR_MACHINE(obj); + + spapr->use_hotplug_event_source = value; +} + static void spapr_machine_initfn(Object *obj) { sPAPRMachineState *spapr = SPAPR_MACHINE(obj); spapr->htab_fd = -1; + spapr->use_hotplug_event_source = true; object_property_add_str(obj, "kvm-type", spapr_get_kvm_type, spapr_set_kvm_type, NULL); object_property_set_description(obj, "kvm-type", "Specifies the KVM virtualization mode (HV, PR)", NULL); + object_property_add_bool(obj, "modern-hotplug-events", + spapr_get_modern_hotplug_events, + spapr_set_modern_hotplug_events, + NULL); + object_property_set_description(obj, "modern-hotplug-events", + "Use dedicated hotplug event mechanism in" + " place of standard EPOW events when possible" + " (required for memory hot-unplug support)", + NULL); } static void spapr_machine_finalizefn(Object *obj) @@ -2599,7 +2624,10 @@ static void phb_placement_2_7(sPAPRMachineState *spapr, uint32_t index, static void spapr_machine_2_7_instance_options(MachineState *machine) { + sPAPRMachineState *spapr = SPAPR_MACHINE(machine); + spapr_machine_2_8_instance_options(machine); + spapr->use_hotplug_event_source = false; } static void spapr_machine_2_7_class_options(MachineClass *mc) From afdbd403563fe91bccc9c8ddce84838817f06a66 Mon Sep 17 00:00:00 2001 From: Bharata B Rao Date: Wed, 26 Oct 2016 21:20:28 -0500 Subject: [PATCH 70/73] spapr: Add DRC count indexed hotplug identifier type Add support for DRC count indexed hotplug ID type which is primarily needed for memory hot unplug. This type allows for specifying the number of DRs that should be plugged/unplugged starting from a given DRC index. Signed-off-by: Bharata B Rao * updated rtas_event_log_v6_hp to reflect count/index field ordering used in PAPR hotplug ACR Signed-off-by: Michael Roth Reviewed-by: David Gibson Signed-off-by: David Gibson --- hw/ppc/spapr_events.c | 76 +++++++++++++++++++++++++++++++++--------- include/hw/ppc/spapr.h | 4 +++ 2 files changed, 65 insertions(+), 15 deletions(-) diff --git a/hw/ppc/spapr_events.c b/hw/ppc/spapr_events.c index 9b0bd410bb..f85a9c32a7 100644 --- a/hw/ppc/spapr_events.c +++ b/hw/ppc/spapr_events.c @@ -175,6 +175,16 @@ struct epow_log_full { struct rtas_event_log_v6_epow epow; } QEMU_PACKED; +union drc_identifier { + uint32_t index; + uint32_t count; + struct { + uint32_t count; + uint32_t index; + } count_indexed; + char name[1]; +} QEMU_PACKED; + struct rtas_event_log_v6_hp { #define RTAS_LOG_V6_SECTION_ID_HOTPLUG 0x4850 /* HP */ struct rtas_event_log_v6_section_header hdr; @@ -191,12 +201,9 @@ struct rtas_event_log_v6_hp { #define RTAS_LOG_V6_HP_ID_DRC_NAME 1 #define RTAS_LOG_V6_HP_ID_DRC_INDEX 2 #define RTAS_LOG_V6_HP_ID_DRC_COUNT 3 +#define RTAS_LOG_V6_HP_ID_DRC_COUNT_INDEXED 4 uint8_t reserved; - union { - uint32_t index; - uint32_t count; - char name[1]; - } drc; + union drc_identifier drc_id; } QEMU_PACKED; struct hp_log_full { @@ -488,7 +495,7 @@ static void spapr_hotplug_set_signalled(uint32_t drc_index) static void spapr_hotplug_req_event(uint8_t hp_id, uint8_t hp_action, sPAPRDRConnectorType drc_type, - uint32_t drc) + union drc_identifier *drc_id) { sPAPRMachineState *spapr = SPAPR_MACHINE(qdev_get_machine()); struct hp_log_full *new_hp; @@ -533,7 +540,7 @@ static void spapr_hotplug_req_event(uint8_t hp_id, uint8_t hp_action, case SPAPR_DR_CONNECTOR_TYPE_PCI: hp->hotplug_type = RTAS_LOG_V6_HP_TYPE_PCI; if (hp->hotplug_action == RTAS_LOG_V6_HP_ACTION_ADD) { - spapr_hotplug_set_signalled(drc); + spapr_hotplug_set_signalled(drc_id->index); } break; case SPAPR_DR_CONNECTOR_TYPE_LMB: @@ -551,9 +558,18 @@ static void spapr_hotplug_req_event(uint8_t hp_id, uint8_t hp_action, } if (hp_id == RTAS_LOG_V6_HP_ID_DRC_COUNT) { - hp->drc.count = cpu_to_be32(drc); + hp->drc_id.count = cpu_to_be32(drc_id->count); } else if (hp_id == RTAS_LOG_V6_HP_ID_DRC_INDEX) { - hp->drc.index = cpu_to_be32(drc); + hp->drc_id.index = cpu_to_be32(drc_id->index); + } else if (hp_id == RTAS_LOG_V6_HP_ID_DRC_COUNT_INDEXED) { + /* we should not be using count_indexed value unless the guest + * supports dedicated hotplug event source + */ + g_assert(spapr_ovec_test(spapr->ov5_cas, OV5_HP_EVT)); + hp->drc_id.count_indexed.count = + cpu_to_be32(drc_id->count_indexed.count); + hp->drc_id.count_indexed.index = + cpu_to_be32(drc_id->count_indexed.index); } rtas_event_log_queue(RTAS_LOG_TYPE_HOTPLUG, new_hp, true); @@ -567,34 +583,64 @@ void spapr_hotplug_req_add_by_index(sPAPRDRConnector *drc) { sPAPRDRConnectorClass *drck = SPAPR_DR_CONNECTOR_GET_CLASS(drc); sPAPRDRConnectorType drc_type = drck->get_type(drc); - uint32_t index = drck->get_index(drc); + union drc_identifier drc_id; + drc_id.index = drck->get_index(drc); spapr_hotplug_req_event(RTAS_LOG_V6_HP_ID_DRC_INDEX, - RTAS_LOG_V6_HP_ACTION_ADD, drc_type, index); + RTAS_LOG_V6_HP_ACTION_ADD, drc_type, &drc_id); } void spapr_hotplug_req_remove_by_index(sPAPRDRConnector *drc) { sPAPRDRConnectorClass *drck = SPAPR_DR_CONNECTOR_GET_CLASS(drc); sPAPRDRConnectorType drc_type = drck->get_type(drc); - uint32_t index = drck->get_index(drc); + union drc_identifier drc_id; + drc_id.index = drck->get_index(drc); spapr_hotplug_req_event(RTAS_LOG_V6_HP_ID_DRC_INDEX, - RTAS_LOG_V6_HP_ACTION_REMOVE, drc_type, index); + RTAS_LOG_V6_HP_ACTION_REMOVE, drc_type, &drc_id); } void spapr_hotplug_req_add_by_count(sPAPRDRConnectorType drc_type, uint32_t count) { + union drc_identifier drc_id; + + drc_id.count = count; spapr_hotplug_req_event(RTAS_LOG_V6_HP_ID_DRC_COUNT, - RTAS_LOG_V6_HP_ACTION_ADD, drc_type, count); + RTAS_LOG_V6_HP_ACTION_ADD, drc_type, &drc_id); } void spapr_hotplug_req_remove_by_count(sPAPRDRConnectorType drc_type, uint32_t count) { + union drc_identifier drc_id; + + drc_id.count = count; spapr_hotplug_req_event(RTAS_LOG_V6_HP_ID_DRC_COUNT, - RTAS_LOG_V6_HP_ACTION_REMOVE, drc_type, count); + RTAS_LOG_V6_HP_ACTION_REMOVE, drc_type, &drc_id); +} + +void spapr_hotplug_req_add_by_count_indexed(sPAPRDRConnectorType drc_type, + uint32_t count, uint32_t index) +{ + union drc_identifier drc_id; + + drc_id.count_indexed.count = count; + drc_id.count_indexed.index = index; + spapr_hotplug_req_event(RTAS_LOG_V6_HP_ID_DRC_COUNT_INDEXED, + RTAS_LOG_V6_HP_ACTION_ADD, drc_type, &drc_id); +} + +void spapr_hotplug_req_remove_by_count_indexed(sPAPRDRConnectorType drc_type, + uint32_t count, uint32_t index) +{ + union drc_identifier drc_id; + + drc_id.count_indexed.count = count; + drc_id.count_indexed.index = index; + spapr_hotplug_req_event(RTAS_LOG_V6_HP_ID_DRC_COUNT_INDEXED, + RTAS_LOG_V6_HP_ACTION_REMOVE, drc_type, &drc_id); } static void check_exception(PowerPCCPU *cpu, sPAPRMachineState *spapr, diff --git a/include/hw/ppc/spapr.h b/include/hw/ppc/spapr.h index 21af971239..bd5bcf70de 100644 --- a/include/hw/ppc/spapr.h +++ b/include/hw/ppc/spapr.h @@ -610,6 +610,10 @@ void spapr_hotplug_req_add_by_count(sPAPRDRConnectorType drc_type, uint32_t count); void spapr_hotplug_req_remove_by_count(sPAPRDRConnectorType drc_type, uint32_t count); +void spapr_hotplug_req_add_by_count_indexed(sPAPRDRConnectorType drc_type, + uint32_t count, uint32_t index); +void spapr_hotplug_req_remove_by_count_indexed(sPAPRDRConnectorType drc_type, + uint32_t count, uint32_t index); void spapr_cpu_init(sPAPRMachineState *spapr, PowerPCCPU *cpu, Error **errp); void *spapr_populate_hotplug_cpu_dt(CPUState *cs, int *fdt_offset, sPAPRMachineState *spapr); From 79b78a6bd47722ce23bc74287cd6322756698f09 Mon Sep 17 00:00:00 2001 From: Michael Roth Date: Wed, 26 Oct 2016 21:20:29 -0500 Subject: [PATCH 71/73] spapr: use count+index for memory hotplug Commit 0a417869: spapr: Move memory hotplug to RTAS_LOG_V6_HP_ID_DRC_COUNT type dropped per-DRC/per-LMB hotplugs event in favor of a bulk add via a single LMB count value. This was to avoid overrunning the guest EPOW event queue with hotplug events. This works fine, but relies on the guest exhaustively scanning for pluggable LMBs to satisfy the requested count by issuing rtas-get-sensor(DR_ENTITY_SENSE, ...) calls until all the LMBs associated with the DIMM are identified. With newer support for dedicated hotplug event source, this queue exhaustion is no longer as much of an issue due to implementation details on the guest side, but we still try to avoid excessive hotplug events by now supporting both a count and a starting index to avoid unecessary work. This patch makes use of that approach when the capability is available. Cc: bharata@linux.vnet.ibm.com Signed-off-by: Michael Roth Reviewed-by: David Gibson Signed-off-by: David Gibson --- hw/ppc/spapr.c | 22 ++++++++++++++++++---- 1 file changed, 18 insertions(+), 4 deletions(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index fe918833cc..531dfeb645 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -2202,14 +2202,16 @@ static void spapr_nmi(NMIState *n, int cpu_index, Error **errp) } } -static void spapr_add_lmbs(DeviceState *dev, uint64_t addr, uint64_t size, - uint32_t node, Error **errp) +static void spapr_add_lmbs(DeviceState *dev, uint64_t addr_start, uint64_t size, + uint32_t node, bool dedicated_hp_event_source, + Error **errp) { sPAPRDRConnector *drc; sPAPRDRConnectorClass *drck; uint32_t nr_lmbs = size/SPAPR_MEMORY_BLOCK_SIZE; int i, fdt_offset, fdt_size; void *fdt; + uint64_t addr = addr_start; for (i = 0; i < nr_lmbs; i++) { drc = spapr_dr_connector_by_id(SPAPR_DR_CONNECTOR_TYPE_LMB, @@ -2228,7 +2230,17 @@ static void spapr_add_lmbs(DeviceState *dev, uint64_t addr, uint64_t size, * guest only in case of hotplugged memory */ if (dev->hotplugged) { - spapr_hotplug_req_add_by_count(SPAPR_DR_CONNECTOR_TYPE_LMB, nr_lmbs); + if (dedicated_hp_event_source) { + drc = spapr_dr_connector_by_id(SPAPR_DR_CONNECTOR_TYPE_LMB, + addr_start / SPAPR_MEMORY_BLOCK_SIZE); + drck = SPAPR_DR_CONNECTOR_GET_CLASS(drc); + spapr_hotplug_req_add_by_count_indexed(SPAPR_DR_CONNECTOR_TYPE_LMB, + nr_lmbs, + drck->get_index(drc)); + } else { + spapr_hotplug_req_add_by_count(SPAPR_DR_CONNECTOR_TYPE_LMB, + nr_lmbs); + } } } @@ -2261,7 +2273,9 @@ static void spapr_memory_plug(HotplugHandler *hotplug_dev, DeviceState *dev, goto out; } - spapr_add_lmbs(dev, addr, size, node, &error_abort); + spapr_add_lmbs(dev, addr, size, node, + spapr_ovec_test(ms->ov5_cas, OV5_HP_EVT), + &error_abort); out: error_propagate(errp, local_err); From cf63246319019c330a214c1ca9284c9405a6eb7a Mon Sep 17 00:00:00 2001 From: Bharata B Rao Date: Wed, 26 Oct 2016 21:20:30 -0500 Subject: [PATCH 72/73] spapr: Memory hot-unplug support Add support to hot remove pc-dimm memory devices. Since we're introducing a machine-level unplug_request hook, we also had handling for CPU unplug there as well to ensure CPU unplug continues to work as it did before. Signed-off-by: Bharata B Rao * add hooks to CAS/cmdline enablement of hotplug ACR support * add hook for CPU unplug Signed-off-by: Michael Roth Reviewed-by: David Gibson Signed-off-by: David Gibson --- hw/ppc/spapr.c | 119 ++++++++++++++++++++++++++++++++++++++++++++- hw/ppc/spapr_drc.c | 17 +++++++ 2 files changed, 135 insertions(+), 1 deletion(-) diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c index 531dfeb645..c8e29212cb 100644 --- a/hw/ppc/spapr.c +++ b/hw/ppc/spapr.c @@ -2281,6 +2281,90 @@ out: error_propagate(errp, local_err); } +typedef struct sPAPRDIMMState { + uint32_t nr_lmbs; +} sPAPRDIMMState; + +static void spapr_lmb_release(DeviceState *dev, void *opaque) +{ + sPAPRDIMMState *ds = (sPAPRDIMMState *)opaque; + HotplugHandler *hotplug_ctrl; + + if (--ds->nr_lmbs) { + return; + } + + g_free(ds); + + /* + * Now that all the LMBs have been removed by the guest, call the + * pc-dimm unplug handler to cleanup up the pc-dimm device. + */ + hotplug_ctrl = qdev_get_hotplug_handler(dev); + hotplug_handler_unplug(hotplug_ctrl, dev, &error_abort); +} + +static void spapr_del_lmbs(DeviceState *dev, uint64_t addr_start, uint64_t size, + Error **errp) +{ + sPAPRDRConnector *drc; + sPAPRDRConnectorClass *drck; + uint32_t nr_lmbs = size / SPAPR_MEMORY_BLOCK_SIZE; + int i; + sPAPRDIMMState *ds = g_malloc0(sizeof(sPAPRDIMMState)); + uint64_t addr = addr_start; + + ds->nr_lmbs = nr_lmbs; + for (i = 0; i < nr_lmbs; i++) { + drc = spapr_dr_connector_by_id(SPAPR_DR_CONNECTOR_TYPE_LMB, + addr / SPAPR_MEMORY_BLOCK_SIZE); + g_assert(drc); + + drck = SPAPR_DR_CONNECTOR_GET_CLASS(drc); + drck->detach(drc, dev, spapr_lmb_release, ds, errp); + addr += SPAPR_MEMORY_BLOCK_SIZE; + } + + drc = spapr_dr_connector_by_id(SPAPR_DR_CONNECTOR_TYPE_LMB, + addr_start / SPAPR_MEMORY_BLOCK_SIZE); + drck = SPAPR_DR_CONNECTOR_GET_CLASS(drc); + spapr_hotplug_req_remove_by_count_indexed(SPAPR_DR_CONNECTOR_TYPE_LMB, + nr_lmbs, + drck->get_index(drc)); +} + +static void spapr_memory_unplug(HotplugHandler *hotplug_dev, DeviceState *dev, + Error **errp) +{ + sPAPRMachineState *ms = SPAPR_MACHINE(hotplug_dev); + PCDIMMDevice *dimm = PC_DIMM(dev); + PCDIMMDeviceClass *ddc = PC_DIMM_GET_CLASS(dimm); + MemoryRegion *mr = ddc->get_memory_region(dimm); + + pc_dimm_memory_unplug(dev, &ms->hotplug_memory, mr); + object_unparent(OBJECT(dev)); +} + +static void spapr_memory_unplug_request(HotplugHandler *hotplug_dev, + DeviceState *dev, Error **errp) +{ + Error *local_err = NULL; + PCDIMMDevice *dimm = PC_DIMM(dev); + PCDIMMDeviceClass *ddc = PC_DIMM_GET_CLASS(dimm); + MemoryRegion *mr = ddc->get_memory_region(dimm); + uint64_t size = memory_region_size(mr); + uint64_t addr; + + addr = object_property_get_int(OBJECT(dimm), PC_DIMM_ADDR_PROP, &local_err); + if (local_err) { + goto out; + } + + spapr_del_lmbs(dev, addr, size, &error_abort); +out: + error_propagate(errp, local_err); +} + void *spapr_populate_hotplug_cpu_dt(CPUState *cs, int *fdt_offset, sPAPRMachineState *spapr) { @@ -2354,10 +2438,42 @@ static void spapr_machine_device_plug(HotplugHandler *hotplug_dev, static void spapr_machine_device_unplug(HotplugHandler *hotplug_dev, DeviceState *dev, Error **errp) { + sPAPRMachineState *sms = SPAPR_MACHINE(qdev_get_machine()); MachineClass *mc = MACHINE_GET_CLASS(qdev_get_machine()); if (object_dynamic_cast(OBJECT(dev), TYPE_PC_DIMM)) { - error_setg(errp, "Memory hot unplug not supported by sPAPR"); + if (spapr_ovec_test(sms->ov5_cas, OV5_HP_EVT)) { + spapr_memory_unplug(hotplug_dev, dev, errp); + } else { + error_setg(errp, "Memory hot unplug not supported for this guest"); + } + } else if (object_dynamic_cast(OBJECT(dev), TYPE_SPAPR_CPU_CORE)) { + if (!mc->query_hotpluggable_cpus) { + error_setg(errp, "CPU hot unplug not supported on this machine"); + return; + } + spapr_core_unplug(hotplug_dev, dev, errp); + } +} + +static void spapr_machine_device_unplug_request(HotplugHandler *hotplug_dev, + DeviceState *dev, Error **errp) +{ + sPAPRMachineState *sms = SPAPR_MACHINE(qdev_get_machine()); + MachineClass *mc = MACHINE_GET_CLASS(qdev_get_machine()); + + if (object_dynamic_cast(OBJECT(dev), TYPE_PC_DIMM)) { + if (spapr_ovec_test(sms->ov5_cas, OV5_HP_EVT)) { + spapr_memory_unplug_request(hotplug_dev, dev, errp); + } else { + /* NOTE: this means there is a window after guest reset, prior to + * CAS negotiation, where unplug requests will fail due to the + * capability not being detected yet. This is a bit different than + * the case with PCI unplug, where the events will be queued and + * eventually handled by the guest after boot + */ + error_setg(errp, "Memory hot unplug not supported for this guest"); + } } else if (object_dynamic_cast(OBJECT(dev), TYPE_SPAPR_CPU_CORE)) { if (!mc->query_hotpluggable_cpus) { error_setg(errp, "CPU hot unplug not supported on this machine"); @@ -2503,6 +2619,7 @@ static void spapr_machine_class_init(ObjectClass *oc, void *data) hc->plug = spapr_machine_device_plug; hc->unplug = spapr_machine_device_unplug; mc->cpu_index_to_socket_id = spapr_cpu_index_to_socket_id; + hc->unplug_request = spapr_machine_device_unplug_request; smc->dr_lmb_enabled = true; smc->tcg_default_cpu = "POWER8"; diff --git a/hw/ppc/spapr_drc.c b/hw/ppc/spapr_drc.c index 6e54fd4743..a0c44ee593 100644 --- a/hw/ppc/spapr_drc.c +++ b/hw/ppc/spapr_drc.c @@ -68,6 +68,23 @@ static uint32_t set_isolation_state(sPAPRDRConnector *drc, } } + /* + * Fail any requests to ISOLATE the LMB DRC if this LMB doesn't + * belong to a DIMM device that is marked for removal. + * + * Currently the guest userspace tool drmgr that drives the memory + * hotplug/unplug will just try to remove a set of 'removable' LMBs + * in response to a hot unplug request that is based on drc-count. + * If the LMB being removed doesn't belong to a DIMM device that is + * actually being unplugged, fail the isolation request here. + */ + if (drc->type == SPAPR_DR_CONNECTOR_TYPE_LMB) { + if ((state == SPAPR_DR_ISOLATION_STATE_ISOLATED) && + !drc->awaiting_release) { + return RTAS_OUT_HW_ERROR; + } + } + drc->isolation_state = state; if (drc->isolation_state == SPAPR_DR_ISOLATION_STATE_ISOLATED) { From 10c21b5c20bf3d20b7b0ad279db37ae89cc7937d Mon Sep 17 00:00:00 2001 From: Nicholas Piggin Date: Thu, 27 Oct 2016 23:50:58 +1100 Subject: [PATCH 73/73] ppc: allow certain HV interrupts to be delivered to guests ppc hypervisors have delivered system reset and machine check exception interrupts to guests in some situations (e.g., see FWNMI feature of LoPAPR, or NMI injection in QEMU). These exceptions are architected to set the HV bit in hardware, however when injected into a guest, the HV bit should be cleared. Current code masks off the HV bit before setting the new MSR, however this happens after the interrupt delivery model has calculated delivery mode for the exception. This can result in the guest's MSR LE bit being lost. Account for this in the exception handler and don't set HV bit for guest delivery. Also add another sanity check to ensure similar bugs get caught. Signed-off-by: Nicholas Piggin Signed-off-by: David Gibson --- target-ppc/excp_helper.c | 32 ++++++++++++++++++++++++++------ 1 file changed, 26 insertions(+), 6 deletions(-) diff --git a/target-ppc/excp_helper.c b/target-ppc/excp_helper.c index 53c407576b..808760bf53 100644 --- a/target-ppc/excp_helper.c +++ b/target-ppc/excp_helper.c @@ -213,7 +213,12 @@ static inline void powerpc_excp(PowerPCCPU *cpu, int excp_model, int excp) cs->halted = 1; cs->interrupt_request |= CPU_INTERRUPT_EXITTB; } - new_msr |= (target_ulong)MSR_HVB; + if (env->msr_mask & MSR_HVB) { + /* ISA specifies HV, but can be delivered to guest with HV clear + * (e.g., see FWNMI in PAPR). + */ + new_msr |= (target_ulong)MSR_HVB; + } ail = 0; /* machine check exceptions don't have ME set */ @@ -391,8 +396,17 @@ static inline void powerpc_excp(PowerPCCPU *cpu, int excp_model, int excp) msr |= 0x10000; new_msr |= ((target_ulong)1 << MSR_ME); } - - new_msr |= (target_ulong)MSR_HVB; + if (env->msr_mask & MSR_HVB) { + /* ISA specifies HV, but can be delivered to guest with HV clear + * (e.g., see FWNMI in PAPR, NMI injection in QEMU). + */ + new_msr |= (target_ulong)MSR_HVB; + } else { + if (msr_pow) { + cpu_abort(cs, "Trying to deliver power-saving system reset " + "exception %d with no HV support\n", excp); + } + } ail = 0; break; case POWERPC_EXCP_DSEG: /* Data segment exception */ @@ -609,9 +623,15 @@ static inline void powerpc_excp(PowerPCCPU *cpu, int excp_model, int excp) env->spr[srr1] = msr; /* Sanity check */ - if (!(env->msr_mask & MSR_HVB) && (srr0 == SPR_HSRR0)) { - cpu_abort(cs, "Trying to deliver HV exception %d with " - "no HV support\n", excp); + if (!(env->msr_mask & MSR_HVB)) { + if (new_msr & MSR_HVB) { + cpu_abort(cs, "Trying to deliver HV exception (MSR) %d with " + "no HV support\n", excp); + } + if (srr0 == SPR_HSRR0) { + cpu_abort(cs, "Trying to deliver HV exception (HSRR) %d with " + "no HV support\n", excp); + } } /* If any alternate SRR register are defined, duplicate saved values */